ctx-sync 1.0.0 → 1.0.2
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/node_modules/@ctx-sync/shared/dist/constants.d.ts +22 -0
- package/node_modules/@ctx-sync/shared/dist/constants.d.ts.map +1 -0
- package/node_modules/@ctx-sync/shared/dist/constants.js +36 -0
- package/node_modules/@ctx-sync/shared/dist/constants.js.map +1 -0
- package/node_modules/@ctx-sync/shared/dist/index.d.ts +10 -0
- package/node_modules/@ctx-sync/shared/dist/index.d.ts.map +1 -0
- package/node_modules/@ctx-sync/shared/dist/index.js +8 -0
- package/node_modules/@ctx-sync/shared/dist/index.js.map +1 -0
- package/node_modules/@ctx-sync/shared/dist/schemas.d.ts +46 -0
- package/node_modules/@ctx-sync/shared/dist/schemas.d.ts.map +1 -0
- package/node_modules/@ctx-sync/shared/dist/schemas.js +290 -0
- package/node_modules/@ctx-sync/shared/dist/schemas.js.map +1 -0
- package/node_modules/@ctx-sync/shared/dist/types.d.ts +154 -0
- package/node_modules/@ctx-sync/shared/dist/types.d.ts.map +1 -0
- package/node_modules/@ctx-sync/shared/dist/types.js +8 -0
- package/node_modules/@ctx-sync/shared/dist/types.js.map +1 -0
- package/node_modules/@ctx-sync/shared/package.json +19 -0
- package/package.json +5 -1
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared constants for ctx-sync.
|
|
3
|
+
*/
|
|
4
|
+
/** Current CLI version */
|
|
5
|
+
export declare const VERSION = "1.0.0";
|
|
6
|
+
/** Default safe-list: env var keys that MAY be stored as plaintext (with --allow-plain) */
|
|
7
|
+
export declare const DEFAULT_SAFE_LIST: readonly string[];
|
|
8
|
+
/** State file names (encrypted) */
|
|
9
|
+
export declare const STATE_FILES: {
|
|
10
|
+
readonly STATE: "state.age";
|
|
11
|
+
readonly ENV_VARS: "env-vars.age";
|
|
12
|
+
readonly DOCKER_STATE: "docker-state.age";
|
|
13
|
+
readonly MENTAL_CONTEXT: "mental-context.age";
|
|
14
|
+
readonly SERVICES: "services.age";
|
|
15
|
+
readonly DIRECTORIES: "directories.age";
|
|
16
|
+
readonly MANIFEST: "manifest.json";
|
|
17
|
+
};
|
|
18
|
+
/** Local config directory name (under ~/.config/) — NEVER synced to Git */
|
|
19
|
+
export declare const CONFIG_DIR = "ctx-sync";
|
|
20
|
+
/** Sync directory name (under ~/) — Git repo for syncing */
|
|
21
|
+
export declare const SYNC_DIR = ".context-sync";
|
|
22
|
+
//# sourceMappingURL=constants.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,0BAA0B;AAC1B,eAAO,MAAM,OAAO,UAAU,CAAC;AAE/B,2FAA2F;AAC3F,eAAO,MAAM,iBAAiB,EAAE,SAAS,MAAM,EAcrC,CAAC;AAEX,mCAAmC;AACnC,eAAO,MAAM,WAAW;;;;;;;;CAQd,CAAC;AAEX,2EAA2E;AAC3E,eAAO,MAAM,UAAU,aAAa,CAAC;AAErC,4DAA4D;AAC5D,eAAO,MAAM,QAAQ,kBAAkB,CAAC"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared constants for ctx-sync.
|
|
3
|
+
*/
|
|
4
|
+
/** Current CLI version */
|
|
5
|
+
export const VERSION = '1.0.0';
|
|
6
|
+
/** Default safe-list: env var keys that MAY be stored as plaintext (with --allow-plain) */
|
|
7
|
+
export const DEFAULT_SAFE_LIST = [
|
|
8
|
+
'NODE_ENV',
|
|
9
|
+
'PORT',
|
|
10
|
+
'HOST',
|
|
11
|
+
'DEBUG',
|
|
12
|
+
'LOG_LEVEL',
|
|
13
|
+
'TZ',
|
|
14
|
+
'LANG',
|
|
15
|
+
'SHELL',
|
|
16
|
+
'EDITOR',
|
|
17
|
+
'TERM',
|
|
18
|
+
'COLORTERM',
|
|
19
|
+
'CI',
|
|
20
|
+
'VERBOSE',
|
|
21
|
+
];
|
|
22
|
+
/** State file names (encrypted) */
|
|
23
|
+
export const STATE_FILES = {
|
|
24
|
+
STATE: 'state.age',
|
|
25
|
+
ENV_VARS: 'env-vars.age',
|
|
26
|
+
DOCKER_STATE: 'docker-state.age',
|
|
27
|
+
MENTAL_CONTEXT: 'mental-context.age',
|
|
28
|
+
SERVICES: 'services.age',
|
|
29
|
+
DIRECTORIES: 'directories.age',
|
|
30
|
+
MANIFEST: 'manifest.json',
|
|
31
|
+
};
|
|
32
|
+
/** Local config directory name (under ~/.config/) — NEVER synced to Git */
|
|
33
|
+
export const CONFIG_DIR = 'ctx-sync';
|
|
34
|
+
/** Sync directory name (under ~/) — Git repo for syncing */
|
|
35
|
+
export const SYNC_DIR = '.context-sync';
|
|
36
|
+
//# sourceMappingURL=constants.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants.js","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,0BAA0B;AAC1B,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC;AAE/B,2FAA2F;AAC3F,MAAM,CAAC,MAAM,iBAAiB,GAAsB;IAClD,UAAU;IACV,MAAM;IACN,MAAM;IACN,OAAO;IACP,WAAW;IACX,IAAI;IACJ,MAAM;IACN,OAAO;IACP,QAAQ;IACR,MAAM;IACN,WAAW;IACX,IAAI;IACJ,SAAS;CACD,CAAC;AAEX,mCAAmC;AACnC,MAAM,CAAC,MAAM,WAAW,GAAG;IACzB,KAAK,EAAE,WAAW;IAClB,QAAQ,EAAE,cAAc;IACxB,YAAY,EAAE,kBAAkB;IAChC,cAAc,EAAE,oBAAoB;IACpC,QAAQ,EAAE,cAAc;IACxB,WAAW,EAAE,iBAAiB;IAC9B,QAAQ,EAAE,eAAe;CACjB,CAAC;AAEX,2EAA2E;AAC3E,MAAM,CAAC,MAAM,UAAU,GAAG,UAAU,CAAC;AAErC,4DAA4D;AAC5D,MAAM,CAAC,MAAM,QAAQ,GAAG,eAAe,CAAC"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @ctx-sync/shared — Shared constants, types, and utilities.
|
|
3
|
+
*
|
|
4
|
+
* @module @ctx-sync/shared
|
|
5
|
+
*/
|
|
6
|
+
export { VERSION, DEFAULT_SAFE_LIST, STATE_FILES, CONFIG_DIR, SYNC_DIR } from './constants.js';
|
|
7
|
+
export type { Project, MachineInfo, StateFile, EnvVarEntry, EnvVars, DockerService, DockerState, Blocker, RelatedLink, Breadcrumb, ProjectMentalContext, MentalContext, Service, ServiceState, RecentDirectory, DirectoryState, TeamMember, RecipientsConfig, UserConfig, ManifestFileEntry, Manifest, } from './types.js';
|
|
8
|
+
export type { ValidationResult } from './schemas.js';
|
|
9
|
+
export { validateStateFile, validateEnvVars, validateManifest, validateDockerState, validateMentalContext, validateServiceState, validateDirectoryState, } from './schemas.js';
|
|
10
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,OAAO,EAAE,iBAAiB,EAAE,WAAW,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAC/F,YAAY,EACV,OAAO,EACP,WAAW,EACX,SAAS,EACT,WAAW,EACX,OAAO,EACP,aAAa,EACb,WAAW,EACX,OAAO,EACP,WAAW,EACX,UAAU,EACV,oBAAoB,EACpB,aAAa,EACb,OAAO,EACP,YAAY,EACZ,eAAe,EACf,cAAc,EACd,UAAU,EACV,gBAAgB,EAChB,UAAU,EACV,iBAAiB,EACjB,QAAQ,GACT,MAAM,YAAY,CAAC;AACpB,YAAY,EAAE,gBAAgB,EAAE,MAAM,cAAc,CAAC;AACrD,OAAO,EACL,iBAAiB,EACjB,eAAe,EACf,gBAAgB,EAChB,mBAAmB,EACnB,qBAAqB,EACrB,oBAAoB,EACpB,sBAAsB,GACvB,MAAM,cAAc,CAAC"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @ctx-sync/shared — Shared constants, types, and utilities.
|
|
3
|
+
*
|
|
4
|
+
* @module @ctx-sync/shared
|
|
5
|
+
*/
|
|
6
|
+
export { VERSION, DEFAULT_SAFE_LIST, STATE_FILES, CONFIG_DIR, SYNC_DIR } from './constants.js';
|
|
7
|
+
export { validateStateFile, validateEnvVars, validateManifest, validateDockerState, validateMentalContext, validateServiceState, validateDirectoryState, } from './schemas.js';
|
|
8
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,OAAO,EAAE,iBAAiB,EAAE,WAAW,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAyB/F,OAAO,EACL,iBAAiB,EACjB,eAAe,EACf,gBAAgB,EAChB,mBAAmB,EACnB,qBAAqB,EACrB,oBAAoB,EACpB,sBAAsB,GACvB,MAAM,cAAc,CAAC"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* JSON schema definitions for ctx-sync state file structures.
|
|
3
|
+
*
|
|
4
|
+
* These schemas provide runtime validation for state data
|
|
5
|
+
* to catch malformed or tampered data before it causes issues.
|
|
6
|
+
* Each schema describes the expected shape of its corresponding
|
|
7
|
+
* decrypted state file.
|
|
8
|
+
*
|
|
9
|
+
* @module schemas
|
|
10
|
+
*/
|
|
11
|
+
/**
|
|
12
|
+
* Simple schema validation result.
|
|
13
|
+
*/
|
|
14
|
+
export interface ValidationResult {
|
|
15
|
+
valid: boolean;
|
|
16
|
+
errors: string[];
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Validate a StateFile structure (decrypted state.age).
|
|
20
|
+
*/
|
|
21
|
+
export declare function validateStateFile(data: unknown): ValidationResult;
|
|
22
|
+
/**
|
|
23
|
+
* Validate an EnvVars structure (decrypted env-vars.age).
|
|
24
|
+
*/
|
|
25
|
+
export declare function validateEnvVars(data: unknown): ValidationResult;
|
|
26
|
+
/**
|
|
27
|
+
* Validate a Manifest structure (manifest.json).
|
|
28
|
+
*/
|
|
29
|
+
export declare function validateManifest(data: unknown): ValidationResult;
|
|
30
|
+
/**
|
|
31
|
+
* Validate a DockerState structure (decrypted docker-state.age).
|
|
32
|
+
*/
|
|
33
|
+
export declare function validateDockerState(data: unknown): ValidationResult;
|
|
34
|
+
/**
|
|
35
|
+
* Validate a MentalContext structure (decrypted mental-context.age).
|
|
36
|
+
*/
|
|
37
|
+
export declare function validateMentalContext(data: unknown): ValidationResult;
|
|
38
|
+
/**
|
|
39
|
+
* Validate a ServiceState structure (decrypted services.age).
|
|
40
|
+
*/
|
|
41
|
+
export declare function validateServiceState(data: unknown): ValidationResult;
|
|
42
|
+
/**
|
|
43
|
+
* Validate a DirectoryState structure (decrypted directories.age).
|
|
44
|
+
*/
|
|
45
|
+
export declare function validateDirectoryState(data: unknown): ValidationResult;
|
|
46
|
+
//# sourceMappingURL=schemas.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"schemas.d.ts","sourceRoot":"","sources":["../src/schemas.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,OAAO,CAAC;IACf,MAAM,EAAE,MAAM,EAAE,CAAC;CAClB;AAwGD;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,OAAO,GAAG,gBAAgB,CAyBjE;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,IAAI,EAAE,OAAO,GAAG,gBAAgB,CAwB/D;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,OAAO,GAAG,gBAAgB,CAsBhE;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,OAAO,GAAG,gBAAgB,CA+BnE;AAED;;GAEG;AACH,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,OAAO,GAAG,gBAAgB,CA8BrE;AAED;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,OAAO,GAAG,gBAAgB,CAyBpE;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,OAAO,GAAG,gBAAgB,CA8BtE"}
|
|
@@ -0,0 +1,290 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* JSON schema definitions for ctx-sync state file structures.
|
|
3
|
+
*
|
|
4
|
+
* These schemas provide runtime validation for state data
|
|
5
|
+
* to catch malformed or tampered data before it causes issues.
|
|
6
|
+
* Each schema describes the expected shape of its corresponding
|
|
7
|
+
* decrypted state file.
|
|
8
|
+
*
|
|
9
|
+
* @module schemas
|
|
10
|
+
*/
|
|
11
|
+
/**
|
|
12
|
+
* Validate that a value is a non-empty string.
|
|
13
|
+
*/
|
|
14
|
+
function isNonEmptyString(value, field, errors) {
|
|
15
|
+
if (typeof value !== 'string' || value.trim().length === 0) {
|
|
16
|
+
errors.push(`${field} must be a non-empty string`);
|
|
17
|
+
return false;
|
|
18
|
+
}
|
|
19
|
+
return true;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Validate that a value is a string (may be empty).
|
|
23
|
+
*/
|
|
24
|
+
function isString(value, field, errors) {
|
|
25
|
+
if (typeof value !== 'string') {
|
|
26
|
+
errors.push(`${field} must be a string`);
|
|
27
|
+
return false;
|
|
28
|
+
}
|
|
29
|
+
return true;
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Validate that a value is a number.
|
|
33
|
+
*/
|
|
34
|
+
function isNumber(value, field, errors) {
|
|
35
|
+
if (typeof value !== 'number' || Number.isNaN(value)) {
|
|
36
|
+
errors.push(`${field} must be a number`);
|
|
37
|
+
return false;
|
|
38
|
+
}
|
|
39
|
+
return true;
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* Validate that a value is a boolean.
|
|
43
|
+
*/
|
|
44
|
+
function isBoolean(value, field, errors) {
|
|
45
|
+
if (typeof value !== 'boolean') {
|
|
46
|
+
errors.push(`${field} must be a boolean`);
|
|
47
|
+
return false;
|
|
48
|
+
}
|
|
49
|
+
return true;
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Validate that a value is an array.
|
|
53
|
+
*/
|
|
54
|
+
function isArray(value, field, errors) {
|
|
55
|
+
if (!Array.isArray(value)) {
|
|
56
|
+
errors.push(`${field} must be an array`);
|
|
57
|
+
return false;
|
|
58
|
+
}
|
|
59
|
+
return true;
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Validate that a value is a plain object.
|
|
63
|
+
*/
|
|
64
|
+
function isObject(value, field, errors) {
|
|
65
|
+
if (typeof value !== 'object' || value === null || Array.isArray(value)) {
|
|
66
|
+
errors.push(`${field} must be an object`);
|
|
67
|
+
return false;
|
|
68
|
+
}
|
|
69
|
+
return true;
|
|
70
|
+
}
|
|
71
|
+
/**
|
|
72
|
+
* Validate an ISO 8601 date string.
|
|
73
|
+
*/
|
|
74
|
+
function isISODateString(value, field, errors) {
|
|
75
|
+
if (typeof value !== 'string') {
|
|
76
|
+
errors.push(`${field} must be a date string`);
|
|
77
|
+
return false;
|
|
78
|
+
}
|
|
79
|
+
const date = new Date(value);
|
|
80
|
+
if (Number.isNaN(date.getTime())) {
|
|
81
|
+
errors.push(`${field} must be a valid ISO date string`);
|
|
82
|
+
return false;
|
|
83
|
+
}
|
|
84
|
+
return true;
|
|
85
|
+
}
|
|
86
|
+
/**
|
|
87
|
+
* Validate a Project object.
|
|
88
|
+
*/
|
|
89
|
+
function validateProject(project, prefix, errors) {
|
|
90
|
+
if (!isObject(project, prefix, errors))
|
|
91
|
+
return;
|
|
92
|
+
const p = project;
|
|
93
|
+
isNonEmptyString(p['id'], `${prefix}.id`, errors);
|
|
94
|
+
isNonEmptyString(p['name'], `${prefix}.name`, errors);
|
|
95
|
+
isNonEmptyString(p['path'], `${prefix}.path`, errors);
|
|
96
|
+
isISODateString(p['lastAccessed'], `${prefix}.lastAccessed`, errors);
|
|
97
|
+
if (isObject(p['git'], `${prefix}.git`, errors)) {
|
|
98
|
+
const git = p['git'];
|
|
99
|
+
isString(git['branch'], `${prefix}.git.branch`, errors);
|
|
100
|
+
isString(git['remote'], `${prefix}.git.remote`, errors);
|
|
101
|
+
isBoolean(git['hasUncommitted'], `${prefix}.git.hasUncommitted`, errors);
|
|
102
|
+
isNumber(git['stashCount'], `${prefix}.git.stashCount`, errors);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
/**
|
|
106
|
+
* Validate a StateFile structure (decrypted state.age).
|
|
107
|
+
*/
|
|
108
|
+
export function validateStateFile(data) {
|
|
109
|
+
const errors = [];
|
|
110
|
+
if (!isObject(data, 'StateFile', errors)) {
|
|
111
|
+
return { valid: false, errors };
|
|
112
|
+
}
|
|
113
|
+
const d = data;
|
|
114
|
+
// machine
|
|
115
|
+
if (isObject(d['machine'], 'machine', errors)) {
|
|
116
|
+
const machine = d['machine'];
|
|
117
|
+
isNonEmptyString(machine['id'], 'machine.id', errors);
|
|
118
|
+
isNonEmptyString(machine['hostname'], 'machine.hostname', errors);
|
|
119
|
+
}
|
|
120
|
+
// projects
|
|
121
|
+
if (isArray(d['projects'], 'projects', errors)) {
|
|
122
|
+
const projects = d['projects'];
|
|
123
|
+
for (let i = 0; i < projects.length; i++) {
|
|
124
|
+
validateProject(projects[i], `projects[${i}]`, errors);
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
return { valid: errors.length === 0, errors };
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Validate an EnvVars structure (decrypted env-vars.age).
|
|
131
|
+
*/
|
|
132
|
+
export function validateEnvVars(data) {
|
|
133
|
+
const errors = [];
|
|
134
|
+
if (!isObject(data, 'EnvVars', errors)) {
|
|
135
|
+
return { valid: false, errors };
|
|
136
|
+
}
|
|
137
|
+
const d = data;
|
|
138
|
+
for (const [projectName, vars] of Object.entries(d)) {
|
|
139
|
+
if (!isObject(vars, `EnvVars.${projectName}`, errors))
|
|
140
|
+
continue;
|
|
141
|
+
const v = vars;
|
|
142
|
+
for (const [key, entry] of Object.entries(v)) {
|
|
143
|
+
const prefix = `EnvVars.${projectName}.${key}`;
|
|
144
|
+
if (isObject(entry, prefix, errors)) {
|
|
145
|
+
const e = entry;
|
|
146
|
+
isString(e['value'], `${prefix}.value`, errors);
|
|
147
|
+
isISODateString(e['addedAt'], `${prefix}.addedAt`, errors);
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
return { valid: errors.length === 0, errors };
|
|
152
|
+
}
|
|
153
|
+
/**
|
|
154
|
+
* Validate a Manifest structure (manifest.json).
|
|
155
|
+
*/
|
|
156
|
+
export function validateManifest(data) {
|
|
157
|
+
const errors = [];
|
|
158
|
+
if (!isObject(data, 'Manifest', errors)) {
|
|
159
|
+
return { valid: false, errors };
|
|
160
|
+
}
|
|
161
|
+
const d = data;
|
|
162
|
+
isNonEmptyString(d['version'], 'version', errors);
|
|
163
|
+
isISODateString(d['lastSync'], 'lastSync', errors);
|
|
164
|
+
if (isObject(d['files'], 'files', errors)) {
|
|
165
|
+
const files = d['files'];
|
|
166
|
+
for (const [filename, entry] of Object.entries(files)) {
|
|
167
|
+
if (isObject(entry, `files.${filename}`, errors)) {
|
|
168
|
+
const e = entry;
|
|
169
|
+
isISODateString(e['lastModified'], `files.${filename}.lastModified`, errors);
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
return { valid: errors.length === 0, errors };
|
|
174
|
+
}
|
|
175
|
+
/**
|
|
176
|
+
* Validate a DockerState structure (decrypted docker-state.age).
|
|
177
|
+
*/
|
|
178
|
+
export function validateDockerState(data) {
|
|
179
|
+
const errors = [];
|
|
180
|
+
if (!isObject(data, 'DockerState', errors)) {
|
|
181
|
+
return { valid: false, errors };
|
|
182
|
+
}
|
|
183
|
+
const d = data;
|
|
184
|
+
for (const [projectName, state] of Object.entries(d)) {
|
|
185
|
+
const prefix = `DockerState.${projectName}`;
|
|
186
|
+
if (!isObject(state, prefix, errors))
|
|
187
|
+
continue;
|
|
188
|
+
const s = state;
|
|
189
|
+
isString(s['composeFile'], `${prefix}.composeFile`, errors);
|
|
190
|
+
if (isArray(s['services'], `${prefix}.services`, errors)) {
|
|
191
|
+
const services = s['services'];
|
|
192
|
+
for (let i = 0; i < services.length; i++) {
|
|
193
|
+
const sp = `${prefix}.services[${i}]`;
|
|
194
|
+
if (isObject(services[i], sp, errors)) {
|
|
195
|
+
const svc = services[i];
|
|
196
|
+
isNonEmptyString(svc['name'], `${sp}.name`, errors);
|
|
197
|
+
isString(svc['image'], `${sp}.image`, errors);
|
|
198
|
+
isNumber(svc['port'], `${sp}.port`, errors);
|
|
199
|
+
isBoolean(svc['autoStart'], `${sp}.autoStart`, errors);
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
return { valid: errors.length === 0, errors };
|
|
205
|
+
}
|
|
206
|
+
/**
|
|
207
|
+
* Validate a MentalContext structure (decrypted mental-context.age).
|
|
208
|
+
*/
|
|
209
|
+
export function validateMentalContext(data) {
|
|
210
|
+
const errors = [];
|
|
211
|
+
if (!isObject(data, 'MentalContext', errors)) {
|
|
212
|
+
return { valid: false, errors };
|
|
213
|
+
}
|
|
214
|
+
const d = data;
|
|
215
|
+
for (const [projectName, context] of Object.entries(d)) {
|
|
216
|
+
const prefix = `MentalContext.${projectName}`;
|
|
217
|
+
if (!isObject(context, prefix, errors))
|
|
218
|
+
continue;
|
|
219
|
+
const c = context;
|
|
220
|
+
isString(c['currentTask'], `${prefix}.currentTask`, errors);
|
|
221
|
+
if (c['nextSteps'] !== undefined) {
|
|
222
|
+
isArray(c['nextSteps'], `${prefix}.nextSteps`, errors);
|
|
223
|
+
}
|
|
224
|
+
if (c['blockers'] !== undefined) {
|
|
225
|
+
isArray(c['blockers'], `${prefix}.blockers`, errors);
|
|
226
|
+
}
|
|
227
|
+
if (c['relatedLinks'] !== undefined) {
|
|
228
|
+
isArray(c['relatedLinks'], `${prefix}.relatedLinks`, errors);
|
|
229
|
+
}
|
|
230
|
+
if (c['breadcrumbs'] !== undefined) {
|
|
231
|
+
isArray(c['breadcrumbs'], `${prefix}.breadcrumbs`, errors);
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
return { valid: errors.length === 0, errors };
|
|
235
|
+
}
|
|
236
|
+
/**
|
|
237
|
+
* Validate a ServiceState structure (decrypted services.age).
|
|
238
|
+
*/
|
|
239
|
+
export function validateServiceState(data) {
|
|
240
|
+
const errors = [];
|
|
241
|
+
if (!isObject(data, 'ServiceState', errors)) {
|
|
242
|
+
return { valid: false, errors };
|
|
243
|
+
}
|
|
244
|
+
const d = data;
|
|
245
|
+
if (isArray(d['services'], 'services', errors)) {
|
|
246
|
+
const services = d['services'];
|
|
247
|
+
for (let i = 0; i < services.length; i++) {
|
|
248
|
+
const prefix = `services[${i}]`;
|
|
249
|
+
if (isObject(services[i], prefix, errors)) {
|
|
250
|
+
const svc = services[i];
|
|
251
|
+
isString(svc['project'], `${prefix}.project`, errors);
|
|
252
|
+
isNonEmptyString(svc['name'], `${prefix}.name`, errors);
|
|
253
|
+
isNumber(svc['port'], `${prefix}.port`, errors);
|
|
254
|
+
isString(svc['command'], `${prefix}.command`, errors);
|
|
255
|
+
isBoolean(svc['autoStart'], `${prefix}.autoStart`, errors);
|
|
256
|
+
}
|
|
257
|
+
}
|
|
258
|
+
}
|
|
259
|
+
return { valid: errors.length === 0, errors };
|
|
260
|
+
}
|
|
261
|
+
/**
|
|
262
|
+
* Validate a DirectoryState structure (decrypted directories.age).
|
|
263
|
+
*/
|
|
264
|
+
export function validateDirectoryState(data) {
|
|
265
|
+
const errors = [];
|
|
266
|
+
if (!isObject(data, 'DirectoryState', errors)) {
|
|
267
|
+
return { valid: false, errors };
|
|
268
|
+
}
|
|
269
|
+
const d = data;
|
|
270
|
+
if (isArray(d['recentDirs'], 'recentDirs', errors)) {
|
|
271
|
+
const dirs = d['recentDirs'];
|
|
272
|
+
for (let i = 0; i < dirs.length; i++) {
|
|
273
|
+
const prefix = `recentDirs[${i}]`;
|
|
274
|
+
if (isObject(dirs[i], prefix, errors)) {
|
|
275
|
+
const dir = dirs[i];
|
|
276
|
+
isNonEmptyString(dir['path'], `${prefix}.path`, errors);
|
|
277
|
+
isNumber(dir['frequency'], `${prefix}.frequency`, errors);
|
|
278
|
+
isISODateString(dir['lastVisit'], `${prefix}.lastVisit`, errors);
|
|
279
|
+
}
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
if (isArray(d['pinnedDirs'], 'pinnedDirs', errors)) {
|
|
283
|
+
const pinned = d['pinnedDirs'];
|
|
284
|
+
for (let i = 0; i < pinned.length; i++) {
|
|
285
|
+
isString(pinned[i], `pinnedDirs[${i}]`, errors);
|
|
286
|
+
}
|
|
287
|
+
}
|
|
288
|
+
return { valid: errors.length === 0, errors };
|
|
289
|
+
}
|
|
290
|
+
//# sourceMappingURL=schemas.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"schemas.js","sourceRoot":"","sources":["../src/schemas.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared TypeScript type definitions for ctx-sync state files.
|
|
3
|
+
*
|
|
4
|
+
* These interfaces describe the **decrypted in-memory** representation
|
|
5
|
+
* of each state file. On disk and in Git, all state is encrypted as .age blobs.
|
|
6
|
+
*/
|
|
7
|
+
/** A tracked project */
|
|
8
|
+
export interface Project {
|
|
9
|
+
id: string;
|
|
10
|
+
name: string;
|
|
11
|
+
path: string;
|
|
12
|
+
git: {
|
|
13
|
+
branch: string;
|
|
14
|
+
remote: string;
|
|
15
|
+
hasUncommitted: boolean;
|
|
16
|
+
stashCount: number;
|
|
17
|
+
};
|
|
18
|
+
lastAccessed: string;
|
|
19
|
+
}
|
|
20
|
+
/** Machine metadata */
|
|
21
|
+
export interface MachineInfo {
|
|
22
|
+
id: string;
|
|
23
|
+
hostname: string;
|
|
24
|
+
}
|
|
25
|
+
/** Decrypted state.age structure */
|
|
26
|
+
export interface StateFile {
|
|
27
|
+
machine: MachineInfo;
|
|
28
|
+
projects: Project[];
|
|
29
|
+
}
|
|
30
|
+
/** A single environment variable */
|
|
31
|
+
export interface EnvVarEntry {
|
|
32
|
+
value: string;
|
|
33
|
+
addedAt: string;
|
|
34
|
+
}
|
|
35
|
+
/** Decrypted env-vars.age structure: project name → key → entry */
|
|
36
|
+
export interface EnvVars {
|
|
37
|
+
[projectName: string]: {
|
|
38
|
+
[key: string]: EnvVarEntry;
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
/** Docker service entry */
|
|
42
|
+
export interface DockerService {
|
|
43
|
+
name: string;
|
|
44
|
+
container: string;
|
|
45
|
+
image: string;
|
|
46
|
+
port: number;
|
|
47
|
+
volumes?: string[];
|
|
48
|
+
autoStart: boolean;
|
|
49
|
+
healthCheck?: string;
|
|
50
|
+
}
|
|
51
|
+
/** Decrypted docker-state.age structure */
|
|
52
|
+
export interface DockerState {
|
|
53
|
+
[projectName: string]: {
|
|
54
|
+
composeFile: string;
|
|
55
|
+
services: DockerService[];
|
|
56
|
+
networks?: string[];
|
|
57
|
+
lastStarted?: string;
|
|
58
|
+
};
|
|
59
|
+
}
|
|
60
|
+
/** A blocker entry */
|
|
61
|
+
export interface Blocker {
|
|
62
|
+
description: string;
|
|
63
|
+
addedAt: string;
|
|
64
|
+
priority: 'low' | 'medium' | 'high';
|
|
65
|
+
}
|
|
66
|
+
/** A related link */
|
|
67
|
+
export interface RelatedLink {
|
|
68
|
+
title: string;
|
|
69
|
+
url: string;
|
|
70
|
+
}
|
|
71
|
+
/** A breadcrumb entry */
|
|
72
|
+
export interface Breadcrumb {
|
|
73
|
+
note: string;
|
|
74
|
+
timestamp: string;
|
|
75
|
+
}
|
|
76
|
+
/** Mental context for a project */
|
|
77
|
+
export interface ProjectMentalContext {
|
|
78
|
+
currentTask: string;
|
|
79
|
+
lastWorkingOn?: {
|
|
80
|
+
file: string;
|
|
81
|
+
line: number;
|
|
82
|
+
column?: number;
|
|
83
|
+
description: string;
|
|
84
|
+
timestamp: string;
|
|
85
|
+
};
|
|
86
|
+
blockers: Blocker[];
|
|
87
|
+
nextSteps: string[];
|
|
88
|
+
relatedLinks: RelatedLink[];
|
|
89
|
+
breadcrumbs: Breadcrumb[];
|
|
90
|
+
}
|
|
91
|
+
/** Decrypted mental-context.age structure */
|
|
92
|
+
export interface MentalContext {
|
|
93
|
+
[projectName: string]: ProjectMentalContext;
|
|
94
|
+
}
|
|
95
|
+
/** A running service entry */
|
|
96
|
+
export interface Service {
|
|
97
|
+
project: string;
|
|
98
|
+
name: string;
|
|
99
|
+
port: number;
|
|
100
|
+
command: string;
|
|
101
|
+
autoStart: boolean;
|
|
102
|
+
}
|
|
103
|
+
/** Decrypted services.age structure */
|
|
104
|
+
export interface ServiceState {
|
|
105
|
+
services: Service[];
|
|
106
|
+
}
|
|
107
|
+
/** A recent directory entry */
|
|
108
|
+
export interface RecentDirectory {
|
|
109
|
+
path: string;
|
|
110
|
+
frequency: number;
|
|
111
|
+
lastVisit: string;
|
|
112
|
+
}
|
|
113
|
+
/** Decrypted directories.age structure */
|
|
114
|
+
export interface DirectoryState {
|
|
115
|
+
recentDirs: RecentDirectory[];
|
|
116
|
+
pinnedDirs: string[];
|
|
117
|
+
}
|
|
118
|
+
/** A team member / recipient */
|
|
119
|
+
export interface TeamMember {
|
|
120
|
+
name: string;
|
|
121
|
+
publicKey: string;
|
|
122
|
+
addedAt: string;
|
|
123
|
+
/** Key fingerprint for out-of-band verification */
|
|
124
|
+
fingerprint: string;
|
|
125
|
+
}
|
|
126
|
+
/** Recipients configuration stored in config dir (never synced) */
|
|
127
|
+
export interface RecipientsConfig {
|
|
128
|
+
/** The owner's public key */
|
|
129
|
+
ownerPublicKey: string;
|
|
130
|
+
/** Team members (recipients) added by the owner */
|
|
131
|
+
members: TeamMember[];
|
|
132
|
+
}
|
|
133
|
+
/**
|
|
134
|
+
* User configuration stored in ~/.config/ctx-sync/config.json (never synced).
|
|
135
|
+
*
|
|
136
|
+
* Contains local preferences such as custom safe-list additions.
|
|
137
|
+
*/
|
|
138
|
+
export interface UserConfig {
|
|
139
|
+
/** Custom env var keys added to the safe-list (merged with DEFAULT_SAFE_LIST) */
|
|
140
|
+
safeList?: string[];
|
|
141
|
+
}
|
|
142
|
+
/** File metadata in manifest */
|
|
143
|
+
export interface ManifestFileEntry {
|
|
144
|
+
lastModified: string;
|
|
145
|
+
}
|
|
146
|
+
/** manifest.json structure (only plaintext file in Git) */
|
|
147
|
+
export interface Manifest {
|
|
148
|
+
version: string;
|
|
149
|
+
lastSync: string;
|
|
150
|
+
files: {
|
|
151
|
+
[filename: string]: ManifestFileEntry;
|
|
152
|
+
};
|
|
153
|
+
}
|
|
154
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared TypeScript type definitions for ctx-sync state files.
|
|
3
|
+
*
|
|
4
|
+
* These interfaces describe the **decrypted in-memory** representation
|
|
5
|
+
* of each state file. On disk and in Git, all state is encrypted as .age blobs.
|
|
6
|
+
*/
|
|
7
|
+
export {};
|
|
8
|
+
//# sourceMappingURL=types.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;;;;GAKG"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@ctx-sync/shared",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "Shared constants, types, and utilities for ctx-sync",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "dist/index.js",
|
|
7
|
+
"types": "dist/index.d.ts",
|
|
8
|
+
"scripts": {
|
|
9
|
+
"build": "tsc",
|
|
10
|
+
"typecheck": "tsc --noEmit",
|
|
11
|
+
"test": "NODE_OPTIONS='--experimental-vm-modules' jest"
|
|
12
|
+
},
|
|
13
|
+
"license": "MIT",
|
|
14
|
+
"devDependencies": {
|
|
15
|
+
"@types/jest": "30.0.0",
|
|
16
|
+
"jest": "30.2.0",
|
|
17
|
+
"ts-jest": "29.4.6"
|
|
18
|
+
}
|
|
19
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "ctx-sync",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.2",
|
|
4
4
|
"description": "Sync your complete development context across machines using Git",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -13,6 +13,9 @@
|
|
|
13
13
|
"README.md",
|
|
14
14
|
"LICENSE"
|
|
15
15
|
],
|
|
16
|
+
"bundledDependencies": [
|
|
17
|
+
"@ctx-sync/shared"
|
|
18
|
+
],
|
|
16
19
|
"scripts": {
|
|
17
20
|
"build": "tsc",
|
|
18
21
|
"typecheck": "tsc --noEmit",
|
|
@@ -48,6 +51,7 @@
|
|
|
48
51
|
"ts-jest": "29.4.6"
|
|
49
52
|
},
|
|
50
53
|
"dependencies": {
|
|
54
|
+
"@ctx-sync/shared": "1.0.0",
|
|
51
55
|
"age-encryption": "0.3.0",
|
|
52
56
|
"chalk": "5.6.2",
|
|
53
57
|
"commander": "14.0.3",
|