__ dirname和 __filename
注意:只要对文件或目录进行操作,大家要使用绝对路径 。( 绝对地址动态化 )
node中的相对地址:是相对于当前执行文件的cmd上的路径。
ENOENT: no such file or directory, open './demo/a.txt'
ENOENT:在计算机中代表没有找到的含义。
const fs = require('fs')
// console.log( __dirname )//获取的是当前文件的绝对路径地址(目录)
let filepath = __dirname + '\\demo\\a.txt'
// console.log( filepath );
let result = fs.readFileSync(filepath,'utf8')
console.log( result,'ok' );
1、服务端与客户端
1.1什么是上网
通俗地说我们可以通过互联网进行资源共享。
打游戏、看电影、看小说、聊天、微博、短视频...
以上都是互联网上的资源 。有专门的人共享这些资源 。上网就是我们享受各种各样服务的一种渠道 。
1.2享受服务的流程
有请求必须有响应
无论什么服务,它的完整的一次过程是一致的。包含请求、处理、响应三个方面。
1、现实生活中的服务
我们去海底捞。享受用餐的服务
用户扮演了主动发起请求的角色 。
服务员扮演了处理请求的角色。(服务器) 处理
服务员上菜(响应的结果),用户享受这个服务(干饭)
一些细节的问题说明:
用户说了,给我来个驴肉火烧(想要的没有)、100斤的小龙虾。
有请求必须有响应,哪怕是一个不好的结果,也得告诉用户。
1000份火锅。超负荷运转。 拥挤状态、宕机。先来后到(排队)
2、互联网上的服务
客户代表着用户
远程计算机(web服务器):餐厅的地址(服务员)
1.3服务器
介绍:就是一台电脑。配置比较高(比普通电脑 personal computer的配置要高100倍甚至更高)。作用:就提供了某些服务(游戏服务、网页服务【web服务】、邮件服务器、视频服务器、数据库服务器),个人电脑和服务器必须联网(internet网络)
举例:CTS服务器、优就业官网、中公教育服务器、淘宝www.taobao.com、百度www.baidu.com、腾讯www.qq.com
1.4客户端
说明:享受服务的,主动发起请求的。
举例(表现形式):笔记本、手机、平板、智能手表、智能电视。
1.5url地址
简单来说就是网址。URL(全称是Uniform Resource Locator)中文叫统一资源定位符,用于标识互联网上每个资源的唯一存放位置。浏览器只有通过URL地址,才能正确定位资源的存放位置,从而成功访问到对应的资源。
协议:
双方约定俗成的规则 。比如:去海底捞只能吃火锅,只能用餐;只能去店铺享受服务。
常见协议:http、https、file、ftp、ssh、
服务器名称:
域名(地址)。北京市 ,朝阳区,青年路,朝阳大悦城 (7层 00001)。区分服务名称的。
taobao.com、baidu.com、ujiuye.com
端口号:
这个才是真正区分服务的。
朝阳大悦城(只有一个大门口),具体的商铺号才是真正的服务。
计算机是一个封闭的的。( qq、微信 ):每一个软件都是一个服务。这个服务就是用端口区分的。
http:80
https:443
默认端口号是可以省略的。
端口号范围:1-65535 但是小于3000尽量别用。计算机内部会占用比较小的端口号。
计算机中不可能有相同的两个服务的端口号
路径:
资源存储在服务器的具体的路径地址。有些路径是不包含文件名的。
黄瓜、西红柿、羊肉等资源在后厨具体哪个位置,这就是路径....
参数:
客户具体要什么,是通过参数告知的。
广义的参数:url地址的每一个部分都可以称为参数
狭义的参数:?key1=value1&key2=value2... 必须是这种格式才能把?后面的参数传递给服务员。
/login?username1=swk&password1=123456
参数怎么传递,需要看后端如何接收的。
1.6 域名与ip的关系
IP:计算机的地址。区分电脑的。 x.x.x.x ,每一个数字都是 0~255
IP的问题:就是不好记
域名:域名指向某个ip。作用:好记,域名越短越有价值 。
baidu.com jd.com taobao.com
DNS服务器:
whois查询可以看域名的信息:
cmd快速查看域名和ip的指向
ping 域名 : 查看此域名通不通
2、互联网传输协议
什么是协议:协议( Protocol)是指双方为了完成一个目标结果所必须遵守的规则和约定。
通俗的理解:双方采用约定好的格式来做某种事情,这种事先约定好的格式,就叫做协议。
2.1协议分类
2.1.1现实中的协议
邮寄规则:寄件人信息、收件人信息
2.1.2互联网中的传输协议
Http(HyperText Transfer Protocol):超文本传输协议 (文本、图片、视频、音频、css、js....)。
作用:约束客户端与服务端如何交互且传递信息。
优就业要把最近一些web开班告诉广大用户。则可以在网页上,同时要把网页放在服务器上。客户需要使用类似浏览器的软件(访问优就业域名,然后客户就获取到信息)
2.2Http协议工作原理
2.2.1交互模型
交互模型(请求与响应):HTTP 协议采用了 请求/响应 的交互模型。也就是说必须是客户端主动发起请求,再由服务器端处理请求,同时被动的把内容响应给客户端( 哪怕是不好的消息,也行告知客户端,要有一个完整的一次请求 )。
2.2.2http协议的组成
请求消息、响应消息、请求方法、状态码
2.2.3请求消息
描述:客户端发起的请求叫做 HTTP 请求,客户端发送到服务器的消息,叫做 HTTP 请求消息(又叫做 HTTP 请求报文。) 简单来说就是客户端告知服务器我要干什么。
请求消息组成
各属性说明:
请求行
-
请求方式 ,比如:get、post
-
空格,是来进行区分 某些值
-
url: ww.ujiuye.com
-
协议版本:http、https
-
换行符
请求头部
额外携带一些参数信息
比如:我要请求一种文件的类型。
host:主机名
user-agent:浏览器信息
content-type
空行
代表:请求行和请求头部描述完毕 。
请求体
只有post方式的请求才有请求体。(post传递参数需要使用请求体)
要求:只要能分清楚请求消息的常用部分即可。
而如何请求的,是浏览器帮我们解决。
2.2.4响应消息
描述:响应消息就是服务器响应给客户端的消息内容,也叫作响应报文。比如:海底捞服务员把后厨准备好的食材交付给用户
组成:状态行、响应头部、空行、响应体、
各属性说明:
状态行
-
协议版本:和请求的协议保持一致
-
状态码:反映了这次请求状态
-
状态码描述:200OK、404Not Found、 500 Server Error
响应头部:
Content-type:‘text/html’。我是一个html文本。浏览器要使用html的方式渲染我 。
‘application/javascript’ .以js的方式渲染我
响应体:
具体的数据。
2.2.5请求方法
用来表明要对服务器上的资源执行的某操作,以何种方式进行请求。
到店铺告知服务员、桌子上的小程序码、美团app进行点。这都是属于请求方法 。
获取数据、删除数据、更新数据。
常见请求方法比如:get获取/post提交数据/delete删除/put更新的
2.2.5状态码
用来标识响应的状态。服务器的结果要用状态码来进行描述。比如:404页面不存在。200成功
格式:3个数字组成。
2** : 成功
3** :重定向
4** : 前端的问题
5**:一定是后端的问题
常见状态码: 404 200
3、Node创建服务器(了解)
总结和复盘:总结以上的知识点。
为什么要创建服务器?没有服务器就没有交互 。
原生的http模块 。
//1. 需要使用http模块 。(内置模块)
const http = require('http')
//2.创建服务器对象
const server = http.createServer()
let num = 0
//4.服务器端通过绑定事件的方式,兼听客户端的请求信息事件s。同时还需要响应给客户端消息
server.on( 'request',(req,res)=>{
//req:请求对象 request
//res:响应对象 response
// res.end('hello nodejs')
let message = `<h2>welcome ${num++} user </h2>`
res.end(message)
} )
//3.开放一个端口(兼听一个端口)
server.listen( 3000 )
//当用node运行这个文件,命令行呈现挂起状态:3000端口的服务器已开启。
/*
访问:自己的IP+端口号。如果是80.则端口号可以省略
127.0.0.1 访问的是自己的电脑
localhost 访问的是自己的电脑
*/
//这个端口一直开启,别人才可以访问
//改了代码必须重新运行、重新node一下。
//原生node写完服务器以后,所有的请求都会被request兼听到。
//要解决的问题?
//login-> 登录页面
//register-> 注册页面
设置响应头
//在end之前设置响应头信息
res.writeHead( 200,{ 'Content-Type': "text/html;charset=utf8"} )
text/html: 以html的格式渲染文本
charset=utf8:编码的设置。解决中文乱码问题
常常遇到的错误
listen EADDRINUSE: address already in use :::3000
端口在同一台计算机中不可能有重复的。
请求对象
打印一下即可。
req.method:请求方法
req.url:根据用户不同的请求地址返回不同的消息。就是通过req.url进行判断 。
在使用浏览器访问网址的时候。浏览器默认会自动请求一个 /favicon.ico这个小图标 。
返回不同的消息
需求:根据不同的url诉求,返回不同消息 。
req.url:请求的地址
/login-> 登录页面
/register-> 注册页面
案例1:
const http = require('http')
//创建服务器
const server = http.createServer()
server.on( 'request',(req,res)=>{
console.log( req.url )//用户访问的地址
if( req.url == '/login' ){
res.end('welcome login form')
}else if( req.url == '/register' ){
res.end('welcome register form')
}else{
res.writeHead( 404 )
res.end('welcome 404 page')
}
} )
server.listen(3000,()=>{
//兼听成功,则解决这个回调函数
console.log( '3000端口已经开启。http://localhost:3000' )
} )
案例2:
const http = require('http')
const fs = require('fs')
//创建服务器
const server = http.createServer()
server.on( 'request',(req,res)=>{
if( req.url == '/login' ){
let filename = __dirname + '\\page\\login.html'
let result = fs.readFileSync( filename )
res.end(result)
}else if( req.url == '/register' ){
let filename = __dirname + '\\page\\register2.html'
let result = fs.readFileSync( filename )
res.end(result)
}else{
res.writeHead( 404 )
res.end('welcome 404 page')
}
} )
server.listen(3000,()=>{
//兼听成功,则解决这个回调函数
console.log( '3000端口已经开启。http://localhost:3000' )
} )
4、其它模块
path
path.extname( 路径 ) :扩展名
const path = require('path')
let filename = './b/c/d/a.html'
let extname = path.extname( filename ) //同步方法
console.log( extname,'后缀名获取' ); //返回 .html
path.join( ...[paths] ) : 把路径进行拼接
//绝对地址动态化
// let filepath = __dirname + '/demo/a.txt' // \\ 虽然操作此路径没有问题,但是不规范。
// // console.log( filepath );
// let result = fs.readFileSync( filepath,'utf8' )
// console.log( result,'我是结果' );
//path.join( ...[paths] ) : 把路径进行拼接,把路径进行规范化
console.log( path.join( __dirname,'demo','a.txt' ) );
console.log( path.join( __dirname,'demo/a.txt' ) );
url
new URL
//此模块不需要引入 全局的一个构造函数
// console.log( URL );
//格式化我们的url。能够方便的获取url的每一部分。
let urlstr = 'http://www.ujiuye.com:3333/zt/webqzgcs/?username=admin&age=20&sex=男'
let urlObj = new URL( urlstr )
console.log( urlObj );
// console.log( urlObj );
console.log( urlObj.searchParams.username ) //注意:?后面的数据以map数据结构进行了返回
console.log( urlObj.searchParams.get('age') )
console.log( urlObj.searchParams.get('username') )
querystring
querystring.parse(): 查询字符串转对象
querystring.stringify(): 对象转查询字符串
url地址页面。?username=admin&age=20&sex=男 这种形式的字符串叫查询字符串,又叫querystring
const qs = require('querystring')
let str = 'username=admin&age=20&sex=男'
let obj1 = qs.parse( str )
console.log( obj1 );
//{ username: 'admin', age: '20', sex: '男' }
let obj2 = { username: 'admin', age: '20', sex: '男',a:[11,22] }
let str2 = qs.stringify( obj2 )
// console.log( str2 );
// /username=admin&age=20&sex=%E7%94%B7&a=11&a=22
//因为是中文,涉及到乱码的问题。默认浏览器/node服务器都会自动转换成这种 %E7%94%B7 形式
// %E7 %94 %B7
console.log( qs.parse( 'username=admin&age=20&sex=%E7%94%B7&a=11&a=22' ) )