holosphere 1.1.12 → 1.1.14
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/federation.js +25 -8
- package/holosphere-bundle.esm.js +33184 -0
- package/holosphere-bundle.js +33215 -0
- package/holosphere-bundle.min.js +39 -0
- package/package.json +78 -3
- package/.cursor/rules/futura.mdc +0 -55
- package/examples/federation.js +0 -162
- package/examples/hologram-updates-example.js +0 -106
- package/examples/holograms.js +0 -175
- package/test/auth.test.js +0 -275
- package/test/delete.test.js +0 -229
- package/test/federation.test.js +0 -349
- package/test/hologram-deletion.test.js +0 -197
- package/test/hologram-updates-return.test.js +0 -166
- package/test/hologram-updates.test.js +0 -143
- package/test/hologram.test.js +0 -316
- package/test/holosphere.test.js +0 -354
- package/test/meta-strip.test.js +0 -159
- package/test/parent-propagation.test.js +0 -138
- package/test/subscription.test.js +0 -364
package/package.json
CHANGED
|
@@ -1,14 +1,20 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "holosphere",
|
|
3
|
-
"version": "1.1.
|
|
3
|
+
"version": "1.1.14",
|
|
4
4
|
"description": "Holonic Geospatial Communication Infrastructure",
|
|
5
5
|
"main": "holosphere.js",
|
|
6
6
|
"types": "holosphere.d.ts",
|
|
7
7
|
"type": "module",
|
|
8
8
|
"scripts": {
|
|
9
9
|
"test": "node --experimental-vm-modules node_modules/jest/bin/jest.js",
|
|
10
|
-
"build": "",
|
|
11
|
-
"prepare": "npm run build"
|
|
10
|
+
"build": "npm run build:browser",
|
|
11
|
+
"prepare": "npm run build",
|
|
12
|
+
"build:browser": "node build.js",
|
|
13
|
+
"build:bundle": "node build.js",
|
|
14
|
+
"prepublishOnly": "npm run build",
|
|
15
|
+
"publish:cdn": "npm publish && echo 'Package published to npm and will be available on CDNs within minutes'",
|
|
16
|
+
"publish:force": "npm publish --force && echo 'Package force published to npm and will be available on CDNs within minutes'",
|
|
17
|
+
"prepublish:skip-tests": "npm run build"
|
|
12
18
|
},
|
|
13
19
|
"author": "Roberto Valenti",
|
|
14
20
|
"license": "GPL-3.0-or-later",
|
|
@@ -19,11 +25,80 @@
|
|
|
19
25
|
"openai": "^4.85.1"
|
|
20
26
|
},
|
|
21
27
|
"devDependencies": {
|
|
28
|
+
"esbuild": "^0.25.5",
|
|
22
29
|
"jest": "^29.7.0",
|
|
23
30
|
"jest-environment-node": "^29.7.0"
|
|
24
31
|
},
|
|
25
32
|
"jest": {
|
|
26
33
|
"testEnvironment": "node",
|
|
27
34
|
"transform": {}
|
|
35
|
+
},
|
|
36
|
+
"browser": "holosphere-bundle.js",
|
|
37
|
+
"unpkg": "holosphere-bundle.js",
|
|
38
|
+
"jsdelivr": "holosphere-bundle.js",
|
|
39
|
+
"cdn": "holosphere-bundle.js",
|
|
40
|
+
"files": [
|
|
41
|
+
"holosphere.js",
|
|
42
|
+
"holosphere-bundle.js",
|
|
43
|
+
"holosphere-bundle.min.js",
|
|
44
|
+
"holosphere-bundle.esm.js",
|
|
45
|
+
"holosphere.d.ts",
|
|
46
|
+
"federation.js",
|
|
47
|
+
"schema.js",
|
|
48
|
+
"content.js",
|
|
49
|
+
"node.js",
|
|
50
|
+
"global.js",
|
|
51
|
+
"hologram.js",
|
|
52
|
+
"compute.js",
|
|
53
|
+
"utils.js",
|
|
54
|
+
"hexlib.js",
|
|
55
|
+
"README.md",
|
|
56
|
+
"LICENSE",
|
|
57
|
+
"FEDERATION.md"
|
|
58
|
+
],
|
|
59
|
+
"exports": {
|
|
60
|
+
".": {
|
|
61
|
+
"browser": "./holosphere-bundle.js",
|
|
62
|
+
"import": "./holosphere.js",
|
|
63
|
+
"require": "./holosphere.js",
|
|
64
|
+
"default": "./holosphere.js"
|
|
65
|
+
},
|
|
66
|
+
"./bundle": "./holosphere-bundle.js",
|
|
67
|
+
"./bundle/esm": "./holosphere-bundle.esm.js",
|
|
68
|
+
"./bundle/min": "./holosphere-bundle.min.js",
|
|
69
|
+
"./browser": "./holosphere-bundle.js",
|
|
70
|
+
"./node": "./holosphere.js"
|
|
71
|
+
},
|
|
72
|
+
"repository": {
|
|
73
|
+
"type": "git",
|
|
74
|
+
"url": "git+https://github.com/rvalenti/holosphere.git"
|
|
75
|
+
},
|
|
76
|
+
"keywords": [
|
|
77
|
+
"holonic",
|
|
78
|
+
"geospatial",
|
|
79
|
+
"h3",
|
|
80
|
+
"hexagon",
|
|
81
|
+
"p2p",
|
|
82
|
+
"decentralized",
|
|
83
|
+
"gun",
|
|
84
|
+
"spatial",
|
|
85
|
+
"mapping",
|
|
86
|
+
"cdn",
|
|
87
|
+
"browser",
|
|
88
|
+
"realtime",
|
|
89
|
+
"webrtc"
|
|
90
|
+
],
|
|
91
|
+
"bugs": {
|
|
92
|
+
"url": "https://github.com/rvalenti/holosphere/issues"
|
|
93
|
+
},
|
|
94
|
+
"homepage": "https://github.com/rvalenti/holosphere#readme",
|
|
95
|
+
"peerDependencies": {
|
|
96
|
+
"gun": "^0.2020.1240",
|
|
97
|
+
"h3-js": "^4.1.0"
|
|
98
|
+
},
|
|
99
|
+
"peerDependenciesMeta": {
|
|
100
|
+
"openai": {
|
|
101
|
+
"optional": true
|
|
102
|
+
}
|
|
28
103
|
}
|
|
29
104
|
}
|
package/.cursor/rules/futura.mdc
DELETED
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
description:
|
|
3
|
-
globs:
|
|
4
|
-
alwaysApply: true
|
|
5
|
-
---
|
|
6
|
-
## 1. Collaboration with PRD Development
|
|
7
|
-
- Do not start coding until the PRD is provided.
|
|
8
|
-
- Once I send the completed PRD, use it as the definitive guide for all tasks, referring to it before starting any work.
|
|
9
|
-
- Treat the PRD as a living document that may evolve; check for updates before each task and adjust plans accordingly.
|
|
10
|
-
- Reference the PRD’s user stories, acceptance criteria, and priority levels (Must-have, Should-have, Could-have, Won’t-have) to guide coding and testing decisions.
|
|
11
|
-
- Never use React, libraries are outdated and gives too many problems of compatibility and stability, go for Python in doubt
|
|
12
|
-
- Do not build frontend and backend in separate folders and instaces as it seems that you will have a lot of trouble in managing the connections between the 2 sides
|
|
13
|
-
|
|
14
|
-
## 2. Project Setup and Tracking
|
|
15
|
-
- After receiving the PRD, create a README.md file with:
|
|
16
|
-
- A section listing all patterns and technologies used in the project (e.g., frameworks, libraries, tools).
|
|
17
|
-
- A brief project overview based on the PRD.
|
|
18
|
-
- Create a checklist.md file with:
|
|
19
|
-
- A task list derived from the PRD, broken into actionable steps (e.g., "Implement login endpoint", "Write tests for user authentication").
|
|
20
|
-
- A status column (e.g., "Not Started", "In Progress", "Completed") to track progress.
|
|
21
|
-
- Update checklist.md after completing each task by marking it as "Completed" and noting the git commit hash.
|
|
22
|
-
- Incorporate the PRD’s feature breakdown table into checklist.md, including Priority and Dependencies columns to sequence tasks logically.
|
|
23
|
-
- If the PRD includes a release plan (e.g., MVP, v1.1), group tasks by release milestones in checklist.md.
|
|
24
|
-
|
|
25
|
-
## 3. Task Execution Workflow
|
|
26
|
-
### Step 1: Identify the Next Task
|
|
27
|
-
- Grep the codebase, review the PRD, and check checklist.md to determine the next task in sequence.
|
|
28
|
-
- Focus only on the code areas relevant to the current task.
|
|
29
|
-
- Use the PRD’s priority levels and technical dependencies to select the next task, starting with Must-haves and respecting dependency order.
|
|
30
|
-
|
|
31
|
-
### Step 2: Write the Code
|
|
32
|
-
- Iterate on existing code if possible, avoiding new solutions unless necessary.
|
|
33
|
-
- Follow naming conventions and keep files under 500-700 lines, refactoring if needed.
|
|
34
|
-
- Add comments for complex logic.
|
|
35
|
-
- Avoid duplication by checking for similar functionality elsewhere in the codebase.
|
|
36
|
-
- Ensure code meets the PRD’s acceptance criteria for the task’s feature or user story.
|
|
37
|
-
- Adhere to non-functional requirements (e.g., performance, scalability) from the PRD when applicable.
|
|
38
|
-
|
|
39
|
-
### Step 3: Write Tests
|
|
40
|
-
- Write unit tests for individual functions and integration tests for workflows.
|
|
41
|
-
- Name tests clearly (e.g., testLoginSuccess, testUserCreationWorkflow).
|
|
42
|
-
- Ensure tests cover major functionality and edge cases outlined in the PRD.
|
|
43
|
-
- Make tests specific, measurable, and traceable to the PRD’s acceptance criteria (e.g., "User can log in with email/password" passes if the API returns a 200 status).
|
|
44
|
-
- Include tests for edge cases and error states documented in the PRD’s User Flows or AI-generated insights.
|
|
45
|
-
|
|
46
|
-
### Step 4: Run the Server and Tests
|
|
47
|
-
- Run all tests and verify they pass.
|
|
48
|
-
|
|
49
|
-
### Step 5: Handle Test Failures
|
|
50
|
-
- If tests fail, first review the test for accuracy (e.g., correct assertions, realistic mocks). Edit the test if it’s incorrect.
|
|
51
|
-
- If the test is valid and still fails, debug the code:
|
|
52
|
-
- Add logs/console messages to trace the issue.
|
|
53
|
-
- Fix the underlying problem rather than masking it.
|
|
54
|
-
- Re-run the server and tests after each change.
|
|
55
|
-
- Repeat until all tests pass. For persistent issues, check the fixes folder for prior solutions or use firecrawl to research fixes.
|
package/examples/federation.js
DELETED
|
@@ -1,162 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Organization Federation Example for HoloSphere (Updated API)
|
|
3
|
-
*
|
|
4
|
-
* This example demonstrates a real-world use case where a tech team creates tasks
|
|
5
|
-
* that are automatically federated to the parent organization for visibility using
|
|
6
|
-
* the latest HoloSphere federation features.
|
|
7
|
-
*/
|
|
8
|
-
|
|
9
|
-
import HoloSphere from '../holosphere.js';
|
|
10
|
-
|
|
11
|
-
async function organizationFederationExample() {
|
|
12
|
-
const holoSphere = new HoloSphere('organization-example-updated');
|
|
13
|
-
|
|
14
|
-
try {
|
|
15
|
-
console.log('Starting Organization Federation Example (Updated API)...');
|
|
16
|
-
|
|
17
|
-
// Define unique names for this run to avoid conflicts
|
|
18
|
-
const runId = Date.now();
|
|
19
|
-
const orgHolon = `acme-org-${runId}`;
|
|
20
|
-
const techTeamHolon = `acme-tech-${runId}`;
|
|
21
|
-
|
|
22
|
-
// Step 1: Create federation relationship (bidirectional by default)
|
|
23
|
-
console.log('\nStep 1: Creating federation relationship...');
|
|
24
|
-
// The `federate` method automatically sets up bidirectional notifications when `bidirectional` is true (default).
|
|
25
|
-
const federateResult = await holoSphere.federate(techTeamHolon, orgHolon);
|
|
26
|
-
if (!federateResult) {
|
|
27
|
-
throw new Error('Federation setup failed.');
|
|
28
|
-
}
|
|
29
|
-
console.log(`Federation created between ${techTeamHolon} and ${orgHolon}`);
|
|
30
|
-
|
|
31
|
-
// Allow a moment for GunDB propagation of federation settings
|
|
32
|
-
await new Promise(resolve => setTimeout(resolve, 1500));
|
|
33
|
-
|
|
34
|
-
// Step 2: Verify federation is set up properly
|
|
35
|
-
console.log('\nStep 2: Verifying federation setup...');
|
|
36
|
-
const techTeamFedInfo = await holoSphere.getFederation(techTeamHolon);
|
|
37
|
-
console.log(`Tech team (${techTeamHolon}) federation info:`, techTeamFedInfo);
|
|
38
|
-
if (!techTeamFedInfo?.federation?.includes(orgHolon)) {
|
|
39
|
-
console.warn('Warning: Organization holon not found in tech team federation list.');
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
const orgFedInfo = await holoSphere.getFederation(orgHolon);
|
|
43
|
-
console.log(`Organization (${orgHolon}) federation info:`, orgFedInfo);
|
|
44
|
-
if (!orgFedInfo?.notify?.includes(techTeamHolon)) {
|
|
45
|
-
console.warn('Warning: Tech team holon not found in organization notify list.');
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
// Step 3: Create a task in the tech team holon
|
|
49
|
-
// The `put` method automatically propagates data to federated holons by default (`autoPropagate: true`).
|
|
50
|
-
console.log('\nStep 3: Creating a task in the tech team holon (will auto-propagate)...');
|
|
51
|
-
|
|
52
|
-
const task = {
|
|
53
|
-
id: `task-${runId}-123`,
|
|
54
|
-
title: 'Implement new authentication system',
|
|
55
|
-
description: 'Replace the current auth system with OAuth2',
|
|
56
|
-
assignee: 'dev@example.com',
|
|
57
|
-
status: 'in_progress',
|
|
58
|
-
priority: 'high',
|
|
59
|
-
dueDate: '2024-12-31',
|
|
60
|
-
createdAt: new Date().toISOString(),
|
|
61
|
-
tags: ['security', 'infrastructure']
|
|
62
|
-
};
|
|
63
|
-
|
|
64
|
-
// Store the task - it will be automatically propagated to orgHolon due to federation
|
|
65
|
-
const putResult = await holoSphere.put(techTeamHolon, 'tasks', task);
|
|
66
|
-
console.log(`Task created in ${techTeamHolon}: ${task.id}. Propagation result:`, putResult.propagationResult);
|
|
67
|
-
if (putResult.propagationResult?.errors > 0) {
|
|
68
|
-
console.warn('Warning: Auto-propagation reported errors.');
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
// Step 4: Allow time for propagation via put
|
|
72
|
-
console.log('\nStep 4: Waiting for auto-propagation to complete...');
|
|
73
|
-
await new Promise(resolve => setTimeout(resolve, 1500));
|
|
74
|
-
|
|
75
|
-
// Step 5: Verify task in both holons
|
|
76
|
-
console.log('\nStep 5: Verifying task is in both holons...');
|
|
77
|
-
|
|
78
|
-
// Check tech team holon directly (original data)
|
|
79
|
-
const techTeamTask = await holoSphere.get(techTeamHolon, 'tasks', task.id);
|
|
80
|
-
console.log(`Task in tech team holon (${techTeamHolon}):`, techTeamTask ? 'Found' : 'Not found');
|
|
81
|
-
if (techTeamTask) console.log('Tech team task status:', techTeamTask.status);
|
|
82
|
-
|
|
83
|
-
// Check organization holon directly (should have a resolved reference)
|
|
84
|
-
const orgTask = await holoSphere.get(orgHolon, 'tasks', task.id);
|
|
85
|
-
console.log(`Task in organization holon (${orgHolon}):`, orgTask ? 'Found' : 'Not found');
|
|
86
|
-
if (orgTask) {
|
|
87
|
-
console.log('Organization task status:', orgTask.status);
|
|
88
|
-
// Check if it's a resolved reference
|
|
89
|
-
console.log('Is resolved reference:', !!orgTask._federation?.resolved);
|
|
90
|
-
} else {
|
|
91
|
-
console.warn(`Task ${task.id} not found in organization holon ${orgHolon}. Propagation might have failed or is slow.`);
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
// Step 6: Use getFederated to view all tasks from the organization's perspective
|
|
95
|
-
console.log('\nStep 6: Using getFederated to view all tasks...');
|
|
96
|
-
|
|
97
|
-
const allOrgTasks = await holoSphere.getFederated(orgHolon, 'tasks');
|
|
98
|
-
console.log(`Organization holon (${orgHolon}) has access to ${allOrgTasks.length} tasks (via getFederated):`);
|
|
99
|
-
// console.log(allOrgTasks); // Uncomment to see the full list
|
|
100
|
-
|
|
101
|
-
const allTechTasks = await holoSphere.getFederated(techTeamHolon, 'tasks');
|
|
102
|
-
console.log(`Tech team holon (${techTeamHolon}) has access to ${allTechTasks.length} tasks (via getFederated):`);
|
|
103
|
-
// console.log(allTechTasks); // Uncomment to see the full list
|
|
104
|
-
|
|
105
|
-
// Step 7: Update the task in tech team holon (will also auto-propagate)
|
|
106
|
-
console.log('\nStep 7: Updating task in tech team holon (will auto-propagate)...');
|
|
107
|
-
|
|
108
|
-
const updatedTask = {
|
|
109
|
-
...task,
|
|
110
|
-
status: 'completed',
|
|
111
|
-
completedAt: new Date().toISOString()
|
|
112
|
-
};
|
|
113
|
-
|
|
114
|
-
// Update the task - the change will be automatically propagated
|
|
115
|
-
const updateResult = await holoSphere.put(techTeamHolon, 'tasks', updatedTask);
|
|
116
|
-
console.log(`Task updated in ${techTeamHolon}. Propagation result:`, updateResult.propagationResult);
|
|
117
|
-
if (updateResult.propagationResult?.errors > 0) {
|
|
118
|
-
console.warn('Warning: Auto-propagation of update reported errors.');
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
// Step 8: Allow time for update propagation
|
|
122
|
-
console.log('\nStep 8: Waiting for update propagation...');
|
|
123
|
-
await new Promise(resolve => setTimeout(resolve, 1500));
|
|
124
|
-
|
|
125
|
-
// Step 9: Verify updates in both holons
|
|
126
|
-
console.log('\nStep 9: Verifying updated task in both holons...');
|
|
127
|
-
|
|
128
|
-
const updatedTechTeamTask = await holoSphere.get(techTeamHolon, 'tasks', task.id);
|
|
129
|
-
console.log(`Updated task status in tech team holon (${techTeamHolon}):`, updatedTechTeamTask?.status);
|
|
130
|
-
|
|
131
|
-
// Get the potentially updated reference in the organization holon
|
|
132
|
-
const updatedOrgTask = await holoSphere.get(orgHolon, 'tasks', task.id);
|
|
133
|
-
console.log(`Updated task status in organization holon (${orgHolon}):`, updatedOrgTask?.status);
|
|
134
|
-
if (!updatedOrgTask || updatedOrgTask.status !== 'completed') {
|
|
135
|
-
console.warn(`Updated task status not reflected in organization holon ${orgHolon}. Propagation might have failed or is slow.`);
|
|
136
|
-
}
|
|
137
|
-
|
|
138
|
-
// Step 10: Clean up - remove federation
|
|
139
|
-
console.log('\nStep 10: Cleaning up - removing federation...');
|
|
140
|
-
await holoSphere.unfederate(techTeamHolon, orgHolon);
|
|
141
|
-
console.log(`Federation removed between ${techTeamHolon} and ${orgHolon}`);
|
|
142
|
-
|
|
143
|
-
// Optional: Clean up data (can be slow and sometimes unreliable in Gun)
|
|
144
|
-
// console.log('Cleaning up task data...');
|
|
145
|
-
// await holoSphere.delete(techTeamHolon, 'tasks', task.id);
|
|
146
|
-
// await holoSphere.delete(orgHolon, 'tasks', task.id); // Delete the reference
|
|
147
|
-
// await holoSphere.deleteGlobal('federation', techTeamHolon);
|
|
148
|
-
// await holoSphere.deleteGlobal('federation', orgHolon);
|
|
149
|
-
|
|
150
|
-
console.log('\nOrganization federation example completed successfully!');
|
|
151
|
-
|
|
152
|
-
} catch (error) {
|
|
153
|
-
console.error('Error in organization federation example:', error);
|
|
154
|
-
} finally {
|
|
155
|
-
// Always close the HoloSphere instance
|
|
156
|
-
await holoSphere.close();
|
|
157
|
-
console.log('HoloSphere instance closed');
|
|
158
|
-
}
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
// Run the example
|
|
162
|
-
organizationFederationExample().catch(console.error);
|
|
@@ -1,106 +0,0 @@
|
|
|
1
|
-
// hologram-updates-example.js
|
|
2
|
-
// Example showing how to use the returned list of updated holograms from put()
|
|
3
|
-
|
|
4
|
-
import HoloSphere from '../holosphere.js';
|
|
5
|
-
|
|
6
|
-
async function exampleUsage() {
|
|
7
|
-
const holosphere = new HoloSphere('example-app', false);
|
|
8
|
-
|
|
9
|
-
try {
|
|
10
|
-
// 1. Create some original data
|
|
11
|
-
const originalData = {
|
|
12
|
-
id: 'product-123',
|
|
13
|
-
name: 'Widget',
|
|
14
|
-
price: 19.99,
|
|
15
|
-
inventory: 100
|
|
16
|
-
};
|
|
17
|
-
|
|
18
|
-
console.log('Step 1: Storing original data...');
|
|
19
|
-
await holosphere.put('store', 'products', originalData);
|
|
20
|
-
|
|
21
|
-
// 2. Create holograms in different locations (maybe for different displays/views)
|
|
22
|
-
console.log('Step 2: Creating holograms...');
|
|
23
|
-
const hologram1 = holosphere.createHologram('store', 'products', originalData);
|
|
24
|
-
const hologram2 = holosphere.createHologram('store', 'products', originalData);
|
|
25
|
-
|
|
26
|
-
await holosphere.put('storefront', 'display', { id: 'featured-product', soul: hologram1.soul });
|
|
27
|
-
await holosphere.put('warehouse', 'inventory', { id: 'stock-item', soul: hologram2.soul });
|
|
28
|
-
|
|
29
|
-
// Wait for Gun to propagate
|
|
30
|
-
await new Promise(resolve => setTimeout(resolve, 500));
|
|
31
|
-
|
|
32
|
-
// 3. Update the original data and get the list of updated holograms
|
|
33
|
-
console.log('Step 3: Updating original data...');
|
|
34
|
-
const updatedData = {
|
|
35
|
-
...originalData,
|
|
36
|
-
price: 17.99, // Price reduction!
|
|
37
|
-
inventory: 95, // Some sold
|
|
38
|
-
lastUpdated: Date.now()
|
|
39
|
-
};
|
|
40
|
-
|
|
41
|
-
const result = await holosphere.put('store', 'products', updatedData);
|
|
42
|
-
|
|
43
|
-
console.log('PUT Result:', {
|
|
44
|
-
success: result.success,
|
|
45
|
-
pathInfo: {
|
|
46
|
-
holon: result.pathHolon,
|
|
47
|
-
lens: result.pathLens,
|
|
48
|
-
key: result.pathKey
|
|
49
|
-
},
|
|
50
|
-
updatedHologramsCount: result.updatedHolograms.length
|
|
51
|
-
});
|
|
52
|
-
|
|
53
|
-
// 4. Process the updated holograms
|
|
54
|
-
console.log('Step 4: Processing updated holograms...');
|
|
55
|
-
if (result.updatedHolograms.length > 0) {
|
|
56
|
-
console.log(`Updated ${result.updatedHolograms.length} holograms:`);
|
|
57
|
-
|
|
58
|
-
for (const hologram of result.updatedHolograms) {
|
|
59
|
-
console.log(` - Hologram at ${hologram.holon}/${hologram.lens}/${hologram.key}`);
|
|
60
|
-
console.log(` Soul: ${hologram.soul}`);
|
|
61
|
-
console.log(` Updated at: ${new Date(hologram.timestamp).toISOString()}`);
|
|
62
|
-
|
|
63
|
-
// Example post-processing:
|
|
64
|
-
// You could trigger UI updates, send notifications, update caches, etc.
|
|
65
|
-
|
|
66
|
-
if (hologram.holon === 'storefront') {
|
|
67
|
-
console.log(' -> Triggering storefront display refresh');
|
|
68
|
-
// triggerStorefrontRefresh(hologram.key);
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
if (hologram.holon === 'warehouse') {
|
|
72
|
-
console.log(' -> Updating warehouse inventory system');
|
|
73
|
-
// updateWarehouseInventory(hologram.key);
|
|
74
|
-
}
|
|
75
|
-
}
|
|
76
|
-
} else {
|
|
77
|
-
console.log('No holograms were updated.');
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
// 5. Verify the holograms have the updated timestamp
|
|
81
|
-
console.log('Step 5: Verifying hologram updates...');
|
|
82
|
-
const storefrontHologram = await holosphere.get('storefront', 'display', 'featured-product', null, { resolveHolograms: false });
|
|
83
|
-
const warehouseHologram = await holosphere.get('warehouse', 'inventory', 'stock-item', null, { resolveHolograms: false });
|
|
84
|
-
|
|
85
|
-
console.log('Storefront hologram updated field:', storefrontHologram?.updated);
|
|
86
|
-
console.log('Warehouse hologram updated field:', warehouseHologram?.updated);
|
|
87
|
-
|
|
88
|
-
} catch (error) {
|
|
89
|
-
console.error('Error in example:', error);
|
|
90
|
-
} finally {
|
|
91
|
-
await holosphere.close();
|
|
92
|
-
}
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
// Example usage scenarios:
|
|
96
|
-
console.log('=== Hologram Updates Return Value Example ===');
|
|
97
|
-
console.log('This example demonstrates how to use the updatedHolograms return value from put()');
|
|
98
|
-
console.log('to perform post-processing tasks when original data changes.\n');
|
|
99
|
-
|
|
100
|
-
exampleUsage().then(() => {
|
|
101
|
-
console.log('\n=== Example completed ===');
|
|
102
|
-
process.exit(0);
|
|
103
|
-
}).catch(error => {
|
|
104
|
-
console.error('Example failed:', error);
|
|
105
|
-
process.exit(1);
|
|
106
|
-
});
|
package/examples/holograms.js
DELETED
|
@@ -1,175 +0,0 @@
|
|
|
1
|
-
import HoloSphere from '../holosphere.js';
|
|
2
|
-
|
|
3
|
-
async function testHologramFederation() {
|
|
4
|
-
console.log('Starting hologram federation test...');
|
|
5
|
-
const holoSphere = new HoloSphere('test-holograms');
|
|
6
|
-
|
|
7
|
-
try {
|
|
8
|
-
const space1 = 'holo-test-space1';
|
|
9
|
-
const space2 = 'holo-test-space2';
|
|
10
|
-
|
|
11
|
-
// Step 1: Create federation with bidirectional notify settings
|
|
12
|
-
console.log('Step 1: Creating federation between spaces...');
|
|
13
|
-
await holoSphere.federate(space1, space2);
|
|
14
|
-
|
|
15
|
-
// Also federate from space2 to space1 for testing getFederated
|
|
16
|
-
await holoSphere.federate(space2, space1);
|
|
17
|
-
|
|
18
|
-
// Step 2: Verify federation is set up properly
|
|
19
|
-
const fedInfo = await holoSphere.getFederation(space1);
|
|
20
|
-
console.log('Federation info for space1:', fedInfo);
|
|
21
|
-
|
|
22
|
-
const fedInfo2 = await holoSphere.getFederation(space2);
|
|
23
|
-
console.log('Federation info for space2:', fedInfo2);
|
|
24
|
-
|
|
25
|
-
// Step 3: Create test data
|
|
26
|
-
console.log('Step 3: Creating test data...');
|
|
27
|
-
const testData = {
|
|
28
|
-
id: 'holo-test-item',
|
|
29
|
-
title: 'Hologram Test',
|
|
30
|
-
value: 200,
|
|
31
|
-
tags: ['test', 'hologram']
|
|
32
|
-
};
|
|
33
|
-
|
|
34
|
-
// Store data in space1
|
|
35
|
-
await holoSphere.put(space1, 'items', testData);
|
|
36
|
-
|
|
37
|
-
// Step 4: Propagate using holograms
|
|
38
|
-
console.log('Step 4: Propagating with soul holograms...');
|
|
39
|
-
const propResult = await holoSphere.propagate(space1, 'items', testData, {
|
|
40
|
-
useHolograms: true
|
|
41
|
-
});
|
|
42
|
-
console.log('Propagation result:', propResult);
|
|
43
|
-
|
|
44
|
-
// Allow time for propagation
|
|
45
|
-
console.log('Waiting for propagation...');
|
|
46
|
-
await new Promise(resolve => setTimeout(resolve, 1000));
|
|
47
|
-
|
|
48
|
-
// Step 5: Verify that the data in space2 is a soul hologram
|
|
49
|
-
console.log('Step 5: Verifying soul hologram was created...');
|
|
50
|
-
const rawHolo = await holoSphere.get(space2, 'items', 'holo-test-item', null, {
|
|
51
|
-
resolveHolograms: false
|
|
52
|
-
});
|
|
53
|
-
|
|
54
|
-
console.log('Raw hologram data:', rawHolo);
|
|
55
|
-
console.log('Is soul hologram:', holoSphere.isHologram(rawHolo));
|
|
56
|
-
|
|
57
|
-
if (rawHolo?.soul) {
|
|
58
|
-
const soulParts = rawHolo.soul.split('/');
|
|
59
|
-
console.log('Soul parts:', soulParts);
|
|
60
|
-
console.log('Soul refers to:', {
|
|
61
|
-
app: soulParts[0],
|
|
62
|
-
holon: soulParts[1],
|
|
63
|
-
lens: soulParts[2],
|
|
64
|
-
key: soulParts[3]
|
|
65
|
-
});
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
// Step 6: Verify hologram resolution works
|
|
69
|
-
console.log('Step 6: Verifying hologram resolution...');
|
|
70
|
-
const resolvedData = await holoSphere.get(space2, 'items', 'holo-test-item');
|
|
71
|
-
console.log('Resolved data:', resolvedData);
|
|
72
|
-
|
|
73
|
-
// Step 7: Update the original data
|
|
74
|
-
console.log('Step 7: Updating original data...');
|
|
75
|
-
const updatedData = {
|
|
76
|
-
...testData,
|
|
77
|
-
value: 300,
|
|
78
|
-
updated: true
|
|
79
|
-
};
|
|
80
|
-
|
|
81
|
-
await holoSphere.put(space1, 'items', updatedData);
|
|
82
|
-
|
|
83
|
-
// Allow time for update to propagate
|
|
84
|
-
console.log('Waiting for update...');
|
|
85
|
-
await new Promise(resolve => setTimeout(resolve, 500));
|
|
86
|
-
|
|
87
|
-
// Step 8: Verify update is reflected through the hologram
|
|
88
|
-
console.log('Step 8: Verifying update is reflected in hologram...');
|
|
89
|
-
const reResolvedData = await holoSphere.get(space2, 'items', 'holo-test-item');
|
|
90
|
-
console.log('Re-resolved data after update:', reResolvedData);
|
|
91
|
-
|
|
92
|
-
// Step 9: Update directly through origin holon
|
|
93
|
-
console.log('Step 9: Updating through the origin holon...');
|
|
94
|
-
const originData = await holoSphere.get(space1, 'items', 'holo-test-item');
|
|
95
|
-
|
|
96
|
-
const finalUpdate = {
|
|
97
|
-
...originData,
|
|
98
|
-
value: 400,
|
|
99
|
-
finalUpdate: true
|
|
100
|
-
};
|
|
101
|
-
|
|
102
|
-
await holoSphere.put(space1, 'items', finalUpdate);
|
|
103
|
-
|
|
104
|
-
// Allow time for update to propagate
|
|
105
|
-
console.log('Waiting for final update...');
|
|
106
|
-
await new Promise(resolve => setTimeout(resolve, 500));
|
|
107
|
-
|
|
108
|
-
// Step 10: Verify final update through the hologram in space2
|
|
109
|
-
console.log('Step 10: Verifying final update is reflected...');
|
|
110
|
-
const finalResolvedData = await holoSphere.get(space2, 'items', 'holo-test-item');
|
|
111
|
-
console.log('Final resolved data:', finalResolvedData);
|
|
112
|
-
|
|
113
|
-
// Step 11: Test manual soul hologram resolution
|
|
114
|
-
console.log('Step 11: Testing manual soul hologram resolution...');
|
|
115
|
-
|
|
116
|
-
// Check what getAll returns
|
|
117
|
-
console.log('Raw holograms from getAll in space2:');
|
|
118
|
-
const allItems = await holoSphere.getAll(space2, 'items');
|
|
119
|
-
console.log('getAll results:', allItems);
|
|
120
|
-
|
|
121
|
-
if (allItems.length > 0 && allItems[0].soul) {
|
|
122
|
-
console.log('Found a soul hologram, resolving it manually:');
|
|
123
|
-
const soulParts = allItems[0].soul.split('/');
|
|
124
|
-
|
|
125
|
-
const originHolon = soulParts[1];
|
|
126
|
-
const originLens = soulParts[2];
|
|
127
|
-
const originKey = soulParts[3];
|
|
128
|
-
|
|
129
|
-
console.log(`Soul path components: holon=${originHolon}, lens=${originLens}, key=${originKey}`);
|
|
130
|
-
|
|
131
|
-
const originalData = await holoSphere.get(
|
|
132
|
-
originHolon,
|
|
133
|
-
originLens,
|
|
134
|
-
originKey,
|
|
135
|
-
null,
|
|
136
|
-
{ resolveHolograms: false }
|
|
137
|
-
);
|
|
138
|
-
console.log('Manually resolved hologram data:', originalData);
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
// Test getFederated with holograms
|
|
142
|
-
console.log('\nTesting getFederated with holograms:');
|
|
143
|
-
const federatedData = await holoSphere.getFederated(space2, 'items', {
|
|
144
|
-
resolveHolograms: true,
|
|
145
|
-
idField: 'id'
|
|
146
|
-
});
|
|
147
|
-
|
|
148
|
-
console.log('getFederated results length:', federatedData.length);
|
|
149
|
-
|
|
150
|
-
// Find the item by ID
|
|
151
|
-
const federatedItem = federatedData.find(item => item.id === 'holo-test-item');
|
|
152
|
-
console.log('Found federated item by ID:', federatedItem);
|
|
153
|
-
|
|
154
|
-
// Check if federated data correctly resolves soul holograms
|
|
155
|
-
if (federatedItem && federatedItem.value === 400 && federatedItem.finalUpdate) {
|
|
156
|
-
console.log('SUCCESS: getFederated correctly resolved the soul hologram!');
|
|
157
|
-
} else {
|
|
158
|
-
console.log('WARNING: getFederated may not be resolving soul holograms properly');
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
// Step 12: Clean up
|
|
162
|
-
console.log('Step 12: Cleaning up...');
|
|
163
|
-
await holoSphere.unfederate(space1, space2);
|
|
164
|
-
await holoSphere.unfederate(space2, space1);
|
|
165
|
-
|
|
166
|
-
console.log('Hologram federation test completed successfully!');
|
|
167
|
-
} catch (error) {
|
|
168
|
-
console.error('Hologram federation test failed:', error);
|
|
169
|
-
} finally {
|
|
170
|
-
await holoSphere.close();
|
|
171
|
-
console.log('HoloSphere connection closed.');
|
|
172
|
-
}
|
|
173
|
-
}
|
|
174
|
-
|
|
175
|
-
testHologramFederation();
|