laminark 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.
- package/README.md +147 -0
- package/package.json +65 -0
- package/plugin/.claude-plugin/plugin.json +13 -0
- package/plugin/.mcp.json +12 -0
- package/plugin/CLAUDE.md +10 -0
- package/plugin/commands/recall.md +55 -0
- package/plugin/commands/remember.md +34 -0
- package/plugin/commands/resume.md +45 -0
- package/plugin/commands/stash.md +34 -0
- package/plugin/commands/status.md +33 -0
- package/plugin/dist/analysis/worker.d.ts +1 -0
- package/plugin/dist/analysis/worker.js +233 -0
- package/plugin/dist/analysis/worker.js.map +1 -0
- package/plugin/dist/config-t8LZeB-u.mjs +90 -0
- package/plugin/dist/config-t8LZeB-u.mjs.map +1 -0
- package/plugin/dist/hooks/handler.d.ts +286 -0
- package/plugin/dist/hooks/handler.d.ts.map +1 -0
- package/plugin/dist/hooks/handler.js +2413 -0
- package/plugin/dist/hooks/handler.js.map +1 -0
- package/plugin/dist/index.d.ts +447 -0
- package/plugin/dist/index.d.ts.map +1 -0
- package/plugin/dist/index.js +7334 -0
- package/plugin/dist/index.js.map +1 -0
- package/plugin/dist/observations-CorAAc1A.d.mts +192 -0
- package/plugin/dist/observations-CorAAc1A.d.mts.map +1 -0
- package/plugin/dist/tool-registry-e710BvXq.mjs +3574 -0
- package/plugin/dist/tool-registry-e710BvXq.mjs.map +1 -0
- package/plugin/hooks/hooks.json +78 -0
- package/plugin/laminark.db +0 -0
- package/plugin/package.json +17 -0
- package/plugin/scripts/README.md +65 -0
- package/plugin/scripts/bump-version.sh +42 -0
- package/plugin/scripts/dev-sync.sh +58 -0
- package/plugin/scripts/ensure-deps.sh +15 -0
- package/plugin/scripts/install.sh +139 -0
- package/plugin/scripts/local-install.sh +138 -0
- package/plugin/scripts/uninstall.sh +133 -0
- package/plugin/scripts/update.sh +39 -0
- package/plugin/scripts/verify-install.sh +87 -0
- package/plugin/skills/status/SKILL.md +6 -0
- package/plugin/ui/activity.js +197 -0
- package/plugin/ui/app.js +1612 -0
- package/plugin/ui/graph.js +2560 -0
- package/plugin/ui/help/activity-feed.png +0 -0
- package/plugin/ui/help/analysis-panel.png +0 -0
- package/plugin/ui/help/graph-toolbar.png +0 -0
- package/plugin/ui/help/graph-view.png +0 -0
- package/plugin/ui/help/settings.png +0 -0
- package/plugin/ui/help/timeline.png +0 -0
- package/plugin/ui/help.js +932 -0
- package/plugin/ui/index.html +756 -0
- package/plugin/ui/settings.js +1414 -0
- package/plugin/ui/styles.css +3856 -0
- package/plugin/ui/timeline.js +652 -0
- package/plugin/ui/tools.js +826 -0
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
# Update Laminark to the latest version via npm
|
|
3
|
+
|
|
4
|
+
set -e
|
|
5
|
+
|
|
6
|
+
echo "Laminark Updater"
|
|
7
|
+
echo "================"
|
|
8
|
+
echo ""
|
|
9
|
+
|
|
10
|
+
# Check if npm is available
|
|
11
|
+
if ! command -v npm &> /dev/null; then
|
|
12
|
+
echo "Error: npm not found"
|
|
13
|
+
exit 1
|
|
14
|
+
fi
|
|
15
|
+
|
|
16
|
+
# Check if installed
|
|
17
|
+
CURRENT_VERSION=$(npm list -g laminark --depth=0 2>/dev/null | grep laminark@ | sed 's/.*@//' || echo "")
|
|
18
|
+
if [ -z "$CURRENT_VERSION" ]; then
|
|
19
|
+
echo "Laminark is not installed globally."
|
|
20
|
+
echo "Run: ./plugin/scripts/install.sh"
|
|
21
|
+
exit 1
|
|
22
|
+
fi
|
|
23
|
+
|
|
24
|
+
echo "Currently installed: v$CURRENT_VERSION"
|
|
25
|
+
echo ""
|
|
26
|
+
echo "Updating..."
|
|
27
|
+
npm update -g laminark
|
|
28
|
+
|
|
29
|
+
NEW_VERSION=$(npm list -g laminark --depth=0 2>/dev/null | grep laminark@ | sed 's/.*@//' || echo "unknown")
|
|
30
|
+
echo ""
|
|
31
|
+
if [ "$CURRENT_VERSION" = "$NEW_VERSION" ]; then
|
|
32
|
+
echo "✓ Already at latest version: v$NEW_VERSION"
|
|
33
|
+
else
|
|
34
|
+
echo "✓ Updated: v$CURRENT_VERSION → v$NEW_VERSION"
|
|
35
|
+
fi
|
|
36
|
+
echo ""
|
|
37
|
+
echo "Restart your Claude Code session for changes to take effect."
|
|
38
|
+
|
|
39
|
+
exit 0
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
# Verify Laminark installation
|
|
3
|
+
# Checks: npm global package, MCP server, hooks in settings.json
|
|
4
|
+
|
|
5
|
+
set -e
|
|
6
|
+
|
|
7
|
+
echo "Checking Laminark installation..."
|
|
8
|
+
echo ""
|
|
9
|
+
|
|
10
|
+
ERRORS=0
|
|
11
|
+
|
|
12
|
+
# Check 1: npm global package
|
|
13
|
+
NPM_VERSION=$(npm list -g laminark --depth=0 2>/dev/null | grep laminark@ | sed 's/.*@//' || echo "")
|
|
14
|
+
if [ -n "$NPM_VERSION" ]; then
|
|
15
|
+
echo "✓ npm package: v$NPM_VERSION"
|
|
16
|
+
else
|
|
17
|
+
# Check for npm link (dev install)
|
|
18
|
+
if command -v laminark-server &> /dev/null; then
|
|
19
|
+
echo "✓ laminark-server on PATH (linked)"
|
|
20
|
+
else
|
|
21
|
+
echo "✗ npm package not installed"
|
|
22
|
+
ERRORS=$((ERRORS + 1))
|
|
23
|
+
fi
|
|
24
|
+
fi
|
|
25
|
+
|
|
26
|
+
# Check 2: laminark-server binary
|
|
27
|
+
if command -v laminark-server &> /dev/null; then
|
|
28
|
+
echo "✓ laminark-server binary available"
|
|
29
|
+
else
|
|
30
|
+
echo "✗ laminark-server not found on PATH"
|
|
31
|
+
ERRORS=$((ERRORS + 1))
|
|
32
|
+
fi
|
|
33
|
+
|
|
34
|
+
# Check 3: laminark-hook binary
|
|
35
|
+
if command -v laminark-hook &> /dev/null; then
|
|
36
|
+
echo "✓ laminark-hook binary available"
|
|
37
|
+
else
|
|
38
|
+
echo "⚠ laminark-hook not on PATH (hooks may use direct node path)"
|
|
39
|
+
fi
|
|
40
|
+
|
|
41
|
+
# Check 4: Claude CLI
|
|
42
|
+
if ! command -v claude &> /dev/null; then
|
|
43
|
+
echo "✗ claude CLI not found"
|
|
44
|
+
ERRORS=$((ERRORS + 1))
|
|
45
|
+
else
|
|
46
|
+
# Check 5: MCP server registration
|
|
47
|
+
if claude mcp list 2>/dev/null | grep -q "laminark"; then
|
|
48
|
+
echo "✓ MCP server registered"
|
|
49
|
+
else
|
|
50
|
+
echo "✗ MCP server not registered"
|
|
51
|
+
echo " Run: claude mcp add-json laminark '{\"command\":\"laminark-server\"}' -s user"
|
|
52
|
+
ERRORS=$((ERRORS + 1))
|
|
53
|
+
fi
|
|
54
|
+
fi
|
|
55
|
+
|
|
56
|
+
# Check 6: Hooks in settings.json
|
|
57
|
+
SETTINGS_FILE="${CLAUDE_HOME:-$HOME/.claude}/settings.json"
|
|
58
|
+
if [ -f "$SETTINGS_FILE" ]; then
|
|
59
|
+
if grep -q "laminark" "$SETTINGS_FILE"; then
|
|
60
|
+
echo "✓ Hooks configured in settings.json"
|
|
61
|
+
else
|
|
62
|
+
echo "✗ No laminark hooks in settings.json"
|
|
63
|
+
ERRORS=$((ERRORS + 1))
|
|
64
|
+
fi
|
|
65
|
+
else
|
|
66
|
+
echo "✗ Settings file not found: $SETTINGS_FILE"
|
|
67
|
+
ERRORS=$((ERRORS + 1))
|
|
68
|
+
fi
|
|
69
|
+
|
|
70
|
+
# Check 7: Data directory
|
|
71
|
+
DATA_DIR="$HOME/.laminark"
|
|
72
|
+
if [ -d "$DATA_DIR" ]; then
|
|
73
|
+
echo "✓ Data directory exists: $DATA_DIR"
|
|
74
|
+
else
|
|
75
|
+
echo "⚠ Data directory not yet created (will be created on first use)"
|
|
76
|
+
fi
|
|
77
|
+
|
|
78
|
+
echo ""
|
|
79
|
+
if [ $ERRORS -eq 0 ]; then
|
|
80
|
+
echo "Installation verified successfully!"
|
|
81
|
+
echo ""
|
|
82
|
+
echo "Start a new Claude Code session to use Laminark."
|
|
83
|
+
else
|
|
84
|
+
echo "Found $ERRORS issue(s). Run ./plugin/scripts/install.sh to fix."
|
|
85
|
+
fi
|
|
86
|
+
|
|
87
|
+
exit $ERRORS
|
|
@@ -0,0 +1,197 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Laminark Activity Feed Module
|
|
3
|
+
*
|
|
4
|
+
* Listens to SSE-dispatched CustomEvents and renders a live activity feed.
|
|
5
|
+
* Max 100 items in memory, newest first. Supports clear and slide-in animation.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
(function () {
|
|
9
|
+
var MAX_ITEMS = 100;
|
|
10
|
+
var items = [];
|
|
11
|
+
var feedEl = null;
|
|
12
|
+
|
|
13
|
+
var EVENT_CONFIG = {
|
|
14
|
+
'laminark:new_observation': {
|
|
15
|
+
icon: '\u{1F4DD}',
|
|
16
|
+
label: 'Observation',
|
|
17
|
+
cssClass: 'activity-observation',
|
|
18
|
+
format: function (d) {
|
|
19
|
+
return d.text || (d.id ? 'Observation ' + d.id.substring(0, 8) : 'New observation');
|
|
20
|
+
},
|
|
21
|
+
},
|
|
22
|
+
'laminark:entity_updated': {
|
|
23
|
+
icon: '\u{1F9E9}',
|
|
24
|
+
label: 'Entity',
|
|
25
|
+
cssClass: 'activity-entity',
|
|
26
|
+
format: function (d) {
|
|
27
|
+
return (d.label || d.name || d.id || 'Unknown') + (d.type ? ' (' + d.type + ')' : '');
|
|
28
|
+
},
|
|
29
|
+
},
|
|
30
|
+
'laminark:topic_shift': {
|
|
31
|
+
icon: '\u{1F500}',
|
|
32
|
+
label: 'Topic Shift',
|
|
33
|
+
cssClass: 'activity-topic-shift',
|
|
34
|
+
format: function (d) {
|
|
35
|
+
var msg = 'Topic shift detected';
|
|
36
|
+
if (d.confidence != null) msg += ' (' + (d.confidence * 100).toFixed(0) + '% confidence)';
|
|
37
|
+
return msg;
|
|
38
|
+
},
|
|
39
|
+
},
|
|
40
|
+
'laminark:session_start': {
|
|
41
|
+
icon: '\u{25B6}\uFE0F',
|
|
42
|
+
label: 'Session Start',
|
|
43
|
+
cssClass: 'activity-session-start',
|
|
44
|
+
format: function (d) {
|
|
45
|
+
return 'Session started' + (d.id ? ': ' + d.id.substring(0, 8) : '');
|
|
46
|
+
},
|
|
47
|
+
},
|
|
48
|
+
'laminark:session_end': {
|
|
49
|
+
icon: '\u{23F9}\uFE0F',
|
|
50
|
+
label: 'Session End',
|
|
51
|
+
cssClass: 'activity-session-end',
|
|
52
|
+
format: function (d) {
|
|
53
|
+
return 'Session ended' + (d.id ? ': ' + d.id.substring(0, 8) : '');
|
|
54
|
+
},
|
|
55
|
+
},
|
|
56
|
+
};
|
|
57
|
+
|
|
58
|
+
function relativeTime(isoString) {
|
|
59
|
+
if (!isoString) return 'just now';
|
|
60
|
+
try {
|
|
61
|
+
var diff = Date.now() - new Date(isoString).getTime();
|
|
62
|
+
if (diff < 0) diff = 0;
|
|
63
|
+
var secs = Math.floor(diff / 1000);
|
|
64
|
+
if (secs < 60) return secs + 's ago';
|
|
65
|
+
var mins = Math.floor(secs / 60);
|
|
66
|
+
if (mins < 60) return mins + 'm ago';
|
|
67
|
+
var hrs = Math.floor(mins / 60);
|
|
68
|
+
if (hrs < 24) return hrs + 'h ago';
|
|
69
|
+
return Math.floor(hrs / 24) + 'd ago';
|
|
70
|
+
} catch (_e) {
|
|
71
|
+
return 'just now';
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
function createItemEl(item) {
|
|
76
|
+
var el = document.createElement('div');
|
|
77
|
+
el.className = 'activity-item ' + item.cssClass + ' activity-slide-in';
|
|
78
|
+
|
|
79
|
+
var iconSpan = document.createElement('span');
|
|
80
|
+
iconSpan.className = 'activity-icon';
|
|
81
|
+
iconSpan.textContent = item.icon;
|
|
82
|
+
el.appendChild(iconSpan);
|
|
83
|
+
|
|
84
|
+
var body = document.createElement('div');
|
|
85
|
+
body.className = 'activity-body';
|
|
86
|
+
|
|
87
|
+
var title = document.createElement('div');
|
|
88
|
+
title.className = 'activity-title';
|
|
89
|
+
title.textContent = item.label;
|
|
90
|
+
body.appendChild(title);
|
|
91
|
+
|
|
92
|
+
var desc = document.createElement('div');
|
|
93
|
+
desc.className = 'activity-desc';
|
|
94
|
+
desc.textContent = item.description;
|
|
95
|
+
body.appendChild(desc);
|
|
96
|
+
|
|
97
|
+
el.appendChild(body);
|
|
98
|
+
|
|
99
|
+
var time = document.createElement('span');
|
|
100
|
+
time.className = 'activity-time';
|
|
101
|
+
time.textContent = relativeTime(item.timestamp);
|
|
102
|
+
el.appendChild(time);
|
|
103
|
+
|
|
104
|
+
return el;
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
function renderFeed() {
|
|
108
|
+
if (!feedEl) return;
|
|
109
|
+
|
|
110
|
+
if (items.length === 0) {
|
|
111
|
+
feedEl.innerHTML = '<p class="empty-state">Waiting for live events...</p>';
|
|
112
|
+
return;
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
feedEl.innerHTML = '';
|
|
116
|
+
items.forEach(function (item) {
|
|
117
|
+
feedEl.appendChild(createItemEl(item));
|
|
118
|
+
});
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
function addItem(eventName, detail) {
|
|
122
|
+
var config = EVENT_CONFIG[eventName];
|
|
123
|
+
if (!config) return;
|
|
124
|
+
|
|
125
|
+
// Filter out events from other projects
|
|
126
|
+
if (detail.projectHash && window.laminarkState && window.laminarkState.currentProject &&
|
|
127
|
+
detail.projectHash !== window.laminarkState.currentProject) {
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
var item = {
|
|
132
|
+
icon: config.icon,
|
|
133
|
+
label: config.label,
|
|
134
|
+
cssClass: config.cssClass,
|
|
135
|
+
description: config.format(detail || {}),
|
|
136
|
+
timestamp: detail.createdAt || detail.timestamp || new Date().toISOString(),
|
|
137
|
+
};
|
|
138
|
+
|
|
139
|
+
items.unshift(item);
|
|
140
|
+
if (items.length > MAX_ITEMS) {
|
|
141
|
+
items = items.slice(0, MAX_ITEMS);
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
// If feed is visible, prepend DOM element directly for performance
|
|
145
|
+
if (feedEl) {
|
|
146
|
+
// Remove empty state if present
|
|
147
|
+
var empty = feedEl.querySelector('.empty-state');
|
|
148
|
+
if (empty) empty.remove();
|
|
149
|
+
|
|
150
|
+
var el = createItemEl(item);
|
|
151
|
+
if (feedEl.firstChild) {
|
|
152
|
+
feedEl.insertBefore(el, feedEl.firstChild);
|
|
153
|
+
} else {
|
|
154
|
+
feedEl.appendChild(el);
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
// Trim excess DOM nodes
|
|
158
|
+
while (feedEl.children.length > MAX_ITEMS) {
|
|
159
|
+
feedEl.removeChild(feedEl.lastChild);
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
function clearFeed() {
|
|
165
|
+
items = [];
|
|
166
|
+
renderFeed();
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
function initActivityFeed() {
|
|
170
|
+
feedEl = document.getElementById('activity-feed');
|
|
171
|
+
|
|
172
|
+
var clearBtn = document.getElementById('activity-clear-btn');
|
|
173
|
+
if (clearBtn) {
|
|
174
|
+
clearBtn.addEventListener('click', clearFeed);
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
// Listen to all SSE event types
|
|
178
|
+
Object.keys(EVENT_CONFIG).forEach(function (eventName) {
|
|
179
|
+
document.addEventListener(eventName, function (e) {
|
|
180
|
+
addItem(eventName, e.detail || {});
|
|
181
|
+
});
|
|
182
|
+
});
|
|
183
|
+
|
|
184
|
+
// Clear feed when project changes
|
|
185
|
+
var projectSelect = document.getElementById('project-selector');
|
|
186
|
+
if (projectSelect) {
|
|
187
|
+
projectSelect.addEventListener('change', clearFeed);
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
renderFeed();
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
window.laminarkActivity = {
|
|
194
|
+
initActivityFeed: initActivityFeed,
|
|
195
|
+
clearFeed: clearFeed,
|
|
196
|
+
};
|
|
197
|
+
})();
|