十二周学习笔记和总结

这周学习 express,写了一个网络相册,可以上传自己的图片并展示,代码放到了我的 github

网络相册

一、express

1. 概述

jquery 框架简化了原生 js 的写法;
express 简化了原生node js 的写法。

2.代码

const express = require('express');
const app = express();

app.get('/', function(req, res){
 res.send('hello world');
});

app.listen(3000, function(){
  console.log('服务已启动监听端口3000');
});

3. res 对象

  • res.send('hello world'); 返回字符串;
  • res.json({ name:'yml' }); 返回 json;
  • res.render('index', { name: 'yml' }); 返回 html;
  • res.redirect('/album'); 重定向到 /album 请求。

4. 设置模板引擎

常见的模板引擎:

  • ejs
  • jade
  • swing

不同的模板引擎语法不同,但是最终都会被翻译成 html 返回给客户端。

experss 中需要设置使用哪种模板引擎,使用前先使用 npm install 下载包。

app.set('view engine', 'ejs'); // 设置 ejs 模板引擎

5. 设置静态页面资源目录

一般来说 css 、js 、图片都放到静态资源目录里。

app.use(express.static(path.join(process.cwd(),'public'))); 

二、path

1. 概述

path 是 nodejs 自带的包,提供一些方法处理文件路径。

2. path.join()

作用:自动格式化文件路径,帮助补齐斜线 /。

示例:

path.join('C://study', 'public'); => ‘C://study/public’。

2. path.dirname()

作用:获取文件目录路径,截取最后一个斜线 / 之前的部分。

示例:

const src = '/aaa/bbb/cccc/dddd';
path.dirname(src);        <= '/aaa/bbb/ccc'

3. path.basename()

作用:获取文件名,截取最后一个斜线 / 之后的部分。

示例:

const src = '/aaa/bbb/ccc/ddd';
path.basename(src);   <= 'ddd'

const src = '/aaa/bbb/ccc/ddd.png';
path.basename(src2);    <= 'ddd.png'

4. path.extname()

作用:获取文件后缀,最后一个点后面的内容。

示例:

const src = '/aaa/bbb/ccc/ddd';
path.extname(src);   <= ''       这里没有后缀,返回空

const src = '/aaa/bbb/ccc/ddd.png';
path.extname(src2);    <= 'png'

5. process.cwd() 和 __dirname

process.cwd() 和 __dirname 这两个都是 nodejs 原生自带的 api,在处理路径的时候也会经常遇到。

|-- express-demo
  |-- test
    |-- index.js

在 express-demo 目录下运行 test/index.js 文件:express-demo> node test/index.js

process.cwd(): /home/yml/express-demo
__dirname: /home/yml/express-demo/test

process.cwd():在哪个目录下运行 node 程序,就会打印这个目录的路径;
__dirname:运行的 js 所在的目录。

三、ejs

1. 变量

// app.js
res.render('album', { files: files });
// views/album.ejs
<%= files %>

2. 循环

在 ejs 里可以混合写 js 代码和 html 代码,但是 js 代码要写在 <% %> 里面。

<% for (var i = 0; i < files.length; i++) { %>
  <div class="pic">
    <img src="/images/<%= files[i] %>" alt="pic">
  </div>
<% } %>

3. 公共模板复用

目录路径:

|-- views
  |-- partials(文件夹,中文意思部分/组件)
    |-- header.ejs(公共的部分)        
  |-- album.ejs

在 album.ejs 里引入公共部分:

<% include partials/header %>

四、文件上传

1. html 写文件上传代码

<form action="/upload" method="POST" enctype="multipart/form-data">
  <div class="form-group">
    <input type="file" name="photo" id="exampleInputFile">
    <p class="help-block">请选择一张照片进行上传</p>
  </div>

  <button class="btn btn-primary" type="submit">上传</button>
</form>

注意事项:

  • 文件上传请求方式一定要是 post;
  • 文件上传在 form 标签里一定要加上 enctype="multipart/form-data";
  • form 标签 action 属性表示请求地址;
  • <button type="submit">上传</button> 按钮只有 type=submit 时,点击按钮才会出发 action 那个请求地址;
  • <input type="file" name="photo" id="exampleInputFile"> 文本框 type="file" 表示这是一个上传文件的文本框,name="photo" 属性必须有,后端通过 name 属性获取上传文件相关内容。

2. nodejs 处理图片上传

文件上传用到第三方包 formidable,使用前要先安装:$ npm install formidable --save

const formidable = require('formidable');
const sd = require('silly-datetime');
const fs = require('fs');

// ......

app.post('/upload', function (req, res) {
    const form = new formidable.IncomingForm();
    form.uploadDir = path.join(process.cwd(), 'public/images');     // 设置上传的文件保存在哪里   
    // 生成随机数,用于对上传的文件进行重命名。因为可能上传多次上传同一个文件。     
    const rand = sd.format(new Date(), 'YYYYMMDDHHmm') + Math.floor((Math.random()*10000));   
  
    form.parse(req, function(err, fields, files) {
      // 不管怎样,先在 public/images 下保存图片
      // /aaaa/bbb/cccc/ddd   这个地方获取的值是没有后缀的
      const oldPath = files.photo.path;
      // /aaa/bbb/ccc/eee.png
      const newPath = path.join(path.dirname(oldPath), rand + path.extname(files.photo.name));

      // 重命名
      fs.renameSync(oldPath, newPath);
  
      res.redirect('/album');
    });
})

五、git

1. 从 github 上拉代码

git clone <url>

2. 往 github 提交代码

  • git add . 把当前目录下所有修改的内容提交到暂存区;
  • git commit -m "备注" 把暂存区里的内容提交到 git 本地仓库;
  • git pull 把 github 上仓库代码同步一次,目的是防止别人改了跟我提交的代码产生冲突;
  • git push 把本地仓库的代码提交到 github。

3. 查看工作区和本地仓库的差异

git status

4. 撤回老版本

[study-node]$ git log --pretty=oneline

b0b2c3f7ebf480a7d845d26cc8ce71698e902aa5 delete node_modules
9ba327f6dcda2e182fff95d94ca23e77d9c159af init commit
693c7fe41943f8df23eef4b8fc4ca541c014f0f2 Update README.md
ede00a6db4a644f9d7f34d2cae6e2463556a01d1 Initial commit

[study-node]$ git reset --hard b0b2c3f

HEAD is now at b0b2c3f delete node_modules
  • git log --pretty=oneline 查看代码备份的记录;
  • git reset --hard <commit-id> 回退到哪一次备份,commit-id 就换成对应的值。

六、supervisor

每次启动 node 程序之后,只要有修改,都要重启才起作用,这很麻烦。使用 supervisor 包之后会自动监控改了哪些文件,并自动重启。使用前先下载这个包 npm install supervisor --save-dev

原本启动 node 程序:node app.js,使用 supervisor 启动 node 程序:supervisor node app.js。每次都敲这么长很麻烦,可以在 package.json 里写个脚本,这样每次输入 npm run dev 时 npm 会自动执行 supervisor node app.js 这个命令。

  "scripts": {
    "dev": "supervisor node app.js",
    "test": "echo \"Error: no test specified\" && exit 1"
  },

七、npm 复习

  • npm init -y 快速创建 package.json 文件;
  • npm install <pgkName> --save 下载包,并记录到 package.json 中的 dependencies 属性里;
  • npm install <pgkName> --save-dev 下载包,并记录到 package.json 中的 devDependencies 属性里;
  • npm run <script> package.json 里有个 script 属性,可以自定义脚本。

八、英文学习

  • import vt 导入
  • repository n. 仓库
  • private adj 私有的
  • public adj 公共的
  • commit vt 提交
  • Initialize 初始化 / 创建
  • album n.相册
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,616评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,020评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,078评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,040评论 1 285
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,154评论 6 385
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,265评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,298评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,072评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,491评论 1 306
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,795评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,970评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,654评论 4 337
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,272评论 3 318
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,985评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,223评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,815评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,852评论 2 351

推荐阅读更多精彩内容

  • 什么是 NPM npm之于Node,就像pip之于Python,gem之于Ruby,composer之于PHP。 ...
    ihoey阅读 6,249评论 2 36
  • 概要 64学时 3.5学分 章节安排 电子商务网站概况 HTML5+CSS3 JavaScript Node 电子...
    阿啊阿吖丁阅读 9,167评论 0 3
  • 个人入门学习用笔记、不过多作为参考依据。如有错误欢迎斧正 目录 简书好像不支持锚点、复制搜索(反正也是写给我自己看...
    kirito_song阅读 2,458评论 1 37
  • Node全栈技术开发介绍 node和js介绍 node服务端开发 node前端vuejs node前端reactj...
    燕京博士阅读 3,646评论 1 19
  • 在晚上,看桥上的灯也变得柔和了起来,白天不可一世的傲娇,终究化为晚上的静谧。脑中的思绪这时也浮显了出来,想说点什么...
    顾心妍阅读 238评论 0 0