假设我有一个包含以下内容的cljs
文件:
(ns foo)
(defn add [x y]
(+ x y))
,并希望将其作为JavaScript库提供给非ClojureScript开发人员(主要侧重于node.js)。我可以这样做:
clj -m cljs.main -c foo
但是问题是输出是针对Google Closure的模块系统(例如goog.require
)的。我可以使用none
标志(与浏览器或节点相对)将目标设置为-t
,但是...无法解决此问题。将其设置为node
也不能解决问题:没有index.js
(在Java中称为main),没有module.exports = blah blah
。似乎它面向的是独立的全节点应用程序,而不是库。
我了解ClojureScript使用google闭包作为其自身的子模块,而且我不是不必要希望摆脱所有这些问题(我不确定您可以< / em>)。而且我知道es2015本机JavaScript模块由于其静态特性而退出了。
我可以手动或通过脚本对输出进行按摩,以使其在npm生态系统中发挥出色的作用,但令我惊讶的是,没有编译器选项实际上可以输出对npm友好的模块。还是在那里?我只是读错了--help
吗?
答案 0 :(得分:2)
shadow-cljs支持通过:target :npm-module以CommonJS格式输出,它确实支持您的要求。 Node和其他JS工具(例如webpack
)可以独立使用单独的命名空间。默认的CLJS工具不支持此模式。
但是,ClojureScript的编写前提是Closure Compiler将优化您的整个程序。这使其不适合编写要包含在其他版本中的库。以这种方式构建的每个“库”都将包含其自己的cljs.core
版本,因此开始时将非常庞大,并且包括以这种方式构建的2个库是灾难的秘诀,因为它们彼此之间不兼容。 / p>
答案 1 :(得分:1)
这假设您已经安装了ClojureScript和Node.js。
给出:
math101
|-- package.json
|-- src
| `-- com
| `-- example
| `-- math.cljs
package.json
{
"name": "math101",
"version": "1.0.0",
"main": "dist/index.js",
"license": "MIT",
"devDependencies": {
"shadow-cljs": "^2.8.52",
"source-map-support": "^0.5.13"
}
}
注意:
dist/index.js
-这将包含转换为JavaScript的ClojureScript代码shadow-cljs
-我们需要的构建(和依赖管理)工具source-map-support
-Required to run ClojureScript on Node.js ?请确保您已安装这两个NPM依赖项,然后再继续。
math.cljs
(ns com.example.math)
(defn add [x y]
(+ x y))
在math101
的根目录运行yarn shadow-cljs init
。
这将创建一个名为shadow-cljs.edn
的文件,其中包含一些默认设置:
;; shadow-cljs configuration
{:source-paths
["src/dev"
"src/main"
"src/test"]
:dependencies
[]
:builds
{}}
让我们进行一些更改。
首先,您不需要太多的源路径:
{:source-paths
["src"]
:dependencies
[]
:builds
{}}
然后添加一个构建配置:
;; shadow-cljs configuration
{:source-paths
["src"]
:dependencies
[]
:builds
{:math101 {:target :node-library
:output-to "dist/index.js"
:exports-var com.example.math/add}}}
注意:
:math101
-这是我们以后将使用的版本ID :target :node-library
-这告诉shadow-cljs
您打算编写一个库:output-to "dist/index.js"
-您打算发布的代码:exports-var com.example.math/add
-您要发布的功能的“完全限定名称”。这将产生一个默认导出。其他说明:
:target:node-library发出的代码可以(通过require)用作标准节点库,并且对于发布代码以用作已编译的Javascript工件很有用。
有一个:npm-module
目标可用,但到目前为止:node-library
已经为我选中了所有复选框。
运行yarn shadow-cljs compile math101
。
首次运行此命令时,shadow-cljs
将下载大量内容。最终它将完成,并且在完成时...
$ node
> var add = require('./dist')
> add(40, 2)
42
✨✨✨
是否需要导出多个功能?没问题。
让我们添加subtract
:
(ns com.example.math)
(defn add [x y]
(+ x y))
(defn subtract [x y]
(- x y))
现在让我们更新构建配置:
;; shadow-cljs configuration
{:source-paths
["src"]
:dependencies
[]
:builds
{:math101 {:target :node-library
:output-to "dist/index.js"
:exports {:add com.example.math/add
:subtract com.example.math/subtract}}}}
再次运行yarn shadow-cljs compile math101
,并在完成时运行:
$ node
> var math101 = require('./dist')
> math101.add(40, 2)
42
> math101.subtract(44, 2)
42
✨✨✨✨✨✨
附录
这仅是为了帮助您入门。 shadow-cljs compile
会生成非生产代码(即未缩小代码,也不会删除死代码AFAIK,并且Google Closure尚未进行任何优化)。
用于生成可用于生产环境的代码的命令为shadow-cljs release
,但您可能想要先调整构建配置。
我强烈建议您花时间阅读shadow-cljs documentation。这是一个了不起的工具。