@nessielabs/daemon 0.1.0 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -2
- package/dist/auth/deviceFlow.js +3 -2
- package/dist/auth/tokens.js +2 -1
- package/dist/cli.js +9 -5
- package/dist/commands/service.js +41 -2
- package/dist/commands/setup.js +48 -13
- package/dist/config/endpoints.js +2 -0
- package/dist/config/paths.js +2 -0
- package/dist/config/store.js +1 -4
- package/dist/service/process.js +134 -0
- package/dist/sync/client.js +12 -2
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -11,10 +11,11 @@ nessie-daemon setup
|
|
|
11
11
|
|
|
12
12
|
`setup` authenticates the device, detects local Codex and Claude Code history directories, lets you choose which sources to ingest, and can install the user `systemd` service.
|
|
13
13
|
|
|
14
|
-
|
|
14
|
+
For non-interactive headless setup, pass a Nessie API key:
|
|
15
15
|
|
|
16
16
|
```bash
|
|
17
|
-
nessie-daemon setup --api-
|
|
17
|
+
nessie-daemon setup --api-key "$NESSIE_API_KEY"
|
|
18
|
+
nessie-daemon start
|
|
18
19
|
```
|
|
19
20
|
|
|
20
21
|
## Commands
|
package/dist/auth/deviceFlow.js
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
import { setTimeout as sleep } from "node:timers/promises";
|
|
2
2
|
import { postJson } from "../api/http.js";
|
|
3
|
+
import { authApiUrl } from "../config/endpoints.js";
|
|
3
4
|
export async function runDeviceAuth(input) {
|
|
4
5
|
const log = input.log ?? console;
|
|
5
6
|
const fetchImpl = input.fetchImpl ?? fetch;
|
|
6
7
|
const sleepMs = input.sleepMs ?? sleep;
|
|
7
|
-
const start = await postJson(
|
|
8
|
+
const start = await postJson(authApiUrl, "/auth/device/start", {
|
|
8
9
|
device_name: input.deviceName,
|
|
9
10
|
platform: "linux",
|
|
10
11
|
}, { fetchImpl });
|
|
@@ -13,7 +14,7 @@ export async function runDeviceAuth(input) {
|
|
|
13
14
|
const expiresAt = Date.now() + Math.max(60, start.expires_in ?? 600) * 1000;
|
|
14
15
|
while (Date.now() < expiresAt) {
|
|
15
16
|
await sleepMs(intervalMs);
|
|
16
|
-
const poll = await postJson(
|
|
17
|
+
const poll = await postJson(authApiUrl, "/auth/device/poll", {
|
|
17
18
|
device_code: start.device_code,
|
|
18
19
|
}, { fetchImpl });
|
|
19
20
|
if (poll.status === "pending")
|
package/dist/auth/tokens.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { ApiError, postJson } from "../api/http.js";
|
|
2
|
+
import { authApiUrl } from "../config/endpoints.js";
|
|
2
3
|
export class AuthRefreshError extends Error {
|
|
3
4
|
}
|
|
4
5
|
export async function refreshAccessToken(config, options = {}) {
|
|
@@ -6,7 +7,7 @@ export async function refreshAccessToken(config, options = {}) {
|
|
|
6
7
|
throw new AuthRefreshError("Access token expired and no refresh token is configured.");
|
|
7
8
|
}
|
|
8
9
|
try {
|
|
9
|
-
const response = await postJson(
|
|
10
|
+
const response = await postJson(authApiUrl, "/auth/refresh", {
|
|
10
11
|
refresh_token: config.refreshToken,
|
|
11
12
|
}, { fetchImpl: options.fetchImpl });
|
|
12
13
|
if (!response.access_token) {
|
package/dist/cli.js
CHANGED
|
@@ -7,12 +7,11 @@ const program = new Command();
|
|
|
7
7
|
program
|
|
8
8
|
.name("nessie-daemon")
|
|
9
9
|
.description("Headless Nessie ingestion daemon for Linux agent machines.")
|
|
10
|
-
.version("0.1
|
|
10
|
+
.version("0.2.1");
|
|
11
11
|
program
|
|
12
12
|
.command("setup")
|
|
13
13
|
.description("Authenticate, select local sources, and optionally install the user systemd service.")
|
|
14
|
-
.option("--api-
|
|
15
|
-
.option("--auth-api-url <url>", "Nessie auth API URL")
|
|
14
|
+
.option("--api-key <key>", "Use a Nessie API key for non-interactive headless setup.")
|
|
16
15
|
.action(runSetup);
|
|
17
16
|
program
|
|
18
17
|
.command("run")
|
|
@@ -20,10 +19,15 @@ program
|
|
|
20
19
|
.option("--once", "Run one sync pass and exit.")
|
|
21
20
|
.option("--interval-seconds <seconds>", "Seconds between sync passes.", "60")
|
|
22
21
|
.action(runDaemon);
|
|
23
|
-
|
|
22
|
+
program
|
|
23
|
+
.command("start")
|
|
24
|
+
.description("Start the daemon.")
|
|
25
|
+
.option("--background", "Start as a detached background process without systemd.")
|
|
26
|
+
.action((options) => runServiceCommand("start", options));
|
|
27
|
+
for (const commandName of ["stop", "status"]) {
|
|
24
28
|
program
|
|
25
29
|
.command(commandName)
|
|
26
|
-
.description(`${commandName[0]?.toUpperCase()}${commandName.slice(1)} the
|
|
30
|
+
.description(`${commandName[0]?.toUpperCase()}${commandName.slice(1)} the daemon.`)
|
|
27
31
|
.action(() => runServiceCommand(commandName));
|
|
28
32
|
}
|
|
29
33
|
await program.parseAsync();
|
package/dist/commands/service.js
CHANGED
|
@@ -1,6 +1,45 @@
|
|
|
1
|
+
import { readConfig } from "../config/store.js";
|
|
2
|
+
import { backgroundDaemonStatus, startBackgroundDaemon, stopBackgroundDaemon } from "../service/process.js";
|
|
1
3
|
import { systemctl } from "../service/systemd.js";
|
|
2
|
-
|
|
3
|
-
|
|
4
|
+
const defaultServiceDeps = {
|
|
5
|
+
backgroundDaemonStatus,
|
|
6
|
+
startBackgroundDaemon,
|
|
7
|
+
stopBackgroundDaemon,
|
|
8
|
+
systemctl,
|
|
9
|
+
readConfig,
|
|
10
|
+
};
|
|
11
|
+
export async function runServiceCommand(command, options = {}, depsOverride = {}) {
|
|
12
|
+
const deps = { ...defaultServiceDeps, ...depsOverride };
|
|
13
|
+
if (command === "start" && await shouldStartBackground(options, deps)) {
|
|
14
|
+
console.log(await deps.startBackgroundDaemon());
|
|
15
|
+
return;
|
|
16
|
+
}
|
|
17
|
+
if (command === "stop") {
|
|
18
|
+
const status = await deps.backgroundDaemonStatus();
|
|
19
|
+
if (status !== null) {
|
|
20
|
+
console.log(await deps.stopBackgroundDaemon());
|
|
21
|
+
return;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
if (command === "status") {
|
|
25
|
+
const status = await deps.backgroundDaemonStatus();
|
|
26
|
+
if (status !== null) {
|
|
27
|
+
console.log(status);
|
|
28
|
+
return;
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
const output = await deps.systemctl(command, "nessie-daemon.service");
|
|
4
32
|
if (output.trim())
|
|
5
33
|
console.log(output.trim());
|
|
6
34
|
}
|
|
35
|
+
async function shouldStartBackground(options, deps) {
|
|
36
|
+
if (options.background)
|
|
37
|
+
return true;
|
|
38
|
+
try {
|
|
39
|
+
const config = await deps.readConfig();
|
|
40
|
+
return Boolean(config.apiKey);
|
|
41
|
+
}
|
|
42
|
+
catch {
|
|
43
|
+
return false;
|
|
44
|
+
}
|
|
45
|
+
}
|
package/dist/commands/setup.js
CHANGED
|
@@ -2,15 +2,22 @@ import { checkbox, confirm } from "@inquirer/prompts";
|
|
|
2
2
|
import { hostname } from "node:os";
|
|
3
3
|
import { runDeviceAuth } from "../auth/deviceFlow.js";
|
|
4
4
|
import { getDaemonPaths } from "../config/paths.js";
|
|
5
|
-
import { createConfig, createInitialState,
|
|
5
|
+
import { createConfig, createInitialState, writeConfig, writeState } from "../config/store.js";
|
|
6
6
|
import { installUserService } from "../service/systemd.js";
|
|
7
7
|
import { detectSources } from "../sources/detect.js";
|
|
8
|
-
export async function runSetup(options) {
|
|
9
|
-
const
|
|
10
|
-
const authApiUrl = options.authApiUrl ?? defaultAuthApiUrl;
|
|
8
|
+
export async function runSetup(options, depsOverride = {}) {
|
|
9
|
+
const deps = resolveSetupDeps(depsOverride);
|
|
11
10
|
const deviceName = hostname();
|
|
12
|
-
|
|
13
|
-
|
|
11
|
+
if (options.apiKey !== undefined) {
|
|
12
|
+
await runAPIKeySetup({
|
|
13
|
+
apiKey: options.apiKey,
|
|
14
|
+
deviceName,
|
|
15
|
+
deps,
|
|
16
|
+
});
|
|
17
|
+
return;
|
|
18
|
+
}
|
|
19
|
+
const auth = await runDeviceAuth({ deviceName });
|
|
20
|
+
const detectedSources = await deps.detectSources();
|
|
14
21
|
if (detectedSources.length === 0) {
|
|
15
22
|
throw new Error("No supported Codex or Claude Code history directories were found.");
|
|
16
23
|
}
|
|
@@ -23,21 +30,49 @@ export async function runSetup(options) {
|
|
|
23
30
|
})),
|
|
24
31
|
required: true,
|
|
25
32
|
});
|
|
26
|
-
const paths = getDaemonPaths();
|
|
27
33
|
const config = createConfig({
|
|
28
34
|
accessToken: auth.accessToken,
|
|
29
35
|
refreshToken: auth.refreshToken,
|
|
30
36
|
deviceId: auth.deviceId,
|
|
31
37
|
deviceName,
|
|
32
|
-
apiUrl,
|
|
33
|
-
authApiUrl,
|
|
34
38
|
selectedSources,
|
|
35
39
|
});
|
|
36
|
-
await writeConfig(config, paths);
|
|
37
|
-
await writeState(createInitialState(), paths);
|
|
38
|
-
console.log(`Saved config to ${paths.configFile}`);
|
|
40
|
+
await deps.writeConfig(config, deps.paths);
|
|
41
|
+
await deps.writeState(createInitialState(), deps.paths);
|
|
42
|
+
console.log(`Saved config to ${deps.paths.configFile}`);
|
|
39
43
|
if (await confirm({ message: "Install and start the user systemd service?", default: true })) {
|
|
40
|
-
await installUserService(paths);
|
|
44
|
+
await installUserService(deps.paths);
|
|
41
45
|
console.log("Installed and started nessie-daemon.service");
|
|
42
46
|
}
|
|
43
47
|
}
|
|
48
|
+
async function runAPIKeySetup(input) {
|
|
49
|
+
const apiKey = input.apiKey.trim();
|
|
50
|
+
if (!apiKey)
|
|
51
|
+
throw new Error("--api-key cannot be empty.");
|
|
52
|
+
const detectedSources = await input.deps.detectSources();
|
|
53
|
+
if (detectedSources.length === 0) {
|
|
54
|
+
throw new Error("No supported Codex or Claude Code history directories were found.");
|
|
55
|
+
}
|
|
56
|
+
const config = createConfig({
|
|
57
|
+
apiKey,
|
|
58
|
+
deviceName: input.deviceName,
|
|
59
|
+
selectedSources: detectedSources,
|
|
60
|
+
});
|
|
61
|
+
await input.deps.writeConfig(config, input.deps.paths);
|
|
62
|
+
await input.deps.writeState(createInitialState(), input.deps.paths);
|
|
63
|
+
console.log("Configured Nessie daemon with API key auth.");
|
|
64
|
+
console.log(`Selected ${detectedSources.length} source(s):`);
|
|
65
|
+
for (const source of detectedSources) {
|
|
66
|
+
console.log(`- ${source.displayName} (${source.basePath})`);
|
|
67
|
+
}
|
|
68
|
+
console.log(`Saved config to ${input.deps.paths.configFile}`);
|
|
69
|
+
console.log("Run `nessie-daemon start` to start syncing.");
|
|
70
|
+
}
|
|
71
|
+
function resolveSetupDeps(overrides) {
|
|
72
|
+
return {
|
|
73
|
+
detectSources: overrides.detectSources ?? detectSources,
|
|
74
|
+
writeConfig: overrides.writeConfig ?? writeConfig,
|
|
75
|
+
writeState: overrides.writeState ?? writeState,
|
|
76
|
+
paths: overrides.paths ?? getDaemonPaths(),
|
|
77
|
+
};
|
|
78
|
+
}
|
package/dist/config/paths.js
CHANGED
|
@@ -11,6 +11,8 @@ export function getDaemonPaths(env = process.env, home = homedir()) {
|
|
|
11
11
|
stateDir,
|
|
12
12
|
configFile: join(configDir, "config.json"),
|
|
13
13
|
stateFile: join(stateDir, "state.json"),
|
|
14
|
+
pidFile: join(stateDir, "daemon.pid"),
|
|
15
|
+
logFile: join(stateDir, "daemon.log"),
|
|
14
16
|
systemdUserDir,
|
|
15
17
|
systemdServiceFile: join(systemdUserDir, "nessie-daemon.service"),
|
|
16
18
|
};
|
package/dist/config/store.js
CHANGED
|
@@ -3,17 +3,14 @@ import { mkdir, readFile, writeFile } from "node:fs/promises";
|
|
|
3
3
|
import { hostname } from "node:os";
|
|
4
4
|
import { dirname } from "node:path";
|
|
5
5
|
import { getDaemonPaths } from "./paths.js";
|
|
6
|
-
export const defaultApiUrl = "https://nessie-codebase-843813578359.us-west1.run.app";
|
|
7
|
-
export const defaultAuthApiUrl = "https://nessie-notes-go-843813578359.us-west1.run.app";
|
|
8
6
|
export function createConfig(input) {
|
|
9
7
|
const deviceId = input.deviceId ?? randomUUID();
|
|
10
8
|
return {
|
|
11
|
-
apiUrl: input.apiUrl ?? defaultApiUrl,
|
|
12
|
-
authApiUrl: input.authApiUrl ?? defaultAuthApiUrl,
|
|
13
9
|
deviceId,
|
|
14
10
|
deviceName: input.deviceName ?? hostname(),
|
|
15
11
|
accessToken: input.accessToken,
|
|
16
12
|
refreshToken: input.refreshToken ?? null,
|
|
13
|
+
apiKey: input.apiKey ?? null,
|
|
17
14
|
selectedSources: input.selectedSources.map((source) => ({
|
|
18
15
|
...source,
|
|
19
16
|
localId: randomUUID(),
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
import { spawn } from "node:child_process";
|
|
2
|
+
import { closeSync, openSync } from "node:fs";
|
|
3
|
+
import { mkdir, readFile, unlink, writeFile } from "node:fs/promises";
|
|
4
|
+
import { getDaemonPaths } from "../config/paths.js";
|
|
5
|
+
const defaultProcessDeps = {
|
|
6
|
+
spawn,
|
|
7
|
+
argv: process.argv,
|
|
8
|
+
execPath: process.execPath,
|
|
9
|
+
kill: process.kill,
|
|
10
|
+
readProcessCmdline,
|
|
11
|
+
};
|
|
12
|
+
export async function startBackgroundDaemon(paths = getDaemonPaths(), depsOverride = {}) {
|
|
13
|
+
const deps = resolveProcessDeps(depsOverride);
|
|
14
|
+
const existingPid = await readPid(paths);
|
|
15
|
+
if (existingPid && await isDaemonRunning(existingPid, deps)) {
|
|
16
|
+
return `nessie-daemon is already running with pid ${existingPid}.`;
|
|
17
|
+
}
|
|
18
|
+
if (existingPid)
|
|
19
|
+
await removePid(paths);
|
|
20
|
+
await mkdir(paths.stateDir, { recursive: true });
|
|
21
|
+
if (!await reservePidFile(paths))
|
|
22
|
+
return "nessie-daemon is already starting.";
|
|
23
|
+
const out = openSync(paths.logFile, "a");
|
|
24
|
+
const err = openSync(paths.logFile, "a");
|
|
25
|
+
let child;
|
|
26
|
+
try {
|
|
27
|
+
child = deps.spawn(deps.execPath, [cliPath(deps.argv), "run"], {
|
|
28
|
+
detached: true,
|
|
29
|
+
stdio: ["ignore", out, err],
|
|
30
|
+
});
|
|
31
|
+
child.unref();
|
|
32
|
+
}
|
|
33
|
+
finally {
|
|
34
|
+
closeSync(out);
|
|
35
|
+
closeSync(err);
|
|
36
|
+
}
|
|
37
|
+
if (!child.pid) {
|
|
38
|
+
await removePid(paths);
|
|
39
|
+
throw new Error("Failed to start nessie-daemon in background.");
|
|
40
|
+
}
|
|
41
|
+
await writeFile(paths.pidFile, `${child.pid}\n`, { mode: 0o600 });
|
|
42
|
+
return `Started nessie-daemon with pid ${child.pid}. Logs: ${paths.logFile}`;
|
|
43
|
+
}
|
|
44
|
+
export async function stopBackgroundDaemon(paths = getDaemonPaths(), depsOverride = {}) {
|
|
45
|
+
const deps = resolveProcessDeps(depsOverride);
|
|
46
|
+
const pid = await readPid(paths);
|
|
47
|
+
if (!pid)
|
|
48
|
+
return "nessie-daemon is not running.";
|
|
49
|
+
if (!await isDaemonRunning(pid, deps)) {
|
|
50
|
+
await removePid(paths);
|
|
51
|
+
return "nessie-daemon is not running.";
|
|
52
|
+
}
|
|
53
|
+
deps.kill(pid, "SIGTERM");
|
|
54
|
+
await removePid(paths);
|
|
55
|
+
return `Stopped nessie-daemon with pid ${pid}.`;
|
|
56
|
+
}
|
|
57
|
+
export async function backgroundDaemonStatus(paths = getDaemonPaths(), depsOverride = {}) {
|
|
58
|
+
const deps = resolveProcessDeps(depsOverride);
|
|
59
|
+
const pid = await readPid(paths);
|
|
60
|
+
if (!pid)
|
|
61
|
+
return null;
|
|
62
|
+
if (!await isDaemonRunning(pid, deps)) {
|
|
63
|
+
await removePid(paths);
|
|
64
|
+
return "nessie-daemon is not running.";
|
|
65
|
+
}
|
|
66
|
+
return `nessie-daemon is running with pid ${pid}. Logs: ${paths.logFile}`;
|
|
67
|
+
}
|
|
68
|
+
async function readPid(paths) {
|
|
69
|
+
try {
|
|
70
|
+
const raw = await readFile(paths.pidFile, "utf8");
|
|
71
|
+
const pid = Number.parseInt(raw.trim(), 10);
|
|
72
|
+
return Number.isFinite(pid) && pid > 0 ? pid : null;
|
|
73
|
+
}
|
|
74
|
+
catch (error) {
|
|
75
|
+
if (typeof error === "object" && error !== null && "code" in error && error.code === "ENOENT")
|
|
76
|
+
return null;
|
|
77
|
+
throw error;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
async function removePid(paths) {
|
|
81
|
+
try {
|
|
82
|
+
await unlink(paths.pidFile);
|
|
83
|
+
}
|
|
84
|
+
catch (error) {
|
|
85
|
+
if (typeof error === "object" && error !== null && "code" in error && error.code === "ENOENT")
|
|
86
|
+
return;
|
|
87
|
+
throw error;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
async function reservePidFile(paths) {
|
|
91
|
+
try {
|
|
92
|
+
await writeFile(paths.pidFile, "starting\n", { mode: 0o600, flag: "wx" });
|
|
93
|
+
return true;
|
|
94
|
+
}
|
|
95
|
+
catch (error) {
|
|
96
|
+
if (typeof error === "object" && error !== null && "code" in error && error.code === "EEXIST")
|
|
97
|
+
return false;
|
|
98
|
+
throw error;
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
async function isDaemonRunning(pid, deps) {
|
|
102
|
+
try {
|
|
103
|
+
deps.kill(pid, 0);
|
|
104
|
+
}
|
|
105
|
+
catch {
|
|
106
|
+
return false;
|
|
107
|
+
}
|
|
108
|
+
const cmdline = await deps.readProcessCmdline(pid);
|
|
109
|
+
if (cmdline === null)
|
|
110
|
+
return false;
|
|
111
|
+
return cmdline.includes(cliPath(deps.argv)) && cmdline.includes(" run");
|
|
112
|
+
}
|
|
113
|
+
async function readProcessCmdline(pid) {
|
|
114
|
+
try {
|
|
115
|
+
const raw = await readFile(`/proc/${pid}/cmdline`);
|
|
116
|
+
const cmdline = raw.toString("utf8").replace(/\0/g, " ").trim();
|
|
117
|
+
return cmdline || null;
|
|
118
|
+
}
|
|
119
|
+
catch {
|
|
120
|
+
return null;
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
function resolveProcessDeps(overrides) {
|
|
124
|
+
return {
|
|
125
|
+
...defaultProcessDeps,
|
|
126
|
+
...overrides,
|
|
127
|
+
};
|
|
128
|
+
}
|
|
129
|
+
function cliPath(argv) {
|
|
130
|
+
const path = argv[1];
|
|
131
|
+
if (!path)
|
|
132
|
+
throw new Error("Cannot determine nessie-daemon CLI path.");
|
|
133
|
+
return path;
|
|
134
|
+
}
|
package/dist/sync/client.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { ApiError, postJson } from "../api/http.js";
|
|
2
2
|
import { refreshAccessToken } from "../auth/tokens.js";
|
|
3
|
+
import { syncApiUrl } from "../config/endpoints.js";
|
|
3
4
|
import { writeConfig } from "../config/store.js";
|
|
4
5
|
export async function runPreflightV3(config, options = {}) {
|
|
5
6
|
return postJsonWithRefresh(config, "/sync/v3/preflight", {
|
|
@@ -22,16 +23,25 @@ export async function pushSyncPayload(config, payload, options = {}) {
|
|
|
22
23
|
}, options);
|
|
23
24
|
}
|
|
24
25
|
async function postJsonWithRefresh(config, path, body, options) {
|
|
26
|
+
const token = authToken(config);
|
|
25
27
|
try {
|
|
26
|
-
await postJson(
|
|
28
|
+
await postJson(syncApiUrl, path, body, { token, fetchImpl: options.fetchImpl });
|
|
27
29
|
return config;
|
|
28
30
|
}
|
|
29
31
|
catch (error) {
|
|
32
|
+
if (config.apiKey)
|
|
33
|
+
throw error;
|
|
30
34
|
if (!(error instanceof ApiError) || error.status !== 401)
|
|
31
35
|
throw error;
|
|
32
36
|
}
|
|
33
37
|
const refreshed = await refreshAccessToken(config, { fetchImpl: options.fetchImpl });
|
|
34
38
|
await (options.persistConfig ?? writeConfig)(refreshed);
|
|
35
|
-
await postJson(
|
|
39
|
+
await postJson(syncApiUrl, path, body, { token: authToken(refreshed), fetchImpl: options.fetchImpl });
|
|
36
40
|
return refreshed;
|
|
37
41
|
}
|
|
42
|
+
function authToken(config) {
|
|
43
|
+
const token = config.apiKey ?? config.accessToken;
|
|
44
|
+
if (!token)
|
|
45
|
+
throw new Error("Daemon config is missing auth credentials. Run nessie-daemon setup.");
|
|
46
|
+
return token;
|
|
47
|
+
}
|
package/package.json
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@nessielabs/daemon",
|
|
3
|
-
"version": "0.1
|
|
3
|
+
"version": "0.2.1",
|
|
4
4
|
"description": "Headless Linux ingestion daemon for Nessie agent traces.",
|
|
5
5
|
"license": "UNLICENSED",
|
|
6
6
|
"type": "module",
|
|
7
7
|
"bin": {
|
|
8
|
-
"nessie-daemon": "
|
|
8
|
+
"nessie-daemon": "dist/cli.js"
|
|
9
9
|
},
|
|
10
10
|
"files": [
|
|
11
11
|
"dist/**/*.js",
|