@greatapps/greatagents-ui 0.3.21 → 0.3.23

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.
@@ -1,7 +1,8 @@
1
1
  import type { Agent } from "../../types";
2
2
  import type { GagentsHookConfig } from "../../hooks/types";
3
3
  import { AgentObjectivesList } from "./agent-objectives-list";
4
- import { AgentPromptEditor } from "./agent-prompt-editor";
4
+ import { AgentDefinitionEditor } from "./agent-definition-editor";
5
+ import { AgentRevisionTab } from "./agent-revision-tab";
5
6
  import { AgentConversationsPanel } from "../conversations/agent-conversations-panel";
6
7
  import { CapabilitiesTab } from "../capabilities/capabilities-tab";
7
8
  import { IntegrationsTab } from "../capabilities/integrations-tab";
@@ -11,7 +12,7 @@ import {
11
12
  TabsTrigger,
12
13
  TabsContent,
13
14
  } from "@greatapps/greatauth-ui/ui";
14
- import { Target, FileText, MessageCircle, Blocks, Plug } from "lucide-react";
15
+ import { Target, Settings2, MessageCircle, Blocks, Plug, History } from "lucide-react";
15
16
 
16
17
  interface AgentTabsProps {
17
18
  agent: Agent;
@@ -25,11 +26,11 @@ export function AgentTabs({
25
26
  renderChatLink,
26
27
  }: AgentTabsProps) {
27
28
  return (
28
- <Tabs defaultValue="prompt">
29
+ <Tabs defaultValue="definicao">
29
30
  <TabsList>
30
- <TabsTrigger value="prompt" className="flex items-center gap-1.5">
31
- <FileText aria-hidden="true" className="h-3.5 w-3.5" />
32
- Prompt
31
+ <TabsTrigger value="definicao" className="flex items-center gap-1.5">
32
+ <Settings2 aria-hidden="true" className="h-3.5 w-3.5" />
33
+ Definição
33
34
  </TabsTrigger>
34
35
  <TabsTrigger value="objetivos" className="flex items-center gap-1.5">
35
36
  <Target aria-hidden="true" className="h-3.5 w-3.5" />
@@ -47,10 +48,14 @@ export function AgentTabs({
47
48
  <MessageCircle aria-hidden="true" className="h-3.5 w-3.5" />
48
49
  Conversas
49
50
  </TabsTrigger>
51
+ <TabsTrigger value="revisao" className="flex items-center gap-1.5">
52
+ <History aria-hidden="true" className="h-3.5 w-3.5" />
53
+ Revisão
54
+ </TabsTrigger>
50
55
  </TabsList>
51
56
 
52
- <TabsContent value="prompt" className="mt-4">
53
- <AgentPromptEditor agent={agent} config={config} />
57
+ <TabsContent value="definicao" className="mt-4">
58
+ <AgentDefinitionEditor agent={agent} config={config} />
54
59
  </TabsContent>
55
60
 
56
61
  <TabsContent value="objetivos" className="mt-4">
@@ -72,6 +77,10 @@ export function AgentTabs({
72
77
  renderChatLink={renderChatLink}
73
78
  />
74
79
  </TabsContent>
80
+
81
+ <TabsContent value="revisao" className="mt-4">
82
+ <AgentRevisionTab agent={agent} config={config} />
83
+ </TabsContent>
75
84
  </Tabs>
76
85
  );
77
86
  }
@@ -0,0 +1,180 @@
1
+ import { useCallback, useRef, useState } from "react";
2
+ import type { ConversationFlowStep } from "../../types";
3
+ import { Button, Input } from "@greatapps/greatauth-ui/ui";
4
+ import {
5
+ Sortable,
6
+ SortableContent,
7
+ SortableItem,
8
+ SortableItemHandle,
9
+ SortableOverlay,
10
+ } from "../ui/sortable";
11
+ import { GripVertical, Plus, Trash2 } from "lucide-react";
12
+ import { cn } from "../../lib";
13
+
14
+ interface StepWithKey extends ConversationFlowStep {
15
+ _key: number;
16
+ }
17
+
18
+ interface ConversationFlowEditorProps {
19
+ steps: ConversationFlowStep[];
20
+ onChange: (steps: ConversationFlowStep[]) => void;
21
+ disabled?: boolean;
22
+ }
23
+
24
+ function renumber(steps: ConversationFlowStep[]): ConversationFlowStep[] {
25
+ return steps.map((s, i) => ({ ...s, order: i + 1 }));
26
+ }
27
+
28
+ function stripKeys(steps: StepWithKey[]): ConversationFlowStep[] {
29
+ return steps.map(({ _key, ...rest }) => rest);
30
+ }
31
+
32
+ export function ConversationFlowEditor({
33
+ steps,
34
+ onChange,
35
+ }: ConversationFlowEditorProps) {
36
+ const nextKey = useRef(steps.length + 1);
37
+
38
+ const [internal, setInternal] = useState<StepWithKey[]>(() =>
39
+ steps.map((s, i) => ({ ...s, _key: i + 1 })),
40
+ );
41
+
42
+ const sync = useCallback(
43
+ (next: StepWithKey[]) => {
44
+ const renumbered = renumber(next).map((s, i) => ({
45
+ ...s,
46
+ _key: next[i]._key,
47
+ })) as StepWithKey[];
48
+ setInternal(renumbered);
49
+ onChange(stripKeys(renumbered));
50
+ },
51
+ [onChange],
52
+ );
53
+
54
+ function handleAdd() {
55
+ nextKey.current += 1;
56
+ const newStep: StepWithKey = {
57
+ order: internal.length + 1,
58
+ instruction: "",
59
+ example: null,
60
+ _key: nextKey.current,
61
+ };
62
+ sync([...internal, newStep]);
63
+ }
64
+
65
+ function handleRemove(key: number) {
66
+ sync(internal.filter((s) => s._key !== key));
67
+ }
68
+
69
+ function handleFieldChange(
70
+ key: number,
71
+ field: "instruction" | "example",
72
+ value: string,
73
+ ) {
74
+ const next = internal.map((s) => {
75
+ if (s._key !== key) return s;
76
+ if (field === "example") {
77
+ return { ...s, example: value || null };
78
+ }
79
+ return { ...s, [field]: value };
80
+ });
81
+ sync(next);
82
+ }
83
+
84
+ function handleReorder(newItems: StepWithKey[]) {
85
+ sync(newItems);
86
+ }
87
+
88
+ return (
89
+ <div className="space-y-3">
90
+ {internal.length === 0 ? (
91
+ <div className="flex flex-col items-center justify-center rounded-lg border border-dashed p-8 text-center">
92
+ <p className="text-sm text-muted-foreground">
93
+ Nenhuma etapa definida. Adicione a primeira etapa do fluxo de
94
+ conversa.
95
+ </p>
96
+ </div>
97
+ ) : (
98
+ <Sortable
99
+ value={internal}
100
+ onValueChange={handleReorder}
101
+ getItemValue={(item) => item._key}
102
+ >
103
+ <SortableContent className="space-y-2">
104
+ {internal.map((step) => (
105
+ <SortableItem
106
+ key={step._key}
107
+ value={step._key}
108
+ className="flex items-center gap-2 rounded-lg border bg-card p-2"
109
+ >
110
+ <SortableItemHandle className="shrink-0 cursor-grab text-muted-foreground hover:text-foreground">
111
+ <GripVertical aria-hidden="true" className="h-4 w-4" />
112
+ </SortableItemHandle>
113
+
114
+ <span className="shrink-0 text-xs font-medium text-muted-foreground tabular-nums w-6 text-right">
115
+ {step.order}.
116
+ </span>
117
+
118
+ <Input
119
+ value={step.instruction}
120
+ onChange={(e) =>
121
+ handleFieldChange(step._key, "instruction", e.target.value)
122
+ }
123
+ placeholder="Instrução (obrigatório)"
124
+ className="flex-1 min-w-0"
125
+ required
126
+ />
127
+
128
+ <Input
129
+ value={step.example ?? ""}
130
+ onChange={(e) =>
131
+ handleFieldChange(step._key, "example", e.target.value)
132
+ }
133
+ placeholder="Exemplo (opcional)"
134
+ className="flex-1 min-w-0"
135
+ />
136
+
137
+ <Button
138
+ type="button"
139
+ variant="ghost"
140
+ size="icon"
141
+ aria-label="Remover etapa"
142
+ className={cn(
143
+ "shrink-0 text-muted-foreground hover:text-destructive",
144
+ )}
145
+ onClick={() => handleRemove(step._key)}
146
+ >
147
+ <Trash2 className="h-4 w-4" />
148
+ </Button>
149
+ </SortableItem>
150
+ ))}
151
+ </SortableContent>
152
+ <SortableOverlay>
153
+ {({ value }) => {
154
+ const step = internal.find((s) => s._key === value);
155
+ return (
156
+ <div className="flex items-center gap-2 rounded-lg border bg-card p-2 shadow-lg">
157
+ <GripVertical
158
+ aria-hidden="true"
159
+ className="h-4 w-4 text-muted-foreground"
160
+ />
161
+ <span className="text-xs font-medium text-muted-foreground">
162
+ {step?.order}.
163
+ </span>
164
+ <span className="text-sm truncate">
165
+ {step?.instruction || "Etapa sem instrução"}
166
+ </span>
167
+ </div>
168
+ );
169
+ }}
170
+ </SortableOverlay>
171
+ </Sortable>
172
+ )}
173
+
174
+ <Button type="button" variant="outline" size="sm" onClick={handleAdd}>
175
+ <Plus className="mr-2 h-4 w-4" />
176
+ Adicionar etapa
177
+ </Button>
178
+ </div>
179
+ );
180
+ }
@@ -34,7 +34,6 @@ export function useCreateAgent(config: GagentsHookConfig) {
34
34
  return useMutation({
35
35
  mutationFn: (body: {
36
36
  title: string;
37
- prompt?: string;
38
37
  photo?: string;
39
38
  delay_typing?: number;
40
39
  waiting_time?: number;
@@ -57,7 +56,13 @@ export function useUpdateAgent(config: GagentsHookConfig) {
57
56
  id: number;
58
57
  body: {
59
58
  title?: string;
60
- prompt?: string;
59
+ identity?: string | null;
60
+ mission?: string | null;
61
+ tone_style_format?: string | null;
62
+ rules?: string | null;
63
+ conversation_flow?: string | null;
64
+ context?: string | null;
65
+ change_notes?: string;
61
66
  photo?: string;
62
67
  delay_typing?: number;
63
68
  waiting_time?: number;
@@ -26,7 +26,10 @@ export function useCreateObjective(config: GagentsHookConfig) {
26
26
  body: {
27
27
  title: string;
28
28
  slug?: string;
29
- prompt?: string | null;
29
+ instruction?: string | null;
30
+ description?: string | null;
31
+ conversation_flow?: string | null;
32
+ rules?: string | null;
30
33
  order?: number;
31
34
  active?: boolean;
32
35
  };
@@ -52,7 +55,10 @@ export function useUpdateObjective(config: GagentsHookConfig) {
52
55
  body: Partial<{
53
56
  title: string;
54
57
  slug: string;
55
- prompt: string | null;
58
+ instruction: string | null;
59
+ description: string | null;
60
+ conversation_flow: string | null;
61
+ rules: string | null;
56
62
  order: number;
57
63
  active: boolean;
58
64
  }>;
package/src/index.ts CHANGED
@@ -19,6 +19,7 @@ export type {
19
19
  CapabilitiesResponse,
20
20
  AgentCapability,
21
21
  AgentCapabilitiesPayload,
22
+ ConversationFlowStep,
22
23
  } from "./types";
23
24
 
24
25
  // Client
@@ -36,7 +37,9 @@ export { AgentsTable } from "./components/agents/agents-table";
36
37
  export { AgentFormDialog } from "./components/agents/agent-form-dialog";
37
38
  export { AgentEditForm } from "./components/agents/agent-edit-form";
38
39
  export { AgentTabs } from "./components/agents/agent-tabs";
39
- export { AgentPromptEditor } from "./components/agents/agent-prompt-editor";
40
+ export { AgentDefinitionEditor } from "./components/agents/agent-definition-editor";
41
+ export { AgentRevisionTab } from "./components/agents/agent-revision-tab";
42
+ export { ConversationFlowEditor } from "./components/agents/conversation-flow-editor";
40
43
  export { AgentObjectivesList } from "./components/agents/agent-objectives-list";
41
44
  export { AgentToolsList } from "./components/agents/agent-tools-list";
42
45
  export { ToolsTable } from "./components/tools/tools-table";
@@ -14,19 +14,34 @@ export interface Agent {
14
14
  openai_assistant_id: string | null;
15
15
  delay_typing: number | null;
16
16
  waiting_time: number | null;
17
+ identity: string | null;
18
+ mission: string | null;
19
+ tone_style_format: string | null;
20
+ rules: string | null;
21
+ conversation_flow: string | null;
22
+ context: string | null;
17
23
  active: boolean;
18
24
  deleted: number;
19
25
  datetime_add: string;
20
26
  datetime_alt: string | null;
21
27
  }
22
28
 
29
+ export interface ConversationFlowStep {
30
+ order: number;
31
+ instruction: string;
32
+ example: string | null;
33
+ }
34
+
23
35
  export interface Objective {
24
36
  id: number;
25
37
  id_account: number;
26
38
  id_agent: number;
27
39
  title: string;
28
40
  slug: string | null;
29
- prompt: string | null;
41
+ instruction: string | null;
42
+ description: string | null;
43
+ conversation_flow: string | null;
44
+ rules: string | null;
30
45
  order: number;
31
46
  active: boolean;
32
47
  deleted: number;