github.com/zhongdalu/gf@v1.0.0/g/net/gtcp/gtcp_func.go (about)

     1  // Copyright 2017 gf Author(https://github.com/zhongdalu/gf). All Rights Reserved.
     2  //
     3  // This Source Code Form is subject to the terms of the MIT License.
     4  // If a copy of the MIT was not distributed with this file,
     5  // You can obtain one at https://github.com/zhongdalu/gf.
     6  
     7  package gtcp
     8  
     9  import (
    10  	"crypto/rand"
    11  	"crypto/tls"
    12  	"github.com/zhongdalu/gf/g/os/gfile"
    13  	"net"
    14  	"time"
    15  )
    16  
    17  const (
    18  	gDEFAULT_RETRY_INTERVAL   = 100 // (毫秒)默认重试时间间隔
    19  	gDEFAULT_READ_BUFFER_SIZE = 128 // (byte)默认数据读取缓冲区大小
    20  )
    21  
    22  type Retry struct {
    23  	Count    int // 重试次数
    24  	Interval int // 重试间隔(毫秒)
    25  }
    26  
    27  // Deprecated.
    28  // 常见的二进制数据校验方式,生成校验结果
    29  func Checksum(buffer []byte) uint32 {
    30  	var checksum uint32
    31  	for _, b := range buffer {
    32  		checksum += uint32(b)
    33  	}
    34  	return checksum
    35  }
    36  
    37  // 创建原生TCP链接, addr地址格式形如:127.0.0.1:80
    38  func NewNetConn(addr string, timeout ...int) (net.Conn, error) {
    39  	if len(timeout) > 0 {
    40  		return net.DialTimeout("tcp", addr, time.Duration(timeout[0])*time.Millisecond)
    41  	} else {
    42  		return net.Dial("tcp", addr)
    43  	}
    44  }
    45  
    46  // 创建支持TLS的原生TCP链接, addr地址格式形如:127.0.0.1:80
    47  func NewNetConnTLS(addr string, tlsConfig *tls.Config) (net.Conn, error) {
    48  	return tls.Dial("tcp", addr, tlsConfig)
    49  }
    50  
    51  // 根据给定的证书和密钥文件创建支持TLS的原生TCP链接, addr地址格式形如:127.0.0.1:80
    52  func NewNetConnKeyCrt(addr, crtFile, keyFile string) (net.Conn, error) {
    53  	tlsConfig, err := LoadKeyCrt(crtFile, keyFile)
    54  	if err != nil {
    55  		return nil, err
    56  	}
    57  	return NewNetConnTLS(addr, tlsConfig)
    58  }
    59  
    60  // (面向短链接)发送数据
    61  func Send(addr string, data []byte, retry ...Retry) error {
    62  	conn, err := NewConn(addr)
    63  	if err != nil {
    64  		return err
    65  	}
    66  	defer conn.Close()
    67  	return conn.Send(data, retry...)
    68  }
    69  
    70  // (面向短链接)发送数据并等待接收返回数据
    71  func SendRecv(addr string, data []byte, receive int, retry ...Retry) ([]byte, error) {
    72  	conn, err := NewConn(addr)
    73  	if err != nil {
    74  		return nil, err
    75  	}
    76  	defer conn.Close()
    77  	return conn.SendRecv(data, receive, retry...)
    78  }
    79  
    80  // (面向短链接)带超时时间的数据发送
    81  func SendWithTimeout(addr string, data []byte, timeout time.Duration, retry ...Retry) error {
    82  	conn, err := NewConn(addr)
    83  	if err != nil {
    84  		return err
    85  	}
    86  	defer conn.Close()
    87  	return conn.SendWithTimeout(data, timeout, retry...)
    88  }
    89  
    90  // (面向短链接)发送数据并等待接收返回数据(带返回超时等待时间)
    91  func SendRecvWithTimeout(addr string, data []byte, receive int, timeout time.Duration, retry ...Retry) ([]byte, error) {
    92  	conn, err := NewConn(addr)
    93  	if err != nil {
    94  		return nil, err
    95  	}
    96  	defer conn.Close()
    97  	return conn.SendRecvWithTimeout(data, receive, timeout, retry...)
    98  }
    99  
   100  // 判断是否是超时错误
   101  func isTimeout(err error) bool {
   102  	if err == nil {
   103  		return false
   104  	}
   105  	if netErr, ok := err.(net.Error); ok && netErr.Timeout() {
   106  		return true
   107  	}
   108  	return false
   109  }
   110  
   111  // 根据证书和密钥生成TLS对象
   112  func LoadKeyCrt(crtFile, keyFile string) (*tls.Config, error) {
   113  	crtPath, err := gfile.Search(crtFile)
   114  	if err != nil {
   115  		return nil, err
   116  	}
   117  	keyPath, err := gfile.Search(keyFile)
   118  	if err != nil {
   119  		return nil, err
   120  	}
   121  	crt, err := tls.LoadX509KeyPair(crtPath, keyPath)
   122  	if err != nil {
   123  		return nil, err
   124  	}
   125  	tlsConfig := &tls.Config{}
   126  	tlsConfig.Certificates = []tls.Certificate{crt}
   127  	tlsConfig.Time = time.Now
   128  	tlsConfig.Rand = rand.Reader
   129  	return tlsConfig, nil
   130  }