{"record":{"id":"5625ea249f69beb8","repo":"larksuite/cli","slug":"busdiscover-malformed-pid-file-s","errorCode":null,"errorMessage":"busdiscover: malformed pid file %s","messagePattern":"busdiscover: malformed pid file (.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"internal/event/adapter/localbus/busdiscover/pidfile.go","lineNumber":70,"sourceCode":"\t\treturn nil, fmt.Errorf(\"busdiscover: write pid tmp: %w\", err)\n\t}\n\tif err := vfs.Rename(tmpPath, pidPath); err != nil {\n\t\t_ = vfs.Remove(tmpPath)\n\t\t_ = lock.Unlock()\n\t\treturn nil, fmt.Errorf(\"busdiscover: rename pid file: %w\", err)\n\t}\n\treturn &Handle{lock: lock}, nil\n}\n\nfunc readPIDFile(eventsDir string) (int, time.Time, error) {\n\tpidPath := filepath.Join(eventsDir, pidFileName)\n\tdata, err := vfs.ReadFile(pidPath)\n\tif err != nil {\n\t\treturn 0, time.Time{}, err\n\t}\n\tlines := strings.SplitN(strings.TrimSpace(string(data)), \"\\n\", 2)\n\tif len(lines) < 2 {\n\t\treturn 0, time.Time{}, fmt.Errorf(\"busdiscover: malformed pid file %s\", pidPath)\n\t}\n\tpid, err := strconv.Atoi(strings.TrimSpace(lines[0]))\n\tif err != nil {\n\t\treturn 0, time.Time{}, fmt.Errorf(\"busdiscover: malformed pid in %s: %w\", pidPath, err)\n\t}\n\tstartTime, err := time.Parse(time.RFC3339, strings.TrimSpace(lines[1]))\n\tif err != nil {\n\t\treturn 0, time.Time{}, fmt.Errorf(\"busdiscover: malformed timestamp in %s: %w\", pidPath, err)\n\t}\n\treturn pid, startTime, nil\n}\n\n// isBusAlive: try-lock the alive file. ErrHeld = live holder; success = stale (release immediately).\nfunc isBusAlive(appDir string) bool {\n\tlockPath := filepath.Join(appDir, aliveLockFileName)\n\tif _, err := vfs.Stat(lockPath); err != nil {\n\t\treturn false\n\t}","sourceCodeStart":52,"sourceCodeEnd":88,"githubUrl":"https://github.com/larksuite/cli/blob/7fd6ef3c07182257ce776cdc5a614e122d5bd4b3/internal/event/adapter/localbus/busdiscover/pidfile.go#L52-L88","documentation":"readPIDFile throws this when the bus.pid file exists but does not contain the expected two-line payload (PID line + RFC3339 timestamp line). The scanner (scanLiveBuses via isBusAlive) treats the bus as live but logs this diagnostic and reports the process with PID 0, so it is a data-integrity signal rather than a fatal failure.","triggerScenarios":"A live-lock-holding app directory contains a bus.pid whose trimmed content has fewer than two newline-separated lines — e.g. empty file, single-line file, or a file truncated/corrupted by a crash between creation and the atomic rename of an older writer.","commonSituations":"Manual edits or truncation of bus.pid, a crash or kill before any successful rename completed, disk corruption, or a third-party tool rewriting the file in an unexpected format.","solutions":["Delete the corrupt bus.pid and restart the bus process so WritePIDFile republishes a valid file (the alive lock still proves liveness)","Check file content with cat bus.pid — expect '<pid>\\n<RFC3339 timestamp>' and fix if manually edited","If the owning bus process is dead, remove the whole stale app dir; the try-lock probe will then report it not alive","If this recurs, check for disk corruption or tools that rewrite files non-atomically in the state dir"],"exampleFix":"// before: truncated pid file -> live bus reported with PID 0\n$ cat ~/.larkcli/events/<appID>/bus.pid\n1234\n// after: delete and let the bus republish\n$ rm ~/.larkcli/events/<appID>/bus.pid && restart the bus process\n$ cat ~/.larkcli/events/<appID>/bus.pid\n1234\n2026-09-04T08:00:00Z","handlingStrategy":"fallback","validationCode":null,"typeGuard":"// Treat PID 0 as 'liveness known, pid unknown' when consuming scan results\nfunc hasUsablePID(p busdiscover.Process) bool { return p.PID > 0 }\n\n// Validate a pid file's shape before relying on it\nfunc pidFileLooksValid(path string) bool {\n    data, err := os.ReadFile(path)\n    if err != nil { return false }\n    lines := strings.SplitN(strings.TrimSpace(string(data)), \"\\n\", 2)\n    if len(lines) < 2 { return false }\n    if _, err := strconv.Atoi(strings.TrimSpace(lines[0])); err != nil { return false }\n    _, err = time.Parse(time.RFC3339, strings.TrimSpace(lines[1]))\n    return err == nil\n}","tryCatchPattern":"procs, err := scanLiveBuses(eventsDir) // readPIDFile failure is logged, not returned\nfor _, p := range procs {\n    if p.PID == 0 {\n        // live lock held but pid file unreadable: cannot signal; treat as unmanaged live bus\n        continue\n    }\n    // safe to signal p.PID\n}","preventionTips":["Do not hand-edit bus.pid; let WritePIDFile publish it atomically","Kill -9 of the bus can leave truncated files — prefer graceful shutdown","Periodically clean stale app directories whose alive lock is no longer held","Treat PID 0 in scan results as a data-integrity warning worth alerting on"],"tags":["go","pidfile","corrupt-file","localbus","discovery"],"backgroundTag":"corrupt-pid-file","analyzedSha":"7fd6ef3c07182257ce776cdc5a614e122d5bd4b3","analyzedAt":"2026-09-04T21:17:44.649Z","contentChangedAt":"2026-09-04T21:17:44.649Z","schemaVersion":2},"datasetVersion":"2026-09-12T02:17:10.037Z"}