nicefox-graphdb 0.1.0

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.
Files changed (57) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +417 -0
  3. package/package.json +78 -0
  4. package/packages/nicefox-graphdb/LICENSE +21 -0
  5. package/packages/nicefox-graphdb/README.md +417 -0
  6. package/packages/nicefox-graphdb/dist/auth.d.ts +66 -0
  7. package/packages/nicefox-graphdb/dist/auth.d.ts.map +1 -0
  8. package/packages/nicefox-graphdb/dist/auth.js +148 -0
  9. package/packages/nicefox-graphdb/dist/auth.js.map +1 -0
  10. package/packages/nicefox-graphdb/dist/backup.d.ts +51 -0
  11. package/packages/nicefox-graphdb/dist/backup.d.ts.map +1 -0
  12. package/packages/nicefox-graphdb/dist/backup.js +201 -0
  13. package/packages/nicefox-graphdb/dist/backup.js.map +1 -0
  14. package/packages/nicefox-graphdb/dist/cli-helpers.d.ts +17 -0
  15. package/packages/nicefox-graphdb/dist/cli-helpers.d.ts.map +1 -0
  16. package/packages/nicefox-graphdb/dist/cli-helpers.js +121 -0
  17. package/packages/nicefox-graphdb/dist/cli-helpers.js.map +1 -0
  18. package/packages/nicefox-graphdb/dist/cli.d.ts +3 -0
  19. package/packages/nicefox-graphdb/dist/cli.d.ts.map +1 -0
  20. package/packages/nicefox-graphdb/dist/cli.js +660 -0
  21. package/packages/nicefox-graphdb/dist/cli.js.map +1 -0
  22. package/packages/nicefox-graphdb/dist/db.d.ts +118 -0
  23. package/packages/nicefox-graphdb/dist/db.d.ts.map +1 -0
  24. package/packages/nicefox-graphdb/dist/db.js +245 -0
  25. package/packages/nicefox-graphdb/dist/db.js.map +1 -0
  26. package/packages/nicefox-graphdb/dist/executor.d.ts +272 -0
  27. package/packages/nicefox-graphdb/dist/executor.d.ts.map +1 -0
  28. package/packages/nicefox-graphdb/dist/executor.js +3579 -0
  29. package/packages/nicefox-graphdb/dist/executor.js.map +1 -0
  30. package/packages/nicefox-graphdb/dist/index.d.ts +54 -0
  31. package/packages/nicefox-graphdb/dist/index.d.ts.map +1 -0
  32. package/packages/nicefox-graphdb/dist/index.js +74 -0
  33. package/packages/nicefox-graphdb/dist/index.js.map +1 -0
  34. package/packages/nicefox-graphdb/dist/local.d.ts +7 -0
  35. package/packages/nicefox-graphdb/dist/local.d.ts.map +1 -0
  36. package/packages/nicefox-graphdb/dist/local.js +115 -0
  37. package/packages/nicefox-graphdb/dist/local.js.map +1 -0
  38. package/packages/nicefox-graphdb/dist/parser.d.ts +300 -0
  39. package/packages/nicefox-graphdb/dist/parser.d.ts.map +1 -0
  40. package/packages/nicefox-graphdb/dist/parser.js +1891 -0
  41. package/packages/nicefox-graphdb/dist/parser.js.map +1 -0
  42. package/packages/nicefox-graphdb/dist/remote.d.ts +6 -0
  43. package/packages/nicefox-graphdb/dist/remote.d.ts.map +1 -0
  44. package/packages/nicefox-graphdb/dist/remote.js +87 -0
  45. package/packages/nicefox-graphdb/dist/remote.js.map +1 -0
  46. package/packages/nicefox-graphdb/dist/routes.d.ts +31 -0
  47. package/packages/nicefox-graphdb/dist/routes.d.ts.map +1 -0
  48. package/packages/nicefox-graphdb/dist/routes.js +202 -0
  49. package/packages/nicefox-graphdb/dist/routes.js.map +1 -0
  50. package/packages/nicefox-graphdb/dist/translator.d.ts +136 -0
  51. package/packages/nicefox-graphdb/dist/translator.d.ts.map +1 -0
  52. package/packages/nicefox-graphdb/dist/translator.js +4849 -0
  53. package/packages/nicefox-graphdb/dist/translator.js.map +1 -0
  54. package/packages/nicefox-graphdb/dist/types.d.ts +133 -0
  55. package/packages/nicefox-graphdb/dist/types.d.ts.map +1 -0
  56. package/packages/nicefox-graphdb/dist/types.js +21 -0
  57. package/packages/nicefox-graphdb/dist/types.js.map +1 -0
@@ -0,0 +1,201 @@
1
+ // Backup System for NiceFox GraphDB
2
+ // Uses SQLite's backup API for hot (online) backups
3
+ import Database from "better-sqlite3";
4
+ import * as fs from "fs";
5
+ import * as path from "path";
6
+ // ============================================================================
7
+ // BackupManager Class
8
+ // ============================================================================
9
+ export class BackupManager {
10
+ backupDir;
11
+ constructor(backupDir) {
12
+ this.backupDir = backupDir;
13
+ }
14
+ /**
15
+ * Create a backup of a single database file using SQLite's backup API.
16
+ * This is a "hot" backup - it works even if the database is open and in use.
17
+ */
18
+ async backupDatabase(sourcePath, project) {
19
+ const startTime = Date.now();
20
+ // Check source exists
21
+ if (!fs.existsSync(sourcePath)) {
22
+ return {
23
+ success: false,
24
+ project,
25
+ sourcePath,
26
+ error: `Source database not found: ${sourcePath}`,
27
+ };
28
+ }
29
+ // Ensure backup directory exists
30
+ if (!fs.existsSync(this.backupDir)) {
31
+ fs.mkdirSync(this.backupDir, { recursive: true });
32
+ }
33
+ // Generate backup filename with timestamp (including milliseconds for uniqueness)
34
+ const now = new Date();
35
+ const timestamp = now.toISOString().replace(/[:.]/g, "-").slice(0, 19);
36
+ const ms = now.getMilliseconds().toString().padStart(3, "0");
37
+ const backupFilename = `${project}_${timestamp}-${ms}.db`;
38
+ const backupPath = path.join(this.backupDir, backupFilename);
39
+ try {
40
+ // Use SQLite's backup API via better-sqlite3
41
+ const sourceDb = new Database(sourcePath, { readonly: true });
42
+ // backup() returns a Promise - wait for it to complete
43
+ await sourceDb.backup(backupPath);
44
+ sourceDb.close();
45
+ const stats = fs.statSync(backupPath);
46
+ const durationMs = Date.now() - startTime;
47
+ return {
48
+ success: true,
49
+ project,
50
+ sourcePath,
51
+ backupPath,
52
+ durationMs,
53
+ sizeBytes: stats.size,
54
+ };
55
+ }
56
+ catch (err) {
57
+ return {
58
+ success: false,
59
+ project,
60
+ sourcePath,
61
+ error: err instanceof Error ? err.message : String(err),
62
+ };
63
+ }
64
+ }
65
+ /**
66
+ * Backup all databases in a data directory.
67
+ * By default, only backs up production databases.
68
+ */
69
+ async backupAll(dataDir, options = {}) {
70
+ const results = [];
71
+ const envs = options.includeTest ? ["production", "test"] : ["production"];
72
+ for (const env of envs) {
73
+ const envPath = path.join(dataDir, env);
74
+ if (!fs.existsSync(envPath)) {
75
+ continue;
76
+ }
77
+ const files = fs.readdirSync(envPath).filter(f => f.endsWith(".db"));
78
+ for (const file of files) {
79
+ const project = file.replace(".db", "");
80
+ const sourcePath = path.join(envPath, file);
81
+ const result = await this.backupDatabase(sourcePath, project);
82
+ results.push(result);
83
+ }
84
+ }
85
+ return results;
86
+ }
87
+ /**
88
+ * List all backups for a specific project, sorted by date (newest first).
89
+ */
90
+ listBackups(project) {
91
+ if (!fs.existsSync(this.backupDir)) {
92
+ return [];
93
+ }
94
+ const files = fs.readdirSync(this.backupDir)
95
+ .filter(f => f.startsWith(`${project}_`) && f.endsWith(".db"))
96
+ .sort((a, b) => b.localeCompare(a)); // Descending order (newest first)
97
+ return files;
98
+ }
99
+ /**
100
+ * Delete old backups, keeping only the specified number of recent ones.
101
+ * Returns the number of deleted backups.
102
+ */
103
+ cleanOldBackups(project, keepCount) {
104
+ const backups = this.listBackups(project);
105
+ if (backups.length <= keepCount) {
106
+ return 0;
107
+ }
108
+ const toDelete = backups.slice(keepCount);
109
+ let deleted = 0;
110
+ for (const file of toDelete) {
111
+ const filePath = path.join(this.backupDir, file);
112
+ try {
113
+ fs.unlinkSync(filePath);
114
+ deleted++;
115
+ }
116
+ catch {
117
+ // Ignore errors during cleanup
118
+ }
119
+ }
120
+ return deleted;
121
+ }
122
+ /**
123
+ * Get overall backup status and statistics.
124
+ */
125
+ getBackupStatus() {
126
+ if (!fs.existsSync(this.backupDir)) {
127
+ return {
128
+ totalBackups: 0,
129
+ totalSizeBytes: 0,
130
+ projects: [],
131
+ };
132
+ }
133
+ const files = fs.readdirSync(this.backupDir).filter(f => f.endsWith(".db"));
134
+ const projects = new Set();
135
+ let totalSizeBytes = 0;
136
+ let oldestBackup;
137
+ let newestBackup;
138
+ for (const file of files) {
139
+ // Extract project name from filename (format: project_timestamp.db)
140
+ const match = file.match(/^(.+)_\d{4}-\d{2}-\d{2}T/);
141
+ if (match) {
142
+ projects.add(match[1]);
143
+ }
144
+ const filePath = path.join(this.backupDir, file);
145
+ const stats = fs.statSync(filePath);
146
+ totalSizeBytes += stats.size;
147
+ // Track oldest and newest
148
+ if (!oldestBackup || file < oldestBackup) {
149
+ oldestBackup = file;
150
+ }
151
+ if (!newestBackup || file > newestBackup) {
152
+ newestBackup = file;
153
+ }
154
+ }
155
+ return {
156
+ totalBackups: files.length,
157
+ totalSizeBytes,
158
+ projects: Array.from(projects).sort(),
159
+ oldestBackup,
160
+ newestBackup,
161
+ };
162
+ }
163
+ /**
164
+ * Restore a backup to a target path.
165
+ */
166
+ restoreBackup(backupFilename, targetPath) {
167
+ const backupPath = path.join(this.backupDir, backupFilename);
168
+ if (!fs.existsSync(backupPath)) {
169
+ return {
170
+ success: false,
171
+ project: "",
172
+ sourcePath: backupPath,
173
+ error: `Backup not found: ${backupFilename}`,
174
+ };
175
+ }
176
+ try {
177
+ // Ensure target directory exists
178
+ const targetDir = path.dirname(targetPath);
179
+ if (!fs.existsSync(targetDir)) {
180
+ fs.mkdirSync(targetDir, { recursive: true });
181
+ }
182
+ // Copy backup to target
183
+ fs.copyFileSync(backupPath, targetPath);
184
+ return {
185
+ success: true,
186
+ project: "",
187
+ sourcePath: backupPath,
188
+ backupPath: targetPath,
189
+ };
190
+ }
191
+ catch (err) {
192
+ return {
193
+ success: false,
194
+ project: "",
195
+ sourcePath: backupPath,
196
+ error: err instanceof Error ? err.message : String(err),
197
+ };
198
+ }
199
+ }
200
+ }
201
+ //# sourceMappingURL=backup.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"backup.js","sourceRoot":"","sources":["../src/backup.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,17 @@
1
+ export interface ApiKeyConfig {
2
+ project?: string;
3
+ env?: string;
4
+ admin?: boolean;
5
+ }
6
+ export declare function formatBytes(bytes: number): string;
7
+ export declare function formatValue(val: unknown): string;
8
+ export declare function getApiKeysPath(dataPath: string): string;
9
+ export declare function loadApiKeys(dataPath: string): Record<string, ApiKeyConfig>;
10
+ export declare function saveApiKeys(dataPath: string, keys: Record<string, ApiKeyConfig>): void;
11
+ export declare function ensureDataDir(dataPath: string): void;
12
+ export declare function formatTableRow(columns: string[], row: Record<string, unknown>, widths: Record<string, number>): string;
13
+ export declare function calculateColumnWidths(columns: string[], rows: Record<string, unknown>[], maxWidth?: number): Record<string, number>;
14
+ export declare function listProjects(dataPath: string): Map<string, string[]>;
15
+ export declare function projectExists(dataPath: string, project: string, env?: string): boolean;
16
+ export declare function getProjectKeyCount(keys: Record<string, ApiKeyConfig>, project: string): number;
17
+ //# sourceMappingURL=cli-helpers.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli-helpers.d.ts","sourceRoot":"","sources":["../src/cli-helpers.ts"],"names":[],"mappings":"AASA,MAAM,WAAW,YAAY;IAC3B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB;AAMD,wBAAgB,WAAW,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAMjD;AAED,wBAAgB,WAAW,CAAC,GAAG,EAAE,OAAO,GAAG,MAAM,CAKhD;AAMD,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAEvD;AAED,wBAAgB,WAAW,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAU1E;AAED,wBAAgB,WAAW,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,GAAG,IAAI,CAGtF;AAMD,wBAAgB,aAAa,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,CAWpD;AAMD,wBAAgB,cAAc,CAC5B,OAAO,EAAE,MAAM,EAAE,EACjB,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC5B,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAC7B,MAAM,CAOR;AAED,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,MAAM,EAAE,EACjB,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,EAC/B,QAAQ,GAAE,MAAW,GACpB,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAoBxB;AAMD,wBAAgB,YAAY,CAAC,QAAQ,EAAE,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAkBpE;AAED,wBAAgB,aAAa,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,GAAG,OAAO,CAWtF;AAED,wBAAgB,kBAAkB,CAChC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,EAClC,OAAO,EAAE,MAAM,GACd,MAAM,CAER"}
@@ -0,0 +1,121 @@
1
+ // CLI Helper Functions
2
+ import * as fs from "fs";
3
+ import * as path from "path";
4
+ // ============================================================================
5
+ // Formatting Helpers
6
+ // ============================================================================
7
+ export function formatBytes(bytes) {
8
+ if (bytes === 0)
9
+ return "0 B";
10
+ const k = 1024;
11
+ const sizes = ["B", "KB", "MB", "GB"];
12
+ const i = Math.floor(Math.log(bytes) / Math.log(k));
13
+ return `${parseFloat((bytes / Math.pow(k, i)).toFixed(2))} ${sizes[i]}`;
14
+ }
15
+ export function formatValue(val) {
16
+ if (val === null)
17
+ return "null";
18
+ if (val === undefined)
19
+ return "";
20
+ if (typeof val === "object")
21
+ return JSON.stringify(val);
22
+ return String(val);
23
+ }
24
+ // ============================================================================
25
+ // API Key Helpers
26
+ // ============================================================================
27
+ export function getApiKeysPath(dataPath) {
28
+ return path.join(dataPath, "api-keys.json");
29
+ }
30
+ export function loadApiKeys(dataPath) {
31
+ const keysFile = getApiKeysPath(dataPath);
32
+ if (fs.existsSync(keysFile)) {
33
+ try {
34
+ return JSON.parse(fs.readFileSync(keysFile, "utf-8"));
35
+ }
36
+ catch {
37
+ return {};
38
+ }
39
+ }
40
+ return {};
41
+ }
42
+ export function saveApiKeys(dataPath, keys) {
43
+ const keysFile = getApiKeysPath(dataPath);
44
+ fs.writeFileSync(keysFile, JSON.stringify(keys, null, 2) + "\n");
45
+ }
46
+ // ============================================================================
47
+ // Directory Helpers
48
+ // ============================================================================
49
+ export function ensureDataDir(dataPath) {
50
+ if (!fs.existsSync(dataPath)) {
51
+ fs.mkdirSync(dataPath, { recursive: true });
52
+ }
53
+ // Ensure env subdirs exist
54
+ for (const env of ["production", "test"]) {
55
+ const envPath = path.join(dataPath, env);
56
+ if (!fs.existsSync(envPath)) {
57
+ fs.mkdirSync(envPath, { recursive: true });
58
+ }
59
+ }
60
+ }
61
+ // ============================================================================
62
+ // Table Formatting
63
+ // ============================================================================
64
+ export function formatTableRow(columns, row, widths) {
65
+ return columns
66
+ .map((col) => {
67
+ const val = formatValue(row[col]);
68
+ return val.slice(0, widths[col]).padEnd(widths[col]);
69
+ })
70
+ .join(" | ");
71
+ }
72
+ export function calculateColumnWidths(columns, rows, maxWidth = 40) {
73
+ const widths = {};
74
+ for (const col of columns) {
75
+ widths[col] = col.length;
76
+ }
77
+ for (const row of rows) {
78
+ for (const col of columns) {
79
+ const val = formatValue(row[col]);
80
+ widths[col] = Math.max(widths[col], val.length);
81
+ }
82
+ }
83
+ // Cap max width
84
+ for (const col of columns) {
85
+ widths[col] = Math.min(widths[col], maxWidth);
86
+ }
87
+ return widths;
88
+ }
89
+ // ============================================================================
90
+ // Project Helpers
91
+ // ============================================================================
92
+ export function listProjects(dataPath) {
93
+ const projects = new Map();
94
+ for (const env of ["production", "test"]) {
95
+ const envPath = path.join(dataPath, env);
96
+ if (fs.existsSync(envPath)) {
97
+ const files = fs.readdirSync(envPath).filter((f) => f.endsWith(".db"));
98
+ for (const file of files) {
99
+ const project = file.replace(".db", "");
100
+ if (!projects.has(project)) {
101
+ projects.set(project, []);
102
+ }
103
+ projects.get(project).push(env);
104
+ }
105
+ }
106
+ }
107
+ return projects;
108
+ }
109
+ export function projectExists(dataPath, project, env) {
110
+ if (env) {
111
+ const dbPath = path.join(dataPath, env, `${project}.db`);
112
+ return fs.existsSync(dbPath);
113
+ }
114
+ // Check both environments
115
+ return (fs.existsSync(path.join(dataPath, "production", `${project}.db`)) ||
116
+ fs.existsSync(path.join(dataPath, "test", `${project}.db`)));
117
+ }
118
+ export function getProjectKeyCount(keys, project) {
119
+ return Object.values(keys).filter((config) => config.project === project).length;
120
+ }
121
+ //# sourceMappingURL=cli-helpers.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli-helpers.js","sourceRoot":"","sources":["../src/cli-helpers.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=cli.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":""}