program tip

서로를 참조하는 여러 기능이있는 ES6 내보내기 기본값

radiobox 2020. 11. 20. 08:49
반응형

서로를 참조하는 여러 기능이있는 ES6 내보내기 기본값


es6에서는 다음과 같은 함수 모듈을 정의 할 수 있습니다.

export default {
    foo() { console.log('foo') }, 
    bar() { console.log('bar') },
    baz() { foo(); bar() }
}

위의 코드는 유효한 코드 인 것 같지만 호출 baz()하면 오류가 발생합니다.

ReferenceError: foo is not defined

foo다른 함수에서 어떻게 호출 합니까? 이 경우baz

편집하다

실제로 작동하지 않는 코드는 다음과 같습니다. 코드를 단순화하여 필요한만큼만 핵심입니다.

const tokenManager =  {
  revokeToken(headers) { 
    ... 
  },
  expireToken(headers) {
    ...
  },
  verifyToken(req, res, next) {
    jwt.verify(... => {
      if (err) {
        expireToken(req.headers)
      }
    })
  }
}

export default tokenManager 

그리고 오류는

expireToken(req.headers);
        ^
ReferenceError: expireToken is not defined

편집 2

방금 tokenManager전에 추가해 보았는데 expireToken마침내 작동합니다.


export default {...}건설은이 같은 단지 바로 가기입니다 :

const funcs = {
    foo() { console.log('foo') }, 
    bar() { console.log('bar') },
    baz() { foo(); bar() }
}

export default funcs

이제 모듈 범위에 foo, bar또는 baz함수 가 없다는 것이 분명 해져야합니다 . 그러나 funcs이러한 함수를 속성으로 포함하고 모듈의 기본 내보내기가 될 이름이 지정된 개체가 있습니다 (실제로는 이름이 없음).

그래서, 바로 가기를 사용하지 않고 그것을 코드, 다시 쓰기를 수정하고 참조하는 foobar의 속성으로 funcs:

const funcs = {
    foo() { console.log('foo') }, 
    bar() { console.log('bar') },
    baz() { funcs.foo(); funcs.bar() } // here is the fix
}

export default funcs

또 다른 옵션은 @pawel이 지적했듯이 명시 적으로 선언하지 않고도 this키워드를 사용하여 funcs객체 를 참조하는 입니다.

또 다른 옵션 (그리고 제가 일반적으로 선호하는 옵션)은 모듈 범위에서 이러한 함수를 선언하는 것입니다. 이를 통해 직접 참조 할 수 있습니다.

function foo() { console.log('foo') }
function bar() { console.log('bar') }
function baz() { foo(); bar() }

export default {foo, bar, baz}

And if you want the convenience of default export and ability to import items individually, you can also export all functions individually:

// util.js

export function foo() { console.log('foo') }
export function bar() { console.log('bar') }
export function baz() { foo(); bar() }

export default {foo, bar, baz}

// a.js, using default export

import util from './util'
util.foo()

// b.js, using named exports

import {bar} from './util'
bar()

Or, as @loganfsmyth suggested, you can do without default export and just use import * as util from './util' to get all named exports in one object.


One alternative is to change up your module. Generally if you are exporting an object with a bunch of functions on it, it's easier to export a bunch of named functions, e.g.

export function foo() { console.log('foo') }, 
export function bar() { console.log('bar') },
export function baz() { foo(); bar() }

In this case you are export all of the functions with names, so you could do

import * as fns from './foo';

to get an object with properties for each function instead of the import you'd use for your first example:

import fns from './foo';

tl;dr: baz() { this.foo(); this.bar() }

In ES2015 this construct:

var obj = {
    foo() { console.log('foo') }
}

is equal to this ES5 code:

var obj = {
    foo : function foo() { console.log('foo') }
}

exports.default = {} is like creating an object, your default export translates to ES5 code like this:

exports['default'] = {
    foo: function foo() {
        console.log('foo');
    },
    bar: function bar() {
        console.log('bar');
    },
    baz: function baz() {
        foo();bar();
    }
};

now it's kind of obvious (I hope) that baz tries to call foo and bar defined somewhere in the outer scope, which are undefined. But this.foo and this.bar will resolve to the keys defined in exports['default'] object. So the default export referencing its own methods shold look like this:

export default {
    foo() { console.log('foo') }, 
    bar() { console.log('bar') },
    baz() { this.foo(); this.bar() }
}

See babel repl transpiled code.

참고URL : https://stackoverflow.com/questions/33178843/es6-export-default-with-multiple-functions-referring-to-each-other

반응형