package rigger import ( "bufio" "fmt" "net/http" "os" "strings" "ciyon/web/admin" c "ciyon/zciyon" ) func Logfile_init(w http.ResponseWriter, r *http.Request) bool { post := c.NewCiyPost(w, r) _, userid := admin.Verifyfast(r, c.CiyDB, post) if userid == 0 { return false } logfiles := []string{} if c.Log.Filename != "" { logfiles = append(logfiles, c.Log.Filename) } ret := map[string]any{} ret["logfiles"] = logfiles return c.SuccJSON(w, r, ret) } func Logfile_viewlog(w http.ResponseWriter, r *http.Request) bool { if !c.SSEInit(w) { w.Write([]byte("不支持SSE Flush")) return false } post := c.NewCiyPost(w, r) _, err := admin.Verifyuser(r, c.CiyDB, post) if err != nil { c.SSESend_event(w, "请重新登录") return false } param := post.Get("param") buf, fsize, err := readfile(param, -102400) if err != nil { c.SSESend_event(w, err.Error()) return false } c.SSESend_event(w, param+", Size:"+c.Tostr(fsize)) lines := strings.Split(string(buf), "\n") for _, line := range lines { c.SSESend_data(w, line) } for { buf, fsize, err = readfile(param, fsize) if err != nil { c.SSESend_event(w, err.Error()) return false } if !c.SSESend_event(w, param+", Size:"+c.Tostr(fsize)) { return true } if buf == nil { c.Sleep(1) } else { lines := strings.Split(string(buf), "\n") for _, line := range lines { if !c.SSESend_data(w, line) { return true } } } } // w.WriteHeader(http.StatusOK) // ctx := r.Context() // done := ctx.Done() // // 捕捉信号以优雅地关闭连接 // ticker := time.NewTicker(time.Second) // 每5秒发送一次消息 // defer ticker.Stop() // // 创建一个缓冲区 // bw := bufio.NewWriter(w) // for { // select { // case <-done: // fmt.Println("Client disconnected or request was canceled.") // return false // case <-ticker.C: // fmt.Fprintf(bw, "data: %s\n\n", time.Now().Format(time.RFC3339)) // if err := bw.Flush(); err != nil { // fmt.Fprintf(os.Stderr, "Flush error: %v\n", err) // return false // } // flusher.Flush() // } // } } func readfile(filename string, seek int) ([]byte, int, error) { f, err := os.OpenFile(filename, os.O_RDONLY, 0640) if err != nil { return nil, 0, fmt.Errorf("open file %s err:%v", filename, err) } defer f.Close() stat, err := f.Stat() if err != nil { return nil, 0, fmt.Errorf("stat file %s err:%v", filename, err) } fileSize := int(stat.Size()) if fileSize == seek { return nil, fileSize, nil } bytesToRead := seek var offset int if bytesToRead < 0 { bytesToRead = -bytesToRead if bytesToRead > fileSize { bytesToRead = fileSize } offset = fileSize - bytesToRead } else { bytesToRead = fileSize - seek offset = seek } reader := bufio.NewReader(f) if offset > 0 { _, err = reader.Discard(offset) if err != nil { return nil, fileSize, fmt.Errorf("discard file %s err:%v", filename, err) } } buffer := make([]byte, bytesToRead) _, err = reader.Read(buffer) if err != nil { return nil, fileSize, fmt.Errorf("read file %s err:%v", filename, err) } return buffer, fileSize, nil }