Module.exports içindeki "local" işlevini module.exports içindeki başka bir işlevden çağır?


327

Bir module.exportsbildirimde başka bir işlev içinden bir işlevi nasıl çağırırsınız ?

app.js
var bla = require('./bla.js');
console.log(bla.bar());
bla.js
module.exports = {

  foo: function (req, res, next) {
    return ('foo');
  },

  bar: function(req, res, next) {
    this.foo();
  }

}

Ben işlevini erişmeye çalışıyorum fooişlev içinde barve ben alıyorum:

TypeError: Nesne # 'foo' yöntemine sahip değil

Ben this.foo()sadece değiştirmek foo()alırsanız:

ReferenceError: foo tanımlanmamış


4
Kodunuzu test ettim ve hiçbir hatam yok. Bar işlevi, herhangi bir return ifadesi olmadığı için tanımsız olarak döner. Doğru test yaptığınızdan emin misiniz?
Ferchi

1
Düğüm sürümünde test edilmiştir v8.12.0ve artık hatayı atmamaktadır. bardönüş bildirimi yok, bu yüzden koşmak console.log(bla.bar())sadece geri dönüyorundefined
VladNeacsu

Yanıtlar:


351

Değişim this.foo()içinmodule.exports.foo()


1
@NamNguyen Aramak exports.foo()biraz garip ve okunması zor görünüyor.
Afshin Mehrabani

4
Bunun kabul edilen cevaptan daha iyi olduğunu düşünüyorum. Dışarıda ihracat kapsam fonksiyonlarını tanımlamak, bu fazladan bir seviyede ekler ve arzu bazen olabilir iken, bu, daha fazla karmaşık hale getirir gözden geçirmeniz, örneğin adlandırma işlevi, vb fonksiyonunun bulmak kullanımı, bir
Pierre Henry

1
soruya doğrudan cevap
Kermit_ice_tea

8
module.exports.foo()ve exports.foo()Node.js v5.8.0 ile çalışmayın.
brain arasında

14
export.foo () çalışmıyor ancak module.exports.foo () NodeJS v6.9.1
R. Canser

191

İşlevlerinizi module.exportsblok dışında bildirebilirsiniz.

var foo = function (req, res, next) {
  return ('foo');
}

var bar = function (req, res, next) {
  return foo();
}

Sonra:

module.exports = {
  foo: foo,
  bar: bar
}

11
yöntemden nesnenin özelliklerine erişmek istersem ne olur?
Rockstar5645

1
TypeError alıyorum: Bunu yaptığımda yourClass.youMethod bir işlev değil. Düğüm sürümü 6.9.1 kullanıyorum. Bir iade beyanınız mı var? Tüm kodlarım işlevlerinde zaman uyumsuz olduğu için return ifadeleri yok.
Brett Mathe

1
Farklı stillerin güzel karşılaştırması - gist.github.com/kimmobrunfeldt/10848413
Tadas V.

Çok güzel bir uygulama! +1
realnsleo

3
Veya, daha kısaca ES6 kullanarak,module.exports = { foo, bar, }
Let It Tink About It Tink

118

Bunu daha özlü ve okunabilir hale getirmek için de yapabilirsiniz. İyi yazılmış açık kaynaklı modüllerin bazılarında yapıldığını gördüm:

var self = module.exports = {

  foo: function (req, res, next) {
    return ('foo');
  },

  bar: function(req, res, next) {
    self.foo();
  }

}

Bu Node.js sürümü belirli mi? Ben v5.8.0 ile deniyorum ve undefined günlüğü.
brain arasında

1
@doublejosh ... soruyu okudun mu? Dışa aktarılan bir işlevi diğerinden nasıl çağırdığınızı soruyor. Bu sahiptir ilgisi erişim kısıtlamaları ile.
Monica'nın Davası

1
Evet okudum, lütfen tekrar okuyun. Bu cevap, foo () 'yu modülle dışa aktarır, bu da sadece modül içinde çağrılan bir "yerel" fonksiyonun noktasına gider.
doublejosh

66

Ayrıca, modülün global kapsamına (module.) Export.somemodule tanımının dışındaki bir referansı da kaydedebilirsiniz:

var _this = this;

exports.somefunction = function() {
   console.log('hello');
}

exports.someotherfunction = function() {
   _this.somefunction();
}

Daha temiz bir çözüm!
IvanZh

_this için gerek yok ve sadece ihtiyacınız olan yerde kullanabilirsiniz
Yuki

thisdoğrudan kullanılır , beyan etmeye gerek yok_this
Darius

1
Bu öneri thisartık doğru olmadığında yararlıdır this. (Vaatler ve geri aramalar)
Andrew McOlash

Bu çözümü en çok sevdim çünkü NodeJS modüllerinde kapsam belirleme örneği veriyor.
miguelmorin

40

OP'nin özgün stiline daha yakın olan başka bir seçenek, dışa aktarmak istediğiniz nesneyi bir değişkene koymak ve nesnedeki diğer yöntemlere çağrı yapmak için bu değişkene başvurmaktır. Daha sonra bu değişkeni dışa aktarabilirsiniz ve başlayabilirsiniz.

var self = {
  foo: function (req, res, next) {
    return ('foo');
  },
  bar: function (req, res, next) {
    return self.foo();
  }
};
module.exports = self;

25
const Service = {
  foo: (a, b) => a + b,
  bar: (a, b) => Service.foo(a, b) * b
}

module.exports = Service

3
Bu özellikle kullanılabilir çünkü kodunuz çağırıyor Service.foo()ve istemci kodunuz da Service.foo()aynı adlandırma ile arıyor olacak .
Vince Bowdren

Bu mükemmel bir cevap!
Jayant Varshney

16

İle başlayan Node.js sürüm 13'ten ES6 Modüllerinden yararlanabilirsiniz .

export function foo() {
    return 'foo';
}

export function bar() {
    return foo();
}

Sınıf yaklaşımını izleyerek:

class MyClass {

    foo() {
        return 'foo';
    }

    bar() {
        return this.foo();
    }
}

module.exports = new MyClass();

Bu, düğümün modül önbelleğe alınması nedeniyle sınıfı yalnızca bir kez başlatır:
https://nodejs.org/api/modules.html#modules_caching


ve bu yaklaşımla nasıl statik bir yöntem denir?
Plixxer

@CodeofGod Diğer statik yöntemleri çağırdığınız gibi çağırmanız yeterlidir. Bu durumda, foostatik oldu sen içeriden çağırır barböyle: MyClass.foo().
m.spyratos

evet bunu anlıyorum, ama onu ithal eden bir denetleyiciden nasıl çağırırsınız? const oAccounts = requir ("...");
Plixxer

Sınıfın bir örneğini değil, gerçek sınıfı dışa aktarabilirsiniz. Bu şekilde statik yöntemlerini kullanabilirsiniz. Daha sonra kendi örnek yöntemlerini kullanmanız gerekiyorsa, sınıfı denetleyicinizde başlatmanız gerekir.
m.spyratos

6

Sorununuzu çözmek için bla.js'de birkaç değişiklik yaptım ve çalışıyor,

var foo= function (req, res, next) {
  console.log('inside foo');
  return ("foo");
}

var  bar= function(req, res, next) {
  this.foo();
}
module.exports = {bar,foo};

ve app.js'de değişiklik yok

var bla = require('./bla.js');
console.log(bla.bar());

1
İşlev çubuğunda this.foo () çalışmıyor ... foo () olması gerekiyor
Falcoa
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.