专栏首页jeremy的技术点滴现代Web开发系列教程_07

现代Web开发系列教程_07

今天结合前面说到的前后端开发知识,做一个小工程,这个小工程并不完全具体的业务功能,但该工程包括前后端,可以作为以后复杂工程的起点。

前端代码

前端代码稍微复杂一点,就先从前端代码开始。

frontend/js/demo6.js

import React from 'react';
import ReactDOM from 'react-dom';
import ReactRouter from 'react-router';
import { Router, Route, IndexRoute, browserHistory } from 'react-router';

class App extends React.Component{
  render(){
    return <div>{this.props.children}</div> ;
  }
}

class Home extends React.Component{
  render(){
    return <h1>Home Page</h1> ;
  }
}

class About extends React.Component{
  render(){
    return <h1>About Page</h1> ;
  }
}

class Features extends React.Component{
  render(){
    return <h1>Features Page</h1> ;
  }
}

document.body.innerHTML = '<div id="reactHolder"></div>';

ReactDOM.render(
  <Router history={browserHistory}>
    <Route path='/' component={App}>
      <IndexRoute component={Home} />
      <Route path='about' component={About} />
      <Route path='features' component={Features} />
      <Route path='*' component={Home} />
    </Route>
  </Router>,
  document.getElementById('reactHolder')
);

可以看到就是定义了几个React组件,并用react-router定义了一个很简的路由,这个路由的history使用的是browserHistoryreact的用法可参考这里react-router的用法可参考这里

写前端代码编译脚本

webpack.config.js

const webpack = require("webpack");
const HtmlWebpackPlugin = require('html-webpack-plugin');

module.exports = {
    entry: {
        demo6 : __dirname + '/frontend/js/demo6.js'
    },
    output: {
        path: __dirname + '/public',
        publicPath: '/',
        filename: 'js/[name].js',
        hotUpdateMainFilename: 'hot-update/[hash].hot-update.json',
        chunkFilename: 'js/chunks/[name].js',
        hotUpdateChunkFilename: 'hot-update/chunks/[id].[hash].hot-update.js',
    },
    plugins: [
        new webpack.SourceMapDevToolPlugin({
            test:      /\.(js|css|less)($|\?)/i,
            filename: '[file].map'
        }),
        new HtmlWebpackPlugin({
          title: 'demo6',
          filename: 'index.html',
          hash : true,
          chunks : ['demo6']
        })
    ],
    module: {
        loaders: [
            {test: /\.(js|jsx)$/, loaders: ["babel"]}
        ]
    },
    resolve: {
        extensions: ['', '.js', '.jsx']
    },
    devtool: 'eval'
};

.babelrc

1

{ "presets": ["react", "es2015"] }

上面的webpack编译配置很简单,就是配置把frontend/js/demo6.js编译到public/js/demo6.js,同时生成public/index.html,其引用生成的public/js/demo6.js

利用npm-scripts来进行webpack的调用

"scripts": {
  "wpack": "./node_modules/.bin/webpack --watch --progress"
},

后端代码

backend/server.js

"use strict";

const koa = require('koa');
const serve = require('koa-static');
const sendfile = require('koa-sendfile')
const path = require('path');
const Promise = require('bluebird');
const fs = require('fs');

const statAsync = Promise.promisify(fs.stat);

const app = koa();

app.use(serve(__dirname + '/../public'));

app.use(function *(next){
    let p = path.resolve(__dirname, '..', 'public', this.path);
    let stats = null;
    try{
        stats = yield statAsync(p);
    }catch(ignore){}
    if (!stats) {
        try {
            stats = yield sendfile(this, path.resolve(__dirname, '..', 'public', 'index.html'));
        }catch(ignore){}
        if (!stats) this.throw(404);
    }
});

const port = 5000;

app.listen(port);

console.log("server started on port " + port);

因为前端使用了browserHistory路由,后端要实现类似nginx的try_files逻辑,详情见这里,如果后端是用Java写法,可以考虑使用TryFilesFilter

这里使用bluebirdpromisify方法将NodeJS风格的API fs.stat 转化成返回Promise对象的方法,这个是为配合koayield而为,详见这里

同样利用npm-scripts启动后端server

"scripts": {
  "serve": "node ./backend/server.js"
},

运行测试

打开两个终端,在一个里面执行npm run serve启动后端server,在另一个里面执行npm run wpack启动webpack对前端代码进行编译。最后使用浏览器分别访问http://127.0.0.1:5000/http://127.0.0.1:5000/abouthttp://127.0.0.1:5000/features,即可看到路由切换的效果。

本篇源代码地址

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • 现代Web开发教程系列_02

    jeremyxu
  • 特别要检查Java文件操作相关方法的返回值

    jeremyxu
  • 修复hexo涉及中文的302问题

    jeremyxu
  • 关于浏览器渲染VM_ xxx.js的问题

    最近有一个站点涉及到改版的问题,由于时间仓促,有很多css和js 都是直接从合适的资源拿过来用的,这就比较容易导致js冲突和css错乱的问题,在...

    相柳
  • Grunt :初次使用及前端构建经验

    这是我们部门前端同学cobish的学习笔记,笔者编辑了一下并分享给大家。

    金蝶云平台
  • Webpack系列——快速入门

    多文件入口 对entry采用对象写法,指定对应的键值对,为了输出这多个文件可以使用占位符

    用户1515472
  • 腾讯云独家详解小程序多人视频通话

    在微信小程序中搜索 腾讯视频云 可以加载到我们的演示用小程序,其中 多人音视频 功能可用于体验和测试多人音视频通话功能。出于 UI 美观和画面大小的考虑,Dem...

    腾讯视频云终端团队
  • 利用js文件反弹shell

    前两天在freebuf上看到一个利用Ink文件触发攻击链的文章,确实佩服作者的脑洞。

    洛米唯熊
  • smartClient 1--框架介绍

    一、是什么(以下简称SC)     smartClient 是一个基于web技术的开发框架,主要包括: 一个无需安装的 Ajax/HTML5 客户端引擎 UI组...

    用户1148399
  • RequireJS实例分析

      随着JS越来越庞大,已经不仅仅是以前复制粘贴做特效的时代了,JS越来越偏向于业务逻辑与应用。恰逢Node的流行,JS在web开发中占有越来越重要的地位。由...

    用户1154259

扫码关注云+社区

领取腾讯云代金券