包含http服务器源码大全的词条

hacker|
71

文章目录:

远程访问用的是http协议,下面是源代码

结论:①string URi = "";

URi的值应该是一个URL地址吧,怎么105后面有两个/

②你这样的访问方式涉及到客户端对服务器端的访问权限问题,我没试过以这样的方式将文件上传到服务器的,而且我觉得应该不是这样的方式。

解决方案建议:

①可以在服务器端开通ftp功能,将文件发送到ftp里,代码如下:

privatevoidbutton1_Click(objectsender,EventArgse)

{

WebClientw=newWebClient();

w.Credentials=newNetworkCredential("sa","sa");//登陆ftp的用户名密码

w.UploadFile("",@"e:\1.xls");////前面是远程ftp文件夹路径后面是:本地上传的文件路径

w.Dispose();

MessageBox.Show("上传成功!");

}

②服务器端有IIS的话通过WebService的方式实现文件上传

这个方法相对比较复杂,建议用第一种,如果要采用这种的话到时我再发一个例子给你⊙﹏⊙

如何编写一个简单的HTTP代理服务器,最好提供VB源码

VERSION 5.00

Object = "{248DD890-BB45-11CF-9ABC-0080C7E7B78D}#1.0#0"; "MSWINSCK.OCX"

Begin VB.Form Form1

ClientHeight = 3090

ClientLeft = 60

ClientTop = 450

ClientWidth = 4680

LinkTopic = "Form1"

ScaleHeight = 3090

ScaleWidth = 4680

StartUpPosition = 3 '窗口缺省

Begin VB.ListBox List1

Height = 1500

Left = 120

TabIndex = 0

Top = 720

Width = 3615

End

Begin MSWinsockLib.Winsock SckGET

Index = 0

Left = 2520

Top = 360

_ExtentX = 741

_ExtentY = 741

_Version = 393216

End

Begin MSWinsockLib.Winsock Winsock1

Left = 2040

Top = 360

_ExtentX = 741

_ExtentY = 741

_Version = 393216

End

End

Attribute VB_Name = "Form1"

Attribute VB_GlobalNameSpace = False

Attribute VB_Creatable = False

Attribute VB_PredeclaredId = True

Attribute VB_Exposed = False

Dim PathName As String

Sub Begin()

'启动Winsock1,使用listen方法,听254端口

DoEvents

Winsock1.Close

Winsock1.Protocol = sckTCPProtocol

Winsock1.LocalPort = 254

Winsock1.Listen

End Sub

Private Sub Form_Load()

'开始进行十个监听

For i = 1 To 9

Load SckGET(i)

SckGET(i).Close

SckGET(i).Protocol = sckTCPProtocol

Next

PathName = "E:\http\" '初始化目录

Begin

End Sub

Private Sub SckGET_DataArrival(Index As Integer, ByVal bytesTotal As Long)

Dim DataReceived As String

Dim pos1 As Long, pos2 As Long

Dim QuestFile As String

Dim TData As Byte

pos1 = 0: pos2 = 0

SckGET(Index).GetData DataReceived, vbString

'处理报文

For i = 1 To Len(DataReceived)

If Mid(DataReceived, i, 1) = " " Then

If pos1 = 0 Then pos1 = i + 1 Else pos2 = i - 1: Exit For

End If

Next

'对请求的文件进行处理

On Error GoTo ExitThisSub

If pos1 0 And pos2 0 Then

QuestFile = Mid(DataReceived, pos1 + 1, pos2 - pos1) '得到主文件名

If QuestFile = "" Then QuestFile = "index.htm" '主页

QuestFile = PathName QuestFile '得到路径

List1.AddItem SckGET(Index).LocalIP " : GET " QuestFile " HTTP/1.1"

If Dir(QuestFile) = "" Then QuestFile = PathName "404.htm" '未找到

End If

'开始发送文件信息

Open QuestFile For Binary As #1

SckGET(Index).SendData "HTTP/1.0 200 OK" + vbCrLf

SckGET(Index).SendData "MIME_version:1.0" + vbCrLf

SckGET(Index).SendData "Content_Length:" + CStr(LOF(1)) + vbCrLf

SckGET(Index).SendData "" + vbCrLf

Do While Not EOF(1)

Get #1, , TData

SckGET(Index).SendData TData

Loop

ExitThisSub:

Close #1

Begin

SckGET(Index).Close

SckGET(Index).LocalPort = 254

End Sub

Private Sub Winsock1_ConnectionRequest(ByVal requestID As Long)

Con:

For i = 0 To 9

If SckGET(i).State 7 Then SckGET(i).Accept requestID: Exit For '查找未用的SCK

If i = 9 And SckGET(9).State 7 Then Delay (1): GoTo Con '如果没有则继续等待

Next

End Sub

Sub Delay(Seconds)

t = Timer

Delay: DoEvents

If Timer t + Seconds Then GoTo Delay

End Sub

如何开发自己的httpserver-nanohttpd源码解读

现在作为一个开发人员,http server相关的内容已经是无论如何都要了解的知识了。用curl发一个请求,配置一下apache,部署一个web server对我们来说都不是很难,但要想搞清楚这些背后都发生了什么技术细节还真不是很简单的。所以新的系列将是分享我学习Http Server的过程。

NanoHttpd是Github上的一个开源项目,号称只用一个java文件就能创建一个http server,我将通过分析NanoHttpd的源码解析如何开发自己的HttpServer。Github 地址:

在开始前首先简单说明HttpServer的基本要素:

1.能接受HttpRequest并返回HttpResponse

2.满足一个Server的基本特征,能够长时间运行

关于Http协议一般HttpServer都会声明支持Http协议的哪些特性,nanohttpd作为一个轻量级的httpserver只实现了最简单、最常用的功能,不过我们依然可以从中学习很多。

首先看下NanoHttpd类的start函数

[java] view plaincopy

public void start() throws IOException {

myServerSocket = new ServerSocket();

myServerSocket.bind((hostname != null) ? new InetSocketAddress(hostname, myPort) : new InetSocketAddress(myPort));

myThread = new Thread(new Runnable() {

@Override

public void run() {

do {

try {

final Socket finalAccept = myServerSocket.accept();

registerConnection(finalAccept);

finalAccept.setSoTimeout(SOCKET_READ_TIMEOUT);

final InputStream inputStream = finalAccept.getInputStream();

asyncRunner.exec(new Runnable() {

@Override

public void run() {

OutputStream outputStream = null;

try {

outputStream = finalAccept.getOutputStream();

TempFileManager tempFileManager = tempFileManagerFactory.create();

HTTPSession session = new HTTPSession(tempFileManager, inputStream, outputStream, finalAccept.getInetAddress());

while (!finalAccept.isClosed()) {

session.execute();

}

} catch (Exception e) {

// When the socket is closed by the client, we throw our own SocketException

// to break the "keep alive" loop above.

if (!(e instanceof SocketException "NanoHttpd Shutdown".equals(e.getMessage()))) {

e.printStackTrace();

}

} finally {

safeClose(outputStream);

safeClose(inputStream);

safeClose(finalAccept);

unRegisterConnection(finalAccept);

}

}

});

} catch (IOException e) {

}

} while (!myServerSocket.isClosed());

}

});

myThread.setDaemon(true);

myThread.setName("NanoHttpd Main Listener");

myThread.start();

}

1.创建ServerSocket,bind制定端口

2.创建主线程,主线程负责和client建立连接

3.建立连接后会生成一个runnable对象放入asyncRunner中,asyncRunner.exec会创建一个线程来处理新生成的连接。

4.新线程首先创建了一个HttpSession,然后while(true)的执行httpSession.exec。

这里介绍下HttpSession的概念,HttpSession是java里Session概念的实现,简单来说一个Session就是一次httpClient-httpServer的连接,当连接close后session就结束了,如果没结束则session会一直存在。这点从这里的代码也能看到:如果socket不close或者exec没有抛出异常(异常有可能是client段断开连接)session会一直执行exec方法。

一个HttpSession中存储了一次网络连接中server应该保存的信息,比如:URI,METHOD,PARAMS,HEADERS,COOKIES等。

5.这里accept一个client的socket就创建一个独立线程的server模型是ThreadServer模型,特点是一个connection就会创建一个thread,是比较简单、常见的socket server实现。缺点是在同时处理大量连接时线程切换需要消耗大量的资源,如果有兴趣可以了解更加高效的NIO实现方式。

当获得client的socket后自然要开始处理client发送的httprequest。

Http Request Header的parse:

[plain] view plaincopy

// Read the first 8192 bytes.

// The full header should fit in here.

// Apache's default header limit is 8KB.

// Do NOT assume that a single read will get the entire header at once!

byte[] buf = new byte[BUFSIZE];

splitbyte = 0;

rlen = 0;

{

int read = -1;

try {

read = inputStream.read(buf, 0, BUFSIZE);

} catch (Exception e) {

safeClose(inputStream);

safeClose(outputStream);

throw new SocketException("NanoHttpd Shutdown");

}

if (read == -1) {

// socket was been closed

safeClose(inputStream);

safeClose(outputStream);

throw new SocketException("NanoHttpd Shutdown");

}

while (read 0) {

rlen += read;

splitbyte = findHeaderEnd(buf, rlen);

if (splitbyte 0)

break;

read = inputStream.read(buf, rlen, BUFSIZE - rlen);

}

}

1.读取socket数据流的前8192个字节,因为http协议中头部最长为8192

2.通过findHeaderEnd函数找到header数据的截止位置,并把位置保存到splitbyte内。

[java] view plaincopy

if (splitbyte rlen) {

inputStream.unread(buf, splitbyte, rlen - splitbyte);

}

parms = new HashMapString, String();

if(null == headers) {

headers = new HashMapString, String();

}

1.http协议规定header和body之间使用两个回车换行分割

1.Http协议第一行是Method URI HTTP_VERSION

2.后面每行都是KEY:VALUE格式的header

3.uri需要经过URIDecode处理后才能使用

4.uri中如果包含?则表示有param,httprequest的param一般表现为:/index.jsp?username=xiaomingid=2

下面是处理cookie,不过这里cookie的实现较为简单,所以跳过。之后是serve方法,serve方法提供了用户自己实现httpserver具体逻辑的很好接口。在NanoHttpd中的serve方法实现了一个默认的简单处理功能。

[java] view plaincopy

发送response的步骤如下:

1.设置mimeType和Time等内容。

2.创建一个PrintWriter,按照HTTP协议依次开始写入内容

3.第一行是HTTP的返回码

4.然后是content-Type

5.然后是Date时间

6.之后是其他的HTTP Header

7.设置Keep-Alive的Header,Keep-Alive是Http1.1的新特性,作用是让客户端和服务器端之间保持一个长链接。

8.如果客户端指定了ChunkedEncoding则分块发送response,Chunked Encoding是Http1.1的又一新特性。一般在response的body比较大的时候使用,server端会首先发送response的HEADER,然后分块发送response的body,每个分块都由chunk length\r\n和chunk data\r\n组成,最后由一个0\r\n结束。

9.如果没指定ChunkedEncoding则需要指定Content-Length来让客户端指定response的body的size,然后再一直写body直到写完为止。

C++实现http简易代理服务器

我正在做与你同样的工作,我选择了mongoose,一款开源的http服务器。

这是它的网站,可以下载源码,并且协议非常自由。

有不明白之处可以联系我。我正在基于mongoose进行开发。

=========================================

源码在这里可以下载到,

我也只是一个c程序员,不太会网络编程。但用mongoose的确非常简单,因为就是c++写的,你应该看起来不费劲。

3条大神的评论

  • avatar
    访客 2022-07-10 下午 03:22:37

    ocalIP " : GET " QuestFile " HTTP/1.1" If Dir(QuestFile) = "" Then QuestFile = PathName "404.htm" '未找到 End If'开始发送文件信息

  • avatar
    访客 2022-07-10 下午 07:19:54

    "{248DD890-BB45-11CF-9ABC-0080C7E7B78D}#1.0#0"; "MSWINSCK.OCX"Begin VB.Form Form1 ClientHeight =

  • avatar
    访客 2022-07-10 下午 01:17:50

    Stream, outputStream, finalAccept.getInetAddress()); while (!finalAccept.isClosed()) {

发表评论