()
| 109 | } |
| 110 | |
| 111 | func main() { |
| 112 | socketPath := flag.String("socket", "/var/run/memlogdq.sock", "memlogd log query socket") |
| 113 | logDir := flag.String("log-dir", "/var/log", "Directory containing log files") |
| 114 | maxLogFiles := flag.Int("max-log-files", 10, "Maximum number of rotated log files before deletion") |
| 115 | maxLogSize := flag.Int("max-log-size", mb, "Maximum size of a log file before rotation") |
| 116 | flag.Parse() |
| 117 | |
| 118 | addr := net.UnixAddr{ |
| 119 | Name: *socketPath, |
| 120 | Net: "unix", |
| 121 | } |
| 122 | conn, err := net.DialUnix("unix", nil, &addr) |
| 123 | if err != nil { |
| 124 | log.Fatal(err) |
| 125 | } |
| 126 | defer conn.Close() |
| 127 | |
| 128 | n, err := conn.Write([]byte{logDumpFollow}) |
| 129 | if err != nil || n < 1 { |
| 130 | log.Fatalf("Failed to write request to memlogd socket: %v", err) |
| 131 | } |
| 132 | |
| 133 | // map of service name to active log file |
| 134 | logs := make(map[string]*LogFile) |
| 135 | |
| 136 | var msg LogMessage |
| 137 | decoder := json.NewDecoder(conn) |
| 138 | for { |
| 139 | if err := decoder.Decode(&msg); err != nil { |
| 140 | log.Println(err) |
| 141 | continue |
| 142 | } |
| 143 | if strings.HasPrefix(msg.Source, "logwrite") { |
| 144 | // don't log our own output in a loop |
| 145 | continue |
| 146 | } |
| 147 | |
| 148 | var logF *LogFile |
| 149 | var ok bool |
| 150 | if logF, ok = logs[msg.Source]; !ok { |
| 151 | logF, err = NewLogFile(*logDir, msg.Source) |
| 152 | if err != nil { |
| 153 | log.Printf("Failed to create log file %s: %v", msg.Source, err) |
| 154 | continue |
| 155 | } |
| 156 | logs[msg.Source] = logF |
| 157 | } |
| 158 | if err = logF.Write(&msg); err != nil { |
| 159 | log.Printf("Failed to write to log file %s: %v", msg.Source, err) |
| 160 | if err := logF.Close(); err != nil { |
| 161 | log.Printf("Failed to close log file %s: %v", msg.Source, err) |
| 162 | } |
| 163 | delete(logs, msg.Source) |
| 164 | continue |
| 165 | } |
| 166 | if logF.BytesWritten > *maxLogSize { |
| 167 | logF.Rotate(*maxLogFiles) |
| 168 | } |
nothing calls this directly
no test coverage detected