__ 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' ) )