[node.js] Node.js 모듈 이해 : 여러 개가 동일한 객체를 반환해야합니까?

모듈 캐싱에 대한 node.js 문서 와 관련된 질문이 있습니다 .

모듈은 처음로드 된 후 캐시됩니다. 이것은 (무엇보다도) require ( ‘foo’)에 대한 모든 호출
이 동일한 파일로 해석된다면 정확히 동일한 객체가 반환된다는 것을 의미합니다.

require ( ‘foo’)를 여러 번 호출 하면 모듈 코드가 여러 번 실행 되지 않을 수 있습니다 . 이것은 중요한 기능입니다. 이를 통해 “부분적으로 수행 된”개체가 반환 될 수 있으므로주기를 유발하는 경우에도 전 이적 종속성을로드 할 수 있습니다.

무엇을 의미 may합니까?

require가 항상 동일한 객체를 반환 하는지 알고 싶습니다 . 그래서 경우에 나는 모듈이 필요 의를 하고 내 수출 객체 변경 (반환을 필요로하는 일을)하고 그 후 모듈이 필요 B 에서 자체 모듈을 필요로 나는 것입니다 항상 그 객체의 수정 된 버전 또는 새를 얻을 수 하나?app.jsapp.jsapp.js

// app.js

var a = require('./a');
a.b = 2;
console.log(a.b); //2

var b = require('./b');
console.log(b.b); //2

// a.js

exports.a = 1;

// b.js

module.exports = require('./a');



답변

두 경우 app.jsb.js상주 같은 프로젝트에 (같은 디렉토리에)를 둘 다 받게됩니다 동일한 인스턴스 의를 A. 로부터 Node.js를 문서 :

… 모든 호출은 require('foo')얻을 것 같은 객체가 정확히 이 해결한다면, 반환 같은 파일을 .


상황이 때 다른 a.js, b.js그리고 app.js에있는 다른 NPM 모듈 . 예를 들면 :

[APP] --> [A], [B]
[B]   --> [A]

그 경우 require('a')에는 app.js다른 사본에 해결하는 것 a.js보다 require('a')에서 b.js하고 따라서 반환 다른 인스턴스 의를 A. 이 동작을 더 자세히 설명 하는 블로그 게시물 이 있습니다.


답변

node.js에는 거대한 서버 프로젝트를 실행하는 동안 노드가 파일을 1000 번 읽는 것을 차단하는 일종의 캐싱이 구현되어 있습니다.

이 캐시는 require.cache개체에 나열됩니다 . 이 개체는 읽기 / 쓰기가 가능하므로 프로세스를 종료하지 않고 캐시에서 파일을 삭제할 수 있습니다.

http://nodejs.org/docs/latest/api/globals.html#require.cache

오, 질문에 대답하는 것을 잊었습니다. 내 보낸 개체를 수정해도 다음 모듈로드에는 영향을주지 않습니다. 이로 인해 많은 문제가 발생합니다. 참조없이 항상 개체의 새 인스턴스를 반환해야합니다. 파일을 편집하고 캐시를 삭제하면 내 보낸 개체가 변경됩니다.

몇 가지 테스트를 수행 한 후 node.js는 module.exports를 캐시합니다. 수정 require.cache[{module}].exports은 새로 수정 된 반환 된 객체로 끝납니다.


답변

질문이 게시 된 후 문서 가 업데이트되어 원래 “may”가 사용 된 이유를 명확히했습니다. 이제는 상황을 명시 적으로 만들어 질문 자체에 답합니다 (변경된 내용을 보여주기 위해 강조).

모듈은 처음로드 된 후 캐시됩니다. 이것은 (무엇보다도) require ( ‘foo’)에 대한 모든 호출이 동일한 파일로 해석된다면 정확히 동일한 객체가 반환된다는 것을 의미합니다.

제공 require.cache이 수정되지 않습니다, 여러 통화 ( ‘foo는’)을 필요로하는 것이다 모듈 코드가 여러 번 실행되도록하지. 이것은 중요한 기능입니다. 이를 통해 “부분적으로 수행 된”개체가 반환 될 수 있으므로주기를 유발하는 경우에도 전 이적 종속성을로드 할 수 있습니다.


답변

내가 본 것처럼 모듈 이름이 이전에로드 된 파일로 확인되면 캐시 된 모듈이 반환되고 그렇지 않으면 새 파일이 별도로로드됩니다.

즉, 캐싱은 확인되는 실제 파일 이름기반으로합니다 . 이는 일반적으로 파일 계층 구조의 다른 수준에 설치되고 그에 따라로드되어야하는 동일한 패키지의 다른 버전이있을 수 있기 때문입니다.

내가 확신하지 못하는 것은 프로그래머의 통제 나 인식하에 있지 않은 캐시 무효화 사례가 있는지 여부입니다. 이로 인해 동일한 패키지 파일을 실수로 여러 번 다시로드 할 수 있습니다.


답변

require(x)매번 새로운 객체를 반환 하려는 이유 는 해당 객체를 직접 수정하기 때문입니다. 즉, 제가 만난 경우입니다. 다음과 같이 복제하고 복제본 만 수정하고 사용하십시오.

var a = require('./a');
a = JSON.parse(JSON.stringify(a));


답변

drex 시도 : https://github.com/yuryb/drex

drex는 업데이트를 위해 모듈을 감시하고 있으며 업데이트 후 모듈을 명확하게 요구합니다. 새 코드는 마치 새 코드가 완전히 다른 모듈 인 것처럼 require () d되므로 require.cache는 문제가되지 않습니다.


답변

객체가 필요할 때 참조 주소가 필요하며 객체를 두 번 요구하면 동일한 주소를 얻게됩니다! 동일한 개체의 복사본을 가지려면이 를 복사 (복제)해야합니다.

var obj = require('./obj');

a = JSON.parse(JSON.stringify(obj));
b = JSON.parse(JSON.stringify(obj));
c = JSON.parse(JSON.stringify(obj));

복제는 여러 방법으로 수행됩니다 . 자세한 내용 은 를 참조하십시오 .