systemd 守护的一个使用golang 实现的tcp服务,
这个服务使用了github.com/jinzhu/gorm ,每隔一小时 服务就会被重启一次,毫无头绪,无从下手,哪位大神可指点指点,怎么排查
我现在只能用最原始,最无脑的办法 就是排除法懵,已经单独启动了一个应用,代码很干净,为了排除日志扩展可能得问题,我临时换了一个扩展,就等结果了,如果一个小时候还会重启,那我就崩塌了,我只能怀疑是systemd有问题,就换个别的守护试试
```golang
package main
import (
"fmt"
"github.com/sirupsen/logrus"
"io"
"net"
"os"
"runtime"
)
func main() {
var log = logrus.New()
log.SetFormatter(&logrus.JSONFormatter{
TimestampFormat: "2006-01-02 15:04:05",
})
log.SetOutput(os.Stdout)
file, err := os.OpenFile("logruss.log", os.O_CREATE|os.O_WRONLY|os.O_APPEND, 0666)
writers := []io.Writer{
file,
os.Stdout}
//同时写文件和屏幕
fileAndStdoutWriter := io.MultiWriter(writers...)
if err == nil {
log.SetOutput(fileAndStdoutWriter)
} else {
log.Info("Failed to log to file")
}
log.WithFields(logrus.Fields{"tips": "服务器启动连接监听", "CPU": runtime.NumCPU()}).Info("POSP")
ln, err := net.Listen("tcp", "127.0.0.1:8888")
if err != nil {
logrus.Error("服务异常", logrus.Fields{"err": err.Error()})
}
for {
conn, e := ln.Accept()
if e != nil {
if ne, ok := e.(net.Error); ok && ne.Temporary() {
logrus.Error("接受到错误信息")
continue
}
}
go goHandlerConn(conn)
}
}
func goHandlerConn(conn net.Conn) {
defer func() {
if conn != nil {
conn.Close()
}
if err := recover(); err != nil {
logrus.Error("发现异常-1")
}
return
}()
fmt.Println("我是执行的么")
}
```
#15
更多评论
在容易出错的地方要加上容错的机制,使用panic recover机制抓住错误信息就可以定位问题在哪里,然后再解决问题。
个人觉得常出错的地方有使用了nil的数据、数组越界了是最常见的,另外还有一些不容易发现的比如没有关闭链接之类的。
最好是能上源码,如果不关乎行业机密的话。
#1
panic 在日志里没有发现,有,我写个伪代码吧
```golang
func main() {
for {
conn, e := ln.Accept()
if e != nil {
if ne, ok := e.(net.Error); ok && ne.Temporary() {
logger.Init("异常").Info("接收错误信息:%v" + fmt.Sprintf("accept temp err: %v", ne))
continue
}
}
// 解析连接消息 路由模式开启
go goHandleConn(conn)
}
}
func goHandleConn(conn net.Conn) {
defer func() {
if conn != nil {
conn.Close()
}
if err := recover(); err != nil {
//获取程序名称
appExeName := os.Args[0]
pid := os.Getegid()
logger.Init("POSP中台").Error("goHandleConn:引发panic异常",
zap.Reflect("error", err),
zap.Reflect("app", appExeName),
zap.Reflect("pid", pid),
zap.Reflect("strack", string(debug.Stack())),
zap.Reflect("LogId", logId),
)
notice.NoticeMsg("goHandleConn:引发panic异常", fmt.Sprintf("LogId:%s %v:app:%v:pid:%v:strack:", logId, err, appExeName, pid, string(debug.Stack())))
}
return
}()
// todo 查询数据库 这个地方用到gorm
_, err = conn.Write(recBuf)
return
}
```
#2