到目前为止,我们这个系列讨论了Bower、AngularJS、GruntJS、PhoneGap、Meteor、Ember和TimelineJS等JavaScript技术。今天的《30天学习30种新技术》,我决定学习前端开发的效率工具Yeoman。本文将首先介绍Yeoman的基本情况,接着我们会使用Yeoman开发一个Ember应用。本文不会介绍EmberJS的基本知识,所以请参考day 19。

Yeoman是什么?

Yeoman按照官方说法,它不只是一个工具,还是一个工作流。它其实包括了三个部分yo、grunt、bower,分别用于项目的启动、文件操作、包管理。

  1. Yo: Yo是一个项目初始化工具,可以生成一套启动某类项目必需的项目文件。

  2. GruntJS: GruntJS是基于JavaScript的命令行构建工具,它可以帮助开发者们自动化重复性的工作。阅读day 5获取更多信息。

  3. Bower: Bower是一个客户端技术的软件包管理器,它可用于搜索、安装和卸载如JavaScript、HTML、CSS之类的网络资源。阅读day 1获取更多信息。

我为什么关心Yeoman

如果你需要说服自己学习Yeoman,你可以读读Yeoman网站上的whyyeoman。

安装

使用npm安装:

npm install -g yeoman

安装Yeoman Ember生成器

Yeoman依赖生成器为web项目提供支架。所有的现代JavaScript MV* 框架都有相应的生成器。本文使用Ember:

npm install -g generator-ember

我们将开发一个社交化书签应用,允许用户提交和分享链接。你可以在这里查看这个应用。这个应用和我们day 19开发的一样。

Github仓库

今天的示例应用代码可从Github取得。

创建Ember应用

现在开始应用开发。首先创建项目目录,接着运行yo ember命令,它会询问你是否使用Twitter Bootstrap。我习惯在自己的项目中使用Bootstrap,所以我选了是。

; mkdir getbookmarks
; cd getbookmarks
; yo ember_-----_|       ||--(o)--|   .--------------------------.---------  |    Welcome to Yeoman,    |( __ )   |   ladies and gentlemen!  |/___A___\   '__________________________'|  ~  |__'.___.'__[?] Would you like to include Twitter Bootstrap for Sass? Yes

之后Yeoman会创建一个Ember应用,自动使用bowernpm安装依赖。

现在让我们看看Yeoman生成的Ember应用。应用有三个顶层目录:appnode_modulestest。还有一些配置文件:.bowerrc.gitignore.jshintrcGruntfile.jspackage.json。目录结构如下所示。

所有的应用相关代码都在app目录下。目录结构遵循Ember的最佳实践。

  1. bower_components目录包括了客户端依赖,例如Ember、Twitter Bootstrap,等等。Bower在所有文件夹内安装所有依赖。

  2. image目录包括了应用相关的图像。Yeoman会优化image目录内的图片。

  3. index.html包含了所有的ember.js依赖,所有的bootstrap依赖,以及build注释(Gruntfile.js可以据此替换或移除引用的未优化的脚本和样式表)。

  4. scripts目录包含了Ember应用的controller、view、model和route。

  5. styles目录包含了应用相关的css文件。

  6. templates目录包含了应用的handlebar模板。

现在我们可以启动预览服务器了:

grunt server

这会使用系统默认浏览器打开应用:

生成Story Model

我们在day19中开发的GetBookmarks应用中创建了一个Ember Model:Story。Yeoman的次级生成器可以用来构建项目的部分,包括model。运行如下命令生成Story model:

yo ember:model Story

命令的输出如下:

   create app/scripts/models/story_model.jsinvoke   ember:controller:/usr/local/lib/node_modules/generator-ember/model/index.jscreate     app/scripts/controllers/stories_controller.jscreate     app/scripts/controllers/story_edit_controller.jscreate     app/scripts/routes/stories_route.jscreate     app/scripts/routes/story_route.jscreate     app/scripts/routes/story_edit_route.jsinvoke       ember:view:/usr/local/lib/node_modules/generator-ember/controller/index.jscreate         app/scripts/views/story_view.jscreate         app/scripts/views/story_edit_view.jscreate         app/scripts/views/stories_view.jscreate         app/templates/story.hbscreate         app/templates/story_edit.hbscreate         app/templates/stories.hbscreate         app/scripts/views/bound_text_field_view.jsinvoke       ember:router:/usr/local/lib/node_modules/generator-ember/controller/index.jsconflict         app/scripts/router.js
[?] Overwrite app/scripts/router.js? overwriteforce         app/scripts/router.js

这会在app/scripts/models目录下生成story_model.js,同时会生成相应的view、controller和route。

修改下story_model

Emberapp.Story = DS.Model.extend({url : DS.attr('string'),tags : DS.attr('string'),fullname : DS.attr('string'),title : DS.attr('string'),excerpt : DS.attr('string'),submittedOn : DS.attr('date')
});

重新启动Grunt server以便改动生效。

安装Ember LocalStorage适配器

我们将使用HTML 5 LocalStorage来存储数据。使用bower安装适配器。

bower install --save ember-localstorage-adapter

然后更新index.html页面,添加依赖:

<script src="bower_components/ember-localstorage-adapter/localstorage_adapter.js"></script>

同时更新app/scripts/store.js,配置应用使用LSAdapter:

Getbookmarks.Store = DS.Store.extend();
Getbookmarks.ApplicationAdapter = DS.LSAdapter.extend({namespace: 'stories'
});

更新路由

修改router.js:

Getbookmarks.Router.map(function () {this.resource('index',{path : '/'});this.resource('story', { path: '/story/:story_id' });this.resource('story_edit', { path: '/story/new' });});

提交新报道

我们首先添加用户访问#/story/new后会出现的表单。修改app/templates/story_edit.hbs

<form class="form-horizontal" role="form"><div class="form-group"><label for="title" class="col-sm-2 control-label">Title</label><div class="col-sm-10"><input type="title" class="form-control" id="title" name="title" placeholder="Title of the link" required></div></div><div class="form-group"><label for="excerpt" class="col-sm-2 control-label">Excerpt</label><div class="col-sm-10"><textarea class="form-control" id="excerpt" name="excerpt" placeholder="Short description of the link" required></textarea></div></div><div class="form-group"><label for="url" class="col-sm-2 control-label">Url</label><div class="col-sm-10"><input type="url" class="form-control" id="url" name="url" placeholder="Url of the link" required></div></div><div class="form-group"><label for="tags" class="col-sm-2 control-label">Tags</label><div class="col-sm-10"><textarea id="tags" class="form-control" name="tags" placeholder="Comma seperated list of tags" rows="3" required></textarea></div></div><div class="form-group"><label for="fullname" class="col-sm-2 control-label">Full Name</label><div class="col-sm-10"><input type="text" class="form-control" id="fullname" name="fullname" placeholder="Enter your Full Name like Shekhar Gulati" required></div></div><div class="form-group"><div class="col-sm-offset-2 col-sm-10"><button type="submit" class="btn btn-success" {{action 'save'}}>Submit Story</button></div></div></form>

现在,访问 http://localhost:9000/#/story/new 可以看到提交报道的表单。

更新StoryEditController,将数据持续化入本地存储:

Getbookmarks.StoryEditController = Ember.ObjectController.extend({save: function(){var url = $('#url').val();var tags = $('#tags').val();var fullname = $('#fullname').val();var title = $('#title').val();var excerpt = $('#excerpt').val();var submittedOn = new Date();var store = this.get('store');console.log('Store .. '+store);var story = store.createRecord('story',{url : url,tags : tags,fullname : fullname,title : title,excerpt : excerpt,submittedOn : submittedOn});story.save();this.transitionToRoute('index');}
});

列出所有报道

接下来我们要实现的功能是在侧边栏展示报道列表。

application_route.js,我们从本地存储获取所有的报道。

Getbookmarks.ApplicationRoute = Ember.Route.extend({model : function(){var stories = this.get('store').findAll('story');return stories;}
});

接着我们更新application.hbs,为每个报道的标题添加链接:

<div><nav class="navbar navbar-default navbar-fixed-top" role="navigation"><div class="navbar-header"><button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-ex1-collapse"><span class="sr-only">Toggle navigation</span><span class="icon-bar"></span><span class="icon-bar"></span><span class="icon-bar"></span></button><a class="navbar-brand" href="#">GetBookmarks</a></div><div class="collapse navbar-collapse navbar-ex1-collapse"><ul class="nav navbar-nav pull-right"><li>{{#link-to 'story_edit'}}<span class="glyphicon glyphicon-plus"></span> Submit Story{{/link-to}}</li></ul></div></nav><div class="container" id="main"><div class="row"><div><div class="col-md-3"><div class="well sidebar-nav"><table class='table'><thead><tr><th>Recent Stories</th></tr></thead>{{#each controller}}<tr><td>{{#link-to 'story' this}}{{title}}{{/link-to}}</td></tr>{{/each}}</table></div></div><div class="col-md-9">{{outlet}}</div></div></div></div>
</div>

应用的用户界面会刷新。

查看单独的报道

最后要添加的功能是,用户访问 http://localhost:9000/#/story/:id 的时候可以查看单独的报道。:id对应于story id。修改story_routejs

Getbookmarks.StoryRoute = Ember.Route.extend({model : function(params){var store = this.get('store');return store.find('story',params.story_id);}
});

修改app/templates/story.hbs

<h1>{{title}}</h1>
<h2> by {{fullname}} <small class="muted">{{submittedOn}}</small></h2>
{{#each tagnames}}<span class="label label-primary">{{this}}</span>
{{/each}}
<hr>
<p class="lead">{{excerpt}}
</p>

为生产环境构建

最后,我们运行grunt build命令创建一个可分发的应用。grunt build命令将app目录下的源文件转换成dist目录下的可分发的应用。

grunt build

今天就这些。保持反馈。


原文 Day 24: Yeoman Ember--The Missing Tutorial
翻译 SegmentFault

Day 24: 使用Yeoman自动构建Ember项目相关推荐

  1. idea自动构建web项目_构建Web应用程序以自动执行系统管理员任务

    idea自动构建web项目 系统管理员(sysadmin)每年在重复性任务上浪费数千小时. 幸运的是,使用开源工具构建的Web应用程序可以自动消除很大一部分痛苦. 例如,使用Python和JavaSc ...

  2. Sencha Cmd自动构建ExtJs项目框架

    Sencha Cmd自动构建ExtJs项目框架 1.下载并安装Sencha Cmd 官网(https://www.sencha.com/products/extjs/evaluate/) 某盘wind ...

  3. Jenkins自动构建部署项目

    1. 楔子 在实际开发中,经常需要编译.静态代码检查.自动化测试.打包.部署.启动等一连串重复机械的动作,浪费时间.而且容易出错,而Jenkins就是专门Continuous integration( ...

  4. P8-07-16 使用 Jenkins 自动构建 Maven 项目

    创建一个项目 从 gitee 上随便拉一个项目,这里我们使用Zrlog项目进行测试.测试项目地址: https://gitee.com/94fzb/zrlog?_from=gitee_search 导 ...

  5. Jenkin+GitLab自动构建Maven项目

    认识jenkins Jenkins是一个开源的.提供友好操作界面的持续集成(CI)工具,起源于Hudson(Hudson是商用的),主要用于持续.自动的构建/测试软件项目.监控外部任务的运行.Jenk ...

  6. ubuntu系统下使用jenkins自动构建Android项目

    一.所需要安装的软件: 1.jdk 2.gradle 3.git  4.android sdk 5.tomcat 6.jenkins 二.安装软件: jdk: 下载地址:Java Downloads ...

  7. CentOS 7.2安装Jenkins自动构建Git项目

    1.环境 本文使用VMWare虚拟机进行实验. 最终实现目标,在Jenkins服务器上新建构建任务,从Git服务器上拉取master HEAD(不编译,仅演示),部署到"目标服务器" ...

  8. ci github 通知_初探CI,Github调戏Action手记——自动构建并发布

    前言 最近在做脚本的说明文档时使用了vuepress这个东西 前端实在是菜,只能随便写写了 正常写完md文件之后推送至github做版本控制 而前端页面的生成则是在本地,部署也是在本地手工进行 一套下 ...

  9. Linux下Jenkins与GitHub自动构建NetCore与部署

    今天我们来谈谈NetCore在Linux底下的持续集成与部署.NetCore我就不多介绍了,持续集成用的是Jenkins,源代码管理器用的是GitHub.我们就跟着博文往下走吧. 1.Linux环境 ...

最新文章

  1. Java格式化日期用斜杠_[java工具类01]__构建格式化输出日期和时间的工具类
  2. 架构周报:微信后台系统的演进之路
  3. 存clob为空的值_给Oracle数据库中CLOB字段插入空值
  4. java判断对象无数据_java利用反射机制判断对象的属性是否为空以及获取和设置该属性的值...
  5. Android异常总结---E/AndroidRuntime(23439): Caused by: java.lang.IllegalArgumentException: column '_id' d
  6. 随想录(以项目为中心的学习)
  7. 【优化调度】基于matlab粒子群算法求解经济调度优化问题【含Matlab源码 1489期】
  8. HTML深海骑兵制作,深海迷航代码独眼巨人号护盾发生器 | 手游网游页游攻略大全...
  9. mysql登录密码mysql重置root密码
  10. Java就业面试问题大全
  11. 康托尔连续统假设(CH)不成立
  12. 主流各云平台主机性能对比
  13. 引用防删——JAVA设计模式总结之六大设计原则
  14. LightOJ - 1395
  15. 静态链接之与静态库的链接
  16. 用python程序编写问卷调查_如何使用Python实现调查问卷的自动填写
  17. 纯日记+游戏推荐(妈妈把我的游戏藏起来了)
  18. 安装cartographer出现的问题及解决方法
  19. 吉他推荐 | Yamaha雅马哈F310和VEAZEN费森VZ200,新手入门吉他应该怎么选?
  20. Halcon 第三章『Morphology形态学』◆第1节:腐蚀与膨胀

热门文章

  1. Java Review - 并发编程_LockSupport
  2. 深入理解分布式技术 - 分布式缓存总结回顾
  3. Oracle优化07-分析及动态采样-DBMS_STATS 包
  4. Oracle增加修改删除字段/主键
  5. Java语言实现二分查找(可查询重复数据)
  6. QT设计器主界面中文介绍
  7. 解决Redis超卖问题
  8. 使用JavaMail发送邮件,465端口开启ssl加密传输
  9. 索爱麦克风免驱动的语音录入测试
  10. 微信小程序验证车牌号(含新能源车牌)