const express = require("express");//调用npm下载到node_moudle的express模块(npm i express -S)
/*
npm使用方法:
到node官网上去下载对应你电脑的node版本,然后安装;
不需要更改路径,若更改路径,则需要配置系统环境变量(鼠标右击图标计算机->属性->高级系统设置->环境变量),不会就百度!!!
安装好之后,npm就有了,下载node自带的。
npm -v node-v 查看版本
npm intall moudleName -S(等同于--save) 将模块下载到"服务"环境,就是你开发和项目维护运行都要用的环境。
简写:npm i moudleName -S || -D 大写:若是其他的写法(不写,小写,-G),将会下载到node的安装路径之下(global)。
npm intall moudleName -D(等同于--Dev) 将模块下载到开发环境,就是你开发需要、项目维护运行不需要的环境。
npm list:列举出当前环境下的模块有哪些,后面可以加参数:-D(开发下) -S(开发与维护)。
require("moudleName"):该函数可以调用npm下载好的模块,也可以引入自己写好的模块
引入自己的模块:需要在被引入的模块里面导出你需要的东西:moudle.exports = ...(可以是变量名,也可以是函数表达式)
引入的各个模块之间不存在变量名冲突的问题
*/
const path = require("path");//这是个内置的路径模块,直接用就行
const app = express();//返回一个app实例对象
// console.log(app);
app.use(express.json());
app.use(express.urlencoded({extended:true}));
//人家写好的基于express用来处理前后端数据的方法,直接用就行了
//这两个是默认写法,这是express模块已经写好的方法,直接可以用来处理数据。
//直接在中间件函数内使用req.query(get方式请求写法)、req.body(post方式请求写法)就可以获取发送过来的数据。
/*
原始方法:
var str = "";
req.on("data",function (data) {
str += data;
});
req.on("end",function () {
console.log(str);
res.end("ok");
});
*/
/*
中间件:其实就是一个函数,可以用来处理下面模块的重复性部分。(就是前面插入use方法)
简单来说 在来到第一个接口之前 有个拦截器,这个拦截器中的路径是/, 所有的接口都先走这个拦截器,在这个拦截器里做逻辑处理,
允许它继续往下走就加next() ,不允许往下走就不用加next(), 例如:验证token,就可以在中间件里进行:
app.use("/",(req,res,next)=>{
console.log("中间件")
let token = req.query;
if(token){
next() // 是否继续往下执行
}else{
res.send("缺少token")
}
})
=>比如:我们在根路由设置了公共的东西,那样每个子路由就不用设置了
@: 但是需要执行next(),不然就会一直转圈圈;没有使用公共数据的路由不受影响!!!
(监听的路由不依赖、“经过”前面设置中间件的路由)
*/
app.listen(5555);
/*
不设置端口监听,前端页面就会访问不到;
一般用到的是1到65535,其中0不使用;
一般的应用程序使用1024到4999用来通讯;
5000以后的用来用户自定义端口 ;
*/
/*
监听路由,可以是app.get,app.post,app.use、app.all(get、post均可),等等
/表示服务器根路由;
req:前端请求对象;
res:后端返回对象;
next:需要在内部执行next();不然浏览器就会停留在公共资源设置的地方!!!
*/
app.get("/",(req,res,next)=>{
// res.send("122")//返回字符串数据,不能是数字,不然会被当做状态码返回,404,400,200
res.sendFile(path.join(__dirname,"./static/index.html"));
//返回文件类型的数据(需要设置为绝对路径,不然会报错,这里使用到了path模块的path.join(__dirname,"相对路径"))
//res.send res.sendFile 同时只能执行一个,每一个也只能执行一次,多次执行就会报错,因为已经返回过了
})
//.....省略很多的监听!!!
/*
require()的使用好处:
当我们需要监听多个子路由时,全部写在当前这个文件之下,就会很冗余,而且后期很难去维护。
所以:
把中间件函数写成require()函数即可,意思就是用require引入已经设置好的相对应路由的请求。
上面只是基本的写法,但是为了规范,以后我们就需要写成require的形式了!!!
*/
app.get("/index",require("./route/index"));
/*
index.js(引入路由是省略了后缀名,任何文件都可以当做路由!!!)
此文件只需要返回一个中间件函数,使用我们写成下面的样子
module.exports = (req,res)=>{
res.send("这是根路由下的一个首页");
//res.sendFile();
}
*/
//多重路由怎么办???
/*
当一个"根路由"下有多个子路由是时(当你需要访问多层路由时),需要把前面所有的路径都加上,这样很麻烦。
如:
app.get("/A/B/C",require("")) app.get("/A/B/C/D/E",require(""))
我们可不可以不加"根路由"直接访问子路由呢???
==>其实并不是不用写,只是我们去require引入的文件里面写了!!!
中心思想:其实就是俄罗斯套娃,在子路由的中间件函数(require内的文件)内一层一层的往下面写,最后返回router对象!!!
当然可以:
此时需要在require引入的文件内部多余写上express模块方法:express.Router();
==>family.js文件:
const express = require("express");
const path = require("path");
-->!!! const router = express.Router();
router.get("/",(req,res)=>{
res.send("这是family首页");
})
router.use("/father",require("./father"));
router.use("/mother",require("./mother"));
router.use("/son",require("./son"));
module.exports = router;
1.如果你需要在此页面引用子路由,则必须要用use()
2.如果子路由又需要子子路由,则需要在他自己的文件内用use()设置子路由,
3.但是获取自己本身的页面可以使用get,post
example:(子子子页面father文件)
const express = require("express");
const path = require("path");
const router = express.Router();
router.get("/",(req,res)=>{
res.send("这是father首页");
})
module.exports = router;
*/
// !!!用 use 才能使用子路由(父级必须用use,子集必须设置router.use子文件)。app.get(),app.post()都不行<已经试验过了>
app.use("/family",require("./route/family"));
/* 虽然不能直接使用app.get(),app.post,但是我们可以在中间键函数内去判断,从而作出相对应的响应。
app.use("/family/father",(req,res)=>{
if (req.method === "GET") {
res.send("这是正确的,访问到了/family/father");
}else if (req.method === "POST"){
res.send("请使用get");
}
});
*/
/*
404返回页
不设置路由,找不到的时候就执行下面的方法(可自由设置返回内容)
app.use不给路由必须要放在所有的路由请求后面,不然后面的请求就没有用了,都是404页面了!!!
*/
app.use((req,res)=>{
res.send("404哟");
})