如何管理客户端JavaScript依赖关系?[关闭]


95

尽管有很好的解决方案来管理服务器端的依赖关系,但我找不到满足我一致的客户端JavaScript依赖关系管理工作流的所有需求的解决方案。我要满足以下5个要求:

  1. 管理我的客户端依赖于类似故宫的格式的package.json亭子bower.json
  2. 它应该可以灵活地指向我的dependency.json文件中的git repo或实际js文件(在网络上还是本地)(鲜为人知的库)(npm可让您指向git repos)
  3. 它应该将所有库缩小并命名为一个文件,例如ender-这是我唯一需要<script>在客户端标记中添加的js文件
  4. 它应该具有对BoxScript 4这样的CoffeeScript的开箱即用支持(现已停用)
  5. 在浏览器中,我应该能够使用任一require样式:

    var $ = require('jquery');
    var _ = require('underscore');
    

    或者更好的是,做headjs样式:

    head.js(['jquery', 'underscore', 'mylib'], function($, _, mylib) {
      // executed when all libraries are loaded
    });
    

如果没有一个这样的工具,那么工具的最佳组合是什么,即我可以使用volo(或grunt)之类的工具链进行组合?

我已经研究了这里链接到的所有工具,它们最多只能单独满足我最多3个要求。因此,请不要再发布有关这些工具的信息。我只接受一个提供满足我所有5个要求的工具的答案,或者如果有人发布了多个满足我所有要求的此类工具的工具链的具体工作流程/脚本/工作示例,则我将只接受一个答案。谢谢。



1
对于更多的“节点式”的解决方案,港口节点的require语法到浏览器考虑browserify
smithclay

1
您能说得更清楚些吗?在我的问题的5个要点中,我认为requirejs / browserify仅满足一两个要点。我正在寻找一种可以满足我所有五个要求的工具(或工具链)
pathikrit 2012年

3
我还没有尝试过,但也许yeoman.io也是一个不错的选择
Guillaume86

1
我刚刚听说过onejs-听起来有些相关:github.com/azer/onejs
dsummersl

Answers:


45

require.js可以满足您的所有需求。

我对这个问题的回答可能对您有帮助

例:

客户端应用程序项目层次结构:

sampleapp
    |___ main.js
    |___ cs.js
    |___ require.js

main.js是您初始化客户端应用程序并配置require.js的地方:

require.config({
    baseUrl: "/sampleapp",
    paths: {
        jquery: "libs/jquery", // Local
        underscore: "http://underscorejs.org/underscore-min.js", // Remote
        backbone: "https://github.com/documentcloud/backbone/blob/master/backbone-min.js" // Remote on github
    },
    shim: {
        backbone: {
            deps: ["underscore", "jquery"] // Backbone depends on jquery and underscore
        }
    }
});

require(["cs!someCoffeescriptFile", "jquery", "backbone", "underscore"], function (SomeCoffeescriptFile, $, Backbone, _) {
    // Dependencies are loaded...
    // Execute code
});

当以“ cs!”为前缀时,依赖项将使用cs插件。cs插件编译coffeescript文件。

当您使用prod时,可以使用r.js预编译整个项目。

node ./node_modules/requirejs/bin/r.js -o buildclientconfig.js

这是您的要求:

  • 以类似于npm的package.json或bower的component.json的格式管理我的客户端依赖项。不一样,但是很好!

  • 我应该可以灵活地在我的dependency.json文件中指向git repo或实际的js文件(在Web上或本地),以使用鲜为人知的库(npm,让您指向git repos)。

  • 它应该将所有库最小化并命名为一个单独的文件,例如ender-这是我唯一需要在客户端的脚本标签中放入的js文件。YES与r.js.

  • 它应该对Box等Coffeescript具有开箱即用的支持。

  • 在浏览器中,我可以使用require样式或headjs。


如果使用r.js,是否可以仅提取所有库的非精简版本,还是应该在精简和非精简库之间做出决定?

唯一的问题是您必须使用最小化代码来进行这requireJS废话。
Ben Sinclair 2014年

1
@安迪不一定!您可以改用杏仁小得多的杏仁!
亚当B

24

我相信http://requirejs.org/是您正在寻找的那个


谢谢你 不知道它存在于nodejs外部
GottZ'Oct

1
谢谢!如果您认为解决了目的,请标记我的答案为正确的答案!
Chandra Sekhar Walajapet 2012年

3
我不是问这个问题的人xD
GottZ'October

哎呀,对不起!没注意到
Chandra Sekhar Walajapet 2012年

3
我很困惑。requirejs如何才能从互联网上提取一个任意的javascript文件(我不是在谈论它的回购中的文件,例如jquery,而是不太知名的文件)?它可以读取package.json文件吗?而且它与CoffeeScript不兼容...我错过了什么吗?
pathikrit 2012年

15

作为@ Guillaume86,我认为下摆会让您最接近想要的位置。

在下摆中,依赖项是通过结合使用npm和下摆来管理的。使用npm显式安装所有项目的外部依赖项。使用hem指定应该为客户端操作将哪些依赖项(外部和本地)缝合在一起。

我为此创建了一个骨架项目,因此您可以看到它是如何工作的-您可以在https://github.com/dsummersl/clientsidehem上看到它

添加依赖

使用npm搜索特定的依赖项,然后修改package.json文件以确保将来会跟踪该依赖项。然后在slug.json中为您的应用程序指定依赖项。

例如,假设您要添加coffee-script依赖项。只需使用npm安装依赖项并将其保存到您的package.json文件中即可:

1. npm --save install coffee-script
2. Manually edit the slug.json file. Add "coffee-script" to "dependencies".

假设您想包括自己的模块“ bloomfilters”,而该模块不在npm注册表中。您可以通过以下方式将其添加到项目中:

1. npm --save install https://github.com/dsummersl/bloomfilters/tarball/master
2. Manually edit the slug.json file. Add "bloomfilters" to "dependencies".

本地模块

如果要包括自己的咖啡或JavaScript,可以通过将这些文件添加到app /文件夹中来实现。请注意,为了通过“ require”方法公开脚本,必须将其设置为CommonJS模块。这非常简单-请参阅hem文档

本地文件

如果要包括非CommonJS非“要求”代码,则还可以通过slug.json中的“库”列表引用自定义的javascript或coffeescript来进行拼接。

的CSS

如果需要,下摆也会将您的CSS缝合在一起。请参阅hem文档

建造

一旦列出了依赖项,就可以使用下摆将它们缝合在一起。

# make sure all dependencies are present:
npm install .
# make public/application.js
hem build
# see your minified js in public/application.js

笔记

Hem是为spinejs项目设计的-但您不必为此使用它。忽略任何希望提及脊椎的文档...


1
+1以争取细节;)
Guillaume86

11

好吧,我很惊讶没有人提到Browserify

  1. 支持package.json格式
  2. 在下面使用npm,可以使用github(或任何git)仓库作为包源
  3. 最小化并将所有依赖关系串联到一个文件中。
  4. 如果将咖啡脚本包含在依赖项中,则支持它
  5. 一路要求风格。
  6. 支持源地图

您可以在浏览器中使用任何github存储库(或Bower包)?是否需要类似napa或否的要求?npmjs.org/package/napa
Connor Leech

9

我很确定Hem可以满足您的要求(我使用了带有其他编译器(玉器和手写笔的个人叉子),可以轻松地根据您的需要进行自定义)。它使用npm来管理权限。


通过阅读这个特定问题,我认为这可以很好地解决1,3,5的问题。对于#2,您可以将自己的本地JS包放在node_modules中(它使用本地npm),并且可以将git子模块用于仅依赖git的任何依赖项。对于#4,我认为您在运行下摆之前必须自己将咖啡编译为js(这很容易)。
dsummersl 2012年

感谢您的评论,但是下摆可以毫无问题地编译我的coffeescript :),它最初是为Spine.js编写的,因为它是一个针对coffeescript的框架,所以这是一个基本要求
Guillaume86

我知道对于像脊椎这样的应用程序(例如,将咖啡放入应用程序/ ...),它会起作用,但是包含coffeescript的外部模块又如何呢?我认为那是Wrick所要问的,但我可能完全错了……
dsummersl 2012年

1
好的,我不知道它是否可以为外部模块编译coffeescript,但是我认为它没有用,外部模块通常提供已编译的JS :)
Guillaume86

是的,我同意。它进入制作cakefile / grunt的领域……
dsummersl 2012年

5

您可能想看看Yeoman,它使用多种技术来帮助您满足需求。

我们的工作流程由三个工具组成,可在构建Web应用程序时提高您的生产率和满意度:yo(脚手架工具),grunt(构建工具)和bower(用于软件包管理)。

对CoffeeScript,指南针等的内置支持。适用于r.js(RequireJS),单元测试等

至于您的要求:

  1. Bower用于依赖性管理
  2. Bower可以使用本地文件git://,http://等
  3. 内置支持缩小和级联(甚至用于图像)
  4. 内置支持以自动编译CoffeeScript和Compass(带有LiveReload)
  5. 如构建过程中所述:如果您使用的是AMD,我将通过r.js传递这些模块,因此您不必这样做。

所有功能:

迅捷的脚手架 -使用可自定义的模板(例如HTML5 Boilerplate,Twitter Bootstrap),RequireJS等轻松地搭建新项目。

出色的构建过程 -不仅获得了缩小和连接;我还将优化所有图像文件,HTML,编译CoffeeScript和Compass文件,如果您使用的是AMD,我将通过r.js传递这些模块,因此您不必这样做。

自动编译CoffeeScript和Compass —我们的LiveReload监视过程会自动编译源文件并在进行更改时刷新您的浏览器,因此您无需这样做。

自动整理脚本 -所有脚本均针对JSHint自动运行,以确保它们遵循语言最佳实践。

内置预览服务器 -无需启动您自己的HTTP Server。我内置的一个命令就可以触发。

令人敬畏的图像优化 -我使用OptiPNG和JPEGTran优化您的所有图像,以便您的用户可以花费更少的时间下载资产,而花费更多的时间使用您的应用程序。

杀手软件包管理 -需要依赖吗?这只是一个按键。我允许您通过命令行轻松地搜索新软件包(例如`bower search jquery),安装它们并保持更新,而无需打开浏览器。

PhantomJS单元测试 —通过PhantomJS在无头WebKit中轻松运行单元测试。当您创建新应用程序时,我还将为您的应用程序提供一些测试支架。


请为-1发表评论?
MarcoK

4

Bower可能满足您的需求(1)和(2),满足您的其余需求。从自述文件:

Bower is a package manager for the web. Bower lets you easily install assets such as images, CSS and JavaScript, and manages dependencies for you.

要安装软件包:

bower install jquery
bower install git://github.com/maccman/package-jquery.git
bower install http://code.jquery.com/jquery-1.7.2.js
bower install ./repos/jquery

我已经研究了我在OP中链接的所有对象(包括Bower),但没有一个能够满足我5个需求中的3个以上。我正在寻找一个可以解决我所有5个问题的工具(或工具组合)。
pathikrit 2012年

不知道这是否值得一票,我说Bower + requirejs可能适合您的需求。您说过您也对“工具的最佳组合”持开放态度。祝您搜寻
顺利!

这有什么问题:(1)bower(2)也是bower(3)requirejs build(4)您已经安装了节点吗?(5)requirejs
user18428

2

果酱包装经理。以下是其主页上的描述

对于渴望获得可维护资产的前端开发人员,Jam是JavaScript的软件包管理器。与其他存储库不同,我们将浏览器放在首位。

它的工作方式似乎与npm非常相似。

如下安装软件包

jam install backbone

通过执行使软件包保持最新

jam upgrade
jam upgrade {package} 

优化生产包装

jam compile compiled.min.js

卡纸依赖项可以添加到package.json文件中。

有关完整的文档,请阅读果酱文档。


2

我刚遇到inject.js

来自项目站点的一些功能:

注入(Apache Software License 2.0)是一种革命性的方法,可以通过“库无关”方式管理依赖项。它的一些主要功能包括:

  • 浏览器中的CommonJS合规性(导出。*)
  • 查看完整的CommonJS支持列表
  • 跨域检索文件(通过easyXDM)
  • localStorage(一次加载一个模块)

我喜欢注射。它比RequireJS干净得多,几乎就像用node编写一样。
Mardok


1

我将hem与npm结合使用,我想添加一些我认为到目前为止尚未涵盖的其他好处。

  • Hem有一个独立的Web服务器(strata),因此您无需重新编译即可开发代码。hem build除非发布应用程序,否则我不会使用。
  • 您无需使用Spine.js来使用hem,如果正确设置了slug.json,则可以使用它来编译任意coffeescript包。这是我用cakefile自动编译的软件包之一:https : //github.com/HarvardEconCS/TurkServer/tree/master/turkserver-js-client
  • 谈到上述内容,hem允许您使用npm link链接本地系统上的其他依赖项,即使在使用Strata Server时也可以无缝组合它们。实际上,您甚至不需要使用cake上面的方法,您可以直接从相关项目中直接链接到coffeescript。
  • Hem支持eco(嵌入式Coffeescript)视图和Stylus CSS,并将所有内容与Coffeescript一起编译为一个JS和一个CSS文件。

这是设置Spine,下摆,coffeescript应用程序的基本列表。随意忽略脊椎部位。实际上,有时我会spine app为非Spine应用程序设置目录结构,然后进行编辑slug.json以更改为其他编译结构。

  1. curl http://npmjs.org/install.sh | sh在* nix系统上安装NPM :。我假设它可以从命令行使用。
  2. 全局安装下摆(npm install -g hem)。开发分支到最近为止,所以您可能想要直接从github(https://github.com/spine/hem)中获取它,签出一个分支,并npm install -g .在该文件夹中。
  3. npm install -g spine.app 将使spine成为全局命令
  4. spine app folder将创建一个名为appin 的Spine项目folder,生成正确的目录结构和一堆框架文件以开始使用。
  5. cd文件夹并编辑dependencies.json所需的库。将它们添加到,slug.json以便下摆也知道在哪里找到它们。
  6. 可选:npm link您正在开发中的任何本地软件包node_modules都可以添加到中,您可以将它们添加到slug.json下摆中(可以index.js直接包含,也可以index.coffee在想要下摆进行编译时添加。)
  7. npm install . 下载您刚刚输入的所有依赖项。
  8. 如果您查看默认的spine配置,则可以在app/lib/setup.coffee其中找到require依赖项所需的所有库。例子:

    # Spine.app had these as dependencies by default
    require('json2ify')
    require('es5-shimify')
    require('jqueryify')
    
    require('spine')
    require('spine/lib/local')
    require('spine/lib/ajax')
    require('spine/lib/manager')
    require('spine/lib/route')
    
    # d3 was installed via dependencies.json
    require 'd3/d3.v2'
  9. 在中index.coffee,您只需require lib/setup为应用加载主控制器。另外,您需要require那些其他控制器中的任何其他类。您可以使用spine controller somethingspine model something生成控制器和模型的模板。典型的Spine控制器使用node的require如下所示:

    Spine = require('spine')
    # Require other controllers
    Payment = require('controllers/payment')
    
    class Header extends Spine.Controller
      constructor: ->
        # initialize the class
    
      active: ->
        super
        @render()
    
      render: ->
        # Pull down some eco files
        @html require('views/header')   
    
    # Makes this visible to other controllers    
    module.exports = Header
  10. 生成的默认值index.html通常适合加载您的应用程序,但可以根据需要进行修改。根据您的要求,它只提取js一个css文件和一个文件,您无需修改​​。

  11. 根据需要在css文件夹中编辑手写笔文件。它比CSS灵活得多:)
  12. 从开始folder,运行hem server以启动下摆服务器,并导航localhost:9294以查看您的应用程序。(如果全局安装了hem。)它具有一些隐藏的参数,例如--host 0.0.0.0在所有端口上侦听。
  13. 使用适当的MVC技术构建应用程序的其余部分,并将手写笔用于CSS,将eco用于视图。或者根本不使用Spine,下摆在Coffeescript和npm上仍然可以很好地工作。有很多使用这两种模型的项目示例。

还有一件事:通常,hem server它将在您更新代码和保存文件时自动更新,这使调试变得很困难。运行hem build将您的应用编译为两个文件application.js,分别为和application.css。如果您hem server在此之后运行,它将使用这些文件并且不再自动更新。因此,hem build直到您真正需要应用的精简版才能进行部署。

其他参考:Spine.js和下摆入门


1

这是采用不同方法的解决方案:将所有模块打包到JSON对象中,并通过读取和执行文件内容来获得模块,而无需其他请求。

纯客户端演示实现:http : //strd6.github.io/editor/

https://github.com/STRd6/require/blob/master/main.coffee.md

STRd6 / require取决于运行时是否提供JSON包。该require函数是为该软件包生成的。该软件包包含您的应用可能需要的所有文件。由于该软件包捆绑了所有依赖项,因此不再发出任何http请求。这与客户端上所需的Node.js样式几乎一样。

软件包的结构如下:

entryPoint: "main"
distribution:
  main: 
    content: "alert(\"It worked!\")"
  ...
dependencies:
  <name>: <a package>

与Node不同,软件包不知道它的外部名称。取决于名称的依赖关系。这提供了完整的封装。

在完成所有设置后,这里提供了一个从包中加载文件的功能:

loadModule = (pkg, path) ->
  unless (file = pkg.distribution[path])
    throw "Could not find file at #{path} in #{pkg.name}" 

  program = file.content
  dirname = path.split(fileSeparator)[0...-1].join(fileSeparator)

  module =
    path: dirname
    exports: {}

  context =
    require: generateRequireFn(pkg, module)        
    global: global
    module: module
    exports: module.exports
    PACKAGE: pkg
    __filename: path
    __dirname: dirname

  args = Object.keys(context)
  values = args.map (name) -> context[name]

  Function(args..., program).apply(module, values)

  return module

该外部上下文提供了模块可以访问的一些变量。

一个require功能公开给模块,因此它们可能需要其他模块。

还公开了其他属性,例如对全局对象的引用和一些元数据。

最后,我们在模块和给定的上下文中执行程序。

对于希望在浏览器中具有同步node.js样式的require语句并且对远程脚本加载解决方案不感兴趣的人,此答案将最有帮助。



0

我建议您检查一下dojo工具箱,它似乎可以满足您的大多数要求。我不确定的是CoffeeScript。

dojo可使用以异步模块定义(AMD)格式编写的模块。它具有一个带有软件包的构建系统,您可以将它们聚合到一个或多个文件(称为层)中。显然,它接受git类型存储库,有关构建系统的更多详细信息,请参见:

http://dojotoolkit.org/documentation/tutorials/1.8/build/

出于记录,预计下个月将发布v1.9 beta。


0

满足我最近发布的所有标准的另一个框架:http//duojs.org/(并且还支持将其他资源(如CSS)视为依赖项)。


By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.