node_express 笔记

Express

一个node框架

安装为

npm inatslll --save express

使用为优先创造一个node项目

npm init
entry point: (index.js)
npm install express --save

Express 脚手架(程序生成器)

npm install express-generator -g
// 创建项目myapp
express --view=pug myapp
// 启动
npm install
SET DEBUG=myapp:* & npm start

Express 路由

请求方式

app.METHOD(PATH, HANDLER)
app是一个实例express。
METHOD是一个HTTP请求方法,小写。
PATH 是服务器上的路径。
HANDLER 是路由匹配时执行的功能。

METHOD可以使用的:(请求方式)

checkout
copy
delete
get
head
lock
merge
mkactivity
mkcol
move
m-search
notify
options
patch
post
purge
put
report
search
subscribe
trace
unlock
unsubscribe
var express = require('express');
var app = express();
//  路由请求事例
app.get('/', function (req, res) {
  res.send('Hello World!')
})
app.post('/', function (req, res) {
  res.send('Got a POST request')
})
app.put('/user', function (req, res) {
  res.send('Got a PUT request at /user')
})
app.delete('/user', function (req, res) {
  res.send('Got a DELETE request at /user')
})
app.all('/user', function (req, res) {
  res.send('Got a DELETE request at /user')
})
app.param([name],callback)
//为确定添加参数内容
app.param('id', function (req, res, next, id) {
  console.log('CALLED ONLY ONCE');
  next();
});

app.get('/user/:id', function (req, res, next) {
  console.log('although this matches');
  next();
});

app.get('/user/:id', function (req, res) {
  console.log('and this matches too');
  res.end();
});
//在GET /user/42,输出
CALLED ONLY ONCE
although this matches
and this matches too
// 使用两个参数
app.param(['id', 'page'], function (req, res, next, value) {
  console.log('CALLED ONLY ONCE with', value);
  next();
});

app.get('/user/:id/:page', function (req, res, next) {
  console.log('although this matches');
  next();
});

app.get('/user/:id/:page', function (req, res) {
  console.log('and this matches too');
  res.end();
});
// 使用/user/42/3,输出
CALLED ONLY ONCE with 42
CALLED ONLY ONCE with 3
although this matches
and this matches too

路由拦截: /只有工作号为1337可以进入

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

// customizing the behavior of app.param()
app.param(function(param, option) {
  return function (req, res, next, val) {
    if (val == option) {
      next();
    }
    else {
      next('route');
    }
  }
});

// using the customized app.param()
app.param('id', 1337);

// route to trigger the capture
app.get('/user/:id', function (req, res) {
  res.send('OK');
});

app.listen(3000, function () {
  console.log('Ready');
});

检测id类型

app.param(function(param, validator) {
  return function (req, res, next, val) {
    if (validator(val)) {
      next();
    }
    else {
      next('route');
    }
  }
});

app.param('id', function (candidate) {
  return !isNaN(parseFloat(candidate)) && isFinite(candidate);
});

可以使用正则来检测路由

//captures '1-a_6' but not '543-azser-sder'
router.get('/[0-9]+-[[\\w]]*', function);

//captures '1-a_6' and '543-az(ser"-sder' but not '5-a s'
router.get('/[0-9]+-[[\\S]]*', function);

//captures all (equivalent to '.*')
router.get('[[\\s\\S]]*', function);

//检测 ‘/user-[\\s\\S]+/’
router.get('/user-[\\s\\S]+/', function);

处理中间件错误

app.use(function(err, req, res, next) {
  console.error(err.stack);
  res.status(500).send('Something broke!');
});

匹配路径类型

app.use('/abcd', function (req, res, next) {
  next();
})`/ abcd``/ abd`开头的路径: '/abc?d';`/ abcd``/ abbcd``/ abbbbbcd`开头的路径: '/ab+cd'`/ abcd``/ abxcd``/ abFOOcd``/ abbArcd`开头的路径: '/ab\*cd'`/ ad``/ abcd`开头的路径: '/a(bc)?d'
// 正则判断`/ abc``/ xyz`开头的路径: /\/abc|\/xyz/
// 排列判断`/ abcd``/ xyza``/ lmn``/ pqr`开头的路径: ['/abcd', '/xyza', /\/lmn|\/pqr/]

req–函数的参数

req.app
req.baseUrl --获取路由取首
当发出请求时/greet/jp,req.baseUrl是“/ greet”。当发出请求时/hello/jp,req.baseUrl是“/ hello”

####req.body–提交的键值对数据

使用方法有多种

一,文档提供使用body-parser解决

var app = require('express')();
var bodyParser = require('body-parser');
var multer = require('multer'); // v1.0.5
var upload = multer(); // for parsing multipart/form-data

app.use(bodyParser.json()); // for parsing application/json
app.use(bodyParser.urlencoded({ extended: true })); // for parsing application/x-www-form-urlencoded

app.post('/profile', upload.array(), function (req, res, next) {
  console.log(req.body);
  res.json(req.body);
});

第二种,不使用

var express = require('express');
var app = express();
var multer = require('multer'); // v1.0.5
var upload = multer(); // for parsing multipart/form-data

app.use(express.json()); // for parsing application/json
app.use(express.urlencoded({ extended: true })); // for parsing application/x-www-form-urlencoded

app.post('/profile', upload.array(), function (req, res, next) {
  console.log(req.body);
  res.json(req.body);
});

####req.cookie

使用cookie-parser中间件时,此属性是包含请求发送的cookie的对象。如果请求不包含cookie,则默认为{}
// Cookie: name=tj
req.cookies.name
// => "tj"
req.ip
包含请求的远程IP地址
req.method --请求方式

包含对应于该请求的HTTP方法的字符串: GETPOSTPUT,等

####req.originalUrl --原始请求URL

app.use('/admin', function(req, res, next) {  // GET 'http://www.example.com/admin/new'
  console.log(req.originalUrl); // '/admin/new'
  console.log(req.baseUrl); // '/admin'
  console.log(req.path); // '/new'
  next();
});
req.params --此属性是一个对象 传入值
如果您有路线/user/:name,则“name”属性可用作req.params.name。该对象默认为{}
// GET /user/tj
req.params.name
// => "tj"
// GET /file/javascripts/jquery.js
req.params[0]
// => "javascripts/jquery.js"

####req.path --包含请求URL的路径部分

req.query–路由中每个查询字符串参数的属性(?q=as)
// GET /search?q=tobi+ferret
req.query.q
// => "tobi ferret"

// GET /shoes?order=desc&shoe[color]=blue&shoe[type]=converse
req.query.order
// => "desc"

req.query.shoe.color
// => "blue"

req.query.shoe.type
// => "converse"
req.route–当前匹配的路由,一个字符串
// app
app.get('/user/:id?', function userIdHandler(req, res) {
  console.log(req.route);
  res.send('GET');
});
// 输出
{ path: '/user/:id?',
  stack:
   [ { handle: [Function: userIdHandler],
       name: 'userIdHandler',
       params: undefined,
       path: undefined,
       keys: [],
       regexp: /^\/?$/i,
       method: 'get' } ],
  methods: { get: true } }

####req.secure – 是否建立了TLS连接

'https' == req.protocol;

####req.xhr–判断是否是如果请求的X-Requested-With头字段是“XMLHttpRequest”,jquery请求

req.xhr
// => true
req.accepts(类型)

根据请求的AcceptHTTP头字段检查指定的内容类型是否可接受。该方法返回最佳匹配,或者如果没有指定的内容类型可接受,则返回false(在这种情况下,应用程序应响应406 "Not Acceptable")。

type值可以是单个MIME类型字符串(例如“application / json”),扩展名如“json”,逗号分隔列表或数组。对于列表或数组,该方法返回最佳匹配(如果有)。

// Accept: text/html
req.accepts('html');
// => "html"

// Accept: text/*, application/json
req.accepts('html');
// => "html"
req.accepts('text/html');
// => "text/html"
req.accepts(['json', 'text']);
// => "json"
req.accepts('application/json');
// => "application/json"

// Accept: text/*, application/json
req.accepts('image/png');
req.accepts('png');
// => undefined

// Accept: text/*;q=.5, application/json
req.accepts(['html', 'json']);
// => "json"
req.acceptsCharsets(charset [,…])

根据请求的Accept-CharsetHTTP头字段返回指定字符集的第一个接受的字符集。如果未接受任何指定的字符集,则返回false

req.acceptsEncodings(encoding [,…])

根据请求的Accept-EncodingHTTP头字段,返回指定编码的第一个接受编码。如果未接受任何指定的编码,则返回false

req.acceptsLanguages(lang [,…])

根据请求的Accept-LanguageHTTP头字段返回指定语言的第一个接受语言。如果未接受任何指定的语言,则返回false

req.get() --返回指定的HTTP请求标头字段(不区分大小写的匹配)
req.get('Content-Type');
// => "text/plain"

req.get('content-type');
// => "text/plain"

req.get('Something');
// => undefined

####req.is(类型)

如果传入请求的“Content-Type”HTTP标头字段与type参数指定的MIME类型匹配,则返回匹配的内容类型。如果请求没有正文,则返回nullfalse否则返回。

// With Content-Type: text/html; charset=utf-8
req.is('html');       // => 'html'
req.is('text/html');  // => 'text/html'
req.is('text/*');     // => 'text/*'

// When Content-Type is application/json
req.is('json');              // => 'json'
req.is('application/json');  // => 'application/json'
req.is('application/*');     // => 'application/*'

req.is('html');
// => false
req.range(size [,options])

Range 头解析器。

size参数是资源的最大尺寸。

所述options参数是一个对象,可以具有以下性质。

combine :指定是否应组合重叠和相邻范围,默认为false。何时true,范围将被组合并返回,就好像它们在标题中指定了那样

将返回范围数组或指示错误解析的负数。

  • -2 表示格式错误的标题字符串

  • -1 表示不可满足的范围

    // parse header from request
    var range = req.range(1000)
    
    // the type of the range
    if (range.type === 'bytes') {
      // the ranges
      range.forEach(function (r) {
        // do something with r.start and r.end
      })
    }
    

res–函数的参数

res.headersSent —布尔属性,指示应用程序是否为响应发送了HTTP标头
app.get('/', function (req, res) {
  console.log(res.headersSent); // false
  res.send('OK');
  console.log(res.headersSent); // true
});

####res.append(field [,value])追加请求头

res.append('Link', ['<http://localhost/>', '<http://localhost:3000/>']);
res.append('Set-Cookie', 'foo=bar; Path=/; HttpOnly');
res.append('Warning', '199 Miscellaneous warning');
res.cookie(name,值)–json格式
属性类型描述
domainCookie的域名。默认为应用程序的域名。
encode功能用于cookie值编码的同步函数。默认为encodeURIComponent
expires日期GMT中cookie的到期日。如果未指定或设置为0,则创建会话cookie。
httpOnly布尔标记cookie只能由Web服务器访问。
maxAge方便的选项,用于设置相对于当前时间的到期时间(以毫秒为单位)。
pathCookie的路径。默认为“/”。
secure布尔将cookie标记为仅与HTTPS一起使用。
signed布尔指示cookie是否应该签名。
sameSite布尔值或字符串“SameSite” Set-Cookie属性的值。更多信息,访问https://tools.ietf.org/html/draft-ietf-httpbis-cookie-same-site-00#section-4.1.1

####res.download(path [,filename][,options] [,fn])–下载

将文件path作为“附件” 传输。通常,浏览器会提示用户下载。默认情况下,Content-Disposition标题“filename =”参数是path(这通常出现在浏览器对话框中)。使用filename参数覆盖此默认值。

发生错误或传输完成时,该方法将调用可选的回调函数fn。此方法使用res.sendFile()来传输文件。

可选options参数传递给基础res.sendFile() 调用,并采用完全相同的参数

res.download('/report-12345.pdf');

res.download('/report-12345.pdf', 'report.pdf');

res.download('/report-12345.pdf', 'report.pdf', function(err){
  if (err) {
    // Handle error, but keep in mind the response may be partially-sent
    // so check res.headersSent
  } else {
    // decrement a download credit, etc.
  }
});

####res.end()–结束响应

用于在没有任何数据的情况下快速结束响应。如果需要响应数据,请使用res.send()和res.json()等方法。

res.end();
res.status(404).end();
res.format(对象)

Accept对请求对象上的HTTP标头执行内容协商(如果存在)。它使用req.accepts()根据质量值排序的可接受类型为请求选择处理程序。如果未指定标头,则调用第一个回调。如果未找到匹配项,则服务器将以406“Not Acceptable”响应,或调用default回调。

Content-Type当选择一个回调响应首部设置。但是,您可以使用诸如res.set()或之类的方法在回调中更改此值res.type()

{ "message": "hey" }Acceptheader字段设置为“application / json”或“* / json” 时,以下示例将响应(但如果它是“* / *”,则响应将为“hey”)。

res.format({
  'text/plain': function(){
    res.send('hey');
  },

  'text/html': function(){
    res.send('<p>hey</p>');
  },

  'application/json': function(){
    res.send({ message: 'hey' });
  },

  'default': function() {
    // log the request and respond with 406
    res.status(406).send('Not Acceptable');
  }
});

除了规范化的MIME类型之外,您还可以使用映射到这些类型的扩展名来实现稍微冗长的实现

res.format({
  text: function(){
    res.send('hey');
  },

  html: function(){
    res.send('<p>hey</p>');
  },

  json: function(){
    res.send({ message: 'hey' });
  }
});
res.get(请求头)-- 获取请求头
res.get('Content-Type');
// => "text/plain"
res.json(对象)–发送JSON数据
res.status(500) --设置状态码
res.json(null);
res.json({ user: 'tobi' });
res.status(500).json({ error: 'message' });
res.jsonp(对象) --jsonp回调
res.jsonp(null);
// => callback(null)

res.jsonp({ user: 'tobi' });
// => callback({ "user": "tobi" })

res.status(500).jsonp({ error: 'message' });
// => callback({ "error": "message" })

默认情况下,JSONP回调名称很简单callback。使用jsonp回调名称设置覆盖它 。

以下是使用相同代码的JSONP响应的一些示例:

// ?callback=foo
res.jsonp({ user: 'tobi' });
// => foo({ "user": "tobi" })

app.set('jsonp callback name', 'cb');

// ?cb=foo
res.status(500).jsonp({ error: 'message' });
// => foo({ "error": "message" })

####res.links(链接)–将links提供的as作为参数的属性加入,以填充响应的 LinkHTTP头字段

res.links({
  next: 'http://api.example.com/users?page=2',
  last: 'http://api.example.com/users?page=5'
});

得到以下结果:

Link: <http://api.example.com/users?page=2>; rel="next",
      <http://api.example.com/users?page=5>; rel="last"

####res.location(路径)

将响应LocationHTTP标头设置为指定的path参数。

res.location('/foo/bar');
res.location('http://example.com');
res.location('back');

####res.redirect([status,] path) --重新定向

重定向到从指定的URL派生的URL path,具有指定的statusHTTP状态代码对应的正整数。如果未指定,则status默认为“302”找到“。

res.redirect('/foo/bar');
res.redirect('http://example.com');
res.redirect(301, 'http://example.com');
res.redirect('../login');
res.sendStatus(的StatusCode)

将响应HTTP状态代码设置为statusCode并将其字符串表示形式发送为响应正文。

res.sendStatus(200); // equivalent to res.status(200).send('OK')
res.sendStatus(403); // equivalent to res.status(403).send('Forbidden')
res.sendStatus(404); // equivalent to res.status(404).send('Not Found')
res.sendStatus(500); // equivalent to res.status(500).send('Internal Server Error')

如果指定了不受支持的状态代码,则HTTP状态仍设置为,statusCode并且代码的字符串版本将作为响应正文发送。

res.sendStatus(2000); // equivalent to res.status(2000).send('2000'
res.set(field [,value]) --设置请求头
res.set('Content-Type', 'text/plain');

res.set({
  'Content-Type': 'text/plain',
  'Content-Length': '123',
  'ETag': '12345'
})

res.type(类型)

Content-TypeHTTP标头设置为由mime.lookup()为指定的MIME类型确定的MIME类型 type。如果type包含“/”字符,则将其设置Content-Typetype

res.type('.html');              // => 'text/html'
res.type('html');               // => 'text/html'
res.type('json');               // => 'application/json'
res.type('application/json');   // => 'application/json'
res.type('png');                // => image/png:

多层回调

var cb0 = function (req, res, next) {
  console.log('CB0')
  next()
}

var cb1 = function (req, res, next) {
  console.log('CB1')
  next()
}

var cb2 = function (req, res) {
  res.send('Hello from C!')
}

app.get('/example/c', [cb0, cb1, cb2])

独立函数和函数数组的组合可以处理路径。例如:

var cb0 = function (req, res, next) {
  console.log('CB0')
  next()
}

var cb1 = function (req, res, next) {
  console.log('CB1')
  next()
}

app.get('/example/d', [cb0, cb1], function (req, res, next) {
  console.log('the response will be sent by the next function ...')
  next()
}, function (req, res) {
  res.send('Hello from D!')
})

Express托管静态文件

express.static(root,[option])
root参数指定为静态资产提供服务的根目录
// 通过如下代码就可以将 public 目录下的图片、CSS 文件、JavaScript 文件对外开放访问了可以开放多个
app.use(express.static('public'))
// 使用/stad来访问,例如http://localhost:3000/static/images/kitten.jpg
app.use('/stad',express.static('public'))

数据库集成

Cassandra

npm install cassandra-driver
var cassandra = require('cassandra-driver')
var client = new cassandra.Client({ contactPoints: ['localhost'] })

client.execute('select key from system.local', function (err, result) {
  if (err) throw err
  console.log(result.rows[0])
})

Couchbase

npm install couchbase
var couchbase = require('couchbase')
var bucket = (new couchbase.Cluster('http://localhost:8091')).openBucket('bucketName')

// add a document to a bucket
bucket.insert('document-key', { name: 'Matt', shoeSize: 13 }, function (err, result) {
  if (err) {
    console.log(err)
  } else {
    console.log(result)
  }
})

// get all documents with shoe size 13
var n1ql = 'SELECT d.* FROM `bucketName` d WHERE shoeSize = $1'
var query = N1qlQuery.fromString(n1ql)
bucket.query(query, [13], function (err, result) {
  if (err) {
    console.log(err)
  } else {
    console.log(result)
  }
})

CouchDB

npm install nano
var nano = require('nano')('http://localhost:5984')
nano.db.create('books')
var books = nano.db.use('books')

// Insert a book document in the books database
books.insert({ name: 'The Art of war' }, null, function (err, body) {
  if (err) {
    console.log(err)
  } else {
    console.log(body)
  }
})

// Get a list of all books
books.list(function (err, body) {
  if (err) {
    console.log(err)
  } else {
    console.log(body.rows)
  }
})

###LevelDB

npm install level levelup leveldown
var levelup = require('levelup')
var db = levelup('./mydb')

db.put('name', 'LevelUP', function (err) {
  if (err) return console.log('Ooops!', err)

  db.get('name', function (err, value) {
    if (err) return console.log('Ooops!', err)

    console.log('name=' + value)
  })
})

MySQL

npm install mysql
var mysql = require('mysql')
var connection = mysql.createConnection({
  host     : 'localhost',
  user     : 'dbuser',
  password : 's3kreee7',
  database : 'my_db'
});

connection.connect()

connection.query('SELECT 1 + 1 AS solution', function (err, rows, fields) {
  if (err) throw err

  console.log('The solution is: ', rows[0].solution)
})

connection.end()

MongoDB

npm install mongodb

MongoDB(2.*)

var MongoClient = require('mongodb').MongoClient

MongoClient.connect('mongodb://localhost:27017/animals', function (err, db) {
  if (err) throw err

  db.collection('mammals').find().toArray(function (err, result) {
    if (err) throw err

    console.log(result)
  })
})

MongoDB(3.*)

var MongoClient = require('mongodb').MongoClient

MongoClient.connect('mongodb://localhost:27017/animals', function (err, client) {
  if (err) throw err

  var db = client.db('animals')
  
  db.collection('mammals').find().toArray(function (err, result) {
    if (err) throw err

    console.log(result)
  })
})

Neo4j

npm install apoc
var apoc = require('apoc')

apoc.query('match (n) return n').exec().then(
  function (response) {
    console.log(response)
  },
  function (fail) {
    console.log(fail)
  }
)

Oracle

npm install oracledb
const oracledb = require('oracledb');
const config = {
  user: '<your db user>',                // Update me
  password: '<your db password>',        // Update me
  connectString: 'localhost:1521/orcl'   // Update me
};

async function getEmployee(empId) {
  let conn;

  try {
    conn = await oracledb.getConnection(config);

    const result = await conn.execute(
      'select * from employees where employee_id = :id',
      [empId]
    );

    console.log(result.rows[0]);
  } catch (err) {
    console.log('Ouch!', err);
  } finally {
    if (conn) { // conn assignment worked, need to close
       await conn.close();
    }
  }
}

getEmployee(101);

PostgreSQL

npm install pg-promise
var pgp = require('pg-promise')(/*options*/)
var db = pgp('postgres://username:password@host:port/database')

db.one('SELECT $1 AS value', 123)
  .then(function (data) {
    console.log('DATA:', data.value)
  })
  .catch(function (error) {
    console.log('ERROR:', error)
  })

Redis

npm install redis
var redis = require('redis')
var client = redis.createClient()

client.on('error', function (err) {
  console.log('Error ' + err)
})

client.set('string key', 'string val', redis.print)
client.hset('hash key', 'hashtest 1', 'some value', redis.print)
client.hset(['hash key', 'hashtest 2', 'some other value'], redis.print)

client.hkeys('hash key', function (err, replies) {
  console.log(replies.length + ' replies:')

  replies.forEach(function (reply, i) {
    console.log('    ' + i + ': ' + reply)
  })

  client.quit()
})

SQL Server

npm install tedious
var Connection = require('tedious').Connection;
var Request = require('tedious').Request;

var config = {
  userName: 'your_username', // update me
  password: 'your_password', // update me
  server: 'localhost'
}

var connection = new Connection(config);

connection.on('connect', function(err) {
  if (err) {
    console.log(err);
  } else {
    executeStatement();
  }
});

function executeStatement() {
  request = new Request("select 123, 'hello world'", function(err, rowCount) {
    if (err) {
      console.log(err);
    } else {
      console.log(rowCount + ' rows');
    }
    connection.close();
  });

  request.on('row', function(columns) {
    columns.forEach(function(column) {
      if (column.value === null) {
        console.log('NULL');
      } else {
        console.log(column.value);
      }
    });
  });

  connection.execSql(request);
}

SQLite

npm install sqlite3
var sqlite3 = require('sqlite3').verbose()
var db = new sqlite3.Database(':memory:')

db.serialize(function () {
  db.run('CREATE TABLE lorem (info TEXT)')
  var stmt = db.prepare('INSERT INTO lorem VALUES (?)')

  for (var i = 0; i < 10; i++) {
    stmt.run('Ipsum ' + i)
  }

  stmt.finalize()

  db.each('SELECT rowid AS id, info FROM lorem', function (err, row) {
    console.log(row.id + ': ' + row.info)
  })
})

db.close()

ElasticSearch

npm install elasticsearch
var elasticsearch = require('elasticsearch')
var client = elasticsearch.Client({
  host: 'localhost:9200'
})

client.search({
  index: 'books',
  type: 'book',
  body: {
    query: {
      multi_match: {
        query: 'express js',
        fields: ['title', 'description']
      }
    }
  }
}).then(function (response) {
  var hits = response.hits.hits
}, function (error) {
  console.trace(error.message)
})
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值