简体   繁体   English

在服务器,客户端和所有文件之间共享Meteor功能而不声明它们为全局文件?

[英]Sharing Meteor functions between server, client, and all files without declaring them global?

Say that I've got functions that I want to re-use between multiple files on BOTH server and client. 假设我有要在服务器和客户端上的多个文件之间重复使用的功能。 I could just make them global, place them into a common code folder, but that's no good. 我可以将它们设置为全局,然后将它们放置在common代码文件夹中,但这不好。

/lib/master_file.js /lib/master_file.js

add = function(num1, num2){
  return num1 + num2;
};

subtract = function(num1, num2){
  return num1 - num2
};

/client/client_file1.js /client/client_file1.js

add(4,4);
subtract(10,3);

/server/server_file1.js /server/server_file1.js

add(9,1);

/server/file2.js /server/file2.js

subtract(8,2);

--POSSIBLE SOLUTIONS-- - 可能的解决方案 -

I can create a global object and attach the functions as values of the global object. 我可以创建一个全局对象,并将这些函数附加为全局对象的值。

/lib/master_file_v2.js /lib/master_file_v2.js

var add = function(num1, num2){
  return num1 + num2;
};

var subtract = function(num1, num2){
  return num1 - num2
};

global = {

  add: function(num1, num2){
    return add(num1, num2);
  },
  subtract: function(num1, num2){
    return subtract(num1, num2);
  }

};

Then I would have to call the functions like so. 然后,我将不得不像这样调用这些函数。

/client/client_file1.js /client/client_file1.js

var add = global.add;
var subtract = global.subtract;
add(4,4);
subtract(10,3);

/server/server_file1.js /server/server_file1.js

var add = global.add;
add(9,1);

/server/server_file2.js /server/server_file2.js

var subtract = global.subtract;
subtract(8,2);

Is there a way to not call the functions like this? 有没有办法不这样调用函数? I would prefer to directly call them by their names but without declaring them as global. 我宁愿直接用它们的名字来称呼它们,而不必声明它们是全局的。

/client/client_file1.js /client/client_file1.js

add(4,4);
subtract(10,3);

/server/server_file1.js /server/server_file1.js

add(9,1);

/server/server_file2.js* /server/server_file2.js*

subtract(8,2);

modules 模块

On the server side I believe I can use module.exports but modules isn't available on the client side, so that doesn't work. 在服务器端,我相信我可以使用module.exports但是在客户端上模块不可用,因此不起作用。 I could use a modules library for the client side but I think it might break with Meteor's unique code-sharing between the client and server in /lib if I were to declare modules there? 我可以在客户端使用modules库,但如果在此处声明modules ,我认为它可能会与流星在/lib的客户端和服务器之间的唯一代码共享相冲突。

Meteor.methods Meteor.methods

Calling them is pretty wordy and when defined in /lib they get run on both the client and server, which isn't always what you want... 调用它们非常麻烦,当在/lib定义它们时,它们可以同时在客户端和服务器上运行,而这并不总是您想要的...

If you want a piece of code not to be seen, you can't push it to the client. 如果您不想看到一段代码,则无法将其推送给客户端。 So you'll have put it in a method . 因此,您将其放入一个method That's the only meteor-native way. 那是唯一的气象方法。 You can nicen up the Meteor.call api with something like this: 您可以使用以下方法完善Meteor.call api:

lib/ LIB /

methodCaller = function methodCaller (methodName) {
  return function (/*arguments...[, callback]*/) {
    var callback = arguments.slice(-1)
    Meteor.apply(methodName, arguments, methodCallback)
  }
}

Meteor.methods({
  test: function (n) {
    return n*2
  }
})

test = methodCaller('test')

anywhere 随地

test(1, function (err, result) {
  console.log(result)
})

If you are afraid of cluttering, just use a closure or as you proposed, a simple object. 如果您担心混乱,只需使用闭包或您建议的简单对象即可。 You don't have to define a local-scope variable to use a function stored in an object. 您不必定义局部作用域变量即可使用存储在对象中的函数。 You can just use it like this: 您可以像这样使用它:

anywhere 随地

globals.add()

Now I think globals is to generic a name. 现在,我认为globals是通用名称。 That just moves the cluttering problem to a different place. 那只是将混乱的问题转移到另一个地方。 In your example you could for an example define a mathUtils object instead. 在您的示例中,您可以作为示例定义一个mathUtils对象。

I don't use closures very often. 我不经常使用闭包。 There are some cases where it can bring a big benefit. 在某些情况下,它可以带来很大的好处。 once is a good example of this: once是一个很好的例子:

once = function (func) {
  var hasBeenTriggered = false
  return function (/*arguments*/) {
    if(hasBeenTriggered) return
    hasBeenTriggered = true
    return func.apply(null, arguments)
  }
}

This might not look like most closures, but it is one. 这可能看起来不像大多数闭包,但它是一个。 Here hiding hasBeenTriggered is essential for the integrity of the function. 在这里隐藏hasBeenTriggered对于功能的完整性至关重要。 Try not to hide unnecessarily. 尽量不要隐藏不必要的东西。 Having lots of hidden functions makes it harder to write good tests. 具有许多隐藏函数使编写好的测试变得更加困难。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM