Server.go
package main
import (
"fmt"
"net"
"time"
)
func main() {
listener, err := net.ListenUDP("udp", &net.UDPAddr{Port: 9527})
if err != nil {
fmt.Println("服务器启动时发生错误", err)
return
}
fmt.Println("服务器启动成功")
defer listener.Close()
//用来存储连接至服务器的节点信息
peers := make([]*net.UDPAddr, 2,2)
buf := make([]byte,256)//存储客户端发送至本服务器的信息
n,addr,err := listener.ReadFromUDP(buf)
if err !=nil {
fmt.Println("读取客户端信息时发生错误",err )
return }
fmt.Printf("Read From > %s.Msg: %s\n",addr.String(),buf[:n])
//提取客户端地址信息
peers[0] = addr
n,addr,err =listener.ReadFromUDP(buf)
peers[1]=addr
//分别向其他节点介绍对应的节点信息
listener.WriteToUDP([]byte(peers[0].String()),peers[1])
listener.WriteToUDP([]byte(peers[1].String()),peers[0])
time.Sleep(time.Second * 10)
}
client.go
package main
import (
"bufio"
"fmt"
"net"
"os"
"strconv"
"strings"
)
//程序执行时必须指定相关的参数
//go run client.go 客户端标识名称 服务器IP 服务器端口号 本节点监听端口号
func main() {
if len(os.Args)<5 {
fmt.Println("参数不正确")
return }
name := os.Args[1] //客户端标识名称
remoteIP := os.Args[2]// 链接的目标ip
remotePort,_ :=strconv.Atoi(os.Args[3])//链接的目标Port
port,_ := strconv.Atoi(os.Args[4])//本节点监听端口号
localAddr := net.UDPAddr{Port:port}
//与服务器进行链接
conn, err := net.DialUDP("udp",&localAddr,&net.UDPAddr{IP:net.ParseIP(remoteIP),Port:remotePort})
if err != nil {
fmt.Println("链接指定节点时发生错去")
return }
conn.Write([]byte("这是"+name+"链接的"))
//读取服务器返回的消息
buf :=make([]byte,256)
n, _, err := conn.ReadFromUDP(buf)
if err!= nil {
fmt.Println("读取接受的消息时发生错误",err )
return }
conn.Close()
//解析接收到的UDPAddress信息
toAddr := parseAddress(string(buf[:n]))
fmt.Println("获取到的节点信息",toAddr)
p2pRS(&localAddr,&toAddr)}
func parseAddress(addr string) net.UDPAddr {
ss := strings.Split(addr, ":")
port,_ :=strconv.Atoi(ss[1])
ip := net.ParseIP(ss[0])
return net.UDPAddr{IP:ip,Port:port}}
func p2pRS(srcAddr *net.UDPAddr, dstAddr *net.UDPAddr) {
//srcAddr :=
conn, err :=net.DialUDP("udp",srcAddr,dstAddr)
if err !=nil {
fmt.Println("节点之间的交互发生错误",err)
return
}
conn.Write([]byte("检测消息"))
//启动携程
//接受消息
go func() {
buf:=make([]byte,256)
for{
n, _, _:=conn.ReadFromUDP(buf)
if n>0 {
fmt.Printf("接收到的信息:%s", buf[:n])
}}}()
//发消息
reader :=bufio.NewReader(os.Stdin)//监控标准输入
for{
fmt.Printf("p2p>")
data,_:=reader.ReadString('\n')
conn.Write([]byte(data))
}}