[javascript] mocha 및 node.js를 사용하여 개인 함수의 단위 테스트

node.js로 작성된 응용 프로그램을 단위 테스트하기 위해 mocha를 사용하고 있습니다.

모듈로 내 보내지 않은 함수를 단위 테스트 할 수 있는지 궁금합니다.

예:

나는 이와 같이 정의 된 많은 기능을 가지고있다. foobar.js

function private_foobar1(){
    ...
}

function private_foobar2(){
    ...
}

공개로 내 보낸 몇 가지 함수 :

exports.public_foobar3 = function(){
    ...
}

테스트 케이스는 다음과 같이 구성됩니다.

describe("private_foobar1", function() {
    it("should do stuff", function(done) {
        var stuff = foobar.private_foobar1(filter);
        should(stuff).be.ok;
        should(stuff).....

private_foobar1내 보내지 않기 때문에 분명히 작동하지 않습니다 .

개인 메소드를 단위 테스트하는 올바른 방법은 무엇입니까? 모카에는 기본 제공 방법이 있습니까?



답변

모듈에서 함수를 내 보내지 않으면 모듈 외부의 테스트 코드로 함수를 호출 할 수 없습니다. 이는 JavaScript가 작동하는 방식 때문이며 Mocha 자체로는이를 피할 수 없습니다.

개인 함수 테스트가 옳은 일이라고 결정한 몇 가지 경우, 내가 한 것은 모듈이 테스트 설정에서 실행 중인지 여부를 확인하기 위해 확인하는 환경 변수를 설정하는 것입니다. 테스트 설정에서 실행되면 테스트 중에 호출 할 수있는 추가 기능을 내 보냅니다.

여기서 “환경”이라는 단어가 느슨하게 사용되었습니다. 이는 process.env“지금 테스트 중입니다”라는 모듈과 통신 할 수있는 검사 또는 다른 것을 의미 할 수 있습니다. 내가해야했던 인스턴스는 RequireJS 환경에 있었고이 module.config목적으로 사용 했습니다.


답변

배선 모듈을 점검하십시오 . 모듈 내에서 개인 변수와 함수를 얻거나 조작 할 수 있습니다.

따라서 귀하의 경우 사용법은 다음과 같습니다.

var rewire = require('rewire'),
    foobar = rewire('./foobar'); // Bring your module in with rewire

describe("private_foobar1", function() {

    // Use the special '__get__' accessor to get your private function.
    var private_foobar1 = foobar.__get__('private_foobar1');

    it("should do stuff", function(done) {
        var stuff = private_foobar1(filter);
        should(stuff).be.ok;
        should(stuff).....


답변

다음은 블로그의 Google 엔지니어 인 필립 월튼 (Philip Walton)이 설명한 개인 분석법을 테스트하기위한 훌륭한 워크 플로우 입니다.

원리

  • 정상적으로 코드 작성
  • 개별 메소드를 별도의 코드 블록으로 객체에 바인딩 _하고 예를 들어
  • 시작 및 종료 주석으로 해당 코드 블록을 둘러 쌉니다.

그런 다음 빌드 작업 또는 자체 빌드 시스템 (예 : grunt-strip-code)을 사용하여 프로덕션 빌드를 위해이 블록을 제거하십시오.

테스트 빌드는 개인 API에 액세스 할 수 있으며 프로덕션 빌드는 액세스 할 수 없습니다.

단편

다음과 같이 코드를 작성하십시오.

var myModule = (function() {

  function foo() {
    // private function `foo` inside closure
    return "foo"
  }

  var api = {
    bar: function() {
      // public function `bar` returned from closure
      return "bar"
    }
  }

  /* test-code */
  api._foo = foo
  /* end-test-code */

  return api
}())

그리고 당신의 그런 임무는

grunt.registerTask("test", [
  "concat",
  "jshint",
  "jasmine"
])
grunt.registerTask("deploy", [
  "concat",
  "strip-code",
  "jshint",
  "uglify"
])

더 깊은

후반 기사에서는 “비공개 메소드 테스트”의 “이유”에 대해 설명합니다.


답변

당신은 간단하게하기 원하는 경우, 단지뿐만 아니라 private 멤버를 내보낼 수 있지만, 분명히으로 어떤 규칙으로 공개 API에서 예를 들어 접두사를 분리 _한 아래 또는 둥지를 개인 객체입니다.

var privateWorker = function() {
    return 1
}

var doSomething = function() {
    return privateWorker()
}

module.exports = {
    doSomething: doSomething,
    _privateWorker: privateWorker
}


답변

: 나는 당신이 유용하다는 사실을 발견이 목적을 위해 NPM 패키지를 만들 필요-에서

기본적으로 다음과 같은 방법으로 비공개 메소드를 공개합니다.

module.testExports = {
    private_foobar1: private_foobar1,
    private_foobar2: private_foobar2,
    ...
}

참고 : 물론 testExports원하는 이름을 사용할 수 있습니다 exports.

그리고 다른 모듈에서 :

var requireFrom = require('require-from');
var private_foobar1 = requireFrom('testExports', './path-to-module').private_foobar1;


답변

Internal () 이라는 추가 함수를 추가하고 거기에서 모든 개인 함수를 반환합니다. 그런 다음 이 Internal () 함수를 내 보냅니다. 예:

function Internal () {
  return { Private_Function1, Private_Function2, Private_Function2}
}

// Exports --------------------------
module.exports = { PublicFunction1, PublicFunction2, Internal }

다음과 같이 내부 함수를 호출 할 수 있습니다.

let test = require('.....')
test.Internal().Private_Function1()

나는이 솔루션을 가장 좋아합니다.

  • Internal () 함수 는 항상 하나만 내보내집니다. 이 Internal () 함수는 항상 개인 함수를 테스트하는 데 사용됩니다.
  • 구현이 간단합니다
  • 생산 코드에 대한 영향이 적음 (한 가지 추가 기능 만)

답변

@ barwin answer에 따라 단위 테스트를 수행하는 방법을 확인했습니다. 재배 선 된 모듈. 이 솔루션이 간단하게 작동하는지 확인할 수 있습니다.

모듈은 공용 및 개인의 두 부분으로 구성되어야합니다. 공용 함수의 경우 표준 방식으로 수행 할 수 있습니다.

const { public_foobar3 } = require('./foobar');

개인 범위의 경우 :

const privateFoobar = require('rewire')('./foobar');
const private_foobar1 = privateFoobar .__get__('private_foobar1');
const private_foobar2 = privateFoobar .__get__('private_foobar2');

이 주제에 대해 더 많이 알기 위해 전체 모듈 테스트로 실제 예제를 만들었습니다. 테스트에는 개인 및 공개 범위가 포함됩니다.

자세한 내용 은 주제를 자세히 설명하는 기사 ( https://medium.com/@macsikora/how-to-test-private-functions-of-es6-module-fb8c1345b25f ) 를 확인하는 것이 좋습니다 . 여기에는 코드 샘플이 포함되어 있습니다.