网络 HTTP协议

Tip1:HTTP简介
1.定义:超文本传输协议(HyperText Transfer Protocol)是互联网上应用最为广泛的一种网络协议。所有WWW文件都必须遵守这个标准。基于TCP/IP协议。
2.特点
(1)支持客户/服务器模式
(2)简单快速:只需要传输请求方法和路径。
(3)灵活:HTTP允许传输任意类型的数据对象。
(4)无连接:限制每次连接只处理一个请求。
(5)无状态:对于事物处理没有记忆能力。
(6) 分段传输数据
3.使用步骤
(1)客户机与服务器建立连接。
(2)建立连接后,客户机发送一个请求给服务器。
(3)服务器接到请求后,给予相应的响应信息。
(4)客户端接收到服务器所返回的信息后通过浏览器显示在用户的显示器上。断开连接。

4.HTTP的请求响应模型
HTTP协议永远都是客户端发起请求,服务器回送响应。当需要服务器主动发送时属于后台推送,不属于HTTP协议内容。
page7image14384
5.重要概念
(1)Connection 连接
(2)Message 消息 :HTTP通信的基本单位。
(3)Request 请求 :(客户端—>服务器)请求信息包括应用于资源的方法、资源的标识符和协议的版本号。
(4)Response 响应:(服务器—>客户端) 返回的信息包括HTTP协议的版本号、请求的状态和文档的MIME类型。
(5)Resource 资源: 由URI标识的网络数据对象或者服务。
(6) Entity  实体:一个实体包括实体头信息和实体本身内容。
   (7)   Client  客户机
   (8)   UserAgent  用户代理: 浏览器、编辑器或者其他用户工具。
   (9)   Server 服务器: 一个接受连接并对请求返回信息的应用程序。
(10) Originserver 源服务器:一个给定资源可以在其上驻留或被创建的。
(11) Proxy 代理:一个中间程序,它可以充当一个服务器也可以充当一个客户机,为其它客户机建立请求。
(12) GateWay 网关
(13)Tunnel通道:是作为两个连接中继的中介程序。一旦激活,通道便被认为不属于HTTP通讯,尽管通道可能是被一个HTTP请求初始化的。当被中继的连接两端关闭时,通道消失。
(14)Cache 缓存:反应信息的局域存储。
其他: 门户(Portal)、中介(Intermediary)
Tip2:HTTP请求详解
1.组成
请求行、请求头、请求正文
2.请求方式 
(1)POST 向指定资源提交数据进行处理请求,数据被包含在请求体中。
(2)GET 向指定的资源发出请求。
url 包括地址和端口号(若没有值默认为80)
接收到的数据都是成段的,需要拼接起来。

int serviceSocketId;

int clientSocketId;

+(void)serviceSocketWithPort:(int)port blockStr:(MyBlock)block{
    
       //获取一个全局队列(任务调度队列--火车站) gcd
    dispatch_queue_t globle = dispatch_get_global_queue(0, 0);
    //添加任务队列
    dispatch_async(globle, ^{
        
        //1.创建socket
        
       serviceSocketId = socket(AF_INET, SOCK_STREAM, 0);
        
        if (!serviceSocketId) {
            
            return ;
        }
        struct sockaddr_in addr;
        
        memset(&addr, 0, sizeof(addr));
        
        addr.sin_family = AF_INET;
        
        addr.sin_port = htons(port);
        
        addr.sin_addr.s_addr = htonl(INADDR_ANY);
        
     int bindId = bind(serviceSocketId, (struct sockaddr *)&addr,
             sizeof(addr));
        
        if (bindId == -1) {
            
            NSLog(@"bind error");
        }
        //3.监听
        
        int listenId = listen(serviceSocketId, 10);
        
        if (listenId == -1) {
            
            NSLog(@"listen error");
        }
//accept停留在这里,等待客户端呼入:首次走一遍,以后每次想发送内容还要走
        while (1) {
            
            int acceptId =  accept(serviceSocketId, NULL, NULL);
            //接收失败是0
            if (!acceptId) {
                
                NSLog(@"accept error");
                //出错时跳出本次循环
                continue;
            }
            //创建数据容器
            char *str = malloc(1000);
            
            
            long recvId = recv(acceptId, str, 1000, 0);
            
            if (recvId == -1) {
                
                NSLog(@"recv error");
            }
            
            //将C字符串转换成OC字符串
            
            NSString *blockStr = [NSString stringWithCString:str encoding:NSUTF8StringEncoding];
            
            //回掉字符串- MyBlock
            block(blockStr);
            
            close(acceptId);

        }
        
    });
    
  }
//客户端
+(void)clientSocketWithPort:(int)port IP:(NSString *)ip msg:(NSString *)msg{

    dispatch_queue_t  globle = dispatch_get_global_queue(0, 0);
    
    dispatch_async(globle, ^{
        //1.创建socket
        
        clientSocketId = socket(AF_INET, SOCK_STREAM, 0);
        
        NSLog(@"clientSocketId:%d",clientSocketId);
        
        if (!clientSocketId) {
            
            return ;
        }
        //2.链接服务器
        
        struct sockaddr_in addr;
        
        memset(&addr, 0, sizeof(addr));
        
        addr.sin_family = AF_INET;
        
        addr.sin_port = htons(port);
        
        const char *cIP = [ip UTF8String];
        
        inet_pton(AF_INET, cIP, &addr.sin_addr);
        
      int  connectId = connect(clientSocketId,(struct sockaddr *) &addr, sizeof(addr));
        
        if (connectId == -1) {
            
            NSLog(@"connect error");
        }
        const char *str = [msg UTF8String];
        
       send(clientSocketId, str, strlen(str), 0);
        
        //接受服务器返回的数据--根据recv返回值判断(-1:出错,0:传输完成,>0 还有内容)
        //创建一个可变字符串 接收传输数据
        NSMutableString *string = [NSMutableString string];
        
        BOOL isOk;
        
        while (!isOk ) {
            
            char *recvStr = malloc(5000);
            
            long recvId = recv(clientSocketId, recvStr, 5000, 0);
            [string appendFormat:@"%s",recvStr];
            if (recvId == 0) {
                
                isOk = YES;
            }

        }
        
        NSLog(@"recvStr is :%@",string);
        close(clientSocketId);
    });
}
+(void)parseWithUrl:(NSURL *)url{

//获取host(要素一)
    NSString *host = url.host;
//获取端口号(要素二)
    NSNumber *port = url.port;
//解析域名
  struct hostent *hostName = gethostbyname([host UTF8String]);
    
//转化地址链表
    struct in_addr **addrList = (struct in_addr**)hostName->h_addr_list;
    
    for (int i = 0; addrList[i] != NULL; i++) {
        
        NSLog(@"IP is :%s",inet_ntoa(*addrList[i]));
        
    }
    //获取IP地址
    
   NSString *ip =  [NSString stringWithCString:inet_ntoa(*addrList[0]) encoding:NSUTF8StringEncoding];
    
    if (!port) {
        
        port = @80;
    }
    //请求信息(要素三)
    NSString *msg = [SocketManager getMsg:url];
    
    //创建客户端发送请求
    [SocketManager clientSocketWithPort:[port intValue] IP:ip msg:msg];
    
  }

//拼接请求信息
+(NSString *)getMsg:(NSURL *)url
{
    //拼接请求信息   \r\n == 换行
    NSString *sendMsg = [NSString stringWithFormat:@"GET %@ HTTP/1.1\r\n",url.path];
    
    sendMsg = [sendMsg stringByAppendingFormat:@"Host: %@\r\n",url.host];
    
    sendMsg =[sendMsg stringByAppendingString:@"Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n\r\n"];
    
    sendMsg =[sendMsg stringByAppendingString:@"Content-Encoding: utf-8\r\n"];
    sendMsg =[sendMsg stringByAppendingString:@"User-Agent: Mozilla/5.0 (Windows NT 6.1; rv:25.0) Gecko/20100101 Firefox/25.0\r\n"];
    sendMsg =[sendMsg stringByAppendingString:@"Connection: close\r\n"];
    
    return sendMsg;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值