ASP.NET本质论第一章网站应用程序学习笔记1
1.统一资源标示符
1) 格式:协议://主机[.端口号][绝对路径[?参数]],在Http://www.kencery.com/hyl/index/login中,http表示协议的名称,www.kencery.com表示主机的地址,可选的端口号没有出现,那么,将使用http协议的默认端口号80,绝对路径为:hyl/index/login,如果没有提供绝对路径,那么,使用默认的绝对路径/。
2) .NET中提供的对URL或者URI操作的方法代码如下:
Uri uri = new Uri("https://www.kencery.com/hyl/index/login");
Console.WriteLine(uri.Scheme); //协议的名称 输出结果:https
Console.WriteLine(uri.Host); //取得Uri地址中的主机部分 输出结果:www.kencery.com
Console.WriteLine(uri.Port); //端口号 输出结果:80
Console.WriteLine(uri.AbsolutePath); //绝对路径 输出结果:/hyl/index/login
Console.WriteLine(uri.Query); //地址中的参数部分 输出结果:
Console.ReadLine();
3) 浏览器要找到我们访问的服务器,需要提供服务器的网络地址,在当前的TCP/IP协议下,所谓的服务器地址其实就是一个IP地址,目前我们使用的是IPV4的地址,每个地址由四个字节共32位组成,理论上讲,可以表示4G的网络地址,微软的IP地址是:207.46.19.254,所以我们直接在地址栏中输入http://207.46.19.254也可以看到微软的网站。
4)HTTP协议
1.当浏览器寻找到Web服务器的地址之后,浏览器将帮助我们把对服务器的请求转换为一系列的参数发送给Web服务器,服务器收到浏览器发来的请求参数之后,将会分析这些数据并进行处理,然后向浏览器回应处理的结果,也就是一些新的数据,浏览器收到之后,就会解析这些数据,并将他们显示在浏览器中。
2,在浏览器与Web服务器之间进行通信的时候,需要双方都要能够理解的规范进行通讯,这种程序之间进行通信的语言规范,我们称之为协议,协议有许多种,根据国际标准化组织ISO的网络参考模型,程序与程序之间的通信可以分为7种,从低到高依次是:物理层,数据链路层,网络层,传输层,会话层,表示层,应用层,每层都有自己对应的协议。
3.请求微软网站的请求信息如图所示:Http请求
2.最简单的Web服务器
2.1 网络插座Socket
在Unix时代,为了解决传输层的编程问题,Unix提供了类似于文件操作的网络操作方式—Socket,通过Socket,开发人员可以像操作文件一样通过打开,写入,读取,关闭等操作来完成网络编程,Socket不负责应用层的协议,仅仅负责传输层的协议。
当通过Socket开发网络应用程序的时候,首先需要考虑所使用的网络类型,主要包括以下三个方面:
1)Socket类型,使用网络协议的类别,IPV4的类型为PF_INET
2)数据通信的类型,常见的数据报(Sock_DGRAM),数据流(SOCK_STREAM)。
3)使用网络协议,比如:TCP协议。
2.2 在.NET中,System.Net命名空间提供了网络编程的大多数数据类型以及常用操作,其中类型如下:
1) IPAddress类用来表示一个IP地址
2) IPEndPoint类用来表示一个IP地址和一个端口号的组合,成为网络的端口。
3) System.NET.Sockets命名空间中提供了基于Socket编程的数据类型。
4) Socket类封装了Socket的操作。常见的操作如下:
a) Listen:设置基于连接通信的Socket进入监听状态,并设置等待队列的长度。
b) Accept:等待一个新的连接,当新连接到达的时候,返回一个针对新连接的Socket对象。通过这个新的Socket对象,可与新连接通信。
c) Receive:通过Socket接收字节数据,保存到一个字节数组中,返回实际接收的字节数。
d) Send:通过Socket发送预先保存在字节数组中的数据。
2.3 通过Socket编程创建一个简单地Web服务器
private static void Main(string[] args)
{
//取得本机的loopbakack网络地址,即127.0.0.1
IPAddress address = IPAddress.Loopback;
//创建可以访问的端点,49152表示端口号,如果设置为0,表示使用一个空闲的端口号
IPEndPoint endPoint = new IPEndPoint(address, );
//创建Socket,使用IPV4地址,传输控制协议TCP,双向,可靠,基于连接的字节流
Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
//将Socket绑定到一个端口上
socket.Bind(endPoint);
//设置连接队列的长度
socket.Listen();
Console.WriteLine("开始监听:端口号:{0}", endPoint.Port);
while (true)
{
//开始监听,这个方法会阻塞线程的执行,直到接收到一个客户端的连接请求
Socket client = socket.Accept();
//输出客户端地址
Console.WriteLine("客户端地址:{0}", client.RemoteEndPoint);
//准备读取客户端请求的地址,读取的数据将保存在一个数组中
byte[] buffer = new byte[];
//接收数据
int length = client.Receive(buffer, , SocketFlags.None);
//将请求的数据翻译成UTF-8
Encoding utf8 = Encoding.UTF8;
string requestString = utf8.GetString(buffer, , length);
//显示请求的信息
Console.WriteLine(requestString);
//回应的状态行
string statusLine = "HTTP/1.1 200 OK\r\n";
byte[] statusLineBytes = utf8.GetBytes(statusLine);
//准备发送到客户端的网页
string responseBody =
"<html><head><title>From Socket Server</title></head><body><h1>Hello,World</h1></body></html>";
byte[] responseBodyBytes = utf8.GetBytes(responseBody);
//回应的头部
string responseHeader = string.Format("Content-type:text/html;charset=UTF-8\r\nContent-Length:{0}\r\n",
responseBody.Length);
byte[] responseHeaderBytes = utf8.GetBytes(responseHeader);
//向客户端发送状态信息
client.Send(statusLineBytes);
//向客户端发送回应头
client.Send(responseBodyBytes);
//头部和内容的分割行
client.Send(new byte[] {, });
//向客户端发送内容部分
client.Send(responseBodyBytes);
//断开与客户端的链接
client.Close();
if (Console.KeyAvailable)
{
break;
}
}
54 //关闭服务器
55 socket.Close();
}
2.4 基于TcpListener的Web服务器
为了简化基于TCP协议的监听程序,.NET在System.Net.Sockets命名空间中提供了TcpListener类,代码如下:
private static void Main(string[] args)
{
//取得本机的loopbakack网络地址,即127.0.0.1
IPAddress address = IPAddress.Loopback;
//创建可以访问的端点,49152表示端口号,如果设置为0,表示使用一个空闲的端口号
IPEndPoint endPoint = new IPEndPoint(address, );
//创建Socket,使用IPV4地址,传输控制协议TCP,双向,可靠,基于连接的字节流
Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
//将Socket绑定到一个端口上
socket.Bind(endPoint);
//设置连接队列的长度
socket.Listen();
Console.WriteLine("开始监听:端口号:{0}", endPoint.Port);
while (true)
{
//开始监听,这个方法会阻塞线程的执行,直到接收到一个客户端的连接请求
Socket client = socket.Accept();
//输出客户端地址
Console.WriteLine("客户端地址:{0}", client.RemoteEndPoint);
//准备读取客户端请求的地址,读取的数据将保存在一个数组中
byte[] buffer = new byte[];
//接收数据
int length = client.Receive(buffer, , SocketFlags.None);
//将请求的数据翻译成UTF-8
Encoding utf8 = Encoding.UTF8;
string requestString = utf8.GetString(buffer, , length);
//显示请求的信息
Console.WriteLine(requestString);
//回应的状态行
string statusLine = "HTTP/1.1 200 OK\r\n";
byte[] statusLineBytes = utf8.GetBytes(statusLine);
//准备发送到客户端的网页
string responseBody =
"<html><head><title>From Socket Server</title></head><body><h1>Hello,World</h1></body></html>";
byte[] responseBodyBytes = utf8.GetBytes(responseBody);
//回应的头部
string responseHeader = string.Format("Content-type:text/html;charset=UTF-8\r\nContent-Length:{0}\r\n",
responseBody.Length);
byte[] responseHeaderBytes = utf8.GetBytes(responseHeader);
//向客户端发送状态信息
client.Send(statusLineBytes);
//向客户端发送回应头
client.Send(responseBodyBytes);
//头部和内容的分割行
client.Send(new byte[] {, });
//向客户端发送内容部分
client.Send(responseBodyBytes);
//断开与客户端的链接
client.Close();
if (Console.KeyAvailable)
{
break;
}
}
//关闭服务器
socket.Close();
}
2.5 基于HttpListener的web服务器
为了进一步简化HTTP协议的监听器,.NET在命名空间System.Net中提供了HttpListener类,伴随这个对象,.NET提供了一系列相关对象封装了HTTP的处理工作,注意,这个类使用Http.sys系统组件来完成工作,所以,只有在Windows XP SP2或者Server2003以上的操作系统中磁能使用。
private static void Main(string[] args)
{
//检查系统是否支持
if (!HttpListener.IsSupported)
{
throw new System.InvalidOperationException("使用HTTPListener必须为Windows XP SP2或者Server 2003以上系统");
}
//注意前缀必须以/正斜杠结尾
string[] prefixes = new string[] {"http://localhost:49125/"};
//创建监听器
HttpListener listener = new HttpListener();
//增加监听的前缀
foreach (string s in prefixes)
{
listener.Prefixes.Add(s);
}
//开始监听
listener.Start();
Console.WriteLine("监听中。。。。。。");
while (true)
{
//注意:GetContext方法将阻塞线程,直到请求到达
HttpListenerContext context = listener.GetContext();
//取得请求对象
HttpListenerRequest request = context.Request;
Console.WriteLine("{0}{1} HTTP/1.1", request.HttpMethod, request.RawUrl);
Console.WriteLine("Accept:{0}", string.Join(",", request.AcceptTypes));
Console.WriteLine("Accept-Language:{0}", string.Join(",", request.UserLanguages));
Console.WriteLine("User-Agent:{0}", request.UserAgent);
Console.WriteLine("Accept-Encoding:{0}", request.Headers["Accept-Encoding"]);
Console.WriteLine("Connection:{0}", request.KeepAlive ? "Keep_Alive" : "close");
Console.WriteLine("Host:{0}", request.UserHostName);
Console.WriteLine("Pragma:{0}", request.Headers["Pragma"]);
//取得回应的对象
HttpListenerResponse response = context.Response;
//构造回应内容
string responseString =
@"<html><head><title>From Socket Server</title></head><body><h1>Hello,World</h1></body></html>";
//设置回应头部内容,成都,编码
response.ContentLength64 = Encoding.UTF8.GetByteCount(responseString);
response.ContentType = "text/html;chrset=UTF-8";
//输出回应内容
Stream output = response.OutputStream;
StreamWriter writer = new StreamWriter(output);
writer.Write(responseString);
//必须关闭输出流
writer.Close();
if (Console.KeyAvailable)
{
break;
}
}
//关闭服务器
listener.Close();
Console.ReadLine();
}
上面三个关于简单地模拟了一下Web服务器的实例,实现结果如图所示:
ASP.NET本质论第一章网站应用程序学习笔记1的更多相关文章
- ASP.NET本质论第一章网站应用程序学习笔记3-对象化的Http
在.NET环境下,万物皆对象,在HttpRuntime收到请求之后,立即将通过HttpWorkerRequest传递的参数进行分析和分解,创建方便用于网站应用程序处理用的对象,其中主要涉及到两个对象类 ...
- ASP.NET本质论第一章网站应用程序学习笔记2
1.初步走进ASP.NET 上篇笔记我们讲述了服务器监听问题,这篇我们就要讲述具体的请求处理了,ASP.NET所涉及的类大多数定义在System.Web程序集中. 在.NET中,程序集管理的最小逻辑单 ...
- ASP.NET本质论第二章应用程序对象学习笔记1
1.请求的处理参数—上下文对象HttpContext 1) 针对每一次请求,ASP.NET将创建一个处理这次请求所使用的HttpContext对象实例,这个对象实例将用来在ASP.NET服务器的处理过 ...
- 0001-20180421-自动化第一章-python基础学习笔记
======================学习python==================介绍: python种类: cpython(*),jpython,ironpython,rubypyth ...
- 01.第一章_C++ Primer学习笔记_开始
1.2 初始输入输出 iostream库里面包含两个基础类型istream和ostream,分别表示输入流和输出流,一个流就是一个字符序列,从IO设备读出或者写入IO设备. 标准的输入输出对象 标准库 ...
- C语言编程入门之--第一章初识程序
第一章 初识程序 导读:计算机程序无时不刻的影响着人类的生活,现代社会已经离不开程序,程序的作用如此巨大,那么程序到底是什么呢?本章主要讨论程序的概念,唤起读者对程序的兴趣,同时对C语言程序与其它语言 ...
- 《算法》第一章部分程序 part 2
▶ 书中第一章部分程序,加上自己补充的代码,包括简单的计时器,链表背包迭代器,表达式计算相关 ● 简单的计时器,分别记录墙上时间和 CPU 时间. package package01; import ...
- 《算法》第一章部分程序 part 1
▶ 书中第一章部分程序,加上自己补充的代码,包括若干种二分搜索,寻找图上连通分量数的两种算法 ● 代码,二分搜索 package package01; import java.util.Arrays; ...
- windows核心编程-第一章 对程序错误的处理
第一章-对程序错误的处理 在开始介绍Microsoft Windows 的特性之前,必须首先了解 Wi n d o w s的各个函数是如何进行错误处理的. 当调用一个Wi n d o w s函数时,它 ...
随机推荐
- (转)Unity3D研究院之异步加载游戏场景与异步加载游戏资源进度条(三十一)
异步任务相信大家应该不会陌生,那么本章内容MOMO将带领大家学习Unity中的一些异步任务.在同步加载游戏场景的时候通常会使用方法 Application.LoadLevel(“yourScene ...
- Android 自定义View实现多行RadioGroup (MultiLineRadioGroup)
一.项目概况 我们都知道RadioGroup可以实现选择框,但它有一个局限性,由于它是继承自LinearLayout的,所以只能有一个方向,横向或者纵向:但有时候仅一行的RadioGroup并不能满足 ...
- 【解析 . PPT版】干货:阿里全息大数据构建与应用(包括:互联网金融、互联网+、精准营销...)
作者:毛波,阿里巴巴资深数据专家,阿里数据管理平台(DMP)产品负责人. 摘要: 回顾传统数据仓库.商业智能到大型分布式数据平台的进化历程,深入阐述阿里的数据发展历史和数据观,以阿里DMP平台为例深入 ...
- perl基本语法--转载
http://www.cnblogs.com/zhtxwd/archive/2012/03/06/2381585.html 本文介绍从变量类型.操作运算符.控制叙述.子程序.I/O和档案处理. Reg ...
- 【转载】C/C++ 函数指针 总结
转载自:http://blog.csdn.net/shihui512/article/details/9787125 什么是函数指针函数指针的声明函数指针的赋值函数指针的使用将函数作为其他函数的参数在 ...
- iOS-AFNetworking-上传图片
一.AFNetworking上传图片 /** 需要Demo,可留言 */ 1.利用AFnetworking上传图片. 2.注意将UIImage类型转化为NSData类型,传给后台. 二.Demo // ...
- Android下拉刷新底部操作栏的隐藏问题
最近自己编写下拉刷新的时候,发现了一个问题,就是有一个需求是这样的:要求页面中是一个Tab切换界面,一个界面有底部操作栏,不可下拉刷新,另一个界面没有底部操作栏,但可以下拉刷新. 按照平常的做法,我在 ...
- .NET指定程序集的位置
有两种方法用来指定程序集的位置: 使用 <codeBase> 元素. 使用 <probing> 元素. 还可以使用 .NET Framework 配置工具 (Mscorcfg. ...
- javascript中&&和||的区别
javascript中&&和||的区别 &&和||操作符两边不是布尔类型时,系统会转换成布尔类型值再计算(空字符串.null.0都会被转成false),结果本身不变. ...
- SQL Server技术问题之游标优缺点
分类: MS SQL SERVER 支持三种类型的游标:Transact_SQL 游标,API 服务器游标和客户游标. (1) Transact_SQL 游标 Transact_SQL 游标是由DEC ...