我想要求我的文件总是通过我的项目的根,而不是相对于当前模块。
例如,如果查看https://github.com/visionmedia/express/blob/2820f2227de0229c5d7f28009aa432f9f3a7b5f9/examples/downloads/app.js第6行,您将看到
express = require('../../')
在我看来,这真的很糟糕。假设我想让我所有的例子都只靠近根结点一层。这是不可能的,因为我必须更新超过30个例子,并且在每个例子中更新很多次。:
express = require('../')
我的解决方案是有一个基于根的特殊情况:如果字符串以$开头,那么它相对于项目的根文件夹。
任何帮助都是感激的,谢谢
更新2
现在我使用require.js,它允许你以一种方式编写,在客户端和服务器上都可以工作。Require.js还允许你创建自定义路径。
更新3
现在我转移到webpack + gulp,我使用enhanced-require来处理服务器端模块。看这里的基本原理:http://hackhat.com/p/110/module-loader-webpack-vs-requirejs-vs-browserify/
我喜欢做的是利用node从node_module目录加载的方式。
如果有人试图加载“thing”模块,他会做如下的事情
require('thing');
Node将在'node_module'目录中查找'thing'目录。
由于node_module通常位于项目的根,所以我们可以利用这种一致性。(如果node_module不在根节点上,那么您就会遇到其他令人头痛的问题。)
如果我们进入目录,然后从目录中返回,我们可以获得到节点项目根的一致路径。
require('thing/../../');
如果我们想访问/happy目录,我们会这样做。
require('thing/../../happy');
虽然这有点粗糙,但是我觉得如果node_modules加载的功能发生了变化,将会有更大的问题需要处理。这种行为应该保持一致。
为了使事情更清楚,我这样做,因为模块的名称并不重要。
require('root/../../happy');
我最近在angular2中使用了它。我想从根目录加载服务。
import {MyService} from 'root/../../app/services/http/my.service';
这里有关于这个问题的很好的讨论。
我遇到了同样的架构问题:想要给我的应用程序更多的组织和内部名称空间,但没有:
将应用程序模块与外部依赖项混合,或者为特定于应用程序的代码使用私有NPM回购
使用相对要求,使得重构和理解更加困难
使用符号链接或更改节点路径,这可能会模糊源代码位置,并且不能很好地进行源代码控制
最后,我决定使用文件命名约定而不是目录来组织我的代码。结构应该是这样的:
npm-shrinkwrap.json
package.json
node_modules
...
src
app.js
app.config.js
app.models.bar.js
app.models.foo.js
app.web.js
app.web.routes.js
...
然后在代码中:
var app_config = require('./app.config');
var app_models_foo = require('./app.models.foo');
或者只是
var config = require('./app.config');
var foo = require('./app.models.foo');
和往常一样,外部依赖项可以从node_modules中获得:
var express = require('express');
通过这种方式,所有应用程序代码都按层次结构组织成模块,相对于应用程序根,所有其他代码都可以使用。
当然,主要的缺点是在文件浏览器中,您不能展开/折叠树,就好像它实际上被组织成目录一样。但我喜欢它非常明确所有代码的来源,而且它没有使用任何“魔法”。
如果你使用yarn而不是npm,你可以使用工作区。
假设我有一个文件夹服务,我希望更容易地需要:
.
├── app.js
├── node_modules
├── test
├── services
│ ├── foo
│ └── bar
└── package.json
要创建Yarn工作空间,需要创建一个包。services文件夹中的Json文件:
{
"name": "myservices",
"version": "1.0.0"
}
在你的主包里。json添加:
"private": true,
"workspaces": ["myservices"]
从项目的根目录运行yarn install。
然后,在代码的任何地方,你可以这样做:
const { myFunc } = require('myservices/foo')
而不是像这样:
const { myFunc } = require('../../../../../../services/foo')
我正在寻找完全相同的简单性,要求文件从任何级别,我发现模块-别名。
安装:
npm i --save module-alias
打开你的包裹。Json文件,在这里你可以为你的路径添加别名,例如。
"_moduleAliases": {
"@root" : ".", // Application's root
"@deep" : "src/some/very/deep/directory/or/file",
"@my_module" : "lib/some-file.js",
"something" : "src/foo", // Or without @. Actually, it could be any string
}
使用你的别名只需:
require('module-alias/register')
const deep = require('@deep')
const module = require('something')