@burdenoff/microfe-vibecontrols 2026.601.20 → 2026.601.22
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/dist/components/actions/ActionCard.js +77 -66
- package/dist/components/actions/ActionCard.js.map +1 -1
- package/dist/components/ai/AIContextsTab.js +186 -173
- package/dist/components/ai/AIContextsTab.js.map +1 -1
- package/dist/components/ai/AITemplatesTab.js +135 -125
- package/dist/components/ai/AITemplatesTab.js.map +1 -1
- package/dist/components/ai/InstructionFilesManager.js +151 -137
- package/dist/components/ai/InstructionFilesManager.js.map +1 -1
- package/dist/components/notes/NoteCard.js +19 -10
- package/dist/components/notes/NoteCard.js.map +1 -1
- package/dist/components/notes/NoteList.js +37 -27
- package/dist/components/notes/NoteList.js.map +1 -1
- package/dist/components/notes/NotesTabPanel.js +128 -111
- package/dist/components/notes/NotesTabPanel.js.map +1 -1
- package/dist/components/sharing/EntityShareButton.js +58 -0
- package/dist/components/sharing/EntityShareButton.js.map +1 -0
- package/dist/components/sharing/NoteShareDialog.js +24 -0
- package/dist/components/sharing/NoteShareDialog.js.map +1 -0
- package/dist/components/sharing/SharedWithMePanel.js +24 -0
- package/dist/components/sharing/SharedWithMePanel.js.map +1 -0
- package/dist/components/sharing/VibeShareButton.js +42 -0
- package/dist/components/sharing/VibeShareButton.js.map +1 -0
- package/dist/components/sharing/entityShareOps.js +277 -0
- package/dist/components/sharing/entityShareOps.js.map +1 -0
- package/dist/components/sharing/index.js +9 -0
- package/dist/components/sharing/shareControllerTypes.js +36 -0
- package/dist/components/sharing/shareControllerTypes.js.map +1 -0
- package/dist/components/sharing/shareRegistry.js +83 -0
- package/dist/components/sharing/shareRegistry.js.map +1 -0
- package/dist/components/sharing/useEntityShareController.js +88 -0
- package/dist/components/sharing/useEntityShareController.js.map +1 -0
- package/dist/components/sharing/useNoteShareController.js +131 -0
- package/dist/components/sharing/useNoteShareController.js.map +1 -0
- package/dist/components/sharing/useVibeShareController.js +131 -0
- package/dist/components/sharing/useVibeShareController.js.map +1 -0
- package/dist/constants/permissions.js +5 -0
- package/dist/constants/permissions.js.map +1 -1
- package/dist/pages/ActionsPage.js +162 -162
- package/dist/pages/ActionsPage.js.map +1 -1
- package/dist/pages/VibeDeckPage.js +1 -1
- package/dist/pages/VibeDetailsPage.js +309 -300
- package/dist/pages/VibeDetailsPage.js.map +1 -1
- package/dist/pages/tunnels/TunnelDetailsPage.js +91 -77
- package/dist/pages/tunnels/TunnelDetailsPage.js.map +1 -1
- package/package.json +2 -2
|
@@ -1,146 +1,157 @@
|
|
|
1
1
|
import { useTr as e } from "../../shared/hooks/useTr.js";
|
|
2
2
|
import { SelectionCheckbox as t } from "../shared/SelectionCheckbox.js";
|
|
3
3
|
import { ActionTypeBadge as n, SourceTypeBadge as r, TriggerTypeBadge as i } from "./ActionTypeBadge.js";
|
|
4
|
-
import {
|
|
5
|
-
import
|
|
6
|
-
import {
|
|
4
|
+
import { EntityShareButton as a } from "../sharing/EntityShareButton.js";
|
|
5
|
+
import "../sharing/index.js";
|
|
6
|
+
import { AlarmClock as o, CalendarClock as s, Clock as c, Copy as l, Hash as u, Pencil as d, Play as f, Trash2 as p } from "lucide-react";
|
|
7
|
+
import { motion as m, useReducedMotion as h } from "framer-motion";
|
|
8
|
+
import { jsx as g, jsxs as _ } from "react/jsx-runtime";
|
|
7
9
|
//#region src/components/actions/ActionCard.tsx
|
|
8
|
-
function
|
|
9
|
-
let
|
|
10
|
-
return /* @__PURE__ */
|
|
11
|
-
className: `bg-bg-surface border rounded-lg p-4 hover:border-border-strong transition-colors group ${
|
|
12
|
-
whileHover:
|
|
10
|
+
function v({ action: v, onExecute: y, onEdit: b, onDuplicate: x, onDelete: S, onSchedule: C, onAddToCalendar: w, canUpdate: T, canDelete: E, canExecute: D, isExecuting: O = !1, selected: k = !1, onToggleSelect: A }) {
|
|
11
|
+
let j = h(), M = e();
|
|
12
|
+
return /* @__PURE__ */ _(m.div, {
|
|
13
|
+
className: `bg-bg-surface border rounded-lg p-4 hover:border-border-strong transition-colors group ${k ? "border-action-primary-bg ring-1 ring-action-primary-bg/25" : "border-border-default"}`,
|
|
14
|
+
whileHover: j ? void 0 : {
|
|
13
15
|
y: -2,
|
|
14
16
|
boxShadow: "0 4px 12px var(--color-border-default)"
|
|
15
17
|
},
|
|
16
18
|
transition: { duration: .15 },
|
|
17
19
|
layout: !0,
|
|
18
20
|
role: "group",
|
|
19
|
-
"aria-label": `Action: ${
|
|
21
|
+
"aria-label": `Action: ${v.displayName || v.name}`,
|
|
20
22
|
children: [
|
|
21
|
-
/* @__PURE__ */
|
|
23
|
+
/* @__PURE__ */ _("div", {
|
|
22
24
|
className: "flex items-start justify-between gap-3 mb-3",
|
|
23
|
-
children: [/* @__PURE__ */
|
|
25
|
+
children: [/* @__PURE__ */ _("div", {
|
|
24
26
|
className: "flex items-start gap-3 min-w-0 flex-1",
|
|
25
|
-
children: [
|
|
27
|
+
children: [A && /* @__PURE__ */ g("div", {
|
|
26
28
|
onClick: (e) => e.stopPropagation(),
|
|
27
|
-
children: /* @__PURE__ */
|
|
28
|
-
checked:
|
|
29
|
-
onChange:
|
|
30
|
-
ariaLabel: `Select action ${
|
|
29
|
+
children: /* @__PURE__ */ g(t, {
|
|
30
|
+
checked: k,
|
|
31
|
+
onChange: A,
|
|
32
|
+
ariaLabel: `Select action ${v.displayName || v.name}`
|
|
31
33
|
})
|
|
32
|
-
}), /* @__PURE__ */
|
|
34
|
+
}), /* @__PURE__ */ _("div", {
|
|
33
35
|
className: "min-w-0 flex-1",
|
|
34
|
-
children: [/* @__PURE__ */
|
|
36
|
+
children: [/* @__PURE__ */ g("h3", {
|
|
35
37
|
className: "font-semibold text-text-primary truncate",
|
|
36
|
-
children:
|
|
37
|
-
}),
|
|
38
|
+
children: v.displayName || v.name
|
|
39
|
+
}), v.description && /* @__PURE__ */ g("p", {
|
|
38
40
|
className: "text-sm text-text-secondary mt-0.5 line-clamp-2",
|
|
39
|
-
children:
|
|
41
|
+
children: v.description
|
|
40
42
|
})]
|
|
41
43
|
})]
|
|
42
|
-
}), /* @__PURE__ */
|
|
44
|
+
}), /* @__PURE__ */ _("div", {
|
|
43
45
|
className: "flex items-center gap-1 opacity-0 group-hover:opacity-100 transition-opacity flex-shrink-0",
|
|
44
46
|
children: [
|
|
45
|
-
|
|
47
|
+
D && /* @__PURE__ */ g("button", {
|
|
46
48
|
type: "button",
|
|
47
49
|
onClick: (e) => {
|
|
48
|
-
e.stopPropagation(), v
|
|
50
|
+
e.stopPropagation(), y(v.id);
|
|
49
51
|
},
|
|
50
|
-
disabled:
|
|
52
|
+
disabled: O,
|
|
51
53
|
className: "p-1.5 rounded-md hover:bg-status-success-bg/20 text-status-success-text transition-colors disabled:opacity-50",
|
|
52
|
-
title:
|
|
53
|
-
children: /* @__PURE__ */
|
|
54
|
+
title: M("vibecontrols.actions.card.execute", "Execute"),
|
|
55
|
+
children: /* @__PURE__ */ g(f, { size: 14 })
|
|
54
56
|
}),
|
|
55
|
-
|
|
57
|
+
T && /* @__PURE__ */ g("button", {
|
|
56
58
|
type: "button",
|
|
57
59
|
onClick: (e) => {
|
|
58
|
-
e.stopPropagation(),
|
|
60
|
+
e.stopPropagation(), b(v.id);
|
|
59
61
|
},
|
|
60
62
|
className: "p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors",
|
|
61
|
-
title:
|
|
62
|
-
children: /* @__PURE__ */
|
|
63
|
+
title: M("vibecontrols.actions.card.edit", "Edit"),
|
|
64
|
+
children: /* @__PURE__ */ g(d, { size: 14 })
|
|
63
65
|
}),
|
|
64
|
-
|
|
66
|
+
C && /* @__PURE__ */ g("button", {
|
|
65
67
|
type: "button",
|
|
66
68
|
onClick: (e) => {
|
|
67
|
-
e.stopPropagation(),
|
|
69
|
+
e.stopPropagation(), C(v.id);
|
|
68
70
|
},
|
|
69
71
|
className: "p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors",
|
|
70
|
-
title:
|
|
71
|
-
children: /* @__PURE__ */
|
|
72
|
+
title: M("vibecontrols.actions.card.schedule", "Schedule this action"),
|
|
73
|
+
children: /* @__PURE__ */ g(o, { size: 14 })
|
|
72
74
|
}),
|
|
73
|
-
|
|
75
|
+
w && /* @__PURE__ */ g("button", {
|
|
74
76
|
type: "button",
|
|
75
77
|
onClick: (e) => {
|
|
76
|
-
e.stopPropagation(),
|
|
78
|
+
e.stopPropagation(), w(v.id);
|
|
77
79
|
},
|
|
78
80
|
className: "p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors",
|
|
79
|
-
title:
|
|
80
|
-
children: /* @__PURE__ */
|
|
81
|
+
title: M("vibecontrols.actions.card.addToCalendar", "Add to calendar"),
|
|
82
|
+
children: /* @__PURE__ */ g(s, { size: 14 })
|
|
81
83
|
}),
|
|
82
|
-
/* @__PURE__ */
|
|
84
|
+
/* @__PURE__ */ g("button", {
|
|
83
85
|
type: "button",
|
|
84
86
|
onClick: (e) => {
|
|
85
|
-
e.stopPropagation(),
|
|
87
|
+
e.stopPropagation(), x(v.id);
|
|
86
88
|
},
|
|
87
89
|
className: "p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors",
|
|
88
|
-
title:
|
|
89
|
-
children: /* @__PURE__ */
|
|
90
|
+
title: M("vibecontrols.actions.card.duplicate", "Duplicate"),
|
|
91
|
+
children: /* @__PURE__ */ g(l, { size: 14 })
|
|
90
92
|
}),
|
|
91
|
-
|
|
93
|
+
/* @__PURE__ */ g(a, {
|
|
94
|
+
entity: "action",
|
|
95
|
+
resource: {
|
|
96
|
+
id: v.id,
|
|
97
|
+
name: v.displayName || v.name,
|
|
98
|
+
vibeId: v.vibeId ?? null
|
|
99
|
+
},
|
|
100
|
+
label: M("vibecontrols.actions.card.share", "Share")
|
|
101
|
+
}),
|
|
102
|
+
E && /* @__PURE__ */ g("button", {
|
|
92
103
|
type: "button",
|
|
93
104
|
onClick: (e) => {
|
|
94
|
-
e.stopPropagation(),
|
|
105
|
+
e.stopPropagation(), S(v.id);
|
|
95
106
|
},
|
|
96
107
|
className: "p-1.5 rounded-md hover:bg-status-error-bg/20 text-status-error-text transition-colors",
|
|
97
|
-
title:
|
|
98
|
-
children: /* @__PURE__ */
|
|
108
|
+
title: M("vibecontrols.actions.card.delete", "Delete"),
|
|
109
|
+
children: /* @__PURE__ */ g(p, { size: 14 })
|
|
99
110
|
})
|
|
100
111
|
]
|
|
101
112
|
})]
|
|
102
113
|
}),
|
|
103
|
-
/* @__PURE__ */
|
|
114
|
+
/* @__PURE__ */ _("div", {
|
|
104
115
|
className: "flex flex-wrap items-center gap-1.5 mb-3",
|
|
105
116
|
children: [
|
|
106
|
-
/* @__PURE__ */
|
|
107
|
-
/* @__PURE__ */
|
|
108
|
-
|
|
117
|
+
/* @__PURE__ */ g(n, { type: v.actionType }),
|
|
118
|
+
/* @__PURE__ */ g(i, { type: v.triggerType }),
|
|
119
|
+
v.sourceType && /* @__PURE__ */ g(r, { type: v.sourceType })
|
|
109
120
|
]
|
|
110
121
|
}),
|
|
111
|
-
(
|
|
122
|
+
(v.category || v.tags && v.tags.length > 0) && /* @__PURE__ */ _("div", {
|
|
112
123
|
className: "flex flex-wrap items-center gap-1.5 mb-3",
|
|
113
|
-
children: [
|
|
124
|
+
children: [v.category && /* @__PURE__ */ g("span", {
|
|
114
125
|
className: "text-xs px-1.5 py-0.5 rounded bg-bg-sunken text-text-secondary",
|
|
115
|
-
children:
|
|
116
|
-
}),
|
|
126
|
+
children: v.category
|
|
127
|
+
}), v.tags?.map((e) => /* @__PURE__ */ _("span", {
|
|
117
128
|
className: "text-xs px-1.5 py-0.5 rounded bg-bg-sunken text-text-placeholder",
|
|
118
129
|
children: ["#", e]
|
|
119
130
|
}, e))]
|
|
120
131
|
}),
|
|
121
|
-
/* @__PURE__ */
|
|
132
|
+
/* @__PURE__ */ _("div", {
|
|
122
133
|
className: "flex items-center gap-4 text-xs text-text-placeholder",
|
|
123
|
-
children: [/* @__PURE__ */
|
|
134
|
+
children: [/* @__PURE__ */ _("span", {
|
|
124
135
|
className: "inline-flex items-center gap-1",
|
|
125
|
-
children: [/* @__PURE__ */
|
|
126
|
-
}), /* @__PURE__ */
|
|
136
|
+
children: [/* @__PURE__ */ g(u, { size: 12 }), M("vibecontrols.actions.card.executionRuns", "{{count}} runs", { count: v.executionCount ?? 0 })]
|
|
137
|
+
}), /* @__PURE__ */ _("span", {
|
|
127
138
|
className: "inline-flex items-center gap-1",
|
|
128
|
-
children: [/* @__PURE__ */
|
|
129
|
-
if (!e) return
|
|
139
|
+
children: [/* @__PURE__ */ g(c, { size: 12 }), ((e) => {
|
|
140
|
+
if (!e) return M("vibecontrols.actions.card.never", "Never");
|
|
130
141
|
let t = new Date(e), n = (/* @__PURE__ */ new Date()).getTime() - t.getTime(), r = Math.floor(n / 6e4);
|
|
131
|
-
if (r < 1) return
|
|
132
|
-
if (r < 60) return
|
|
142
|
+
if (r < 1) return M("vibecontrols.actions.card.justNow", "Just now");
|
|
143
|
+
if (r < 60) return M("vibecontrols.actions.card.minutesAgo", "{{count}}m ago", { count: r });
|
|
133
144
|
let i = Math.floor(r / 60);
|
|
134
|
-
if (i < 24) return
|
|
145
|
+
if (i < 24) return M("vibecontrols.actions.card.hoursAgo", "{{count}}h ago", { count: i });
|
|
135
146
|
let a = Math.floor(i / 24);
|
|
136
147
|
return a < 7 ? `${a}d ago` : t.toLocaleDateString();
|
|
137
|
-
})(
|
|
148
|
+
})(v.lastExecutedAt)]
|
|
138
149
|
})]
|
|
139
150
|
})
|
|
140
151
|
]
|
|
141
152
|
});
|
|
142
153
|
}
|
|
143
154
|
//#endregion
|
|
144
|
-
export {
|
|
155
|
+
export { v as ActionCard };
|
|
145
156
|
|
|
146
157
|
//# sourceMappingURL=ActionCard.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ActionCard.js","names":[],"sources":["../../../src/components/actions/ActionCard.tsx"],"sourcesContent":["import { Play, Pencil, Copy, Trash2, Clock, Hash, CalendarClock, AlarmClock } from 'lucide-react';\nimport { motion, useReducedMotion } from 'framer-motion';\nimport { ActionTypeBadge, TriggerTypeBadge, SourceTypeBadge } from './ActionTypeBadge';\nimport { SelectionCheckbox } from '../shared/SelectionCheckbox';\nimport { useTr } from '../../shared/hooks/useTr';\n\ninterface ActionCardAction {\n id: string;\n name: string;\n displayName?: string | null;\n description?: string | null;\n actionType: string;\n sourceType?: string | null;\n triggerType: string;\n category?: string | null;\n tags?: string[] | null;\n executionCount?: number | null;\n lastExecutedAt?: string | null;\n confirmationRequired?: boolean;\n}\n\ninterface ActionCardProps {\n action: ActionCardAction;\n onExecute: (id: string) => void;\n onEdit: (id: string) => void;\n onDuplicate: (id: string) => void;\n onDelete: (id: string) => void;\n onSchedule?: (id: string) => void;\n onAddToCalendar?: (id: string) => void;\n canUpdate: boolean;\n canDelete: boolean;\n canExecute: boolean;\n isExecuting?: boolean;\n selected?: boolean;\n onToggleSelect?: (checked: boolean) => void;\n}\n\nexport function ActionCard({\n action,\n onExecute,\n onEdit,\n onDuplicate,\n onDelete,\n onSchedule,\n onAddToCalendar,\n canUpdate,\n canDelete,\n canExecute,\n isExecuting = false,\n selected = false,\n onToggleSelect,\n}: ActionCardProps) {\n const shouldReduceMotion = useReducedMotion();\n const tr = useTr();\n\n const formatDate = (dateStr: string | null | undefined) => {\n if (!dateStr) return tr('vibecontrols.actions.card.never', 'Never');\n const date = new Date(dateStr);\n const now = new Date();\n const diffMs = now.getTime() - date.getTime();\n const diffMin = Math.floor(diffMs / 60000);\n if (diffMin < 1) return tr('vibecontrols.actions.card.justNow', 'Just now');\n if (diffMin < 60)\n return tr('vibecontrols.actions.card.minutesAgo', '{{count}}m ago', { count: diffMin });\n const diffHr = Math.floor(diffMin / 60);\n if (diffHr < 24)\n return tr('vibecontrols.actions.card.hoursAgo', '{{count}}h ago', { count: diffHr });\n const diffDays = Math.floor(diffHr / 24);\n if (diffDays < 7) return `${diffDays}d ago`;\n return date.toLocaleDateString();\n };\n\n return (\n <motion.div\n className={`bg-bg-surface border rounded-lg p-4 hover:border-border-strong transition-colors group ${\n selected\n ? 'border-action-primary-bg ring-1 ring-action-primary-bg/25'\n : 'border-border-default'\n }`}\n whileHover={\n shouldReduceMotion\n ? undefined\n : { y: -2, boxShadow: '0 4px 12px var(--color-border-default)' }\n }\n transition={{ duration: 0.15 }}\n layout\n role=\"group\"\n aria-label={`Action: ${action.displayName || action.name}`}\n >\n {/* Header */}\n <div className=\"flex items-start justify-between gap-3 mb-3\">\n <div className=\"flex items-start gap-3 min-w-0 flex-1\">\n {onToggleSelect && (\n <div onClick={(event) => event.stopPropagation()}>\n <SelectionCheckbox\n checked={selected}\n onChange={onToggleSelect}\n ariaLabel={`Select action ${action.displayName || action.name}`}\n />\n </div>\n )}\n <div className=\"min-w-0 flex-1\">\n <h3 className=\"font-semibold text-text-primary truncate\">\n {action.displayName || action.name}\n </h3>\n {action.description && (\n <p className=\"text-sm text-text-secondary mt-0.5 line-clamp-2\">\n {action.description}\n </p>\n )}\n </div>\n </div>\n {/* Action buttons */}\n <div className=\"flex items-center gap-1 opacity-0 group-hover:opacity-100 transition-opacity flex-shrink-0\">\n {canExecute && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onExecute(action.id);\n }}\n disabled={isExecuting}\n className=\"p-1.5 rounded-md hover:bg-status-success-bg/20 text-status-success-text transition-colors disabled:opacity-50\"\n title={tr('vibecontrols.actions.card.execute', 'Execute')}\n >\n <Play size={14} />\n </button>\n )}\n {canUpdate && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onEdit(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.edit', 'Edit')}\n >\n <Pencil size={14} />\n </button>\n )}\n {onSchedule && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onSchedule(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.schedule', 'Schedule this action')}\n >\n <AlarmClock size={14} />\n </button>\n )}\n {onAddToCalendar && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onAddToCalendar(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.addToCalendar', 'Add to calendar')}\n >\n <CalendarClock size={14} />\n </button>\n )}\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onDuplicate(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.duplicate', 'Duplicate')}\n >\n <Copy size={14} />\n </button>\n {canDelete && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onDelete(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-status-error-bg/20 text-status-error-text transition-colors\"\n title={tr('vibecontrols.actions.card.delete', 'Delete')}\n >\n <Trash2 size={14} />\n </button>\n )}\n </div>\n </div>\n\n {/* Badges */}\n <div className=\"flex flex-wrap items-center gap-1.5 mb-3\">\n <ActionTypeBadge type={action.actionType} />\n <TriggerTypeBadge type={action.triggerType} />\n {action.sourceType && <SourceTypeBadge type={action.sourceType} />}\n </div>\n\n {/* Category and Tags */}\n {(action.category || (action.tags && action.tags.length > 0)) && (\n <div className=\"flex flex-wrap items-center gap-1.5 mb-3\">\n {action.category && (\n <span className=\"text-xs px-1.5 py-0.5 rounded bg-bg-sunken text-text-secondary\">\n {action.category}\n </span>\n )}\n {action.tags?.map((tag) => (\n <span\n key={tag}\n className=\"text-xs px-1.5 py-0.5 rounded bg-bg-sunken text-text-placeholder\"\n >\n #{tag}\n </span>\n ))}\n </div>\n )}\n\n {/* Stats */}\n <div className=\"flex items-center gap-4 text-xs text-text-placeholder\">\n <span className=\"inline-flex items-center gap-1\">\n <Hash size={12} />\n {tr('vibecontrols.actions.card.executionRuns', '{{count}} runs', {\n count: action.executionCount ?? 0,\n })}\n </span>\n <span className=\"inline-flex items-center gap-1\">\n <Clock size={12} />\n {formatDate(action.lastExecutedAt)}\n </span>\n </div>\n </motion.div>\n );\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"ActionCard.js","names":[],"sources":["../../../src/components/actions/ActionCard.tsx"],"sourcesContent":["import { Play, Pencil, Copy, Trash2, Clock, Hash, CalendarClock, AlarmClock } from 'lucide-react';\nimport { motion, useReducedMotion } from 'framer-motion';\nimport { ActionTypeBadge, TriggerTypeBadge, SourceTypeBadge } from './ActionTypeBadge';\nimport { SelectionCheckbox } from '../shared/SelectionCheckbox';\nimport { EntityShareButton } from '../sharing';\nimport { useTr } from '../../shared/hooks/useTr';\n\ninterface ActionCardAction {\n id: string;\n name: string;\n displayName?: string | null;\n description?: string | null;\n actionType: string;\n sourceType?: string | null;\n triggerType: string;\n category?: string | null;\n tags?: string[] | null;\n executionCount?: number | null;\n lastExecutedAt?: string | null;\n confirmationRequired?: boolean;\n vibeId?: string | null;\n}\n\ninterface ActionCardProps {\n action: ActionCardAction;\n onExecute: (id: string) => void;\n onEdit: (id: string) => void;\n onDuplicate: (id: string) => void;\n onDelete: (id: string) => void;\n onSchedule?: (id: string) => void;\n onAddToCalendar?: (id: string) => void;\n canUpdate: boolean;\n canDelete: boolean;\n canExecute: boolean;\n isExecuting?: boolean;\n selected?: boolean;\n onToggleSelect?: (checked: boolean) => void;\n}\n\nexport function ActionCard({\n action,\n onExecute,\n onEdit,\n onDuplicate,\n onDelete,\n onSchedule,\n onAddToCalendar,\n canUpdate,\n canDelete,\n canExecute,\n isExecuting = false,\n selected = false,\n onToggleSelect,\n}: ActionCardProps) {\n const shouldReduceMotion = useReducedMotion();\n const tr = useTr();\n\n const formatDate = (dateStr: string | null | undefined) => {\n if (!dateStr) return tr('vibecontrols.actions.card.never', 'Never');\n const date = new Date(dateStr);\n const now = new Date();\n const diffMs = now.getTime() - date.getTime();\n const diffMin = Math.floor(diffMs / 60000);\n if (diffMin < 1) return tr('vibecontrols.actions.card.justNow', 'Just now');\n if (diffMin < 60)\n return tr('vibecontrols.actions.card.minutesAgo', '{{count}}m ago', { count: diffMin });\n const diffHr = Math.floor(diffMin / 60);\n if (diffHr < 24)\n return tr('vibecontrols.actions.card.hoursAgo', '{{count}}h ago', { count: diffHr });\n const diffDays = Math.floor(diffHr / 24);\n if (diffDays < 7) return `${diffDays}d ago`;\n return date.toLocaleDateString();\n };\n\n return (\n <motion.div\n className={`bg-bg-surface border rounded-lg p-4 hover:border-border-strong transition-colors group ${\n selected\n ? 'border-action-primary-bg ring-1 ring-action-primary-bg/25'\n : 'border-border-default'\n }`}\n whileHover={\n shouldReduceMotion\n ? undefined\n : { y: -2, boxShadow: '0 4px 12px var(--color-border-default)' }\n }\n transition={{ duration: 0.15 }}\n layout\n role=\"group\"\n aria-label={`Action: ${action.displayName || action.name}`}\n >\n {/* Header */}\n <div className=\"flex items-start justify-between gap-3 mb-3\">\n <div className=\"flex items-start gap-3 min-w-0 flex-1\">\n {onToggleSelect && (\n <div onClick={(event) => event.stopPropagation()}>\n <SelectionCheckbox\n checked={selected}\n onChange={onToggleSelect}\n ariaLabel={`Select action ${action.displayName || action.name}`}\n />\n </div>\n )}\n <div className=\"min-w-0 flex-1\">\n <h3 className=\"font-semibold text-text-primary truncate\">\n {action.displayName || action.name}\n </h3>\n {action.description && (\n <p className=\"text-sm text-text-secondary mt-0.5 line-clamp-2\">\n {action.description}\n </p>\n )}\n </div>\n </div>\n {/* Action buttons */}\n <div className=\"flex items-center gap-1 opacity-0 group-hover:opacity-100 transition-opacity flex-shrink-0\">\n {canExecute && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onExecute(action.id);\n }}\n disabled={isExecuting}\n className=\"p-1.5 rounded-md hover:bg-status-success-bg/20 text-status-success-text transition-colors disabled:opacity-50\"\n title={tr('vibecontrols.actions.card.execute', 'Execute')}\n >\n <Play size={14} />\n </button>\n )}\n {canUpdate && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onEdit(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.edit', 'Edit')}\n >\n <Pencil size={14} />\n </button>\n )}\n {onSchedule && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onSchedule(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.schedule', 'Schedule this action')}\n >\n <AlarmClock size={14} />\n </button>\n )}\n {onAddToCalendar && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onAddToCalendar(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.addToCalendar', 'Add to calendar')}\n >\n <CalendarClock size={14} />\n </button>\n )}\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onDuplicate(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-bg-elevated text-text-secondary transition-colors\"\n title={tr('vibecontrols.actions.card.duplicate', 'Duplicate')}\n >\n <Copy size={14} />\n </button>\n <EntityShareButton\n entity=\"action\"\n resource={{\n id: action.id,\n name: action.displayName || action.name,\n vibeId: action.vibeId ?? null,\n }}\n label={tr('vibecontrols.actions.card.share', 'Share')}\n />\n {canDelete && (\n <button\n type=\"button\"\n onClick={(event) => {\n event.stopPropagation();\n onDelete(action.id);\n }}\n className=\"p-1.5 rounded-md hover:bg-status-error-bg/20 text-status-error-text transition-colors\"\n title={tr('vibecontrols.actions.card.delete', 'Delete')}\n >\n <Trash2 size={14} />\n </button>\n )}\n </div>\n </div>\n\n {/* Badges */}\n <div className=\"flex flex-wrap items-center gap-1.5 mb-3\">\n <ActionTypeBadge type={action.actionType} />\n <TriggerTypeBadge type={action.triggerType} />\n {action.sourceType && <SourceTypeBadge type={action.sourceType} />}\n </div>\n\n {/* Category and Tags */}\n {(action.category || (action.tags && action.tags.length > 0)) && (\n <div className=\"flex flex-wrap items-center gap-1.5 mb-3\">\n {action.category && (\n <span className=\"text-xs px-1.5 py-0.5 rounded bg-bg-sunken text-text-secondary\">\n {action.category}\n </span>\n )}\n {action.tags?.map((tag) => (\n <span\n key={tag}\n className=\"text-xs px-1.5 py-0.5 rounded bg-bg-sunken text-text-placeholder\"\n >\n #{tag}\n </span>\n ))}\n </div>\n )}\n\n {/* Stats */}\n <div className=\"flex items-center gap-4 text-xs text-text-placeholder\">\n <span className=\"inline-flex items-center gap-1\">\n <Hash size={12} />\n {tr('vibecontrols.actions.card.executionRuns', '{{count}} runs', {\n count: action.executionCount ?? 0,\n })}\n </span>\n <span className=\"inline-flex items-center gap-1\">\n <Clock size={12} />\n {formatDate(action.lastExecutedAt)}\n </span>\n </div>\n </motion.div>\n );\n}\n"],"mappings":"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"}
|