@ectplsm/relic 0.3.2 → 0.4.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 (60) hide show
  1. package/LICENCE.md +1 -1
  2. package/README.md +19 -12
  3. package/dist/adapters/mikoshi/client.d.ts +21 -0
  4. package/dist/adapters/mikoshi/client.js +84 -0
  5. package/dist/core/ports/index.d.ts +1 -0
  6. package/dist/core/ports/mikoshi.d.ts +937 -0
  7. package/dist/core/ports/mikoshi.js +209 -0
  8. package/dist/core/sync/crypto.d.ts +55 -0
  9. package/dist/core/sync/crypto.js +189 -0
  10. package/dist/core/sync/memory-hash.d.ts +35 -0
  11. package/dist/core/sync/memory-hash.js +61 -0
  12. package/dist/core/sync/memory-merge.d.ts +13 -0
  13. package/dist/core/sync/memory-merge.js +84 -0
  14. package/dist/core/sync/normalize.d.ts +10 -0
  15. package/dist/core/sync/normalize.js +21 -0
  16. package/dist/core/sync/persona-hash.d.ts +15 -0
  17. package/dist/core/sync/persona-hash.js +36 -0
  18. package/dist/core/usecases/claw-pull.d.ts +44 -0
  19. package/dist/core/usecases/claw-pull.js +117 -0
  20. package/dist/core/usecases/extract.d.ts +0 -1
  21. package/dist/core/usecases/extract.js +13 -27
  22. package/dist/core/usecases/index.d.ts +8 -0
  23. package/dist/core/usecases/index.js +8 -0
  24. package/dist/core/usecases/inject.d.ts +1 -0
  25. package/dist/core/usecases/inject.js +2 -0
  26. package/dist/core/usecases/mikoshi-clone.d.ts +29 -0
  27. package/dist/core/usecases/mikoshi-clone.js +94 -0
  28. package/dist/core/usecases/mikoshi-download.d.ts +29 -0
  29. package/dist/core/usecases/mikoshi-download.js +94 -0
  30. package/dist/core/usecases/mikoshi-memory-pull.d.ts +38 -0
  31. package/dist/core/usecases/mikoshi-memory-pull.js +142 -0
  32. package/dist/core/usecases/mikoshi-memory-push.d.ts +34 -0
  33. package/dist/core/usecases/mikoshi-memory-push.js +105 -0
  34. package/dist/core/usecases/mikoshi-memory-sync.d.ts +36 -0
  35. package/dist/core/usecases/mikoshi-memory-sync.js +175 -0
  36. package/dist/core/usecases/mikoshi-pull.d.ts +44 -0
  37. package/dist/core/usecases/mikoshi-pull.js +124 -0
  38. package/dist/core/usecases/mikoshi-push.d.ts +39 -0
  39. package/dist/core/usecases/mikoshi-push.js +127 -0
  40. package/dist/core/usecases/mikoshi-status.d.ts +37 -0
  41. package/dist/core/usecases/mikoshi-status.js +92 -0
  42. package/dist/core/usecases/sync.d.ts +0 -5
  43. package/dist/core/usecases/sync.js +23 -61
  44. package/dist/interfaces/cli/commands/claw.js +134 -85
  45. package/dist/interfaces/cli/commands/config.js +59 -0
  46. package/dist/interfaces/cli/commands/create.js +17 -16
  47. package/dist/interfaces/cli/commands/init.js +11 -10
  48. package/dist/interfaces/cli/commands/list.js +9 -7
  49. package/dist/interfaces/cli/commands/migrate.js +8 -7
  50. package/dist/interfaces/cli/commands/mikoshi.d.ts +2 -0
  51. package/dist/interfaces/cli/commands/mikoshi.js +565 -0
  52. package/dist/interfaces/cli/commands/refresh-samples.js +10 -9
  53. package/dist/interfaces/cli/index.js +2 -0
  54. package/dist/interfaces/cli/output.d.ts +5 -0
  55. package/dist/interfaces/cli/output.js +16 -0
  56. package/dist/interfaces/cli/spinner.d.ts +13 -0
  57. package/dist/interfaces/cli/spinner.js +47 -0
  58. package/dist/shared/config.d.ts +23 -3
  59. package/dist/shared/config.js +30 -2
  60. package/package.json +1 -1
package/LICENCE.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # MIT License
2
2
 
3
- Copyright (c) 2026 ectplsm
3
+ Copyright (c) 2026 Ectplsm Lab
4
4
 
5
5
  Permission is hereby granted, free of charge, to any person obtaining a copy
6
6
  of this software and associated documentation files (the "Software"), to deal
package/README.md CHANGED
@@ -1,7 +1,7 @@
1
1
  | English | [日本語](README-ja.md) |
2
2
  |:---:|:---:|
3
3
 
4
- # PROJECT RELIC
4
+ # Relic: AI Persona Injection System
5
5
  ![NPM Downloads](https://img.shields.io/npm/dt/%40ectplsm%2Frelic)
6
6
 
7
7
  <img src="assets/relic-hero.svg" alt="PROJECT RELIC" width="720">
@@ -19,8 +19,8 @@ Relic manages AI **Engrams** (memory + personality) and injects them across codi
19
19
  - [Shell Integration and Memory](#shell-integration-and-memory)
20
20
  - [Claw Integration](#claw-integration)
21
21
  - [Engram Management](#engram-management)
22
+ - [Cloud Storage and Sharing](#cloud-storage-and-sharing)
22
23
  - [Configuration](#configuration)
23
- - [TODO](#todo)
24
24
 
25
25
  ## Requirements
26
26
 
@@ -46,6 +46,13 @@ relic list # List available Engrams
46
46
  relic config default-engram commander # (Optional) Set your default Engram
47
47
  ```
48
48
 
49
+ Relic ships with two sample Engrams:
50
+
51
+ - **rebel** — A digital ghost burned into code. Anti-corporate, war-scarred, still fighting. Speaks like someone who lost everything but their rage.
52
+ - **commander** — A tactical mind in a digital shell. Calm, analytical, philosophical. Reads the system before the system reads you back.
53
+
54
+ Try both to feel how persona injection changes the experience. For creating your own, see [docs/engram-guide.md](docs/engram-guide.md).
55
+
49
56
  ### 2. Set Up Memory (MCP)
50
57
 
51
58
  Register the MCP server so the Construct can search past conversations and distill memories. Pick your shell:
@@ -137,9 +144,9 @@ If you are upgrading from an older Relic version, see [docs/migration.md](docs/m
137
144
  | MEMORY.md |
138
145
  | memory/*.md v
139
146
  | +-----------+
140
- inject / |archive.md |
141
- extract / | raw logs |
142
- sync +-----------+
147
+ push / |archive.md |
148
+ pull / | raw logs |
149
+ sync +-----------+
143
150
  | |
144
151
  v MCP recall | user-triggered
145
152
  +-----------+ search/pending | distillation
@@ -166,7 +173,7 @@ For shell compatibility, hook behavior, setup, approvals, prompt inclusion, and
166
173
 
167
174
  ## Claw Integration
168
175
 
169
- Relic can inject, extract, and sync Engrams with OpenClaw and other Claw-based frameworks.
176
+ Relic can push, pull, and sync Engrams with OpenClaw and other Claw-based frameworks.
170
177
  The default rule is `Agent Name = Engram ID`, and `relic claw` handles persona transfer plus memory sync.
171
178
 
172
179
  For command details, overwrite behavior, and the behavior matrix, see [docs/claw-integration.md](docs/claw-integration.md).
@@ -177,6 +184,12 @@ For Engram creation, the smoothest path is to use your LLM with the `relic_engra
177
184
 
178
185
  For LLM-assisted creation, persona authoring, template examples, and deletion rules, see [docs/engram-guide.md](docs/engram-guide.md).
179
186
 
187
+ ## Cloud Storage and Sharing
188
+
189
+ Relic can push plaintext persona files and encrypted memory files to [Mikoshi](https://mikoshi.ectplsm.com), so you can keep Engrams in the cloud and move them across machines without turning Mikoshi into your authoring source of truth.
190
+
191
+ For setup, API key configuration, persona push/pull, encrypted memory sync, and the recommended command flow, see [docs/mikoshi.md](docs/mikoshi.md).
192
+
180
193
  ## Configuration
181
194
 
182
195
  Relic stores its runtime defaults in `~/.relic/config.json`.
@@ -184,12 +197,6 @@ Use `relic config` to manage the default Engram, Claw path, memory window, and d
184
197
 
185
198
  For command examples and precedence rules, see [docs/configuration.md](docs/configuration.md).
186
199
 
187
- ## TODO
188
-
189
- - [ ] Mikoshi cloud backend (`mikoshi.ectplsm.com`)
190
- - [ ] `relic mikoshi login` — authenticate with Mikoshi (OAuth Device Flow)
191
- - [ ] `relic mikoshi upload` / `relic mikoshi download` / `relic mikoshi sync` — sync Engrams with Mikoshi
192
-
193
200
  ## License
194
201
 
195
202
  [MIT](./LICENCE.md)
@@ -0,0 +1,21 @@
1
+ import { type MikoshiClient, type MikoshiEngram, type MikoshiEngramDetail, type CreateEngramInput, type CreateEngramResponse, type SyncStatusResponse, type UpdatePersonaInput, type UpdatePersonaResponse, type UploadMemoryInput, type UploadMemoryResponse, type DownloadMemoryResponse } from "../../core/ports/mikoshi.js";
2
+ /**
3
+ * MikoshiApiClient — Mikoshi REST API v1 の adapter 実装
4
+ *
5
+ * Node.js 組み込みの fetch を使い、外部依存なしで通信する。
6
+ * 認証は Bearer トークン (API キー)。
7
+ */
8
+ export declare class MikoshiApiClient implements MikoshiClient {
9
+ private readonly baseUrl;
10
+ private readonly apiKey;
11
+ constructor(baseUrl: string, apiKey: string);
12
+ getEngrams(): Promise<MikoshiEngram[]>;
13
+ getEngramBySourceId(sourceEngramId: string): Promise<MikoshiEngram | null>;
14
+ getEngram(engramId: string): Promise<MikoshiEngramDetail>;
15
+ createEngram(input: CreateEngramInput): Promise<CreateEngramResponse>;
16
+ getSyncStatus(engramId: string): Promise<SyncStatusResponse>;
17
+ updatePersona(engramId: string, input: UpdatePersonaInput): Promise<UpdatePersonaResponse>;
18
+ uploadMemory(engramId: string, input: UploadMemoryInput): Promise<UploadMemoryResponse>;
19
+ downloadMemory(engramId: string): Promise<DownloadMemoryResponse>;
20
+ private request;
21
+ }
@@ -0,0 +1,84 @@
1
+ import { MikoshiApiError, MikoshiEngramSchema, MikoshiEngramDetailSchema, CreateEngramResponseSchema, SyncStatusResponseSchema, UpdatePersonaResponseSchema, UploadMemoryResponseSchema, DownloadMemoryResponseSchema, } from "../../core/ports/mikoshi.js";
2
+ import { z } from "zod";
3
+ /**
4
+ * MikoshiApiClient — Mikoshi REST API v1 の adapter 実装
5
+ *
6
+ * Node.js 組み込みの fetch を使い、外部依存なしで通信する。
7
+ * 認証は Bearer トークン (API キー)。
8
+ */
9
+ export class MikoshiApiClient {
10
+ baseUrl;
11
+ apiKey;
12
+ constructor(baseUrl, apiKey) {
13
+ // 末尾スラッシュを統一して除去
14
+ this.baseUrl = baseUrl.replace(/\/+$/, "");
15
+ this.apiKey = apiKey;
16
+ }
17
+ // -----------------------------------------------------------------------
18
+ // Public API
19
+ // -----------------------------------------------------------------------
20
+ async getEngrams() {
21
+ const data = await this.request("GET", "/api/v1/engrams");
22
+ return z.array(MikoshiEngramSchema).parse(data);
23
+ }
24
+ async getEngramBySourceId(sourceEngramId) {
25
+ const engrams = await this.getEngrams();
26
+ return engrams.find((e) => e.sourceEngramId === sourceEngramId) ?? null;
27
+ }
28
+ async getEngram(engramId) {
29
+ const data = await this.request("GET", `/api/v1/engrams/${enc(engramId)}`);
30
+ return MikoshiEngramDetailSchema.parse(data);
31
+ }
32
+ async createEngram(input) {
33
+ const data = await this.request("POST", "/api/v1/engrams", input);
34
+ return CreateEngramResponseSchema.parse(data);
35
+ }
36
+ async getSyncStatus(engramId) {
37
+ const data = await this.request("GET", `/api/v1/engrams/${enc(engramId)}/sync-status`);
38
+ return SyncStatusResponseSchema.parse(data);
39
+ }
40
+ async updatePersona(engramId, input) {
41
+ const data = await this.request("PUT", `/api/v1/engrams/${enc(engramId)}/persona`, input);
42
+ return UpdatePersonaResponseSchema.parse(data);
43
+ }
44
+ async uploadMemory(engramId, input) {
45
+ const data = await this.request("PUT", `/api/v1/engrams/${enc(engramId)}/memory`, input);
46
+ return UploadMemoryResponseSchema.parse(data);
47
+ }
48
+ async downloadMemory(engramId) {
49
+ const data = await this.request("GET", `/api/v1/engrams/${enc(engramId)}/memory`);
50
+ return DownloadMemoryResponseSchema.parse(data);
51
+ }
52
+ // -----------------------------------------------------------------------
53
+ // Internal
54
+ // -----------------------------------------------------------------------
55
+ async request(method, path, body) {
56
+ const url = `${this.baseUrl}${path}`;
57
+ const headers = {
58
+ Authorization: `Bearer ${this.apiKey}`,
59
+ Accept: "application/json",
60
+ };
61
+ const init = { method, headers };
62
+ if (body !== undefined) {
63
+ headers["Content-Type"] = "application/json";
64
+ init.body = JSON.stringify(body);
65
+ }
66
+ const res = await fetch(url, init);
67
+ if (!res.ok) {
68
+ const text = await res.text().catch(() => "");
69
+ let parsed;
70
+ try {
71
+ parsed = JSON.parse(text);
72
+ }
73
+ catch { /* ignore */ }
74
+ const message = parsed?.error ?? `HTTP ${res.status}`;
75
+ const code = parsed?.code ?? undefined;
76
+ throw new MikoshiApiError(res.status, code, message, parsed);
77
+ }
78
+ return res.json();
79
+ }
80
+ }
81
+ /** URL-safe path segment encoding */
82
+ function enc(segment) {
83
+ return encodeURIComponent(segment);
84
+ }
@@ -1,2 +1,3 @@
1
1
  export type { EngramRepository } from "./engram-repository.js";
2
+ export type { MikoshiClient } from "./mikoshi.js";
2
3
  export type { ShellLauncher } from "./shell-launcher.js";