利用connect建立前端开发服务器

对于前后端完全分离的系统,开发时候我们需要给前端配置服务器,当然我们可以选择Nginx之类的服务器进行配置,但我们也能使用NodeJS构建高自由度的前端开发服务器。

简单静态服务器

下面是一个简单的静态服务器:

  1. var http = require('http'),
  2. url = require('url'),
  3. fs = require('fs')
  4. path = require('path');
  5.  
  6. function getContentType(_path){
  7. var contentType,
  8. ext = path.extname(_path);
  9.  
  10. switch(ext){
  11. case '.html':
  12. case '.htm':
  13. contentType = 'text/html';
  14. break;
  15. case '.js':
  16. contentType = 'text/javascript';
  17. break;
  18. case '.css':
  19. contentType = 'text/css';
  20. break;
  21. case '.gif':
  22. contentType = 'image/gif';
  23. break;
  24. case '.jpg':
  25. contentType = 'image/jpeg';
  26. break;
  27. case '.png':
  28. contentType = 'image/png';
  29. break;
  30. case '.ico':
  31. contentType = 'image/icon';
  32. break;
  33. default:
  34. contentType = 'application/octet-stream';
  35. }
  36.  
  37. return contentType;
  38. }
  39.  
  40. function httpService(req, res){
  41. var reqUrl = req.url,
  42. pathName = url.parse(reqUrl).pathname,
  43. filePath;
  44.  
  45. if(Path.extname(pathName) === ""){
  46. pathName += "/";
  47. }
  48. if(pathName.charAt(pathName.length - 1) === "/"){
  49. pathName += "index.html";
  50. }
  51.  
  52. filePath = path.join('./', pathName);
  53. fs.exists(filePath, function(exists){
  54. if(exists){
  55. res.writeHead(200, {'Content-Type': getContentType(filePath)});
  56. var stream = fs.createReadStream(filePath, {flags : "r", encoding : null});
  57. stream.on('error', function(){
  58. res.writeHead(404);
  59. res.end('<h1>404 Read Error</h1>');
  60. });
  61. stream.pipe(res);
  62. }else{
  63. res.writeHead(404, {'Content-Type': 'text/html'});
  64. res.end('<h1>404 Not Found</h1>');
  65. }
  66. });
  67.  
  68. }
  69.  
  70. var webService = http.createServer(httpService);
  71. webService.on('error', function(error){
  72. console.log('[WebService][error] ' + error);
  73. });
  74. webService.listen(300, function(){
  75. console.log('[WebService][Start] running at http://127.0.0.1:' + 3000 + '/');
  76. });

可以发现一个静态服务器也要写很多行代码才能完成,但是如果我们使用connect,会发现这一切只要几行代码。

Connect?

connect是高性能NodeJS Web中间件框架,提供了二十余个中间件,并有众多第三方中间件支持。connect使用非常简单,例如上面的静态服务器,在connect中只需:

  1. var connect = require('connect');
  2.  
  3. var app = connect()
  4. .use(connect.static('public'))
  5. .listen(3000);

安装connect

我们只要在命令行中输入:

npm install connect

便可以安装了。

模型

connect的模型非常简单,通过use注册中间件,每个中间件接收request和response,如果发现request是该中间件处理的,那么处理完后通过response.end输出,否则通过next交给下一个中间件处理。

需求

OK,现在我们看看需求是怎样的:

  • 由于前后端是分离的,所以开发的时候前后端也是分离的,那么前端和后端做交互就会跨域,所以首先要能反向代理到后端。
  • 可以简单配置静态服务器(我们假设前端的文件全是静态的)。
  • 可以在前端模拟数据交互,也就是在特定的文件夹存储模拟的数据,然后对应返回。
  • 力求简便,通过json配置。

路径结构:

/static:静态服务路径与后端交互

/prototype/static:原型路径与模拟数据交互

/prototype/static/mockup-data/:模拟数据路径

代码

static.js:

  1. module.exports = (function(){
  2. "use strict"
  3. var connect = require('connect'),
  4. http = require('http'),
  5. url = require('url'),
  6. path = require('path'),
  7. proxy = require('proxy-middleware'),
  8. fs = require('fs'),
  9. pkg = JSON.parse(fs.readFileSync('./package.json'));
  10.  
  11. // 通过后缀名得到content type
  12. function _getType(extname){
  13. switch(extname){
  14. case '.json':
  15. return 'application/json';
  16. case '.xhtml':
  17. case '.html':
  18. return 'text/html';
  19. default:
  20. return 'application/json';
  21. }
  22. }
  23.  
  24. // 使用connect
  25. var app = connect()
  26. // 使用logger中间件
  27. .use(connect.logger('dev'))
  28. // 用static中间件处理静态服务
  29. .use(pkg.static.path, connect.static(pkg.static.root, {maxAge: pkg.maxAge}))
  30. .use(pkg.prototype.path + '/static/mockup-data', function(req, res, next){
  31. // 如果是GET方法,交由下面的中间件处理
  32. if(req.method === 'GET') return next();
  33.  
  34. var urlObj = url.parse(pkg.prototype.root + req.originalUrl.replace(pkg.prototype.path, '')),
  35. filePath = urlObj.protocol + urlObj.pathname,
  36. contentType = _getType(path.extname(urlObj.pathname)),
  37. method = req.method.toLowerCase(),
  38. // 得到与方法名对应的模拟文件路径,例如原来文件路径是1.json,在POST方法中变成1.post.json
  39. methodFilePath = filePath.replace(/(\.xhtml|\.html|\.json)$/, '.' + method + '$1');
  40.  
  41. fs.exists(methodFilePath, function(exist){
  42. // 如果方法名对应的模拟文件存在
  43. if(exist){
  44. // 替换文件路径
  45. filePath = methodFilePath;
  46. }
  47. // 读取文件
  48. fs.readFile(filePath, function(err, data){
  49. if(err) return next(err);
  50. res.writeHead(200, {'Content-Type': contentType});
  51. res.statuCode = 200;
  52. res.end(data);
  53. });
  54. });
  55. })
  56. // 用static中间件处理原型的静态服务
  57. .use(pkg.prototype.path, connect.static(pkg.prototype.root, {maxAge: pkg.maxAge}))
  58. // 使用proxy-middleware中间件进行反向代理
  59. .use(proxy(url.parse(pkg.proxy)))
  60. .listen(pkg.port, function(){console.log('Connect with: http://127.0.0.1:' + pkg.port)});
  61. })();

package.json:

  1. {
  2. "maxAge": 3600,
  3. "port": 80,
  4. "proxy": "http://192.168.10.202:8080",
  5. "prototype": {
  6. "path": "/prototype",
  7. "root": "C:/Users/Desktop/manggis/manggis_web/src/main/webapp/prototype"
  8. },
  9. "static": {
  10. "path": "/manggis_web/static",
  11. "root": "C:/Users/Desktop/manggis/manggis_web/src/main/webapp/static"
  12. },
  13. "devDependencies": {
  14. "connect": "~2.8.4",
  15. "proxy-middleware": "~0.4.0"
  16. }
  17. }

所见即所得的游戏界面开发

基于flash的网页游戏UI开发,常规基于flash IDEflex两种方式,这两种方式都提供了可视化的操作方式,但是各自的弊端都非常明显

存在的问题:
先说flash IDE, 是Adobe最早的矢量图开发工具,定位为画图及动画制作工具。可视化操作很方便,但他对组件的支持极其有限,大家不得不仅仅用他来对UI的位置,再通过各种方式转换为对应的组件,非常不方便,组件参数设置更无从谈起。这些诸多不便,带来的是UI开发效率低下,美术和程序工作相互交叉,可视化力度不够,协助不方便,项目一旦大了资源也很不好管理。
再说flex,adobe希望把他做成一个通用框架,实现所有需求,正因为如此,框架变的庞大而臃肿,很多类和函数你甚至一辈子都不会用到,和网页游戏追求高性能,低加载量背道而驰,最终也被广大页游开发商所抛弃。

理想化的UI开发工具:
理想化的UI开发工具应该是什么样的呢?
1.可视化,应该具有flash IDE的可视化,比如拖拽,层操作,双击层级关系,任何界面都能可视化的拼出来,所有操作可撤销
2.组件化,应具有flex的组件化功能,所以界面均为组件,能方便的设置参数并立即看到效果
3.能自动管理资源,并且自动生成UI代码
4.能让美术和程序工作分离,相互配合但互不影响,方便svn管理合并,让多部门协调工作
5.UI库需高性能,代码轻量能迅速上手,编辑器便于使用,美术易于简单学习甚至无需学习直接上手
6.方便扩展,能随意扩展组件并让编辑器自动可视化支持,实现多样化需求
7.支持多项目,支持矢量图特效,支持多语言等等

解决方案:
Morn就是基于以上特点而设计的,吸取了flash IDE和flex各自的优点,并加以扩展,具有可视化,高性能,轻量级,易扩展等等特点,组件库开源,编辑器免费授权,可用来做商业开发,大大提供webgame开发效率。由于开源,Morn UI组件库代码完全可以自己控制,并且编辑器也支持插件化扩展,实现自定义的功能,可谓强大。Morn UI的官方网站http://www.mornui.com/

我也是一名网页游戏开发者,利用业余时间开发这个工具,只为提高工作效率,现在分享给大家免费使用,后面我会陆续奉上系列教程,方便业界同学,好的工具能大大提高工作效率,希望对大家有所帮助

编辑器整体图

开源的组件库

 
 
分类: as3游戏
 
 
分类: NodeJS
标签: JavascriptNodeJS

利用connect建立前端开发服务器的更多相关文章

  1. 利用HBuilder打包前端开发webapp为apk

    转载 标签: apk / 打包 / vue 现在的前端开发可谓是,百花齐放啦,什么都可以做,只有想不到没有做不到的,今天就简单的介绍用vue,ng或者是react开发的单页应用如何打包为apk,在移动 ...

  2. 简单利用jQuery加tomcat,让前端开发不再依赖于后端的接口

    前端开发的过程中,我们免不了和后端进行联调,这时候就会出现以下的尴尬场景: 接口没写好,没法做接下来的功能 功能写好了,接口没写好,没法测这个功能 联调了,除了BUG,不知道锅在谁身上,只得陪后端耗时 ...

  3. 前端开发 Grunt 之 Connect

    在前端开发过程中,我们需要在开发过程中,将开发中的站点部署到服务器上,然后,在浏览器中查看实际的效果,在 Grunt 环境下,可以直接使用集成在 Grunt 中的 Connect 插件完成站点服务器的 ...

  4. 利用 Grunt (几乎)无痛地做前端开发 (一)之单元测试

    前言 如果你想开发一个js应用,甭管多简单,都要先创建整个宇宙 来看看我们的Javascript小宇宙: 确定如何根据需求.功能划分模块,如何将代码分成多个文件开发,合成一个发布 保证上一条的同时,使 ...

  5. 前端开发 Grunt 之 Connect详解

    在前端开发过程中,我们需要在开发过程中,将开发中的站点部署到服务器上,然后,在浏览器中查看实际的效果,在 Grunt 环境下,可以直接使用集成在 Grunt 中的 Connect 插件完成站点服务器的 ...

  6. 简单利用jQuery,让前端开发不再依赖于后端的接口

    前端开发的过程中,我们免不了和后端进行联调,这时候就会出现以下的尴尬场景: 接口没写好,没法做接下来的功能 功能写好了,接口没写好,没法测这个功能 联调了,出了BUG,不知道锅在谁身上,只得陪后端耗时 ...

  7. Web前端开发如何利用css样式来控制Html中的h1/h2/h3标签不换行

      H1/H2/H3/H4标题标签常常使用在一个网页中唯一标题.重要栏目.重要标题等情形下. H1在一个网页中最好只使用一次,如对一个网页唯一标题使用.H2.H3.H4标签则可以在一个网页中多次出现, ...

  8. 利用NIO建立Socket服务器

    传统的Java 的IO,利用Socket建立服务器,接收客户端连接,一般都是为每一个连接建立一个线程,如果连接数巨大,那么服务器开销也将巨大..NIO的原理,可以参照图:http://new.51ct ...

  9. 前端开发的使用服务器环境开源项目 D2Server 可替代Apache

    推荐一个前端开发的使用服务器环境开源项目 D2Server 可替代Apache   攻欲善其事,必先利其器.前端开发,编辑器我们有了Sublime Text2,配置Server环境用……你可能会选择A ...

随机推荐

  1. Swift语言指南(七)--语言基础之布尔值和类型别名

    原文:Swift语言指南(七)--语言基础之布尔值和类型别名 布尔值 Swift有一个基本布尔类型,叫做布尔(bool),布尔值又称逻辑值(logical),因为它只能为真(true)或假(false ...

  2. C#面向对象复习概要

    1.面向对象:我们将具有统一行为和属性的对象抽象划分为类,通过类去创建对象.这种编程思想叫做面向对象的编程思想. 2.属性:对象具有的属性 using System; using System.Col ...

  3. [CLR via C#]5.2 引用类型和值类型

    原文:[CLR via C#]5.2 引用类型和值类型 CLR支持两种类型:引用类型和值类型. 虽然FCL中大多数都是引用类型,但开发人员用的最多的还是值类型.引用类型总是在托管堆上分配的,C#的ne ...

  4. Spark集群搭建简配+它到底有多快?【单挑纯C/CPP/HADOOP】

    最近耳闻Spark风生水起,这两天利用休息时间研究了一下,果然还是给人不少惊喜.可惜,笔者不善JAVA,只有PYTHON和SCALA接口.花了不少时间从零开始认识PYTHON和SCALA,不少时间答了 ...

  5. Spring之使用Annotation注解开发项目

    我们也可以使用Annotation来实现注入操作,提高我们写代码的灵活性和效率.spring中要使用annotation,需要在配置文件中增加: <beans xmlns="http: ...

  6. Cf 444C DZY Loves Colors(段树)

    DZY loves colors, and he enjoys painting. On a colorful day, DZY gets a colorful ribbon, which consi ...

  7. Pki原则

    核心提示: 公开密钥和公开密钥证明书,产生的私钥client要么server证书.加密的公共密钥才能解密私钥文件只.私钥只能解密公开的加密文件.公众认为,它是开放的.所有的人都能够得到它.私人还表明, ...

  8. nodejs开发aspnet5项目

    结合nodejs开发aspnet5项目 1.安装kvm   官方教程地址:https://github.com/ligershark/Kulture 打开 powershell命令窗口,找不到可以在开 ...

  9. 设计模式之职责链模式(Chain of Responsibility)摘录

    23种GOF设计模式一般分为三大类:创建型模式.结构型模式.行为模式. 创建型模式抽象了实例化过程,它们帮助一个系统独立于怎样创建.组合和表示它的那些对象.一个类创建型模式使用继承改变被实例化的类,而 ...

  10. Talend open studio数据导入、导出、同步Mysql、oracle、sqlserver简单案例

    推荐大家一个BI工具:talend open studio.我也是刚接触,懂得不多,感觉比较神奇就想大家推荐一下... 由于公司项目,接触了一下BI工具talend,感觉功能很强大, 可以同步多种数据 ...