Programing

Express / Node.JS를 사용하여 모든보기에서 액세스 할 수있는 전역 변수를 만드는 방법은 무엇입니까?

lottogame 2020. 10. 21. 07:35
반응형

Express / Node.JS를 사용하여 모든보기에서 액세스 할 수있는 전역 변수를 만드는 방법은 무엇입니까?


좋습니다. 저는 Jekyll을 사용하여 블로그를 만들었 _config.yml으며 모든 템플릿 / 레이아웃에서 액세스 할 수 있는 파일에 변수를 정의 할 수 있습니다. 내가 현재 사용하고 Node.js를 / 익스프레스EJS의 템플릿 및 EJS - 지역 주민을 파셜 / 레이아웃에 (. 내가 좋아하는 전역 변수 비슷한 할 찾고 site.title에서 발견되는 그 _config.yml사람이 지킬 잘 알고있는 경우. 나는 등 변수가 내 모든 페이지에서 동일하게 유지되는 사이트의 제목 (페이지 제목이 아님), 작성자 / 회사 이름.

다음은 내가 현재하고있는 작업의 예입니다. :

exports.index = function(req, res){
    res.render('index', { 
        siteTitle: 'My Website Title',
        pageTitle: 'The Root Splash Page',
        author: 'Cory Gross',
        description: 'My app description',
        indexSpecificData: someData
    });
};

exports.home = function (req, res) {
    res.render('home', {
        siteTitle: 'My Website Title',
        pageTitle: 'The Home Page',
        author: 'Cory Gross',
        description: 'My app description',
        homeSpecificData: someOtherData
    });
};

내 사이트의 제목, 설명, 작성자 등과 같은 변수를 한 곳에서 정의하고 .NET에 대한 각 호출에 대한 옵션으로 전달할 필요없이 EJS를 통해 내 레이아웃 / 템플릿에서 액세스 할 수 있도록하고 싶습니다 res.render. 이 작업을 수행하고 각 페이지에 특정한 다른 변수를 전달할 수있는 방법이 있습니까?


Express 3 API Reference 를 조금 더 공부 한 후 제가 찾고있는 것을 발견했습니다. 특히 항목에 대한 app.locals다음 조금 더 아래로 res.locals내가 필요한 답변을 보유했습니다.

나는 함수 app.locals가 객체를 취하고 모든 속성을 응용 프로그램 범위의 전역 변수로 저장 한다는 것을 스스로 발견했습니다 . 이러한 전역은 각 뷰에 지역 변수로 전달됩니다. 그러나 함수 res.locals는 요청 범위가 지정되므로 응답 지역 변수는 해당 특정 요청 / 응답 중에 렌더링 된 뷰에서만 액세스 할 수 있습니다.

그래서 내 경우에는 다음을 app.js추가했습니다.

app.locals({
    site: {
        title: 'ExpressBootstrapEJS',
        description: 'A boilerplate for a simple web application with a Node.JS and Express backend, with an EJS template with using Twitter Bootstrap.'
    },
    author: {
        name: 'Cory Gross',
        contact: 'CoryG89@gmail.com'
    }
});

그리고이 모든 변수가 아니라 내보기에 액세스 할 수 있습니다 site.title, site.description, author.name, author.contact.

를 사용하여 요청에 대한 각 응답에 대해 지역 변수를 정의 res.locals하거나 호출 options매개 변수 로 페이지 제목과 같은 변수를 간단히 전달할 수도 render있습니다.

편집 : 이 방법 을 사용하면 미들웨어에서 이러한 지역을 사용할 수 없습니다 . Pickels가 아래 의견에서 제안한 것처럼 실제로 이것을 실행했습니다. 이 경우 그의 대안 (및 감사) 답변에서 미들웨어 기능을 만들어야합니다. 미들웨어 함수는 res.locals각 응답에 대해 추가 한 다음 next. 이 미들웨어 기능은 이러한 로컬을 사용해야하는 다른 미들웨어 위에 배치되어야합니다.

편집 : 를 통해 지역 주민을 선언하는 또 다른 차이점 app.localsres.locals함께 있다는 것입니다 app.locals변수 하나의 시간을 설정하고 응용 프로그램의 수명이 다할 때까지 유지됩니다. res.locals미들웨어에서 로컬을 설정하면 요청을받을 때마다 설정됩니다. app.localsreq이 미들웨어에 전달 된 요청 변수 에 의존하지 않는 한 기본적으로 전역 설정을 선호해야합니다 . 값이 변경되지 않으면에서 한 번만 설정하는 것이 더 효율적입니다 app.locals.


일반 미들웨어의 locals 개체에 추가하여이를 수행 할 수 있습니다.

app.use(function (req, res, next) {
   res.locals = {
     siteTitle: "My Website's Title",
     pageTitle: "The Home Page",
     author: "Cory Gross",
     description: "My app's description",
   };
   next();
});

Locals는 또한 locals 객체를 덮어 쓰지 않고 확장하는 함수입니다. 따라서 다음도 작동합니다.

res.locals({
  siteTitle: "My Website's Title",
  pageTitle: "The Home Page",
  author: "Cory Gross",
  description: "My app's description",
});

전체 예

var app = express();

var middleware = {

    render: function (view) {
        return function (req, res, next) {
            res.render(view);
        }
    },

    globalLocals: function (req, res, next) {
        res.locals({ 
            siteTitle: "My Website's Title",
            pageTitle: "The Root Splash Page",
            author: "Cory Gross",
            description: "My app's description",
        });
        next();
    },

    index: function (req, res, next) {
        res.locals({
            indexSpecificData: someData
        });
        next();
    }

};


app.use(middleware.globalLocals);
app.get('/', middleware.index, middleware.render('home'));
app.get('/products', middleware.products, middleware.render('products'));

I also added a generic render middleware. This way you don't have to add res.render to each route which means you have better code reuse. Once you go down the reusable middleware route you'll notice you will have lots of building blocks which will speed up development tremendously.


For Express 4.0 I found that using application level variables works a little differently & Cory's answer did not work for me.

From the docs: http://expressjs.com/en/api.html#app.locals

I found that you could declare a global variable for the app in

app.locals

e.g

app.locals.baseUrl = "http://www.google.com"

And then in your application you can access these variables & in your express middleware you can access them in the req object as

req.app.locals.baseUrl

e.g.

console.log(req.app.locals.baseUrl)
//prints out http://www.google.com

In your app.js you need add something like this

global.myvar = 100;

Now, in all your files you want use this variable, you can just access it as myvar


One way to do this by updating the app.locals variable for that app in app.js

Set via following

var app = express();
app.locals.appName = "DRC on FHIR";

Get / Access

app.listen(3000, function () {
    console.log('[' + app.locals.appName + '] => app listening on port 3001!');
});

Elaborating with a screenshot from @RamRovi example with slight enhancement.

enter image description here


you can also use "global"

Example:

declare like this :

  app.use(function(req,res,next){
      global.site_url = req.headers.host;   // hostname = 'localhost:8080'
      next();
   });

Use like this: in any views or ejs file <% console.log(site_url); %>

in js files console.log(site_url);


What I do in order to avoid having a polluted global scope is to create a script that I can include anywhere.

// my-script.js
const ActionsOverTime = require('@bigteam/node-aot').ActionsOverTime;
const config = require('../../config/config').actionsOverTime;
let aotInstance;

(function () {
  if (!aotInstance) {
    console.log('Create new aot instance');
    aotInstance = ActionsOverTime.createActionOverTimeEmitter(config);
  }
})();

exports = aotInstance;

Doing this will only create a new instance once and share that everywhere where the file is included. I am not sure if it is because the variable is cached or of it because of an internal reference mechanism for the application (that might include caching). Any comments on how node resolves this would be great.

Maybe also read this to get the gist on how require works: http://fredkschott.com/post/2014/06/require-and-the-module-system/

참고URL : https://stackoverflow.com/questions/16452123/how-to-create-global-variables-accessible-in-all-views-using-express-node-js

반응형