ReactJS+Compass+Gulp+RESTful多页应用组件化开发
2016-01-12 17:54
483 查看
前言
我也是一个入坑的前端工程师,从一个无知的少年,变成了又一个无知的少年。一次一次觉得自己学的让自己兴奋的东西,总有另外一个西瓜让你丢掉这个芝麻。做出来好看不过css写起来好麻烦,响应式要自己写media query,css3适配要自己写,选择器父子嵌套很麻烦,Grid要自己写。不能统一管理变量(如颜色,字体大小等),之后学了sass觉得nb,写css方便多了(没有基础还是不行,css中一些原理还是要学习,各种position的区别,各种display的区别,BFC还有一些小而细的细节得钻研)。然而由出现了compass,据说是css界的jquery库,然后又学习了oocss, smacss巴拉巴拉如何写css能有更高的maintainability和reusability。JS方面,学了jQuery,我可以抬起头走路了,然后在实习的过程中,ReactJs, AngularJs, BackboneJs, Zepto, YUI, UnderscoreJS, CanJs, SeaJs一下子撑爆了我的任务表。具体哪种技术有什么优点,要使用过之后才能说得出来。如今40天完成的项目,我用了Compass 和 ReactJs可以在这里做一个总结,给后人一个模版,共同推进前端的发展。这篇文章不讲解具体的技术细节如css的属性或者哪个js函数有什么用,而是带你一起来探讨如何组织项目文件以及其中的逻辑
欢迎来喷!:-(
项目结构
项目的资源文件的分布是 按资源类型 进行分布的。接下来的项目我会对组件采用 按组件 分布的方式。样式
_base.scss: 储存项目的基础变量,如间距、颜色等_helper.scss 辅助类,提供快速的css设置,如.text-center, .font-color-red, .full-width, padding-sm, margin-sm,理念与bootstrap中的快速浮动有关。
_layout.scss 包括了Grid的实现以及项目特有的布局类
_components.scss 组件实现具体的组件的样式
上述的文件将会由 compass compile -s compressed 编译成一个main.min.css文件,并且进行压缩,压缩后由68kb压缩到了30kb,自动取掉了注释的发布版本。对于组件类的命名,我借鉴的是BEM的命名法则。对于自己的项目,可以有自己命名方法论。
最后样式就是一个文件,包括所有的组件,做永久cache,并且用gulp-rev-append做MD5摘要方便修改后的缓存刷新
JS组件
脚本分类
display组件:从controller组件(父元素)中获得数据进行渲染controller组件:维护数据和控制数据的注入
page组件:包装controller组件,指定controller的参数(如加载数据的api等),在页面中布局定位
util:包括service以及其他的与业务逻辑无关的模块
main.js 定义了modules对象作为一个全局变量,然后将定义的所有的其它变量接在modules上面。将display放到modules.dipslay中,将controller放到modules.controller,以此类推
由于React的JSX的格式需要babel –presets = react 进行转换,并且不希望在浏览器中导入browser.js 让客户端浏览器转换,所以要用npm install babel 与 npm install babel-preset-react,以及npm install gulp-babel,然后在gulpfile.js中定义自动脚本转换任务(关于脚本打包在后面一块儿说)
上述的display组件由父元素设置属性来传递数据,自己只有渲染数据的功能,父元素也可以为display组件提供一些方法,如对于一个Form组件,封装了Form的样式和数据接口,父元素controller中的render函数中渲染
<Form submitHanlder={this.submit}/>,为Form提供一个submit的方法。
上述controller组件主要的功能就是维护整个组件的数据模型的状态,并且用数据模型来渲染。这个也是React的特点,M —> V单向数据流。对与数据的获取,我才用$.ajax的方法从服务器获取json格式的数据。
最后page组件就很简单,
//Page_Index.js var Page_Index = React.createClass({ render:function(){ return ( <div> <Navigator /> <Controller_A /> </div> ) } }) //index.html <script type="text/javascript"> //这个代码不需要Babel的转换,其它的JSX在服务端转换好,用户可以直接使用了,不需要浏览器端再browser.js动态转换 ReactDOM.render(React.createElement(modules.Page_Index, null), document.getElementById('content')); </script>
脚本打包
var gulp = require('gulp'); //concat用于将其它js文件合并到一个文件中 //由于使用了modules对象,不存在变量名污染的问题 var concat = require('gulp-concat'); //将JSX转换成正常的js var babel = require('gulp-babel'); //丑化js(压缩js文件成min.js) var uglify = require('gulp-uglify'); var config = { scripts:['components/src/main.js','components/src/modules/**/*.js','components/src/util/*.js'], styles_sass:['public/sass/**/*.scss'] } gulp.task('react-script',function(){ return gulp.src(config.scripts) .pipe(concat("components.min.js")) .pipe(babel({ presets:['react'] })) .pipe(uglify()) .pipe(gulp.dest('./components/build')) }); //自动编译 gulp.task('watch',function(){ gulp.watch(config.scripts,['react-script']); }) gulp.task('default',['watch'],function(){})
总结
详细的技术我不会在这里说,网上太多的技术资料了。前端技术还年轻,有太多的可能性等你发觉。总的来说,做出来后,维护非常的方便,添加新组件,修改旧组件,不会对其它部分有任何影响。这样下来,终于摆脱了之前做前端的时候各种混乱的局面了。相关文章推荐
- ReactJs + BootStrap + Pager 分页
- React 入门实例教程
- ionic & react-natice 安装tips
- 整理的react相关的一些学习地址,包括 react-router、redux、webpack、flux
- 【无源汇点上下界最大流】[SGU194]Reactor Cooling
- React-Native入门
- ReactNative之开发Mac环境配置
- [React Testing] Redux Reducers
- React Native ——实现一个简单的抓取github上的项目数据列表
- netty reactor线程模型分析
- 最快让你上手ReactiveCocoa之进阶篇
- 最快让你上手ReactiveCocoa之基础篇
- React编写聊天室(1)
- [React Testing] The Redux Store - Multiple Actions
- ReactiveCocoa v2.5 源码解析 之 架构总览
- muduo源码分析:reactor模型封装
- React Native Flex布局
- React 复用组件 含表单radio/checkbox注意的问题
- React with TypeScript 系列(二) --基础篇
- react native组件学习(三)