{"record":{"id":"174bbaf91271cdde","repo":"tailscale/tailscale","slug":"can-t-parse-expiry-time-expects-a-unix-timestamp","errorCode":null,"errorMessage":"can't parse expiry time, expects a unix timestamp","messagePattern":"can't parse expiry time, expects a unix timestamp","errorType":"http","errorClass":null,"httpStatus":400,"severity":"error","filePath":"ipn/localapi/localapi.go","lineNumber":1246,"sourceCode":"}\n\n// serveSetExpirySooner sets the expiry date on the current machine, specified\n// by an `expiry` unix timestamp as POST or query param.\nfunc (h *Handler) serveSetExpirySooner(w http.ResponseWriter, r *http.Request) {\n\tif !h.PermitWrite {\n\t\thttp.Error(w, \"access denied\", http.StatusForbidden)\n\t\treturn\n\t}\n\tif r.Method != httpm.POST {\n\t\thttp.Error(w, \"POST required\", http.StatusMethodNotAllowed)\n\t\treturn\n\t}\n\n\tvar expiryTime time.Time\n\tif v := r.FormValue(\"expiry\"); v != \"\" {\n\t\texpiryInt, err := strconv.ParseInt(v, 10, 64)\n\t\tif err != nil {\n\t\t\thttp.Error(w, \"can't parse expiry time, expects a unix timestamp\", http.StatusBadRequest)\n\t\t\treturn\n\t\t}\n\t\texpiryTime = time.Unix(expiryInt, 0)\n\t} else {\n\t\thttp.Error(w, \"missing 'expiry' parameter, a unix timestamp\", http.StatusBadRequest)\n\t\treturn\n\t}\n\terr := h.b.SetExpirySooner(r.Context(), expiryTime)\n\tif err != nil {\n\t\thttp.Error(w, err.Error(), http.StatusBadRequest)\n\t\treturn\n\t}\n\tw.Header().Set(\"Content-Type\", \"text/plain\")\n\tio.WriteString(w, \"done\\n\")\n}\n\nfunc (h *Handler) servePing(w http.ResponseWriter, r *http.Request) {\n\tctx := r.Context()","sourceCodeStart":1228,"sourceCodeEnd":1264,"githubUrl":"https://github.com/tailscale/tailscale/blob/6e0912f97994f927632b34ae9e63b53d6516a6ac/ipn/localapi/localapi.go#L1228-L1264","documentation":"Sent as 400 by serveSetExpirySooner when the 'expiry' parameter is present but not an integer Unix timestamp.","triggerScenarios":"Thrown at ipn/localapi/localapi.go:1246 when the library encounters an invalid state.","commonSituations":"See trigger scenarios.","solutions":["Pass expiry as seconds since Unix epoch (e.g. 1735689600)","Remove quotes/whitespace from the parameter","Validate client-side before sending"],"exampleFix":null,"handlingStrategy":"validation","validationCode":null,"typeGuard":null,"tryCatchPattern":null,"preventionTips":[],"tags":[],"backgroundTag":null,"analyzedSha":"6e0912f97994f927632b34ae9e63b53d6516a6ac","analyzedAt":"2026-08-18T08:17:25.280Z","contentChangedAt":"2026-08-18T08:17:25.280Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}