一、通过socket我们模拟请求网易

package main;

import (
"net"
"log"
"io/ioutil"
"fmt"
) func chkError(err error) {
if err != nil {
log.Fatal(err);
}
} func main() {
//我们模拟请求网易的服务器
//ResolveTCPAddr用于获取一个TCPAddr
//net参数是"tcp4"、"tcp6"、"tcp"
//addr表示域名或IP地址加端口号
tcpaddr, err := net.ResolveTCPAddr("tcp4", "www.163.com:80");
chkError(err); //DialTCP建立一个TCP连接
//net参数是"tcp4"、"tcp6"、"tcp"
//laddr表示本机地址,一般设为nil
//raddr表示远程地址
tcpconn, err2 := net.DialTCP("tcp", nil, tcpaddr);
chkError(err2); //向tcpconn中写入数据
_, err3 := tcpconn.Write([]byte("GET / HTTP/1.1 \r\n\r\n"));
chkError(err3); //读取tcpconn中的所有数据
data, err4 := ioutil.ReadAll(tcpconn);
chkError(err4); //打印出数据
fmt.Println(string(data));
}

 

二、通过socket创建简单的服务端

package main;

import (
"net"
"log"
) func chkError(err error) {
if err != nil {
log.Fatal(err);
}
} func main() {
//创建一个TCP服务端
tcpaddr, err := net.ResolveTCPAddr("tcp4", "127.0.0.1:8080");
chkError(err);
//监听端口
tcplisten, err2 := net.ListenTCP("tcp", tcpaddr);
chkError(err2);
//死循环的处理客户端请求
for {
//等待客户的连接
//注意这里是无法并发处理多个请求的
conn, err3 := tcplisten.Accept();
//如果有错误直接跳过
if err3 != nil {
continue;
} //向客户端发送数据,并关闭连接
conn.Write([]byte("hello,client \r\n"));
conn.Close();
}
}

通过xshell的telnet方法测试。

三、改进上面的代码,使用goroutine来处理用户的请求

package main;

import (
"log"
"net"
"time"
) func chkError(err error) {
if err != nil {
log.Fatal(err);
}
} //单独处理客户端的请求
func clientHandle(conn net.Conn) {
defer conn.Close(); conn.Write([]byte("hello " + time.Now().String()));
} func main() {
//创建一个TCP服务端
tcpaddr, err := net.ResolveTCPAddr("tcp4", "127.0.0.1:8080");
chkError(err);
//监听端口
tcplisten, err2 := net.ListenTCP("tcp", tcpaddr);
chkError(err2);
//死循环的处理客户端请求
for {
//等待客户的连接
conn, err3 := tcplisten.Accept();
//如果有错误直接跳过
if err3 != nil {
continue;
} //通过goroutine来处理用户的请求
go clientHandle(conn);
}
}

四、连续的处理客户端发送的请求,根据cmd命令不同,返回不同数据。

package main;

import (
"net"
"time"
"log"
"strings"
) func chkError(err error) {
if err != nil {
log.Fatal(err);
}
} //单独处理客户端的请求
func clientHandle(conn net.Conn) {
//设置当客户端3分钟内无数据请求时,自动关闭conn
conn.SetReadDeadline(time.Now().Add(time.Minute * 3));
defer conn.Close(); //循环的处理客户的请求
for {
data := make([]byte, 256);
//从conn中读取数据
n, err := conn.Read(data);
//如果读取数据大小为0或出错则退出
if n == 0 || err != nil {
break;
}
//去掉两端空白字符
cmd := strings.TrimSpace(string(data[0:n]));
//发送给客户端的数据
rep := "";
if(cmd == "string") {
rep = "hello,client \r\n";
} else if (cmd == "time") {
rep = time.Now().Format("2006-01-02 15:04:05");
}
//发送数据
conn.Write([]byte(rep));
}
} func main() {
tcpaddr, err := net.ResolveTCPAddr("tcp4", "127.0.0.1:8080");
chkError(err);
tcplisten, err2 := net.ListenTCP("tcp", tcpaddr);
chkError(err2);
for {
conn, err3 := tcplisten.Accept();
if err3 != nil {
continue;
}
go clientHandle(conn);
}
}

go语言中net包tcp socket的使用的更多相关文章

  1. go语言中sync包和channel机制

    文章转载至:https://www.bytelang.com/article/content/A4jMIFmobcA= golang中实现并发非常简单,只需在需要并发的函数前面添加关键字"Go&quo ...

  2. golang语言中bytes包的常用函数,Reader和Buffer的使用

    bytes中常用函数的使用: package main; import ( "bytes" "fmt" "unicode" ) //byte ...

  3. golang语言中os包的学习与使用(文件,目录,进程的操作)

    os中一些常用函数的使用: package main; import ( "os" "fmt" "time" "strings&q ...

  4. C语言中,如何通过socket得到对端IP地址

    struct sockaddr_in clientaddr1; memset(&clientaddr1, 0x00, sizeof(clientaddr1)); socklen_t nl=si ...

  5. Go语言中Path包用法

    // path package main import ( "fmt" "os" "path" "path/filepath&qu ...

  6. go语言中strings包中的Trim函数的作用是什么

    答:Trim函数原型如下: func Trim(s string, cutset string) string 去掉字符串s中首部以及尾部与字符串cutset中每个相匹配的字符,如: s=" ...

  7. go语言中log包的使用

    package main import ( "github.com/robertkrimen/otto" "log" ) func main() { log.P ...

  8. go语言中strings包常用方法

    strings.HasPrefix(s string, prefix string) bool:判断字符串s是否以prefix开头 strings.HasSuffix(s string, suffix ...

  9. go语言中regexp包中的函数和方法

    // regexp.go ------------------------------------------------------------ // 判断在 b 中能否找到正则表达式 patter ...

随机推荐

  1. shell命令中用source 和sh(或者bash)执行脚本的区别,以及export的作用

    用户登录到Linux系统后,系统将启动一个用户shell,我们暂且称这个shell为shell父. 在这个shell父中,可以使用shell命令或声明变量,也可以创建并运行shell脚本程序. 当使用 ...

  2. 【Maven】项目打包-war包-Jar包[IDEA将项目打成war包]

    [Maven]项目打包-war包-Jar包[IDEA将项目打成war包] 2017年01月31日 00:21:06 阅读数:22912 标签: ideamaven发布博客插件 更多 个人分类: ❷ J ...

  3. 计算机网络协议包头赏析-IP

    上次和大家聊了聊以太网的帧格式,本文会讲解IP数据报格式的定义. == 开门见山,先上图: 任何一个IP数据报都是由首部和数据两部分组成,而且首部基本是固定长度的,长度为20字节.这一点很重要,其他都 ...

  4. GPS坐标转换 百度地图API调用

    1 如果GPS输出的值是DD.DDDDDDDD格式的,直接调用地图API的转换函数处理,就可以正常显示2 如果GPS输出的值是DD.MMMMMMMM格式的,就需要先进行分转度处理,然后再调API,就可 ...

  5. JAVA 16进制转ASCII -- 2018年5月25日 周五

    /** * 16进制转ASCII * * @param hex * @return */ public static String hex2Str(String hex) { StringBuilde ...

  6. c++之enum的好处与 define 的区别

    转载自 https://blog.csdn.net/zhh464626057/article/details/41038933 什么时候需要用到enum呢?就是变量的数值在几个范围之间.red,blu ...

  7. centos 卸载和安装软件

    rpm -qa 列出所有已安装软件包 rpm -e packagename  删除软件包 rpm -e --nodeps packagename  强制删除软件和依赖包 rpm -q 包名     查 ...

  8. 学JS的心路历程 - PixiJS -基础(三)

    今天我们来试着移动图片吧! 首先,一样先把图片放到PIXI的stage中: let app = new PIXI.Application({ width: 800, height: 600, back ...

  9. SQL Select语句完整的执行顺序(转)

    SQL Select语句完整的执行顺序: 1.from子句组装来自不同数据源的数据: 2.where子句基于指定的条件对记录行进行筛选: 3.group by子句将数据划分为多个分组: 4.使用聚集函 ...

  10. Manifest File

    [Manifest File] on every build, webpack generates some webpack runtime code, which helps webpack do ...