写 gulp requirejs 编译流程的笔记

不再将重点放在 RequireJS, 建议切换 Webpack: http://segmentfault.com/t/webpack/blogs

官方的 gulp-requirejs 插件有点问题, end 事件没有正常触发
找 zensh 一起看了下, 他找到问题给了解决方案, 我才把坑填了
后来微博上有提醒说用 gulp-requirejs-optimize, 但是下载量远远不行
http://weibo.com/1651843872/BBzG2sHQm

这里我打算记录一下这个脚本, 其中涉及到了怎样对付流
我匆忙之中搜罗了一些资料, 慢慢摸索出来的, 对于理解 Gulp 会有帮助
脚本的内容是这样的:

coffeegulp.task 'mainjs', ->
  rjs = require 'requirejs'
  uglify = require 'gulp-uglify'
  rename = require 'gulp-rename'
  vinyl = require 'vinyl'
  through2 = require 'through2'

  stream = through2.obj()

  rjs.optimize
    wrap: true
    preserveLicenseComments: false
    optimize: 'none'
    name: 'main'
    baseUrl: 'build/script/'
    mainConfigFile: 'build/script/config.js'
    exclude: ['deps']
    out: (chunk) ->
      buffer = new vinyl
        path: 'main.js'
        contents: new Buffer chunk
      stream.write buffer
    (output) ->
      stream.end()

  stream
  .pipe uglify()
  .pipe rename(suffix: '.min')
  .pipe gulp.dest('./build/')

我当时面对的事情是, 已经有个 requirejs 模块可以编译了,
我需要调用编译, 然后把输入以 gulp file stream 的形式继续传递
后面再继续用 uglify 等等对代码进行后续的操作
阅读过一下 gulp-requirejs 的代码, 我知道我需要解决两个问题:
https://github.com/RobinThrift/gulp-requirejs/blob/master/index.js

  1. 需要创建一个新的 Stream 出来, 并且和 Gulp 插件兼容
    我尝试了一个学习原来的代码, 发现他用的 event-stream 模块太复杂搞不定

  2. requirejs 模块生成的数据, 我要能接受并且传入流当中
    麻烦的是 gutil.File 这个构造器在新的版本里不见了

创建 Stream

之前我已经知道 Gulp 的 Stream 是封装过的文件流有 pathcontents
根据文档跟尝试, 我了解到 Stream 中只能使用 String 或者 Buffer
那么对象怎样传送呢, 我只记得例子里 through2 封装的 stream 是可以的
后来又看到有提到, Stream 有个 objectMode 可以传送对象:
http://nodejs.org/api/stream.html#stream_object_mode
不过操作的 API 看起来挺复杂的, 我没搞明白..

后来尝试了一下直接用 through2, 发现正常运行了:

coffeestream = though2.obj()
stream.write buffer
stream.end()

文档给的用发是 .obj(fn) 当中会有个 write 函数的
我的用法里没写用正常跑了, 忘了参考的是哪一份代码
这个地方留了一些疑惑.. 但好歹完成了 Stream 的创建

构造文件数据

另外一个问题, requirejs 模块, out 函数传的参数, 实际上是对应 emit 的数据
上边的代码可以看到有两个函数, 一个处理 emit, 另一个处理 end
虽然是 emit, 但因为 requirejs 要读所有文件, 实际上只是最终调用一次而已

我找了半天 gulp.File 找不到, 我尝试去 gulp 源码房中找封装文件对象的代码
最后在 vinyl 的文档上翻到相似的内容:
https://github.com/wearefractal/vinyl
文档上的参数更多一些, 而我通过这样的写法, 终于成功创建了文件数据:

coffeevinyl = require 'vinyl'
new vinyl
  path: 'main.js'
  contents: new Buffer 'data'

Stream 对于我来说还是很陌生, 以后慢慢想办法加强..
关于上面两个, 如果你了解更过, 请留言指点一下

    原文作者:题叶
    原文地址: https://segmentfault.com/a/1190000002441027
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞