Node.js——Express详解(一)

Express详解

1、Express概述

1.1、安装Express

Express是一个可以在Node.js中使用的MVC框架,该框架现在已经得到了广泛利用,可以使用该框架中的各种特性更为方便、快速地开发出一个完整的Web应用程序。

可以使用npm包安装工具来安装Express开发包,命令如下所示。

shell 复制代码
npm install -g express@4

1.2、简单示例

在安装Express开发包之后,首先要在我们的应用程序主模块文件中引用express模块并创建一个应用程序,代码如下所示。

js 复制代码
const express = require('express');
let app = express();

在应用程序实例对象创建之后,可以使用应用程序实例对象的listen方法指定服务器所要监听的地址(可以为一个IP地址,也可以为一个主机名)及端口,该方法的使用方式与第8章中HTTP服务器的listen方法完全相同,代码示例如下所示。

js 复制代码
app.listen(1337, "127.0.0.1");

在创建应用程序实例对象之后,可以根据客户端请求所使用的路径返回不同的服务器端响应结果。这些响应结果可以简单如一个"你好。​"字符串,也可以复杂如一个对数据库中数据进行各种处理并渲染的HTML 5页面。

在Express中,可以使用应用程序实例对象的get方法接收客户端提供的GET请求并返回服务器端响应结果,get方法的最简单的使用方式如下所示(不使用中间件,稍后介绍中间件的使用方法)​。

js 复制代码
app.get(path,callback)
  • path:一个字符串,用于指定针对客户端提交时使用的哪一个路径进行处理,如果路径参数值为"/",则代表对网站根目录的请求
  • callback:一个回调函数,用于指定当接收到客户端请求时所需执行的处理,该回调函数的指定方法如下所示。
js 复制代码
function (request,response) {
    // 回调函数代码略
}
  • request:一个http.IncomingMessage对象,代表一个客户端请求
  • response:一个http.ServerResponse对象,代表一个服务器端响应对象
1.2.1、创建服务

示例:创建一个Express应用程序示例对象,指定HTTP服务器(在使用应用程序实例对象的listen方法时被隐式创建)监听本地主机名localhost,端口号为1337。然后监听客户端对网站根目录下"index.html"路径的GET提交请求,当接收到客户端请求时向客户端返回一个页面,页面中只显示一个"你好"字符串。

js 复制代码
const express = require('express');
const http = require('http');
let app = express();
app.get('/index.html',(req, res)=>{
    res.writeHead(200, {'Content-Type': 'text/html'});
    res.write('<head><meta charset="utf-8"/></head>');
    res.end('你好\n');
});
app.listen(1337, "127.0.0.1");

在使用应用程序实例对象的listen方法时,一个HTTP服务器被隐式创建。可以使用Node.js中的http模块或https模块中的createServer方法显式创建一个HTTP服务器或HTTPS服务器,代码如下所示。

js 复制代码
// 创建HTTP服务器并指定服务器监听地址及端口号
http.createServer(app).listen(1337);
// 创建HTTPS服务器并指定服务器监听地址及端口号
https.createServer(options,app).listen(443);
1.2.2、send()发送响应

在Express框架中,为http.ServerResponse对象提供一个send方法,该方法用于发送一个服务器端响应结果。在使用该方法时,不需要使用http.ServerResponse对象的writeHead方法或setHeader方法来发送响应头信息,send方法将根据服务器端响应结果自动计算响应头信息。在使用send方法时,也不需要使用http.ServerResponse对象的end方法来显式结束响应内容的发送,该方法已被封装在send方法内部。

js 复制代码
const express = require('express');
const http = require('http');
let app = express();
app.get('/index.html',(req, res)=>{
    res.send('你好');
});
app.listen(1337, "127.0.0.1");

1.3、app.set()配置服务

常用内置参数:

  1. port(约定俗成)
js 复制代码
app.set('port', 3000)
js 复制代码
app.listen(app.get('port'))
  1. env(非常重要)
js 复制代码
app.set('env', 'production')
js 复制代码
//等价于
NODE_ENV=production
  1. view engine(模板引擎)
js 复制代码
app.set('view engine', 'ejs')
js 复制代码
app.set('views', './views')
  1. views(模板目录)
js 复制代码
app.set('views', path.join(__dirname, 'views'))
  1. case sensitive routing
js 复制代码
app.set('case sensitive routing', true)
复制代码
/user  ≠  /User
  1. strict routing
js 复制代码
app.set('strict routing', true)
复制代码
/user   ≠  /user/

查看已设置的参数:

js 复制代码
app.get('port')       // 3000
app.get('env')        // production
app.get('view engine') // ejs

自定义参数:

js 复制代码
app.set('dbHost', 'localhost')
app.set('dbPort', 27017)
js 复制代码
console.log(app.get('dbHost'))

2、设置路由

路由是Express框架中的一个重要概念,在Express框架中使用路由来根据客户端请求所提交的不同URL地址返回不同的服务器端响应结果。

在路由中,可以使用"​:​"+参数名的方式来指定一个参数。

2.1、路由中使用参数

示例:指定针对"/index.html/:id/:name"路由返回服务器端响应结果,在这个路由中,指定了id参数与name参数,当接收到客户端提交的URL请求后,将客户端指定的id参数值与name参数值作为服务器端响应结果返回给客户端。

js 复制代码
const express = require('express');
const http = require('http');
let app = express();
app.get('/index.html/:id/:name',(req, res)=>{
    res.setDefaultEncoding = 'utf8';
    let str = "";
    for (key in req.params){
        if(str != "") {
            str += "<br/>";
        }
        str += "参数名:" + key;
        str += String.fromCharCode(9) + "参数值:" + req.params[key];
    }
    res.send(str);
});
app.listen(1337, "127.0.0.1");

运行该文件,接着在浏览器的地址栏中输入"http://localhost:1337/index.html/1101/陆凌牛"地址,此时,浏览器中显示客户端指定的id参数值与name参数值,如图所示。

2.2、路由中使用正则表达式

示例:指定针对"index.html/:id?/:name?"路由返回服务器端响应结果,在这个路由中,指定了id参数与name参数,但通过正则表达式的使用允许客户端不指定id参数值或name参数值。在接收到客户端提交的URL请求后,将客户端指定的参数值作为服务器端响应结果返回给客户端。

js 复制代码
const express = require('express');
const http = require('http');
let app = express();
app.get('/index.html/:id?/:name?',(req, res)=>{
    let str = "";
    if(req.params.id) {
        str += "ID参数值:" + req.params.id;
    }
    if(str != "") {
        str += "<br/>";
    }
    if(req.params.name) {
        str += "name参数值:" + req.params.name;
    }
    res.send(str);
});
app.listen(1337, "127.0.0.1");

运行该文件,接着在浏览器的地址栏中输入"http://localhost:1337/index.html"地址,此时,浏览器中显示空白,如图所示。

在浏览器的地址栏中输入"http://localhost:1337/index.html/1101"地址,浏览器中显示客户端指定的id参数值,如图所示。

在浏览器的地址栏中输入"http://localhost:1337/index.html/1101/陆凌牛"地址,浏览器中显示客户端指定的id参数值与name参数值,如图所示。

在路由中可以使用通配符。

可以使用一个正则表达式来指定路由。将代码清单14-1中的路由修改为/\/(\d+)/,代码如下所示。

js 复制代码
app.get(/\/(\d+)/,function (req, res) {
    // 回调函数代码略
});

该正则表达式表示客户端指定的目标路径必须以数字开头。在浏览器的地址栏中输入"http://localhost:1337/1"地址或"http://localhost:1337/12"地址,浏览器窗口中显示"你好"文字。

由于正则表达式//(\d+)/中没有使用结束符"$"​,因此可以在客户端指定的目标路径中书写数字后书写字母或其他符号。在浏览器的地址栏中输入"http://localhost:1337/1d"地址,浏览器窗口中显示"你好"文字。

可以在路由中通过正则表达式的使用来限定参数值的类型。

示例:将代码清单所示代码中的路由修改为"/index.html/:id(\d+)/:name"​,以限定id参数值必须为数值。在浏览器的地址栏中输入"http://localhost:1337/index.html/a/陆凌牛"地址,浏览器窗口中显示该URL地址未被处理。在浏览器的地址栏中输入"http://localhost:1337/index.html/1101/陆凌牛"地址,浏览器中显示客户端指定的id参数值与name参数值,同图所示。

js 复制代码
const express = require('express');
const http = require('http');
let app = express();
app.get('/index.html/:id(\\d+)/:name',(req, res)=>{
    res.setDefaultEncoding = 'utf8';
    let str = "";
    if(req.params.id) {
        str += "ID参数值:" + req.params.id;
    }
    if(str != "") {
        str += "<br/>";
    }
    if(req.params.name) {
        str += "name参数值:" + req.params.name;
    }
    res.send(str);
});
app.listen(1337, "127.0.0.1");

2.3、next()调用多个相同路由

在Express框架中,可以使用多个应用程序实例对象的get方法并在这些get方法中使用相同的路由。可以在一个get方法中使用Express框架中提供的next方法调用下一个使用相同路由的get方法。如果要在一个get方法中使用next方法,必须在该方法所使用的回调函数中使用next参数值,使回调函数的指定方法如下所示。

js 复制代码
function (req,res,next) {
    // 回调函数代码略
}

示例:在第一个get方法中判断客户端请求目标URL地址中所指定的id参数值是否大于10,如果id参数值小于或等于10,向客户端返回"id参数值必须大于10。​"字符串,否则调用下一个使用相同路由的get方法向客户端返回"你好。​"字符串。

js 复制代码
const express = require('express');
const http = require('http');
let app = express();
app.get('/index.html/:id(\\d+)',(req, res, next)=>{
    if(req.params.id > 10) {
        next();
    } else {
        res.send('id参数值必须大于10。');
    }
});
app.get('/index.html/:id(\\d+)',(req, res)=>{
    res.send('你好。');
});
app.listen(1337, "127.0.0.1");

运行该文件,接着在浏览器的地址栏中输入"http://localhost:1337/index.html/10"地址,浏览器中显示"id参数值必须大于10。​"字符串,如图所示。

在浏览器的地址栏中输入"http://localhost:1337/index.html/11"地址,浏览器中显示"你好。​"字符串,如图所示。

3、各种提交数据或请求数据的方法

3.1、post方法接收客户端提交的POST请求

在Express中,可以使用应用程序实例对象的post方法接收客户端提交的POST请求并返回服务器端响应结果,post方法最简单的使用方式如下所示(不使用中间件,稍后介绍中间件的使用方法)​。

js 复制代码
app.post(path,callback)

在不使用中间件时,post方法中可以有两个参数,这两个参数的含义与指定方法与应用程序实例对象的get方法中所使用的path参数与callback参数的含义与指定方法完全相同。

示例:使用应用程序实例对象的get方法监听客户端向服务器端index.html页面发出的GET请求,当接收到该请求时,将应用程序根目录下的index.html文件中的内容作为服务器端响应结果返回给客户端。该页面中显示两个文本框,供用户输入用户姓与用户名。在该页面返回给客户端后,监听客户端向服务器端index.html页面发出的POST请求,在接收到客户端提交数据后,将客户端提交的用户姓与用户名保存在服务器端MySQL数据库中,在数据保存成功后,将"在服务器端MySQL数据库中插入数据成功。​"字符串作为服务器端响应结果返回给客户端。

js 复制代码
const express = require('express');
const fs = require('fs');
const querystring = require('querystring');
const app = express();
let mysql = require('mysql');
let pool = mysql.createPool({
    host     : 'localhost',
    port     : 3306,
    database : 'test',
    user     : 'root',
    password : '123456',
});
app.get('/index.html',(req,res)=>{
    res.writeHead(200, {'Content-Type': 'text/html'});
    res.write('<head><meta charset="utf-8"/><title>使用post方法向服务器端提'
     + '交数据</title></head>');
    let file = fs.createReadStream('index.html');
    file.pipe(res);
});
app.post('/index.html',(req,res)=>{
    req.on('data',(data)=>{
        let obj = querystring.parse(data.toString());
        pool.getConnection((err, connection)=>{
            if(err) {
                res.send('与MySQL数据库建立连接失败。');
            } else{
                let str;
                connection.query('INSERT INTO users SET ?',
                    {username:obj.username,firstname:obj.firstname},
                    (err,result)=>{
                        if(err) {
                            str = '在服务器端MySQL数据库中插入数据失败。';
                        } else {
                            str = '在服务器端MySQL数据库中插入数据成功。';
                        }   
                    connection.release();
                    res.send(str);
                });
            }
        });
    });
});
app.listen(1337, "127.0.0.1");
html 复制代码
<form id="form1" action="index.html" method="post">
姓:<input type="text" name="firstname" value="陆"><br/>
名:<input type="text" name="username" value="凌牛"><br/>
<input type="submit" value="提交"/>
</form>

运行该文件,接着在浏览器的地址栏中输入"http://localhost:1337/index.html"地址,浏览器中显示应用程序根目录下的index.html页面中的内容,如图所示。

在Express中,支持使用http.ServerResponse对象的sendFile方法向客户端发送一个文件,在该方法中可以使用一个字符串型参数,参数值为被发送文件的完整路径及文件名。

修改本示例中应用程序实例对象的get方法中的代码如下所示。

js 复制代码
app.get('/index.html',function (req,res) {
    res.sendfile(__dirname+'/index.html');;
});

修改应用程序根目录下的index.html文件中的内容如下所示。

html 复制代码
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8"/>
<title>使用post方法向服务器端提交数据</title>
</head>
<body>
<form id="form1" action="index.html" method="post">
姓:<input type="text" name="firstname" value="陆"><br/>
名:<input type="text" name="username" value="凌牛"><br/>
<input type="submit" value="提交"/>
</form>
</body>
</html>

3.2、put方法接收客户端提交的PUT请求

在Express中,可以使用应用程序实例对象的put方法接收客户端提交的PUT请求并返回服务器端响应结果,put方法最简单的使用方式如下所示(不使用中间件,稍后介绍中间件的使用方法)​。

js 复制代码
app.put(path,callback)

在不使用中间件时,put方法中有两个参数,这两个参数的含义与指定方法与应用程序实例对象的post方法中所使用的path参数与callback参数的含义与指定方法完全相同。

示例:使用应用程序实例对象的get方法监听客户端向服务器端index.html页面发出的GET请求,当接收到该请求时将应用程序根目录下的index.html文件中的内容作为服务器端响应结果返回给客户端。该页面中显示两个文本框与一个提交按钮,其中两个按钮分别供用户输入用户姓与用户名。当用户单击"提交"按钮后,调用HTML 5中的XMLHttpRequest对象以AJAX方式向服务器端发送PUT请求,并在请求中将用户输入数据以JSON字符串的格式进行发送。在服务器端脚本中监听客户端向服务器端index.html页面发出的PUT请求,在接收到客户端提交数据后,将客户端提交的数据转换为一个JSON对象,然后将该JSON对象中保存的用户姓与用户名存储到服务器端MySQL数据库中。在数据保存成功后,将"在服务器端MySQL数据库中插入数据成功。​"字符串作为服务器端响应结果返回给客户端。在客户端接收到服务器端返回的响应数据后,将服务器端响应数据显示在页面中。

js 复制代码
const express = require('express');
const fs = require('fs');
const app = express();
const mysql = require('mysql');
let pool = mysql.createPool({
    host     : 'localhost',
    port     : 3306,
    database : 'test',
    user     : 'root',
    password : '123456',
});
app.get('/index.html',(req,res)=>{
    res.sendfile(__dirname + '/index.html');
});
app.put('/index.html',(req,res)=>{
    req.on('data',(data)=>{
        let obj = JSON.parse(data.toString());
        pool.getConnection((err, connection)=>{
            if(err) {
                res.send('与MySQL数据库建立连接失败。');
            } else {
                let str;
                connection.query('INSERT INTO users SET ?',
                    {username:obj.username,firstname:obj.firstname},
                    (err,result)=>{
                        if(err) {
                            str = '在服务器端MySQL数据库中插入数据失败。';
                        } else {
                            str = '在服务器端MySQL数据库中插入数据成功。';
                        }   
                    connection.release();
                    res.send(str);
                });
            }
        });
    });
});
app.listen(1337, "127.0.0.1");
html 复制代码
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8"/>
<title>使用PUT方法向服务器端提交数据</title>
<script>
function submitData() {
    var obj={
        firstname:document.getElementById("txtFirstName").value,
        username:document.getElementById("txtUserName").value
    };
    var xhr = new XMLHttpRequest();
    xhr.open('put','index.html',true);
    xhr.onload = function(e) {
        if (this.status == 200) {
            document.getElementById("result").innerHTML=this.response;
            }
        };
        xhr.send(JSON.stringify(obj));
}
</script>
</head>
<body>
<form id="form1">
姓:<input type="text" id="txtFirstName" name="firstname" value="陆"><br/>
名:<input type="text" id="txtUserName" name="username" value="凌牛"><br/>
<input type="button" value="提交" onclick="submitData();"/>
</form>
<output id="result" ></output>
</body>
</html>

运行该文件,接着在浏览器的地址栏中输入"http://localhost:1337/index.html"地址,此时,浏览器中显示应用程序根目录下的index.html页面中的内容,显示结果同图所示。

3.3、delete方法接收客户端提交的DELETE请求

在Express中,可以使用应用程序实例对象的delete方法接收客户端提交的DELETE请求并返回服务器端响应结果。delete方法最简单的使用方式如下所示(不使用中间件,稍后介绍中间件的使用方法)​。

在不使用中间件时,delete方法有两个参数,这两个参数的含义与指定方法与应用程序实例对象的post方法中所使用的path参数与callback参数的含义与指定方法完全相同。

示例:使用应用程序实例对象的get方法监听客户端向服务器端index.html页面发出的GET请求,当接收到该请求时将应用程序根目录下的index.html文件中的内容作为服务器端响应结果返回给客户端。该页面中显示两个文本框与一个提交按钮,其中两个按钮分别供用户输入用户姓与用户名。在用户单击"提交"按钮后,调用HTML 5中的XMLHttpRequest对象以AJAX方式向服务器端发送DELETE请求,并在请求中将用户输入数据以JSON字符串的格式进行发送。在服务器端脚本中监听客户端向服务器端index.html页面发出的DELETE请求,在接收到客户端提交数据后,将客户端提交的数据转换为一个JSON对象,然后将从服务器端MySQL数据库中删除firstname字段值等于JSON对象中保存的用户姓、username字段值等于JSON对象中保存的用户名的数据。在成功删除数据后,将"在服务器端MySQL数据库中删除数据成功。​"字符串作为服务器端响应结果返回给客户端。在客户端接收到服务器端返回的响应数据后,将服务器端响应数据显示在页面中。

js 复制代码
const express = require('express');
const fs = require('fs');
const app = express();
const mysql = require('mysql');
let pool = mysql.createPool({
    host     : 'localhost',
    port     : 3306,
    database : 'test',
    user     : 'root',
    password : '123456',
});
app.get('/index.html',(req,res)=>{
    res.sendfile(__dirname + '/index.html');
});
app.delete('/index.html', (req,res)=>{
    req.on('data',(data)=>{
        let obj = JSON.parse(data.toString());
        pool.getConnection((err, connection)=>{
            if(err) {
                res.send('与MySQL数据库建立连接失败。');
            } else {
                let str;
                connection.query('DELETE FROM users where username=? and'
                    + 'firstname=?',[obj.username,obj.firstname],
                    (err,result)=>{
                        if(err) {
                            str='在服务器端MySQL数据库中删除数据失败。';
                        } else {
                            str='在服务器端MySQL数据库中删除数据成功。';
                        }   
                    connection.release();
                    res.send(str);
                });
            }
        });
    });
});
app.listen(1337, "127.0.0.1");

应用程序根目录下的index.html文件中的内容基本上同代码所示,只是将标题修改为"使用DELETE方法向服务器端提交数据"​,同时将XMLHttpRequest对象的put方法修改为delete方法,代码如下所示。

js 复制代码
// xhr.open('put','index.html',true);
删除原语句
xhr.open('delete','index.html',true);

在页面文本框中输入用户姓与用户名后单击"提交"按钮,服务器端MySQL数据库中firstname字段值等于JSON对象中保存的用户姓、username字段值等于JSON对象中保存的用户名的数据被删除,在成功删除数据后页面中显示"在服务器端MySQL数据库中删除数据成功。​"字符串。

3.4、all方法接收客户端提交的各种请求

客户端提交的各种请求(包括GET请求、POST请求、PUT请求与DELETE请求)并返回服务器端响应结果,all方法最简单的使用方式如下所示(不使用中间件,稍后介绍中间件的使用方法)​。

在不使用中间件时,all方法有两个参数,这两个参数的含义与指定方法与应用程序实例对象的post方法中所使用的path参数与callback参数的含义与指定方法完全相同。

示例:使用一个all方法接收客户端提交的各种请求,使用一个get方法接收客户端提交的GET请求,使用一个post方法接收客户端提交的POST请求。在接收到客户端请求时,在all方法中获取客户端提交的目标URL地址中使用的id参数,然后在MySQL数据库的users表中判断是否存在id字段值等于id参数值的数据,如果存在,则使用next方法调用get方法(当客户端提交GET请求时)或post方法(当客户端提交POST请求时)​。在get方法中将应用程序根目录下的index.html文件中的内容作为服务器端响应结果返回给客户端。该页面中显示两个文本框与一个提交按钮,其中两个按钮分别供用户输入用户姓与用户名。在用户单击"提交"按钮后,调用HTML 5中的XMLHttpRequest对象以AJAX方式向服务器端发送POST请求,并在请求中将用户输入数据以JSON字符串的格式进行发送。在post方法中将客户端提交的数据转换为一个JSON对象,然后将该JSON对象中保存的数据更新到users表中,更新条件为id字段值等于客户端请求的URL字符串中的id参数值。在数据更新成功后,将"在服务器端MySQL数据库中更新数据成功。​"字符串作为服务器端响应结果返回给客户端。在客户端接收到服务器端返回的响应数据后,将服务器端响应数据显示在页面中。

js 复制代码
const express = require('express');
const fs = require('fs');
const app = express();
const mysql = require('mysql');
let pool = mysql.createPool({
    host     : 'localhost',
    port     : 3306,
    database : 'test',
    user     : 'root',
    password : '123456',
});
app.all('/index.html/:id(\\d+)',(req, res, next)=>{
    pool.getConnection((err, connection)=>{
        if(err) {
            res.send('与MySQL数据库建立连接失败。');
        } else {
            connection.query('SELECT count(1) count FROM users where '
                + 'id=?',[req.params.id],function(err,result){
                    if(err) {
                        res.send('在服务器端MySQL数据库中查询数据失败。');
                        connection.release();
                    } else{
                        connection.release();
                        if(result[0].count>0) {
                            next();
                        } else {
                            res.send('您没有操作数据表的权限。');
                        }
                    }
            });
        }
    });
});
app.get('/index.html/:id(\\d+)',(req,res)=>{
    res.sendfile(__dirname+'/index.html');
});
app.post('/index.html',(req,res)=>{
    req.on('data',(data)=>{
        let obj = JSON.parse(data.toString());
        pool.getConnection((err, connection)=>{
                if(err) {
                    res.send('与MySQL数据库建立连接失败。');
                } else {
                    let str;
                    connection.query('update users set username=?,firstname=? '
                    + 'where id=?',[obj.username,obj.firstname,req.params.id],
                    (err,result)=>{
                        if(err) {
                            str='在服务器端MySQL数据库中更新数据失败。';
                        } else {
                            str='在服务器端MySQL数据库中更新数据成功。';
                        }   
                    connection.release();
                    res.send(str);
                });
            }
        });
    });
});
app.listen(1337, "127.0.0.1");

应用程序根目录下的index.html文件中的内容基本同代码所示,只是将标题修改为"使用POST方法向服务器端提交数据"​,将XMLHttpRequest对象的put方法修改为post方法,代码如下所示。

js 复制代码
// xhr.open('put','index.html',true);
删除原语句
xhr.open('post','/index.html',true);

运行该文件,接着在浏览器的地址栏中输入"http://localhost:1337/index.html/1000"地址(1000为MySQL数据库的users表中不存在的id字段值)​,浏览器中显示"您没有操作数据表的权限。​"字符串,如图所示。

在浏览器的地址栏中输入"http://localhost:1337/index.html/1"地址(1为MySQL数据库的users表中已存在的id字段值)​,浏览器中显示应用程序根目录下的index.html页面中的内容,显示结果同图所示。

在页面文本框中输入用户姓与用户名后单击"提交"按钮,用户提交数据被更新到users数据表中,数据更新成功后页面中显示"在服务器端MySQL数据库中更新数据成功。​"字符串,如图所示。

相关推荐
zhensherlock1 天前
Protocol Launcher 系列:1Writer iOS 上的 Markdown 文档管理
javascript·笔记·ios·typescript·node.js·iphone·ipad
吴声子夜歌1 天前
Node.js——操作MongoDB
数据库·mongodb·node.js
吴声子夜歌1 天前
Node.js——dns模块
开发语言·node.js·php
吴声子夜歌1 天前
Node.js——zlib压缩模块
java·spring·node.js
"Wild dream"1 天前
NodeJs内置的Npm
前端·npm·node.js
摇滚侠1 天前
JAVA 项目教程《苍穹外卖-12》,微信小程序项目,前后端分离,从开发到部署
java·开发语言·vue.js·node.js
怣疯knight2 天前
Termux 运行 Node.js 实操记录(精简版)
node.js
AiSchoober2 天前
schoober-ai-sdk:核心ReAct 引擎的实现
人工智能·ai·node.js·agent·ai编程