webrtc远程控制系统源码学习笔记(一)
1. http.go
port := flag.Int("port", 8080, "http server port")
flag.Parse()
通过flag.Int() ,String(),等flag.Xxx()方法,该种方式返回一个相应的指针,参数有三个:第一个为参数名称,第二个为默认值,第三个是说明。
调用flag.Parse()可以解析命令行。
sdpChan := make(chan string)
在此系统中涉及到主线程和子线程,在golang中程序会优先执行主线程,主线程执行完成后,程序会立即退出。如果在程序的最后没有让主线程休眠,那程序就不会有足够的时间去执行子线程。
而在线程之间的信息传递的一种办法就是通道(channel)。
//创建无缓冲channel
ch :=make(chan int)//创建读写channel
ch := make(<-chan int) //创建只读channel
ch := make(chan<- int) //创建只写channel
//创建有一个缓冲的channel
ch :=make(chan int,1)
http.HandleFunc 是http.server server对象 里的handler;用户访问后,触发的一个处理函数。
HandleFunc 的第一个参数指的是请求路径,第二个参数是一个函数类型,表示这个请求需要处理的事情。
http.HandleFunc("/sdp", func(w
http.ResponseWriter, r *http.Request) {
body, _ := ioutil.ReadAll(r.Body)
fmt.Fprintf(w, "done")
sdpChan <- string(body)
})
此处,这段代码的作用是当服务端将SDP发送给设备端时,设备端接受,并放入管道,以便其他线程使用。
结合图:
由于sdpChan是无缓冲的channel,需要等待接收方准备好才可以,否则一直阻塞。所以程序会执行子线程,就是下面的代码,将8080作为监听端口。
go func() {
err := http.ListenAndServe(":"+strconv.Itoa(*port), nil)//将8080作为监听端口
if err != nil {
panic(err)//一种异常处理
}
}()
http.go 主要的功能就是将8080作为监听端口,并接受来自服务端传来的SDP,并通过channel传递。
2.rand.go
func RandSeq(n int) string {
r := rand.New(rand.NewSource(time.Now().UnixNano()))
letters := []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ")
b := make([]rune, n)
for i := range b {
b[i] = letters[r.Intn(len(letters))]
}
return string(b)
}
这部分代码的主要功能是生成一个随机字符串作为伪数据.
rand.NewSource(time.Now().UnixNano())设置随机数种子,可以保证每次随机都是随机的.
rune是一种数据类型,可以通过此类型获得真实的字符串长度而不是其所占用字节数。通过rune()可以转化为rune类型。
3. signal.go
func MustReadStdin() string {
r := bufio.NewReader(os.Stdin)
var in string
for {
var err error
in, err = r.ReadString('\n')
if err != io.EOF {
if err != nil {
panic(err)
}
}
in = strings.TrimSpace(in)
//直到读取了标准输入跳出循环
if len(in) > 0 {
break
}
}
fmt.Println("")
return in
}
bufio 包实现了带缓存的 I/O 操作, 它封装一个 io.Reader 或 io.Writer 对象,使其具有缓存和一些文本读写功能.
bufio.NewReader()将 os.Stdin 封装成一个拥有4096 B 大小缓存的 bufio.Reader 对象.
r.ReadString(’\n’)读行,并返回一个字符串。
strings.TrimSpace(in)去除两端的空格。
此函数的功能是 直到从stdin接收到输入,否则一直阻塞,返回读取的字符串。
func Encode(obj interface{}) string {
b, err := json.Marshal(obj) //将obj编码成json格式
if err != nil {
panic(err)
}
//如果没有压缩,则在将json格式的字符压缩
//使得应答绕过终端输入的限制
if compress {
b = zip(b)
}
return base64.StdEncoding.EncodeToString(b)
}
此函数的功能是将数据编码,并通过压缩使得可以绕过终端的输入限制,返回base64数据。
func Decode(in string, obj interface{})函数同理,如果数据是压缩的则先进行解压,然后在解码。
func zip(in []byte) []byte {
var b bytes.Buffer
gz := gzip.NewWriter(&b)
_, err := gz.Write(in)
if err != nil {
panic(err)
}
err = gz.Flush()
if err != nil {
panic(err)
}
err = gz.Close()
if err != nil {
panic(err)
}
return b.Bytes()
}
func zip(in []byte) []byte,func unzip(in []byte) []byte 是压缩和解压函数。
其中gzip.NewWriter(&b)是创建空的zip档案。
gz.Write(in)是将in写入到zip档案中,即b中。
gz.Flush()是刷新内部缓冲区。