diff --git a/chat-agent/api-go/chatAgent.go b/chat-agent/api-go/chatAgent.go index 93f2cab..7afcd63 100644 --- a/chat-agent/api-go/chatAgent.go +++ b/chat-agent/api-go/chatAgent.go @@ -3,6 +3,7 @@ package main import ( "encoding/json" "fmt" + "time" "github.com/hypermodeinc/modus/sdk/go/pkg/agents" "github.com/hypermodeinc/modus/sdk/go/pkg/models" @@ -10,76 +11,573 @@ import ( ) const ( - MAX_HISTORY = 10 - MODEL_NAME = "text-generator" + MODEL_NAME = "text-generator" + MAX_HISTORY = 20 + TOOL_LOOP_LIMIT = 3 ) -type ChatAgent struct { - agents.AgentBase - state ChatAgentState +// Response item types +type ResponseItemType string + +const ( + ResponseTypeMessage ResponseItemType = "message" + ResponseTypeToolCall ResponseItemType = "tool_call" + ResponseTypeCard ResponseItemType = "card" +) + +type ResponseItem struct { + ID string `json:"id"` + Type ResponseItemType `json:"type"` + Timestamp string `json:"timestamp,omitempty"` +} + +type MessageItem struct { + ResponseItem + Content string `json:"content"` + Role string `json:"role"` +} + +type ToolCallItem struct { + ResponseItem + ToolCall ToolCallData `json:"toolCall"` +} + +type CardItem struct { + ResponseItem + Card CardData `json:"card"` +} + +type ToolCallData struct { + ID string `json:"id"` + Name string `json:"name"` + Arguments map[string]interface{} `json:"arguments"` + Status string `json:"status"` + Result interface{} `json:"result,omitempty"` + Error string `json:"error,omitempty"` +} + +type CardData struct { + ID string `json:"id"` + Type string `json:"type"` + Title string `json:"title,omitempty"` + Content map[string]interface{} `json:"content"` + Actions []CardAction `json:"actions,omitempty"` +} + +type CardAction struct { + ID string `json:"id"` + Label string `json:"label"` + Type string `json:"type"` + Action string `json:"action"` + Data map[string]interface{} `json:"data,omitempty"` } type ChatAgentState struct { - ChatHistory string + ConversationId string `json:"conversationId"` + Items []interface{} `json:"items"` + ChatHistory []openai.RequestMessage `json:"chatHistory"` + LastActivity time.Time `json:"lastActivity"` +} + +type ChatAgent struct { + agents.AgentBase + conversationId string + items []interface{} + chatHistory []openai.RequestMessage + lastActivity time.Time } func (c *ChatAgent) Name() string { - return "Chat-v1" + return "KnowledgeAgent" } func (c *ChatAgent) GetState() *string { - serializedState, _ := json.Marshal(c.state) - serializedStateStr := string(serializedState) - return &serializedStateStr + state := ChatAgentState{ + ConversationId: c.conversationId, + Items: c.items, + ChatHistory: c.chatHistory, + LastActivity: c.lastActivity, + } + + data, err := json.Marshal(state) + if err != nil { + fmt.Printf("Error marshaling state: %v\n", err) + return nil + } + + stateStr := string(data) + return &stateStr } func (c *ChatAgent) SetState(data *string) { - err := json.Unmarshal([]byte(*data), &c.state) - if err != nil { - fmt.Println("Error unmarshalling state:", err) + if data == nil { + return } + + var state ChatAgentState + if err := json.Unmarshal([]byte(*data), &state); err != nil { + fmt.Printf("Error unmarshaling state: %v\n", err) + return + } + + c.conversationId = state.ConversationId + c.items = state.Items + c.chatHistory = state.ChatHistory + c.lastActivity = state.LastActivity } -func (c *ChatAgent) OnStart() error { - c.state.ChatHistory = "" - fmt.Println("Agent started") +func (c *ChatAgent) OnInitialize() error { + c.lastActivity = time.Now() + c.chatHistory = []openai.RequestMessage{} + return nil +} + +func (c *ChatAgent) OnSuspend() error { + return nil +} + +func (c *ChatAgent) OnResume() error { + return nil +} + +func (c *ChatAgent) OnTerminate() error { return nil } func (c *ChatAgent) OnReceiveMessage(msgName string, data *string) (*string, error) { switch msgName { - case "new_user_message": - return c.chat(data) - case "get_chat_history": - return &c.state.ChatHistory, nil + case "chat": + return c.handleChat(data) + case "get_items": + return c.getConversationItems() + case "clear_items": + return c.clearConversationItems() + default: + return nil, fmt.Errorf("unknown message type: %s", msgName) + } +} + +func (c *ChatAgent) handleChat(data *string) (*string, error) { + if data == nil { + return nil, fmt.Errorf("no message data provided") + } + + var request struct { + Message string `json:"message"` + } + if err := json.Unmarshal([]byte(*data), &request); err != nil { + return nil, fmt.Errorf("failed to parse chat request: %v", err) + } + + if c.conversationId == "" { + c.conversationId = fmt.Sprintf("conv_%d", time.Now().UnixNano()) + } + + // Add user message to items and chat history + userMessage := MessageItem{ + ResponseItem: ResponseItem{ + ID: fmt.Sprintf("%d", time.Now().UnixNano()), + Type: ResponseTypeMessage, + Timestamp: time.Now().Format(time.RFC3339), + }, + Content: request.Message, + Role: "user", + } + c.items = append(c.items, userMessage) + c.chatHistory = append(c.chatHistory, openai.NewUserMessage(request.Message)) + c.lastActivity = time.Now() + + var responseItems []interface{} + + // Generate AI response with tools + response, toolItems, err := c.generateAIResponseWithTools(request.Message) + if err != nil { + return nil, fmt.Errorf("failed to generate AI response: %v", err) + } + + // Add tool call items to response + for _, item := range toolItems { + c.items = append(c.items, item) + responseItems = append(responseItems, item) + } + + // Add assistant message + if response != "" { + assistantMessage := MessageItem{ + ResponseItem: ResponseItem{ + ID: fmt.Sprintf("%d", time.Now().UnixNano()), + Type: ResponseTypeMessage, + Timestamp: time.Now().Format(time.RFC3339), + }, + Content: response, + Role: "assistant", + } + c.items = append(c.items, assistantMessage) + responseItems = append(responseItems, assistantMessage) + } + + // Limit chat history size + if len(c.chatHistory) > MAX_HISTORY { + c.chatHistory = c.chatHistory[len(c.chatHistory)-MAX_HISTORY:] + } + + // Create response + chatResponse := struct { + Items []interface{} `json:"items"` + ConversationId string `json:"conversationId"` + }{ + Items: responseItems, + ConversationId: c.conversationId, + } + + responseData, err := json.Marshal(chatResponse) + if err != nil { + return nil, fmt.Errorf("failed to marshal response: %v", err) + } + + responseStr := string(responseData) + return &responseStr, nil +} + +func (c *ChatAgent) generateAIResponseWithTools(userMessage string) (string, []interface{}, error) { + model, err := models.GetModel[openai.ChatModel](MODEL_NAME) + if err != nil { + return "", nil, fmt.Errorf("failed to get model: %v", err) + } + + tools := c.getKnowledgeTools() + systemPrompt := c.getSystemPrompt() + + var toolItems []interface{} + loops := 0 + + // Create a working copy of chat history for this conversation + workingHistory := make([]openai.RequestMessage, len(c.chatHistory)) + copy(workingHistory, c.chatHistory) + + for loops < TOOL_LOOP_LIMIT { + input, err := model.CreateInput() + if err != nil { + return "", nil, fmt.Errorf("failed to create input: %v", err) + } + + // Build messages: system + history + input.Messages = []openai.RequestMessage{openai.NewSystemMessage(systemPrompt)} + input.Messages = append(input.Messages, workingHistory...) + + input.Temperature = 0.7 + input.Tools = tools + input.ToolChoice = openai.ToolChoiceAuto + + output, err := model.Invoke(input) + if err != nil { + return "", nil, fmt.Errorf("model invocation failed: %v", err) + } + + message := output.Choices[0].Message + + // Add assistant message to working history + workingHistory = append(workingHistory, message.ToAssistantMessage()) + + // Check if there are tool calls + if len(message.ToolCalls) > 0 { + // Process each tool call + for _, toolCall := range message.ToolCalls { + // Create tool call item for UI + toolCallItem := ToolCallItem{ + ResponseItem: ResponseItem{ + ID: fmt.Sprintf("tool_%d", time.Now().UnixNano()), + Type: ResponseTypeToolCall, + Timestamp: time.Now().Format(time.RFC3339), + }, + ToolCall: ToolCallData{ + ID: toolCall.Id, + Name: toolCall.Function.Name, + Arguments: c.parseToolArguments(toolCall.Function.Arguments), + Status: "executing", + }, + } + + // Execute tool + result, err := c.executeKnowledgeTool(toolCall) + if err != nil { + toolCallItem.ToolCall.Status = "error" + toolCallItem.ToolCall.Error = err.Error() + } else { + toolCallItem.ToolCall.Status = "completed" + toolCallItem.ToolCall.Result = result + } + + toolItems = append(toolItems, toolCallItem) + + // Add tool response to working history + var toolResponse string + if err != nil { + toolResponse = fmt.Sprintf("Error: %s", err.Error()) + } else { + resultJSON, _ := json.Marshal(result) + toolResponse = string(resultJSON) + } + workingHistory = append(workingHistory, openai.NewToolMessage(&toolResponse, toolCall.Id)) + } + } else { + // No more tool calls, we have our final response + c.chatHistory = workingHistory + return message.Content, toolItems, nil + } + + loops++ + } + + // If we hit the loop limit, return what we have + c.chatHistory = workingHistory + return "I've processed your request with the available tools.", toolItems, nil +} + +func (c *ChatAgent) getKnowledgeTools() []openai.Tool { + return []openai.Tool{ + openai.NewToolForFunction("save_fact", "Save a fact when user states something to remember"). + WithParameter("fact", "string", "The fact to be remembered"). + WithParameter("entities", "string", "Comma-separated list of entities like 'place:Paris, person:Will, person:John'"). + WithParameter("happened_on", "string", "Date in format YYYY-MM-DD if the fact is associated with a specific date"), + + openai.NewToolForFunction("search_fact_by_term", "Search for facts using keywords"). + WithParameter("terms", "string", "Search terms separated by spaces"), + + openai.NewToolForFunction("search_by_entity", "Search for facts related to a specific entity"). + WithParameter("entity", "string", "Name of the entity to search for"), + + openai.NewToolForFunction("all_facts", "Retrieve all saved facts"), + } +} + +func (c *ChatAgent) getSystemPrompt() string { + return fmt.Sprintf(`Today is %s. You are a knowledge assistant that can remember and retrieve facts. + +When users tell you facts, use the save_fact tool to store them with relevant entities. +When users ask questions, use the search tools to find relevant information. +Always acknowledge when you save facts and provide helpful responses when searching. + +For fact saving, extract entities like places, people, organizations, events, etc. +For first-person statements, link to "user" as a person entity. + +Be conversational and helpful in your responses.`, time.Now().UTC().Format(time.RFC3339)) +} + +func (c *ChatAgent) parseToolArguments(argsJSON string) map[string]interface{} { + var args map[string]interface{} + if err := json.Unmarshal([]byte(argsJSON), &args); err != nil { + return map[string]interface{}{"raw": argsJSON} + } + return args +} + +func (c *ChatAgent) executeKnowledgeTool(toolCall openai.ToolCall) (interface{}, error) { + var args map[string]interface{} + if err := json.Unmarshal([]byte(toolCall.Function.Arguments), &args); err != nil { + return nil, fmt.Errorf("failed to parse tool arguments: %v", err) + } + + switch toolCall.Function.Name { + case "save_fact": + fact := c.getStringArg(args, "fact", "") + entities := c.getStringArg(args, "entities", "") + happenedOn := c.getStringArg(args, "happened_on", "") + + // Save to Dgraph + result, err := save_fact(fact, entities, happenedOn) + if err != nil { + return nil, err + } + + // Create a card to show the saved fact + cardItem := CardItem{ + ResponseItem: ResponseItem{ + ID: fmt.Sprintf("card_%d", time.Now().UnixNano()), + Type: ResponseTypeCard, + Timestamp: time.Now().Format(time.RFC3339), + }, + Card: CardData{ + ID: fmt.Sprintf("fact_card_%d", time.Now().UnixNano()), + Type: "fact", + Title: "Fact Saved", + Content: map[string]interface{}{ + "fact": fact, + "entities": entities, + "saved_at": time.Now().Format("2006-01-02 15:04:05"), + }, + Actions: []CardAction{ + { + ID: "view_details", + Label: "View Details", + Type: "button", + Action: "view_details", + Data: map[string]interface{}{"fact": fact}, + }, + }, + }, + } + c.items = append(c.items, cardItem) + + return result, nil + + case "search_fact_by_term": + terms := c.getStringArg(args, "terms", "") + result, err := search_fact(terms) + if err != nil { + return nil, err + } + + // Parse the result and create a card if facts were found + var factsData map[string]interface{} + if err := json.Unmarshal([]byte(*result), &factsData); err == nil { + if facts, ok := factsData["facts"].([]interface{}); ok && len(facts) > 0 { + cardItem := CardItem{ + ResponseItem: ResponseItem{ + ID: fmt.Sprintf("card_%d", time.Now().UnixNano()), + Type: ResponseTypeCard, + Timestamp: time.Now().Format(time.RFC3339), + }, + Card: CardData{ + ID: fmt.Sprintf("search_card_%d", time.Now().UnixNano()), + Type: "search_results", + Title: fmt.Sprintf("Search Results for '%s'", terms), + Content: map[string]interface{}{ + "query": terms, + "results_count": len(facts), + "facts": facts, + }, + Actions: []CardAction{ + { + ID: "show_facts", + Label: "Show All Facts", + Type: "button", + Action: "show_facts", + Data: map[string]interface{}{"facts": facts}, + }, + }, + }, + } + c.items = append(c.items, cardItem) + } + } + + return result, nil + + case "search_by_entity": + entity := c.getStringArg(args, "entity", "") + result, err := facts_by_entity(entity) + if err != nil { + return nil, err + } + + // Create a card for entity results + var entityData map[string]interface{} + if err := json.Unmarshal([]byte(*result), &entityData); err == nil { + cardItem := CardItem{ + ResponseItem: ResponseItem{ + ID: fmt.Sprintf("card_%d", time.Now().UnixNano()), + Type: ResponseTypeCard, + Timestamp: time.Now().Format(time.RFC3339), + }, + Card: CardData{ + ID: fmt.Sprintf("entity_card_%d", time.Now().UnixNano()), + Type: "entity_facts", + Title: fmt.Sprintf("Facts about '%s'", entity), + Content: map[string]interface{}{ + "entity": entity, + "data": entityData, + }, + Actions: []CardAction{ + { + ID: "search_entity", + Label: "Search Related", + Type: "button", + Action: "search_entity", + Data: map[string]interface{}{"entity": entity}, + }, + }, + }, + } + c.items = append(c.items, cardItem) + } + + return result, nil + + case "all_facts": + result, err := all_facts() + if err != nil { + return nil, err + } + + // Create a card for all facts + var factsData map[string]interface{} + if err := json.Unmarshal([]byte(*result), &factsData); err == nil { + cardItem := CardItem{ + ResponseItem: ResponseItem{ + ID: fmt.Sprintf("card_%d", time.Now().UnixNano()), + Type: ResponseTypeCard, + Timestamp: time.Now().Format(time.RFC3339), + }, + Card: CardData{ + ID: fmt.Sprintf("all_facts_card_%d", time.Now().UnixNano()), + Type: "all_facts", + Title: "All Saved Facts", + Content: map[string]interface{}{ + "facts": factsData["facts"], + "total": len(factsData["facts"].([]interface{})), + }, + Actions: []CardAction{ + { + ID: "show_facts", + Label: "View All", + Type: "button", + Action: "show_facts", + Data: factsData, + }, + }, + }, + } + c.items = append(c.items, cardItem) + } + + return result, nil + default: - return nil, nil + return nil, fmt.Errorf("unknown tool: %s", toolCall.Function.Name) } } -func (c *ChatAgent) chat(data *string) (*string, error) { - model, _ := models.GetModel[openai.ChatModel](MODEL_NAME) - loopLimit := 3 +func (c *ChatAgent) getStringArg(args map[string]interface{}, key, defaultValue string) string { + if val, ok := args[key]; ok { + if str, ok := val.(string); ok { + return str + } + } + return defaultValue +} - llmResponse := llmWithTools( - model, - chatTools(), - systemPrompt(), - *data, - c.state.ChatHistory, - openai.ResponseFormatText, - executeToolCall, - loopLimit, - MAX_HISTORY, - ) +func (c *ChatAgent) getConversationItems() (*string, error) { + response := struct { + Items []interface{} `json:"items"` + Count int `json:"count"` + }{ + Items: c.items, + Count: len(c.items), + } - c.state.ChatHistory = llmResponse.ChatHistory - fmt.Println(llmResponse.Response) + itemsData, err := json.Marshal(response) + if err != nil { + return nil, fmt.Errorf("failed to marshal items: %v", err) + } - return &llmResponse.Response, nil + itemsStr := string(itemsData) + return &itemsStr, nil } -func (c *ChatAgent) DeleteAgent(id string) error { - _, err := agents.Stop(id) - return err +func (c *ChatAgent) clearConversationItems() (*string, error) { + c.items = []interface{}{} + c.chatHistory = []openai.RequestMessage{} + c.lastActivity = time.Now() + return nil, nil } diff --git a/chat-agent/api-go/main.go b/chat-agent/api-go/main.go index f60618f..57bf2a8 100644 --- a/chat-agent/api-go/main.go +++ b/chat-agent/api-go/main.go @@ -1,56 +1,129 @@ package main import ( + "encoding/json" + "fmt" + "github.com/hypermodeinc/modus/sdk/go/pkg/agents" ) -type SearchResponse struct { - Message string `json:"message"` - History string `json:"history"` - User_preferences string `json:"user_preferences"` +type ChatRequest struct { + Message string `json:"message"` +} + +type ChatResponse struct { + Items string `json:"items"` // JSON string of items array + ConversationId string `json:"conversationId"` +} + +type HistoryResponse struct { + Items string `json:"items"` // JSON string of items array + Count int `json:"count"` } func init() { agents.Register(&ChatAgent{}) } -// The following are regular Modus functions. +// The following are regular Modus functions exposed via GraphQL -func CreateConversation() (id *string, err error) { - // ChatAgent Name is "Chat-v1" +func CreateConversation() (string, error) { + // ChatAgent Name is "KnowledgeAgent" // A Conversation is an instance of the ChatAgent. - info, err := agents.Start("Chat-v1") + info, err := agents.Start("KnowledgeAgent") if err != nil { - return nil, err + return "", err } - return &info.Id, nil + return info.Id, nil } -func ContinueChat(id string, query string) (*string, error) { + +func ContinueChat(id string, query string) (ChatResponse, error) { // Send a message to the agent in charge of the conversation. - response, err := agents.SendMessage(id, "new_user_message", agents.WithData(query)) + request := ChatRequest{ + Message: query, + } + + requestData, err := json.Marshal(request) if err != nil { - return nil, err + return ChatResponse{}, fmt.Errorf("failed to marshal request: %v", err) } - return response, nil -} + requestStr := string(requestData) + response, err := agents.SendMessage(id, "chat", agents.WithData(requestStr)) + if err != nil { + return ChatResponse{}, err + } + + if response == nil { + return ChatResponse{}, fmt.Errorf("no response received") + } + + // Parse the response to extract items and conversation ID + var agentResponse struct { + Items []interface{} `json:"items"` + ConversationId string `json:"conversationId"` + } + if err := json.Unmarshal([]byte(*response), &agentResponse); err != nil { + return ChatResponse{}, fmt.Errorf("failed to unmarshal response: %v", err) + } + + // Convert items array to JSON string for GraphQL + itemsJson, err := json.Marshal(agentResponse.Items) + if err != nil { + return ChatResponse{}, fmt.Errorf("failed to marshal items: %v", err) + } -func ChatHistory(id string) (*string, error) { - // Send a message to the agent and get a response. - return agents.SendMessage(id, "get_chat_history") + return ChatResponse{ + Items: string(itemsJson), + ConversationId: agentResponse.ConversationId, + }, nil } -/*func SaveFact(id string, fact string, location string) (*string, error) { - // Send a message to the agent to save a fact. - return (save_fact(id, fact, location)) +func ChatHistory(id string) (HistoryResponse, error) { + // Send a message to the agent and get response items. + response, err := agents.SendMessage(id, "get_items") + if err != nil { + return HistoryResponse{}, err + } + + if response == nil { + return HistoryResponse{Items: "[]", Count: 0}, nil + } + + // Parse the response to extract items and count + var agentResponse struct { + Items []interface{} `json:"items"` + Count int `json:"count"` + } + if err := json.Unmarshal([]byte(*response), &agentResponse); err != nil { + return HistoryResponse{}, fmt.Errorf("failed to unmarshal items: %v", err) + } + + // Convert items array to JSON string for GraphQL + itemsJson, err := json.Marshal(agentResponse.Items) + if err != nil { + return HistoryResponse{}, fmt.Errorf("failed to marshal items: %v", err) + } + + return HistoryResponse{ + Items: string(itemsJson), + Count: agentResponse.Count, + }, nil } -*/ -func DeleteAgent(id string) (*string, error) { +func DeleteAgent(id string) (string, error) { _, err := agents.Stop(id) if err != nil { - return nil, err + return "", err + } + return id, nil +} + +func DeleteConversationHistory(id string) (bool, error) { + _, err := agents.SendMessage(id, "clear_items") + if err != nil { + return false, err } - return &id, nil + return true, nil } diff --git a/chat-agent/api-go/myChat.go b/chat-agent/api-go/myChat.go index 30d55eb..4d693f6 100644 --- a/chat-agent/api-go/myChat.go +++ b/chat-agent/api-go/myChat.go @@ -107,58 +107,74 @@ func parseEntities(entities string) []Entity { } func save_fact(fact string, entities string, happened_on string) (*string, error) { - fmt.Println("Fact:", fact) fmt.Println("Entities:", entities) fmt.Println("Happened on:", happened_on) + // Parse entities string into an array of key-value pairs entitiesArray := parseEntities(entities) // Save a fact as a node in Dgraph with attributes sessionId, fact and timestamp timestamp := time.Now().UTC().Format(time.RFC3339) - rdf := "" - queryBlock := "{" - // add each entity as a variable in the query + + // Build query for finding existing entities + queryBlock := "" + if len(entitiesArray) > 0 { + queryBlock = "{\n" + for i, entity := range entitiesArray { + entityUrn := entity.entityType + "." + entity.name + entityVar := fmt.Sprintf("entity_%d", i) + queryBlock += fmt.Sprintf(` %s as var(func: eq(entity.id, "%s"))`+"\n", entityVar, entityUrn) + } + queryBlock += "}" + } + + // Build RDF mutation + rdf := fmt.Sprintf(` + <_:fact> "%s" . + <_:fact> "%s" .`, timestamp, fact) + + // Add entity relationships for i, entity := range entitiesArray { entityUrn := entity.entityType + "." + entity.name entityVar := fmt.Sprintf("entity_%d", i) - queryBlock += fmt.Sprintf(`%s as var(func:eq(entity.id,"%s")) `, entityVar, entityUrn) rdf += fmt.Sprintf(` <_:fact> uid(%s) . uid(%s) "%s" . uid(%s) "%s" . - uid(%s) "%s" . - `, entityVar, entityVar, entityUrn, entityVar, entity.entityType, entityVar, entity.name) + uid(%s) "%s" .`, + entityVar, entityVar, entityUrn, entityVar, entity.entityType, entityVar, entity.name) } - queryBlock += `}` - query := dgraph.NewQuery(queryBlock) - - rdf += fmt.Sprintf(` - <_:fact> "%s" . - <_:fact> "%s" . - `, timestamp, fact) // If the fact is associated with a date, add it to the RDF if happened_on != "" { - // convert the YYYY-MM-DD format to a full ISO 8601 date - // Parse the date string into a time.Time object _, err := time.Parse("2006-01-02", happened_on) if err == nil { rdf += fmt.Sprintf(` - <_:fact> "%s" . - `, happened_on) + <_:fact> "%s" .`, happened_on) } } + // Create query and mutation + var query *dgraph.Query + if queryBlock != "" { + query = dgraph.NewQuery(queryBlock) + } else { + query = dgraph.NewQuery("{}") + } + mutation := dgraph.NewMutation().WithSetNquads(rdf) _, err := dgraph.ExecuteQuery(connection, query, mutation) if err != nil { + fmt.Printf("Error executing DQL: %v\n", err) + fmt.Printf("Query: %s\n", queryBlock) + fmt.Printf("RDF: %s\n", rdf) return nil, err } + defaultResponse := "Fact saved" return &defaultResponse, nil - } func search_fact(terms string) (*string, error) { diff --git a/chat-agent/docker-compose.yml b/chat-agent/docker-compose.yml new file mode 100644 index 0000000..94edf20 --- /dev/null +++ b/chat-agent/docker-compose.yml @@ -0,0 +1,27 @@ +version: "3.8" + +services: + # Dgraph Zero controls the cluster + zero: + image: dgraph/dgraph:latest + container_name: chat-dgraph-zero + volumes: + - ~/chat-dgraph:/dgraph + ports: + - 5080:5080 + - 6080:6080 + command: > + dgraph zero --my=zero:5080 --logtostderr -v=1 + + # Dgraph Alpha hosts the graph and indexes + alpha: + image: dgraph/dgraph:latest + container_name: chat-dgraph-alpha + volumes: + - ~/chat-dgraph:/dgraph + ports: + - 8080:8080 + - 9080:9080 + command: > + dgraph alpha --my=alpha:7080 --zero=zero:5080 --security whitelist=0.0.0.0/0 --logtostderr + -v=1 diff --git a/chat-agent/docker-dgraph.md b/chat-agent/docker-dgraph.md new file mode 100644 index 0000000..5dfcdb4 --- /dev/null +++ b/chat-agent/docker-dgraph.md @@ -0,0 +1,54 @@ +# Dgraph Docker Setup + +Simple Docker Compose setup for the Dgraph database used by the chat agent. + +## Quick Start + +```bash +# Start Dgraph +docker-compose up -d + +# Load schema manually +curl --data-binary '@schema.dql' -H 'content-type: application/dql' http://localhost:8080/alter + +# Start the Go API (separate terminal) +cd api-go && modus dev +``` + +## Services + +- **Dgraph Alpha**: http://localhost:8080 (HTTP API), localhost:9080 (gRPC) +- **Dgraph Zero**: localhost:5080 (cluster control), localhost:6080 (HTTP) +- **API**: http://localhost:8686/graphql (via `modus dev`) + +## Commands + +```bash +# Start/stop +docker-compose up -d +docker-compose down + +# Fresh start (clears data) +docker-compose down +rm -rf ~/chat-dgraph +docker-compose up -d + +# View logs +docker-compose logs -f alpha +docker-compose logs -f zero + +# Load schema +curl --data-binary '@schema.dql' -H 'content-type: application/dql' http://localhost:8080/alter + +# Check status +docker-compose ps +``` + +## Data Location + +Data is stored in `~/chat-dgraph` on your host machine for persistence. + +## Requirements + +- Docker & Docker Compose +- `api-go/.env` with `MODUS_HYPERMODE_ROUTER_TOKEN=your_token` diff --git a/hypermode-chat/package-lock.json b/hypermode-chat/package-lock.json index 8e6c0ef..bb1d8f0 100644 --- a/hypermode-chat/package-lock.json +++ b/hypermode-chat/package-lock.json @@ -8,16 +8,16 @@ "name": "chat-app", "version": "0.1.0", "dependencies": { - "@aichatkit/apollo-adapter": "0.0.0-alpha.4", - "@aichatkit/localstorage-adapter": "0.0.0-alpha.4", - "@aichatkit/types": "0.0.0-alpha.4", - "@aichatkit/ui": "0.0.0-alpha.4", + "@aichatkit/apollo-adapter": "0.0.0-alpha.6", + "@aichatkit/localstorage-adapter": "0.0.0-alpha.6", + "@aichatkit/types": "0.0.0-alpha.6", + "@aichatkit/ui": "0.0.0-alpha.6", "@phosphor-icons/react": "^2.1.7", "@radix-ui/react-slot": "^1.2.2", "class-variance-authority": "^0.7.1", "clsx": "^2.1.1", "framer-motion": "^12.11.3", - "lucide-react": "^0.488.0 || ^0.512.0 || ^0.513.0 || ^0.514.0 || ^0.517.0", + "lucide-react": "^0.488.0", "next": "15.3.4", "react": "^19.1.0", "react-dom": "^19.1.0", @@ -36,13 +36,13 @@ } }, "node_modules/@aichatkit/apollo-adapter": { - "version": "0.0.0-alpha.4", - "resolved": "https://registry.npmjs.org/@aichatkit/apollo-adapter/-/apollo-adapter-0.0.0-alpha.4.tgz", - "integrity": "sha512-Hmy3cAONwfIG2qu3m09WJtk1kiJNswwG68CgNMOm4/B+t9hMgkaWw0ULHi3N0jzi7eAGgBp6S24CPL0QfbjbQA==", + "version": "0.0.0-alpha.6", + "resolved": "https://registry.npmjs.org/@aichatkit/apollo-adapter/-/apollo-adapter-0.0.0-alpha.6.tgz", + "integrity": "sha512-S3X561bl7TAePxzWzFnEJ0Lbkc0mxZl21n9zAWxi9l03i09EmU6xlnWWQ8kC9IN+LOqsGyNi5tfjQbA3Tig+WQ==", "license": "MIT", "dependencies": { - "@aichatkit/network-adapter": "0.0.0-alpha.4", - "@aichatkit/types": "0.0.0-alpha.4" + "@aichatkit/network-adapter": "0.0.0-alpha.6", + "@aichatkit/types": "0.0.0-alpha.6" }, "peerDependencies": { "@apollo/client": "^3.8.0", @@ -51,48 +51,48 @@ } }, "node_modules/@aichatkit/localstorage-adapter": { - "version": "0.0.0-alpha.4", - "resolved": "https://registry.npmjs.org/@aichatkit/localstorage-adapter/-/localstorage-adapter-0.0.0-alpha.4.tgz", - "integrity": "sha512-HicmPnbyG+qhlM1FB/slHaLkb4/EpqVVnXO12TNrCHxftbB2yuIcYPFvsQqgAxx/aTQ/Px1fvLhSQKLcCdg5xw==", + "version": "0.0.0-alpha.6", + "resolved": "https://registry.npmjs.org/@aichatkit/localstorage-adapter/-/localstorage-adapter-0.0.0-alpha.6.tgz", + "integrity": "sha512-5BBMxc7YgMRYDlev3r8BkwOaqsmv1Ore+5O4ZuwePS7qzSD7UFCo0GbvE1XuRBF5h1Q8qGp6z2q70LXl2A9Jrw==", "license": "MIT", "dependencies": { - "@aichatkit/storage-adapter": "0.0.0-alpha.4", - "@aichatkit/types": "0.0.0-alpha.4" + "@aichatkit/storage-adapter": "0.0.0-alpha.6", + "@aichatkit/types": "0.0.0-alpha.6" } }, "node_modules/@aichatkit/network-adapter": { - "version": "0.0.0-alpha.4", - "resolved": "https://registry.npmjs.org/@aichatkit/network-adapter/-/network-adapter-0.0.0-alpha.4.tgz", - "integrity": "sha512-K/e6kYvy4BUkYSWs2NKqXSDcicpD/Mv3gdcdYQS6Z0B5yrEqH3Ubdc14UFKQQUtVXyeu+/LrmTEnpsF64I6DUg==", + "version": "0.0.0-alpha.6", + "resolved": "https://registry.npmjs.org/@aichatkit/network-adapter/-/network-adapter-0.0.0-alpha.6.tgz", + "integrity": "sha512-eqkyj7ZykD1E9rE6tbPWD9zMUY9NLUF/8hU7s3n5F04LGJ58+MG2cPzP5HR4tw1gKyBccvWsileYnhn8ftajnw==", "license": "MIT", "dependencies": { - "@aichatkit/types": "0.0.0-alpha.4" + "@aichatkit/types": "0.0.0-alpha.6" } }, "node_modules/@aichatkit/storage-adapter": { - "version": "0.0.0-alpha.4", - "resolved": "https://registry.npmjs.org/@aichatkit/storage-adapter/-/storage-adapter-0.0.0-alpha.4.tgz", - "integrity": "sha512-cqfsc1/nlp/zkjouiwHQEY5x1B7BuL9UDr2vlowhnQhC/ZGASYQnEFI2tXwF+CCM+2M3asL0EAYozSWhkLSbSg==", + "version": "0.0.0-alpha.6", + "resolved": "https://registry.npmjs.org/@aichatkit/storage-adapter/-/storage-adapter-0.0.0-alpha.6.tgz", + "integrity": "sha512-g9kuMAP63vpvtCbjjZI/KAzGzxcPa6TH/Q57IqARFPxPyzc+rvqlIhh5CHv4RkzWV6+vJmOdBRY5ifBf2gMc3w==", "license": "MIT", "dependencies": { - "@aichatkit/types": "0.0.0-alpha.4" + "@aichatkit/types": "0.0.0-alpha.6" } }, "node_modules/@aichatkit/types": { - "version": "0.0.0-alpha.4", - "resolved": "https://registry.npmjs.org/@aichatkit/types/-/types-0.0.0-alpha.4.tgz", - "integrity": "sha512-sWKxTw++iEgwQH6YMc5GhAJE87U3FAWlrQJqaJTZjFSpzykMsKl5QXqn7x4oJ8EYmMkVFSqkSFjExRluu5BZsA==", + "version": "0.0.0-alpha.6", + "resolved": "https://registry.npmjs.org/@aichatkit/types/-/types-0.0.0-alpha.6.tgz", + "integrity": "sha512-haLzNxLhmYfrRGh4BTy/YqE5X1dPELBGIS2th9gzsqXWCXnQH8XT5hCEEuL1hrSRziTMysQGQapfEHjXxVKc9g==", "license": "MIT" }, "node_modules/@aichatkit/ui": { - "version": "0.0.0-alpha.4", - "resolved": "https://registry.npmjs.org/@aichatkit/ui/-/ui-0.0.0-alpha.4.tgz", - "integrity": "sha512-aiipFCQNHXQliGt2Be9Bh+Vt+S8pT+XvYXlXM3SxuI1vosOEY0JPT/n/0UOiIOzPUDMLfqn2icjWYtA2PX4n8g==", + "version": "0.0.0-alpha.6", + "resolved": "https://registry.npmjs.org/@aichatkit/ui/-/ui-0.0.0-alpha.6.tgz", + "integrity": "sha512-3iJiDGCzUkwxWsPv/s8plmyQu1Rm68V8a7U39ZJ+R42NROQ1RXtrt3Hn92eiKGcIx/E7HGhZa3GEwyz5SP2hKQ==", "license": "MIT", "dependencies": { - "@aichatkit/network-adapter": "0.0.0-alpha.4", - "@aichatkit/storage-adapter": "0.0.0-alpha.4", - "@aichatkit/types": "0.0.0-alpha.4", + "@aichatkit/network-adapter": "0.0.0-alpha.6", + "@aichatkit/storage-adapter": "0.0.0-alpha.6", + "@aichatkit/types": "0.0.0-alpha.6", "@radix-ui/react-slot": "^1.0.2", "class-variance-authority": "^0.7.0", "clsx": "^2.0.0", @@ -234,9 +234,9 @@ } }, "node_modules/@eslint/config-array": { - "version": "0.20.0", - "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.20.0.tgz", - "integrity": "sha512-fxlS1kkIjx8+vy2SjuCB94q3htSNrufYTXubwiBFeaQHbH6Ipi43gFJq2zCMt6PHhImH3Xmr0NksKDvchWlpQQ==", + "version": "0.21.0", + "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.21.0.tgz", + "integrity": "sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -249,9 +249,9 @@ } }, "node_modules/@eslint/config-helpers": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.2.2.tgz", - "integrity": "sha512-+GPzk8PlG0sPpzdU5ZvIRMPidzAnZDl/s9L+y13iodqvb8leL53bTannOrQ/Im7UkpsmFU5Ily5U60LWixnmLg==", + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.3.0.tgz", + "integrity": "sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==", "dev": true, "license": "Apache-2.0", "engines": { @@ -296,9 +296,9 @@ } }, "node_modules/@eslint/js": { - "version": "9.27.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.27.0.tgz", - "integrity": "sha512-G5JD9Tu5HJEu4z2Uo4aHY2sLV64B7CDMXxFzqzjl3NKd6RVzSXNoE80jk7Y0lJkTTkjiIhBAqmlYwjuBY3tvpA==", + "version": "9.30.0", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.30.0.tgz", + "integrity": "sha512-Wzw3wQwPvc9sHM+NjakWTcPx11mbZyiYHuwWa/QfZ7cIRX7WK54PSk7bdyXDaoaopUcMatv1zaQvOAAO8hCdww==", "dev": true, "license": "MIT", "engines": { @@ -319,19 +319,32 @@ } }, "node_modules/@eslint/plugin-kit": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.1.tgz", - "integrity": "sha512-0J+zgWxHN+xXONWIyPWKFMgVuJoZuGiIFu8yxk7RJjxkzpGmyja5wRFqZIVtjDVOQpV+Rw0iOAjYPE2eQyjr0w==", + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.3.tgz", + "integrity": "sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==", "dev": true, "license": "Apache-2.0", "dependencies": { - "@eslint/core": "^0.14.0", + "@eslint/core": "^0.15.1", "levn": "^0.4.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, + "node_modules/@eslint/plugin-kit/node_modules/@eslint/core": { + "version": "0.15.1", + "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.15.1.tgz", + "integrity": "sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@types/json-schema": "^7.0.15" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, "node_modules/@graphql-typed-document-node/core": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/@graphql-typed-document-node/core/-/core-3.2.0.tgz", @@ -870,9 +883,9 @@ } }, "node_modules/@napi-rs/wasm-runtime": { - "version": "0.2.10", - "resolved": "https://registry.npmjs.org/@napi-rs/wasm-runtime/-/wasm-runtime-0.2.10.tgz", - "integrity": "sha512-bCsCyeZEwVErsGmyPNSzwfwFn4OdxBj0mmv6hOFucB/k81Ojdu68RbZdxYsRQUPc9l6SU5F/cG+bXgWs3oUgsQ==", + "version": "0.2.11", + "resolved": "https://registry.npmjs.org/@napi-rs/wasm-runtime/-/wasm-runtime-0.2.11.tgz", + "integrity": "sha512-9DPkXtvHydrcOsopiYpUgPHpmj0HWZKMUnL2dZqpvC42lsratuBG06V5ipyno0fUek5VlFsNQ+AcFATSrJXgMA==", "dev": true, "license": "MIT", "optional": true, @@ -1135,9 +1148,9 @@ "license": "MIT" }, "node_modules/@rushstack/eslint-patch": { - "version": "1.11.0", - "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.11.0.tgz", - "integrity": "sha512-zxnHvoMQVqewTJr/W4pKjF0bMGiKJv1WX7bSrkl46Hg0QjESbzBROWK0Wg4RphzSOS5Jiy7eFimmM3UgMrMZbQ==", + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.12.0.tgz", + "integrity": "sha512-5EwMtOqvJMMa3HbmxLlF74e+3/HhwBTMcvt3nqVJgGCozO6hzIPOBlwm8mGVNR9SN2IJpxSnlxczyDjcn7qIyw==", "dev": true, "license": "MIT" }, @@ -1168,9 +1181,9 @@ } }, "node_modules/@types/estree": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.7.tgz", - "integrity": "sha512-w28IoSUCJpidD/TGviZwwMJckNESJZXFu7NBZ5YJ4mEUnNraUn9Pm8HSZm/jDF1pDWYKspWE7oVphigUPRakIQ==", + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", + "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", "dev": true, "license": "MIT" }, @@ -1189,9 +1202,9 @@ "license": "MIT" }, "node_modules/@types/node": { - "version": "22.15.24", - "resolved": "https://registry.npmjs.org/@types/node/-/node-22.15.24.tgz", - "integrity": "sha512-w9CZGm9RDjzTh/D+hFwlBJ3ziUaVw7oufKA3vOFSOZlzmW9AkZnfjPb+DLnrV6qtgL/LNmP0/2zBNCFHL3F0ng==", + "version": "22.15.34", + "resolved": "https://registry.npmjs.org/@types/node/-/node-22.15.34.tgz", + "integrity": "sha512-8Y6E5WUupYy1Dd0II32BsWAx5MWdcnRd8L84Oys3veg1YrYtNtzgO4CFhiBg6MDSjk7Ay36HYOnU7/tuOzIzcw==", "dev": true, "license": "MIT", "dependencies": { @@ -1199,9 +1212,9 @@ } }, "node_modules/@types/react": { - "version": "19.1.6", - "resolved": "https://registry.npmjs.org/@types/react/-/react-19.1.6.tgz", - "integrity": "sha512-JeG0rEWak0N6Itr6QUx+X60uQmN+5t3j9r/OVDtWzFXKaj6kD1BwJzOksD0FF6iWxZlbE1kB0q9vtnU2ekqa1Q==", + "version": "19.1.8", + "resolved": "https://registry.npmjs.org/@types/react/-/react-19.1.8.tgz", + "integrity": "sha512-AwAfQ2Wa5bCx9WP8nZL2uMZWod7J7/JSplxbTmBQ5ms6QpqNYm672H0Vu9ZVKVngQ+ii4R/byguVEUZQyeg44g==", "devOptional": true, "license": "MIT", "dependencies": { @@ -1209,9 +1222,9 @@ } }, "node_modules/@types/react-dom": { - "version": "19.1.5", - "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-19.1.5.tgz", - "integrity": "sha512-CMCjrWucUBZvohgZxkjd6S9h0nZxXjzus6yDfUb+xLxYM7VvjKNH1tQrE9GWLql1XoOP4/Ds3bwFqShHUYraGg==", + "version": "19.1.6", + "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-19.1.6.tgz", + "integrity": "sha512-4hOiT/dwO8Ko0gV1m/TJZYk3y0KBnY9vzDh7W+DH17b2HFSOGgdj33dhihPeuy3l0q23+4e+hoXHV6hCC4dCXw==", "dev": true, "license": "MIT", "peerDependencies": { @@ -1219,17 +1232,17 @@ } }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.33.0.tgz", - "integrity": "sha512-CACyQuqSHt7ma3Ns601xykeBK/rDeZa3w6IS6UtMQbixO5DWy+8TilKkviGDH6jtWCo8FGRKEK5cLLkPvEammQ==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.35.0.tgz", + "integrity": "sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/regexpp": "^4.10.0", - "@typescript-eslint/scope-manager": "8.33.0", - "@typescript-eslint/type-utils": "8.33.0", - "@typescript-eslint/utils": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0", + "@typescript-eslint/scope-manager": "8.35.0", + "@typescript-eslint/type-utils": "8.35.0", + "@typescript-eslint/utils": "8.35.0", + "@typescript-eslint/visitor-keys": "8.35.0", "graphemer": "^1.4.0", "ignore": "^7.0.0", "natural-compare": "^1.4.0", @@ -1243,15 +1256,15 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "@typescript-eslint/parser": "^8.33.0", + "@typescript-eslint/parser": "^8.35.0", "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <5.9.0" } }, "node_modules/@typescript-eslint/eslint-plugin/node_modules/ignore": { - "version": "7.0.4", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-7.0.4.tgz", - "integrity": "sha512-gJzzk+PQNznz8ysRrC0aOkBNVRBDtE1n53IqyqEf3PXrYwomFs5q4pGMizBMJF+ykh03insJ27hB8gSrD2Hn8A==", + "version": "7.0.5", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-7.0.5.tgz", + "integrity": "sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==", "dev": true, "license": "MIT", "engines": { @@ -1259,16 +1272,16 @@ } }, "node_modules/@typescript-eslint/parser": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.33.0.tgz", - "integrity": "sha512-JaehZvf6m0yqYp34+RVnihBAChkqeH+tqqhS0GuX1qgPpwLvmTPheKEs6OeCK6hVJgXZHJ2vbjnC9j119auStQ==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.35.0.tgz", + "integrity": "sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/scope-manager": "8.33.0", - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/typescript-estree": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0", + "@typescript-eslint/scope-manager": "8.35.0", + "@typescript-eslint/types": "8.35.0", + "@typescript-eslint/typescript-estree": "8.35.0", + "@typescript-eslint/visitor-keys": "8.35.0", "debug": "^4.3.4" }, "engines": { @@ -1284,14 +1297,14 @@ } }, "node_modules/@typescript-eslint/project-service": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.33.0.tgz", - "integrity": "sha512-d1hz0u9l6N+u/gcrk6s6gYdl7/+pp8yHheRTqP6X5hVDKALEaTn8WfGiit7G511yueBEL3OpOEpD+3/MBdoN+A==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.35.0.tgz", + "integrity": "sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.33.0", - "@typescript-eslint/types": "^8.33.0", + "@typescript-eslint/tsconfig-utils": "^8.35.0", + "@typescript-eslint/types": "^8.35.0", "debug": "^4.3.4" }, "engines": { @@ -1300,17 +1313,20 @@ "funding": { "type": "opencollective", "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "typescript": ">=4.8.4 <5.9.0" } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.33.0.tgz", - "integrity": "sha512-LMi/oqrzpqxyO72ltP+dBSP6V0xiUb4saY7WLtxSfiNEBI8m321LLVFU9/QDJxjDQG9/tjSqKz/E3380TEqSTw==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.35.0.tgz", + "integrity": "sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0" + "@typescript-eslint/types": "8.35.0", + "@typescript-eslint/visitor-keys": "8.35.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -1321,9 +1337,9 @@ } }, "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.33.0.tgz", - "integrity": "sha512-sTkETlbqhEoiFmGr1gsdq5HyVbSOF0145SYDJ/EQmXHtKViCaGvnyLqWFFHtEXoS0J1yU8Wyou2UGmgW88fEug==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.35.0.tgz", + "integrity": "sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==", "dev": true, "license": "MIT", "engines": { @@ -1338,14 +1354,14 @@ } }, "node_modules/@typescript-eslint/type-utils": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.33.0.tgz", - "integrity": "sha512-lScnHNCBqL1QayuSrWeqAL5GmqNdVUQAAMTaCwdYEdWfIrSrOGzyLGRCHXcCixa5NK6i5l0AfSO2oBSjCjf4XQ==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.35.0.tgz", + "integrity": "sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/typescript-estree": "8.33.0", - "@typescript-eslint/utils": "8.33.0", + "@typescript-eslint/typescript-estree": "8.35.0", + "@typescript-eslint/utils": "8.35.0", "debug": "^4.3.4", "ts-api-utils": "^2.1.0" }, @@ -1362,9 +1378,9 @@ } }, "node_modules/@typescript-eslint/types": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.33.0.tgz", - "integrity": "sha512-DKuXOKpM5IDT1FA2g9x9x1Ug81YuKrzf4mYX8FAVSNu5Wo/LELHWQyM1pQaDkI42bX15PWl0vNPt1uGiIFUOpg==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.35.0.tgz", + "integrity": "sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==", "dev": true, "license": "MIT", "engines": { @@ -1376,16 +1392,16 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.33.0.tgz", - "integrity": "sha512-vegY4FQoB6jL97Tu/lWRsAiUUp8qJTqzAmENH2k59SJhw0Th1oszb9Idq/FyyONLuNqT1OADJPXfyUNOR8SzAQ==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.35.0.tgz", + "integrity": "sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.33.0", - "@typescript-eslint/tsconfig-utils": "8.33.0", - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0", + "@typescript-eslint/project-service": "8.35.0", + "@typescript-eslint/tsconfig-utils": "8.35.0", + "@typescript-eslint/types": "8.35.0", + "@typescript-eslint/visitor-keys": "8.35.0", "debug": "^4.3.4", "fast-glob": "^3.3.2", "is-glob": "^4.0.3", @@ -1405,9 +1421,9 @@ } }, "node_modules/@typescript-eslint/typescript-estree/node_modules/brace-expansion": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -1461,16 +1477,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.33.0.tgz", - "integrity": "sha512-lPFuQaLA9aSNa7D5u2EpRiqdAUhzShwGg/nhpBlc4GR6kcTABttCuyjFs8BcEZ8VWrjCBof/bePhP3Q3fS+Yrw==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.35.0.tgz", + "integrity": "sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.7.0", - "@typescript-eslint/scope-manager": "8.33.0", - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/typescript-estree": "8.33.0" + "@typescript-eslint/scope-manager": "8.35.0", + "@typescript-eslint/types": "8.35.0", + "@typescript-eslint/typescript-estree": "8.35.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -1485,14 +1501,14 @@ } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.33.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.33.0.tgz", - "integrity": "sha512-7RW7CMYoskiz5OOGAWjJFxgb7c5UNjTG292gYhWeOAcFmYCtVCSqjqSBj5zMhxbXo2JOW95YYrUWJfU0zrpaGQ==", + "version": "8.35.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.35.0.tgz", + "integrity": "sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.0", - "eslint-visitor-keys": "^4.2.0" + "@typescript-eslint/types": "8.35.0", + "eslint-visitor-keys": "^4.2.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -1502,10 +1518,38 @@ "url": "https://opencollective.com/typescript-eslint" } }, + "node_modules/@unrs/resolver-binding-android-arm-eabi": { + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-android-arm-eabi/-/resolver-binding-android-arm-eabi-1.9.2.tgz", + "integrity": "sha512-tS+lqTU3N0kkthU+rYp0spAYq15DU8ld9kXkaKg9sbQqJNF+WPMuNHZQGCgdxrUOEO0j22RKMwRVhF1HTl+X8A==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@unrs/resolver-binding-android-arm64": { + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-android-arm64/-/resolver-binding-android-arm64-1.9.2.tgz", + "integrity": "sha512-MffGiZULa/KmkNjHeuuflLVqfhqLv1vZLm8lWIyeADvlElJ/GLSOkoUX+5jf4/EGtfwrNFcEaB8BRas03KT0/Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, "node_modules/@unrs/resolver-binding-darwin-arm64": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-darwin-arm64/-/resolver-binding-darwin-arm64-1.7.8.tgz", - "integrity": "sha512-rsRK8T7yxraNRDmpFLZCWqpea6OlXPNRRCjWMx24O1V86KFol7u2gj9zJCv6zB1oJjtnzWceuqdnCgOipFcJPA==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-darwin-arm64/-/resolver-binding-darwin-arm64-1.9.2.tgz", + "integrity": "sha512-dzJYK5rohS1sYl1DHdJ3mwfwClJj5BClQnQSyAgEfggbUwA9RlROQSSbKBLqrGfsiC/VyrDPtbO8hh56fnkbsQ==", "cpu": [ "arm64" ], @@ -1517,9 +1561,9 @@ ] }, "node_modules/@unrs/resolver-binding-darwin-x64": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-darwin-x64/-/resolver-binding-darwin-x64-1.7.8.tgz", - "integrity": "sha512-16yEMWa+Olqkk8Kl6Bu0ltT5OgEedkSAsxcz1B3yEctrDYp3EMBu/5PPAGhWVGnwhtf3hNe3y15gfYBAjOv5tQ==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-darwin-x64/-/resolver-binding-darwin-x64-1.9.2.tgz", + "integrity": "sha512-gaIMWK+CWtXcg9gUyznkdV54LzQ90S3X3dn8zlh+QR5Xy7Y+Efqw4Rs4im61K1juy4YNb67vmJsCDAGOnIeffQ==", "cpu": [ "x64" ], @@ -1531,9 +1575,9 @@ ] }, "node_modules/@unrs/resolver-binding-freebsd-x64": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-freebsd-x64/-/resolver-binding-freebsd-x64-1.7.8.tgz", - "integrity": "sha512-ST4uqF6FmdZQgv+Q73FU1uHzppeT4mhX3IIEmHlLObrv5Ep50olWRz0iQ4PWovadjHMTAmpuJAGaAuCZYb7UAQ==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-freebsd-x64/-/resolver-binding-freebsd-x64-1.9.2.tgz", + "integrity": "sha512-S7QpkMbVoVJb0xwHFwujnwCAEDe/596xqY603rpi/ioTn9VDgBHnCCxh+UFrr5yxuMH+dliHfjwCZJXOPJGPnw==", "cpu": [ "x64" ], @@ -1545,9 +1589,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-arm-gnueabihf": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm-gnueabihf/-/resolver-binding-linux-arm-gnueabihf-1.7.8.tgz", - "integrity": "sha512-Z/A/4Rm2VWku2g25C3tVb986fY6unx5jaaCFpx1pbAj0OKkyuJ5wcQLHvNbIcJ9qhiYwXfrkB7JNlxrAbg7YFg==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm-gnueabihf/-/resolver-binding-linux-arm-gnueabihf-1.9.2.tgz", + "integrity": "sha512-+XPUMCuCCI80I46nCDFbGum0ZODP5NWGiwS3Pj8fOgsG5/ctz+/zzuBlq/WmGa+EjWZdue6CF0aWWNv84sE1uw==", "cpu": [ "arm" ], @@ -1559,9 +1603,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-arm-musleabihf": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm-musleabihf/-/resolver-binding-linux-arm-musleabihf-1.7.8.tgz", - "integrity": "sha512-HN0p7o38qKmDo3bZUiQa6gP7Qhf0sKgJZtRfSHi6JL2Gi4NaUVF0EO1sQ1RHbeQ4VvfjUGMh3QE5dxEh06BgQQ==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm-musleabihf/-/resolver-binding-linux-arm-musleabihf-1.9.2.tgz", + "integrity": "sha512-sqvUyAd1JUpwbz33Ce2tuTLJKM+ucSsYpPGl2vuFwZnEIg0CmdxiZ01MHQ3j6ExuRqEDUCy8yvkDKvjYFPb8Zg==", "cpu": [ "arm" ], @@ -1573,9 +1617,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-arm64-gnu": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm64-gnu/-/resolver-binding-linux-arm64-gnu-1.7.8.tgz", - "integrity": "sha512-HsoVqDBt9G69AN0KWeDNJW+7i8KFlwxrbbnJffgTGpiZd6Jw+Q95sqkXp8y458KhKduKLmXfVZGnKBTNxAgPjw==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm64-gnu/-/resolver-binding-linux-arm64-gnu-1.9.2.tgz", + "integrity": "sha512-UYA0MA8ajkEDCFRQdng/FVx3F6szBvk3EPnkTTQuuO9lV1kPGuTB+V9TmbDxy5ikaEgyWKxa4CI3ySjklZ9lFA==", "cpu": [ "arm64" ], @@ -1587,9 +1631,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-arm64-musl": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm64-musl/-/resolver-binding-linux-arm64-musl-1.7.8.tgz", - "integrity": "sha512-VfR2yTDUbUvn+e/Aw22CC9fQg9zdShHAfwWctNBdOk7w9CHWl2OtYlcMvjzMAns8QxoHQoqn3/CEnZ4Ts7hfrA==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm64-musl/-/resolver-binding-linux-arm64-musl-1.9.2.tgz", + "integrity": "sha512-P/CO3ODU9YJIHFqAkHbquKtFst0COxdphc8TKGL5yCX75GOiVpGqd1d15ahpqu8xXVsqP4MGFP2C3LRZnnL5MA==", "cpu": [ "arm64" ], @@ -1601,9 +1645,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-ppc64-gnu": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-ppc64-gnu/-/resolver-binding-linux-ppc64-gnu-1.7.8.tgz", - "integrity": "sha512-xUauVQNz4uDgs4UJJiUAwMe3N0PA0wvtImh7V0IFu++UKZJhssXbKHBRR4ecUJpUHCX2bc4Wc8sGsB6P+7BANg==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-ppc64-gnu/-/resolver-binding-linux-ppc64-gnu-1.9.2.tgz", + "integrity": "sha512-uKStFlOELBxBum2s1hODPtgJhY4NxYJE9pAeyBgNEzHgTqTiVBPjfTlPFJkfxyTjQEuxZbbJlJnMCrRgD7ubzw==", "cpu": [ "ppc64" ], @@ -1615,9 +1659,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-riscv64-gnu": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-riscv64-gnu/-/resolver-binding-linux-riscv64-gnu-1.7.8.tgz", - "integrity": "sha512-GqyIB+CuSHGhhc8ph5RrurtNetYJjb6SctSHafqmdGcRuGi6uyTMR8l18hMEhZFsXdFMc/MpInPLvmNV22xn+A==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-riscv64-gnu/-/resolver-binding-linux-riscv64-gnu-1.9.2.tgz", + "integrity": "sha512-LkbNnZlhINfY9gK30AHs26IIVEZ9PEl9qOScYdmY2o81imJYI4IMnJiW0vJVtXaDHvBvxeAgEy5CflwJFIl3tQ==", "cpu": [ "riscv64" ], @@ -1629,9 +1673,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-riscv64-musl": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-riscv64-musl/-/resolver-binding-linux-riscv64-musl-1.7.8.tgz", - "integrity": "sha512-eEU3rWIFRv60xaAbtsgwHNWRZGD7cqkpCvNtio/f1TjEE3HfKLzPNB24fA9X/8ZXQrGldE65b7UKK3PmO4eWIQ==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-riscv64-musl/-/resolver-binding-linux-riscv64-musl-1.9.2.tgz", + "integrity": "sha512-vI+e6FzLyZHSLFNomPi+nT+qUWN4YSj8pFtQZSFTtmgFoxqB6NyjxSjAxEC1m93qn6hUXhIsh8WMp+fGgxCoRg==", "cpu": [ "riscv64" ], @@ -1643,9 +1687,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-s390x-gnu": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-s390x-gnu/-/resolver-binding-linux-s390x-gnu-1.7.8.tgz", - "integrity": "sha512-GVLI0f4I4TlLqEUoOFvTWedLsJEdvsD0+sxhdvQ5s+N+m2DSynTs8h9jxR0qQbKlpHWpc2Ortz3z48NHRT4l+w==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-s390x-gnu/-/resolver-binding-linux-s390x-gnu-1.9.2.tgz", + "integrity": "sha512-sSO4AlAYhSM2RAzBsRpahcJB1msc6uYLAtP6pesPbZtptF8OU/CbCPhSRW6cnYOGuVmEmWVW5xVboAqCnWTeHQ==", "cpu": [ "s390x" ], @@ -1657,9 +1701,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-x64-gnu": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-x64-gnu/-/resolver-binding-linux-x64-gnu-1.7.8.tgz", - "integrity": "sha512-GX1pZ/4ncUreB0Rlp1l7bhKAZ8ZmvDIgXdeb5V2iK0eRRF332+6gRfR/r5LK88xfbtOpsmRHU6mQ4N8ZnwvGEA==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-x64-gnu/-/resolver-binding-linux-x64-gnu-1.9.2.tgz", + "integrity": "sha512-jkSkwch0uPFva20Mdu8orbQjv2A3G88NExTN2oPTI1AJ+7mZfYW3cDCTyoH6OnctBKbBVeJCEqh0U02lTkqD5w==", "cpu": [ "x64" ], @@ -1671,9 +1715,9 @@ ] }, "node_modules/@unrs/resolver-binding-linux-x64-musl": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-x64-musl/-/resolver-binding-linux-x64-musl-1.7.8.tgz", - "integrity": "sha512-n1N84MnsvDupzVuYqJGj+2pb9s8BI1A5RgXHvtVFHedGZVBCFjDpQVRlmsFMt6xZiKwDPaqsM16O/1isCUGt7w==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-x64-musl/-/resolver-binding-linux-x64-musl-1.9.2.tgz", + "integrity": "sha512-Uk64NoiTpQbkpl+bXsbeyOPRpUoMdcUqa+hDC1KhMW7aN1lfW8PBlBH4mJ3n3Y47dYE8qi0XTxy1mBACruYBaw==", "cpu": [ "x64" ], @@ -1685,9 +1729,9 @@ ] }, "node_modules/@unrs/resolver-binding-wasm32-wasi": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-wasm32-wasi/-/resolver-binding-wasm32-wasi-1.7.8.tgz", - "integrity": "sha512-x94WnaU5g+pCPDVedfnXzoG6lCOF2xFGebNwhtbJCWfceE94Zj8aysSxdxotlrZrxnz5D3ijtyFUYtpz04n39Q==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-wasm32-wasi/-/resolver-binding-wasm32-wasi-1.9.2.tgz", + "integrity": "sha512-EpBGwkcjDicjR/ybC0g8wO5adPNdVuMrNalVgYcWi+gYtC1XYNuxe3rufcO7dA76OHGeVabcO6cSkPJKVcbCXQ==", "cpu": [ "wasm32" ], @@ -1695,16 +1739,16 @@ "license": "MIT", "optional": true, "dependencies": { - "@napi-rs/wasm-runtime": "^0.2.10" + "@napi-rs/wasm-runtime": "^0.2.11" }, "engines": { "node": ">=14.0.0" } }, "node_modules/@unrs/resolver-binding-win32-arm64-msvc": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-arm64-msvc/-/resolver-binding-win32-arm64-msvc-1.7.8.tgz", - "integrity": "sha512-vst2u8EJZ5L6jhJ6iLis3w9rg16aYqRxQuBAMYQRVrPMI43693hLP7DuqyOBRKgsQXy9/jgh204k0ViHkqQgdg==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-arm64-msvc/-/resolver-binding-win32-arm64-msvc-1.9.2.tgz", + "integrity": "sha512-EdFbGn7o1SxGmN6aZw9wAkehZJetFPao0VGZ9OMBwKx6TkvDuj6cNeLimF/Psi6ts9lMOe+Dt6z19fZQ9Ye2fw==", "cpu": [ "arm64" ], @@ -1716,9 +1760,9 @@ ] }, "node_modules/@unrs/resolver-binding-win32-ia32-msvc": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-ia32-msvc/-/resolver-binding-win32-ia32-msvc-1.7.8.tgz", - "integrity": "sha512-yb3LZOLMFqnA+/ShlE1E5bpYPGDsA590VHHJPB+efnyowT776GJXBoh82em6O9WmYBUq57YblGTcMYAFBm72HA==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-ia32-msvc/-/resolver-binding-win32-ia32-msvc-1.9.2.tgz", + "integrity": "sha512-JY9hi1p7AG+5c/dMU8o2kWemM8I6VZxfGwn1GCtf3c5i+IKcMo2NQ8OjZ4Z3/itvY/Si3K10jOBQn7qsD/whUA==", "cpu": [ "ia32" ], @@ -1730,9 +1774,9 @@ ] }, "node_modules/@unrs/resolver-binding-win32-x64-msvc": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-x64-msvc/-/resolver-binding-win32-x64-msvc-1.7.8.tgz", - "integrity": "sha512-hHKFx+opG5BA3/owMXon8ypwSotBGTdblG6oda/iOu9+OEYnk0cxD2uIcGyGT8jCK578kV+xMrNxqbn8Zjlpgw==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-x64-msvc/-/resolver-binding-win32-x64-msvc-1.9.2.tgz", + "integrity": "sha512-ryoo+EB19lMxAd80ln9BVf8pdOAxLb97amrQ3SFN9OCRn/5M5wvwDgAe4i8ZjhpbiHoDeP8yavcTEnpKBo7lZg==", "cpu": [ "x64" ], @@ -1796,9 +1840,9 @@ } }, "node_modules/acorn": { - "version": "8.14.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.14.1.tgz", - "integrity": "sha512-OvQ/2pUDKmgfCg++xsTX1wGxfTaszcHVcTctW4UJB4hibJx2HXxxO5UmVgyjMa+ZDsiaf5wWLXYpRWMmBI0QHg==", + "version": "8.15.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", + "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", "dev": true, "license": "MIT", "bin": { @@ -1922,18 +1966,20 @@ } }, "node_modules/array-includes": { - "version": "3.1.8", - "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.8.tgz", - "integrity": "sha512-itaWrbYbqpGXkGhZPGUulwnhVf5Hpy1xiCFsGqyIGglbBxmG5vSjxQen3/WGOjPpNEv1RtBLKxbmVXm8HpJStQ==", + "version": "3.1.9", + "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.9.tgz", + "integrity": "sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==", "dev": true, "license": "MIT", "dependencies": { - "call-bind": "^1.0.7", + "call-bind": "^1.0.8", + "call-bound": "^1.0.4", "define-properties": "^1.2.1", - "es-abstract": "^1.23.2", - "es-object-atoms": "^1.0.0", - "get-intrinsic": "^1.2.4", - "is-string": "^1.0.7" + "es-abstract": "^1.24.0", + "es-object-atoms": "^1.1.1", + "get-intrinsic": "^1.3.0", + "is-string": "^1.1.1", + "math-intrinsics": "^1.1.0" }, "engines": { "node": ">= 0.4" @@ -2134,9 +2180,9 @@ } }, "node_modules/brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "version": "1.1.12", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.12.tgz", + "integrity": "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==", "dev": true, "license": "MIT", "dependencies": { @@ -2237,9 +2283,9 @@ } }, "node_modules/caniuse-lite": { - "version": "1.0.30001720", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001720.tgz", - "integrity": "sha512-Ec/2yV2nNPwb4DnTANEV99ZWwm3ZWfdlfkQbWSDDt+PsXEVYwlhPH8tdMaPunYTKKmz7AnHi2oNEi1GcmKCD8g==", + "version": "1.0.30001726", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001726.tgz", + "integrity": "sha512-VQAUIUzBiZ/UnlM28fSp2CRF3ivUn1BWEvxMcVTNwpw91Py1pGbPIyIKtd+tzct9C3ouceCVdGAXxZOpZAsgdw==", "funding": [ { "type": "opencollective", @@ -2803,19 +2849,19 @@ } }, "node_modules/eslint": { - "version": "9.27.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.27.0.tgz", - "integrity": "sha512-ixRawFQuMB9DZ7fjU3iGGganFDp3+45bPOdaRurcFHSXO1e/sYwUX/FtQZpLZJR6SjMoJH8hR2pPEAfDyCoU2Q==", + "version": "9.30.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.30.0.tgz", + "integrity": "sha512-iN/SiPxmQu6EVkf+m1qpBxzUhE12YqFLOSySuOyVLJLEF9nzTf+h/1AJYc1JWzCnktggeNrjvQGLngDzXirU6g==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.2.0", "@eslint-community/regexpp": "^4.12.1", - "@eslint/config-array": "^0.20.0", - "@eslint/config-helpers": "^0.2.1", + "@eslint/config-array": "^0.21.0", + "@eslint/config-helpers": "^0.3.0", "@eslint/core": "^0.14.0", "@eslint/eslintrc": "^3.3.1", - "@eslint/js": "9.27.0", + "@eslint/js": "9.30.0", "@eslint/plugin-kit": "^0.3.1", "@humanfs/node": "^0.16.6", "@humanwhocodes/module-importer": "^1.0.1", @@ -2827,9 +2873,9 @@ "cross-spawn": "^7.0.6", "debug": "^4.3.2", "escape-string-regexp": "^4.0.0", - "eslint-scope": "^8.3.0", - "eslint-visitor-keys": "^4.2.0", - "espree": "^10.3.0", + "eslint-scope": "^8.4.0", + "eslint-visitor-keys": "^4.2.1", + "espree": "^10.4.0", "esquery": "^1.5.0", "esutils": "^2.0.2", "fast-deep-equal": "^3.1.3", @@ -2949,9 +2995,9 @@ } }, "node_modules/eslint-module-utils": { - "version": "2.12.0", - "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.12.0.tgz", - "integrity": "sha512-wALZ0HFoytlyh/1+4wuZ9FJCD/leWHQzzrxJ8+rebyReSLk7LApMyd3WJaLVoN+D5+WIdJyDK1c6JnE65V4Zyg==", + "version": "2.12.1", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.12.1.tgz", + "integrity": "sha512-L8jSWTze7K2mTg0vos/RuLRS5soomksDPoJLXIslC7c8Wmut3bx7CPpJijDcBZtxQ5lrbUdM+s0OlNbz0DCDNw==", "dev": true, "license": "MIT", "dependencies": { @@ -2977,30 +3023,30 @@ } }, "node_modules/eslint-plugin-import": { - "version": "2.31.0", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.31.0.tgz", - "integrity": "sha512-ixmkI62Rbc2/w8Vfxyh1jQRTdRTF52VxwRVHl/ykPAmqG+Nb7/kNn+byLP0LxPgI7zWA16Jt82SybJInmMia3A==", + "version": "2.32.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.32.0.tgz", + "integrity": "sha512-whOE1HFo/qJDyX4SnXzP4N6zOWn79WhnCUY/iDR0mPfQZO8wcYE4JClzI2oZrhBnnMUCBCHZhO6VQyoBU95mZA==", "dev": true, "license": "MIT", "dependencies": { "@rtsao/scc": "^1.1.0", - "array-includes": "^3.1.8", - "array.prototype.findlastindex": "^1.2.5", - "array.prototype.flat": "^1.3.2", - "array.prototype.flatmap": "^1.3.2", + "array-includes": "^3.1.9", + "array.prototype.findlastindex": "^1.2.6", + "array.prototype.flat": "^1.3.3", + "array.prototype.flatmap": "^1.3.3", "debug": "^3.2.7", "doctrine": "^2.1.0", "eslint-import-resolver-node": "^0.3.9", - "eslint-module-utils": "^2.12.0", + "eslint-module-utils": "^2.12.1", "hasown": "^2.0.2", - "is-core-module": "^2.15.1", + "is-core-module": "^2.16.1", "is-glob": "^4.0.3", "minimatch": "^3.1.2", "object.fromentries": "^2.0.8", "object.groupby": "^1.0.3", - "object.values": "^1.2.0", + "object.values": "^1.2.1", "semver": "^6.3.1", - "string.prototype.trimend": "^1.0.8", + "string.prototype.trimend": "^1.0.9", "tsconfig-paths": "^3.15.0" }, "engines": { @@ -3135,9 +3181,9 @@ } }, "node_modules/eslint-scope": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-8.3.0.tgz", - "integrity": "sha512-pUNxi75F8MJ/GdeKtVLSbYg4ZI34J6C0C7sbL4YOp2exGwen7ZsuBqKzUhXd0qMQ362yET3z+uPwKeg/0C2XCQ==", + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-8.4.0.tgz", + "integrity": "sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==", "dev": true, "license": "BSD-2-Clause", "dependencies": { @@ -3152,9 +3198,9 @@ } }, "node_modules/eslint-visitor-keys": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.0.tgz", - "integrity": "sha512-UyLnSehNt62FFhSwjZlHmeokpRK59rcz29j+F1/aDgbkbRTk7wIc9XzdoasMUbRNKDM0qQt/+BJ4BrpFeABemw==", + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", + "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", "dev": true, "license": "Apache-2.0", "engines": { @@ -3165,15 +3211,15 @@ } }, "node_modules/espree": { - "version": "10.3.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-10.3.0.tgz", - "integrity": "sha512-0QYC8b24HWY8zjRnDTL6RiHfDbAWn63qb4LMj1Z4b076A4une81+z03Kg7l7mn/48PUTqoLptSXez8oknU8Clg==", + "version": "10.4.0", + "resolved": "https://registry.npmjs.org/espree/-/espree-10.4.0.tgz", + "integrity": "sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==", "dev": true, "license": "BSD-2-Clause", "dependencies": { - "acorn": "^8.14.0", + "acorn": "^8.15.0", "acorn-jsx": "^5.3.2", - "eslint-visitor-keys": "^4.2.0" + "eslint-visitor-keys": "^4.2.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3384,13 +3430,13 @@ } }, "node_modules/framer-motion": { - "version": "12.15.0", - "resolved": "https://registry.npmjs.org/framer-motion/-/framer-motion-12.15.0.tgz", - "integrity": "sha512-XKg/LnKExdLGugZrDILV7jZjI599785lDIJZLxMiiIFidCsy0a4R2ZEf+Izm67zyOuJgQYTHOmodi7igQsw3vg==", + "version": "12.19.2", + "resolved": "https://registry.npmjs.org/framer-motion/-/framer-motion-12.19.2.tgz", + "integrity": "sha512-0cWMLkYr+i0emeXC4hkLF+5aYpzo32nRdQ0D/5DI460B3O7biQ3l2BpDzIGsAHYuZ0fpBP0DC8XBkVf6RPAlZw==", "license": "MIT", "dependencies": { - "motion-dom": "^12.15.0", - "motion-utils": "^12.12.1", + "motion-dom": "^12.19.0", + "motion-utils": "^12.19.0", "tslib": "^2.4.0" }, "peerDependencies": { @@ -3567,9 +3613,9 @@ } }, "node_modules/glob/node_modules/brace-expansion": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "license": "MIT", "dependencies": { "balanced-match": "^1.0.0" @@ -4293,15 +4339,12 @@ } }, "node_modules/jiti": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/jiti/-/jiti-2.4.2.tgz", - "integrity": "sha512-rg9zJN+G4n2nfJl5MW3BMygZX56zKPNVEYYqq7adpmMh4Jn2QNEwhvQlFy6jPVdcod7txZtKHWnyZiA3a0zP7A==", - "dev": true, + "version": "1.21.7", + "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.7.tgz", + "integrity": "sha512-/imKNG4EbWNrVjoNC/1H5/9GFy+tqjGBHCaSsN+P2RnPqjsLmv6UD3Ej+Kj8nBWaRAwyk7kK5ZUc+OEatnTR3A==", "license": "MIT", - "optional": true, - "peer": true, "bin": { - "jiti": "lib/jiti-cli.mjs" + "jiti": "bin/jiti.js" } }, "node_modules/js-tokens": { @@ -4477,9 +4520,9 @@ "license": "ISC" }, "node_modules/lucide-react": { - "version": "0.517.0", - "resolved": "https://registry.npmjs.org/lucide-react/-/lucide-react-0.517.0.tgz", - "integrity": "sha512-TQCwwbwIuVG6SSutUC2Ol6PRXcuZndqoVAnDa7S7xb/RWPaiKTvLwX7byUKeh0pUgvtFh0NZZwFIDuMSeB7Iwg==", + "version": "0.488.0", + "resolved": "https://registry.npmjs.org/lucide-react/-/lucide-react-0.488.0.tgz", + "integrity": "sha512-ronlL0MyKut4CEzBY/ai2ZpKPxyWO4jUqdAkm2GNK5Zn3Rj+swDz+3lvyAUXN0PNqPKIX6XM9Xadwz/skLs/pQ==", "license": "ISC", "peerDependencies": { "react": "^16.5.1 || ^17.0.0 || ^18.0.0 || ^19.0.0" @@ -4550,18 +4593,18 @@ } }, "node_modules/motion-dom": { - "version": "12.15.0", - "resolved": "https://registry.npmjs.org/motion-dom/-/motion-dom-12.15.0.tgz", - "integrity": "sha512-D2ldJgor+2vdcrDtKJw48k3OddXiZN1dDLLWrS8kiHzQdYVruh0IoTwbJBslrnTXIPgFED7PBN2Zbwl7rNqnhA==", + "version": "12.19.0", + "resolved": "https://registry.npmjs.org/motion-dom/-/motion-dom-12.19.0.tgz", + "integrity": "sha512-m96uqq8VbwxFLU0mtmlsIVe8NGGSdpBvBSHbnnOJQxniPaabvVdGgxSamhuDwBsRhwX7xPxdICgVJlOpzn/5bw==", "license": "MIT", "dependencies": { - "motion-utils": "^12.12.1" + "motion-utils": "^12.19.0" } }, "node_modules/motion-utils": { - "version": "12.12.1", - "resolved": "https://registry.npmjs.org/motion-utils/-/motion-utils-12.12.1.tgz", - "integrity": "sha512-f9qiqUHm7hWSLlNW8gS9pisnsN7CRFRD58vNjptKdsqFLpkVnX00TNeD6Q0d27V9KzT7ySFyK1TZ/DShfVOv6w==", + "version": "12.19.0", + "resolved": "https://registry.npmjs.org/motion-utils/-/motion-utils-12.19.0.tgz", + "integrity": "sha512-BuFTHINYmV07pdWs6lj6aI63vr2N4dg0vR+td0rtrdpWOhBzIkEklZyLcvKBoEtwSqx8Jg06vUB5RS0xDiUybw==", "license": "MIT" }, "node_modules/ms": { @@ -4601,9 +4644,9 @@ } }, "node_modules/napi-postinstall": { - "version": "0.2.4", - "resolved": "https://registry.npmjs.org/napi-postinstall/-/napi-postinstall-0.2.4.tgz", - "integrity": "sha512-ZEzHJwBhZ8qQSbknHqYcdtQVr8zUgGyM/q6h6qAyhtyVMNrSgDhrC4disf03dYW0e+czXyLnZINnCTEkWy0eJg==", + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/napi-postinstall/-/napi-postinstall-0.2.5.tgz", + "integrity": "sha512-kmsgUvCRIJohHjbZ3V8avP0I1Pekw329MVAMDzVxsrkjgdnqiwvMX5XwR+hWV66vsAtZ+iM+fVnq8RTQawUmCQ==", "dev": true, "license": "MIT", "bin": { @@ -5033,9 +5076,9 @@ } }, "node_modules/postcss": { - "version": "8.5.4", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.4.tgz", - "integrity": "sha512-QSa9EBe+uwlGTFmHsPKokv3B/oEMQZxfqW0QqNCyhpa6mB1afzulwn8hihglqAb2pOw+BJgNlmXQ8la2VeHB7w==", + "version": "8.5.6", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.6.tgz", + "integrity": "sha512-3Ybi1tAuwAP9s0r1UQ2J4n5Y0G05bJkpUIO0/bI9MhwmD70S5aTWbXGBwxHrelT+XM1k6dM0pk+SwNkpTRN7Pg==", "funding": [ { "type": "opencollective", @@ -6010,9 +6053,9 @@ } }, "node_modules/tailwind-merge": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/tailwind-merge/-/tailwind-merge-3.3.0.tgz", - "integrity": "sha512-fyW/pEfcQSiigd5SNn0nApUOxx0zB/dm6UDU/rEwc2c3sX2smWUNbapHv+QRqLGVp9GWX3THIa7MUGPo+YkDzQ==", + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/tailwind-merge/-/tailwind-merge-3.3.1.tgz", + "integrity": "sha512-gBXpgUm/3rp1lMZZrM/w7D8GKqshif0zAymAhbCyIt8KMe+0v9DQ7cdYLR4FHH/cKpdTXb+A/tKKU3eolfsI+g==", "license": "MIT", "funding": { "type": "github", @@ -6093,15 +6136,6 @@ "node": ">= 6" } }, - "node_modules/tailwindcss/node_modules/jiti": { - "version": "1.21.7", - "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.7.tgz", - "integrity": "sha512-/imKNG4EbWNrVjoNC/1H5/9GFy+tqjGBHCaSsN+P2RnPqjsLmv6UD3Ej+Kj8nBWaRAwyk7kK5ZUc+OEatnTR3A==", - "license": "MIT", - "bin": { - "jiti": "bin/jiti.js" - } - }, "node_modules/tailwindcss/node_modules/postcss-load-config": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/postcss-load-config/-/postcss-load-config-4.0.2.tgz", @@ -6176,9 +6210,9 @@ } }, "node_modules/tinyglobby/node_modules/fdir": { - "version": "6.4.5", - "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.4.5.tgz", - "integrity": "sha512-4BG7puHpVsIYxZUbiUE3RqGloLaSSwzYie5jvasC4LWuBWzZawynvYouhjbQKw2JuIGYdm0DzIxl8iVidKlUEw==", + "version": "6.4.6", + "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.4.6.tgz", + "integrity": "sha512-hiFoqpyZcfNm1yc4u8oWCf9A2c4D3QjCrks3zmoVKVxpQRzmPNar1hUJcBG2RQHvEVGDN+Jm81ZheVLAQMK6+w==", "dev": true, "license": "MIT", "peerDependencies": { @@ -6398,36 +6432,38 @@ "license": "MIT" }, "node_modules/unrs-resolver": { - "version": "1.7.8", - "resolved": "https://registry.npmjs.org/unrs-resolver/-/unrs-resolver-1.7.8.tgz", - "integrity": "sha512-2zsXwyOXmCX9nGz4vhtZRYhe30V78heAv+KDc21A/KMdovGHbZcixeD5JHEF0DrFXzdytwuzYclcPbvp8A3Jlw==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/unrs-resolver/-/unrs-resolver-1.9.2.tgz", + "integrity": "sha512-VUyWiTNQD7itdiMuJy+EuLEErLj3uwX/EpHQF8EOf33Dq3Ju6VW1GXm+swk6+1h7a49uv9fKZ+dft9jU7esdLA==", "dev": true, "hasInstallScript": true, "license": "MIT", "dependencies": { - "napi-postinstall": "^0.2.2" + "napi-postinstall": "^0.2.4" }, "funding": { "url": "https://opencollective.com/unrs-resolver" }, "optionalDependencies": { - "@unrs/resolver-binding-darwin-arm64": "1.7.8", - "@unrs/resolver-binding-darwin-x64": "1.7.8", - "@unrs/resolver-binding-freebsd-x64": "1.7.8", - "@unrs/resolver-binding-linux-arm-gnueabihf": "1.7.8", - "@unrs/resolver-binding-linux-arm-musleabihf": "1.7.8", - "@unrs/resolver-binding-linux-arm64-gnu": "1.7.8", - "@unrs/resolver-binding-linux-arm64-musl": "1.7.8", - "@unrs/resolver-binding-linux-ppc64-gnu": "1.7.8", - "@unrs/resolver-binding-linux-riscv64-gnu": "1.7.8", - "@unrs/resolver-binding-linux-riscv64-musl": "1.7.8", - "@unrs/resolver-binding-linux-s390x-gnu": "1.7.8", - "@unrs/resolver-binding-linux-x64-gnu": "1.7.8", - "@unrs/resolver-binding-linux-x64-musl": "1.7.8", - "@unrs/resolver-binding-wasm32-wasi": "1.7.8", - "@unrs/resolver-binding-win32-arm64-msvc": "1.7.8", - "@unrs/resolver-binding-win32-ia32-msvc": "1.7.8", - "@unrs/resolver-binding-win32-x64-msvc": "1.7.8" + "@unrs/resolver-binding-android-arm-eabi": "1.9.2", + "@unrs/resolver-binding-android-arm64": "1.9.2", + "@unrs/resolver-binding-darwin-arm64": "1.9.2", + "@unrs/resolver-binding-darwin-x64": "1.9.2", + "@unrs/resolver-binding-freebsd-x64": "1.9.2", + "@unrs/resolver-binding-linux-arm-gnueabihf": "1.9.2", + "@unrs/resolver-binding-linux-arm-musleabihf": "1.9.2", + "@unrs/resolver-binding-linux-arm64-gnu": "1.9.2", + "@unrs/resolver-binding-linux-arm64-musl": "1.9.2", + "@unrs/resolver-binding-linux-ppc64-gnu": "1.9.2", + "@unrs/resolver-binding-linux-riscv64-gnu": "1.9.2", + "@unrs/resolver-binding-linux-riscv64-musl": "1.9.2", + "@unrs/resolver-binding-linux-s390x-gnu": "1.9.2", + "@unrs/resolver-binding-linux-x64-gnu": "1.9.2", + "@unrs/resolver-binding-linux-x64-musl": "1.9.2", + "@unrs/resolver-binding-wasm32-wasi": "1.9.2", + "@unrs/resolver-binding-win32-arm64-msvc": "1.9.2", + "@unrs/resolver-binding-win32-ia32-msvc": "1.9.2", + "@unrs/resolver-binding-win32-x64-msvc": "1.9.2" } }, "node_modules/uri-js": { diff --git a/hypermode-chat/package.json b/hypermode-chat/package.json index a2fedc1..8ba950d 100644 --- a/hypermode-chat/package.json +++ b/hypermode-chat/package.json @@ -19,10 +19,10 @@ "react-dom": "^19.1.0", "tailwind-merge": "^3.3.0", "tailwindcss-animate": "^1.0.7", - "@aichatkit/types": "0.0.0-alpha.4", - "@aichatkit/ui": "0.0.0-alpha.4", - "@aichatkit/apollo-adapter": "0.0.0-alpha.4", - "@aichatkit/localstorage-adapter": "0.0.0-alpha.4", + "@aichatkit/types": "0.0.0-alpha.6", + "@aichatkit/ui": "0.0.0-alpha.6", + "@aichatkit/apollo-adapter": "0.0.0-alpha.6", + "@aichatkit/localstorage-adapter": "0.0.0-alpha.6", "lucide-react": "^0.488.0" }, "devDependencies": { diff --git a/hypermode-chat/src/app/chat-agent-adapter.tsx b/hypermode-chat/src/app/chat-agent-adapter.tsx deleted file mode 100644 index 7bfedf1..0000000 --- a/hypermode-chat/src/app/chat-agent-adapter.tsx +++ /dev/null @@ -1,206 +0,0 @@ -"use client" - -import { NetworkAdapter } from "@aichatkit/network-adapter" -import { Message } from "@aichatkit/types" -import { ApolloClient, gql, NormalizedCacheObject } from "@apollo/client" - -export interface CustomAgentAdapterOptions { - apolloClient: ApolloClient - timeout?: number - debug?: boolean -} - -const CREATE_CONVERSATION_MUTATION = gql` - mutation CreateConversation { - createConversation - } -` - -const CONTINUE_CHAT_QUERY = gql` - query ContinueChat($id: String!, $query: String!) { - continueChat(id: $id, query: $query) - } -` - -const CHAT_HISTORY_QUERY = gql` - query ChatHistory($id: String!) { - chatHistory(id: $id) - } -` - -const DELETE_AGENT_MUTATION = gql` - mutation DeleteAgent($id: String!) { - deleteAgent(id: $id) - } -` - -const CLEAR_HISTORY_MUTATION = gql` - mutation ClearHistory($id: String!) { - clearHistory(id: $id) - } -` - -export class CustomAgentAdapter extends NetworkAdapter { - private client: ApolloClient - private debug: boolean - - constructor(options: CustomAgentAdapterOptions) { - super() - this.client = options.apolloClient - this.debug = options.debug || false - } - - private log(...args: any[]): void { - if (this.debug) { - console.log("[CustomAgentAdapter]", ...args) - } - } - - async startChatAgent(): Promise { - this.log("Starting new chat agent...") - - try { - const { data } = await this.client.mutate({ - mutation: CREATE_CONVERSATION_MUTATION, - errorPolicy: "all", - fetchPolicy: "no-cache", - }) - - const agentId = data?.createConversation - - if (!agentId) { - throw new Error("No agent ID returned from createConversation") - } - - this.log("Started chat agent with ID:", agentId) - return agentId - } catch (error) { - this.log("Error starting chat agent:", error) - throw new Error( - `Failed to start chat agent: ${error instanceof Error ? error.message : "Unknown error"}`, - ) - } - } - - async sendMessage(agentId: string, message: string): Promise { - this.log("Sending message to agent:", agentId, "Message:", message) - - try { - const { data } = await this.client.query({ - query: CONTINUE_CHAT_QUERY, - variables: { - id: agentId, - query: message, - }, - errorPolicy: "all", - fetchPolicy: "no-cache", - }) - - const response = data?.continueChat - - if (!response) { - throw new Error("No response returned from continueChat") - } - - this.log("Received response:", response) - - const assistantMessage: Message = { - id: `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`, - content: response, - role: "assistant", - timestamp: new Date().toISOString(), - } - - return assistantMessage - } catch (error) { - this.log("Error sending message:", error) - throw new Error( - `Failed to send message: ${error instanceof Error ? error.message : "Unknown error"}`, - ) - } - } - - async getConversationHistory(agentId: string): Promise { - this.log("Getting conversation history for agent:", agentId) - - try { - const { data } = await this.client.query({ - query: CHAT_HISTORY_QUERY, - variables: { id: agentId }, - errorPolicy: "all", - fetchPolicy: "no-cache", - }) - - const historyJson = data?.chatHistory - - if (!historyJson) { - this.log("No history returned, returning empty array") - return [] - } - - const chatMessages = JSON.parse(historyJson) - - const messages: Message[] = chatMessages.map((msg: any, index: number) => ({ - id: `history-${index}-${Date.now()}`, - content: msg.content || msg.Content || "", - role: (msg.role || msg.Role || "assistant").toLowerCase() as "user" | "assistant", - timestamp: new Date().toISOString(), - })) - - this.log("Parsed conversation history:", messages) - return messages - } catch (error) { - this.log("Error getting conversation history:", error) - return [] - } - } - - async clearConversationHistory(agentId: string): Promise { - this.log("Clearing conversation history for agent:", agentId) - - try { - await this.client.mutate({ - mutation: CLEAR_HISTORY_MUTATION, - variables: { id: agentId }, - errorPolicy: "all", - fetchPolicy: "no-cache", - }) - } catch (error) { - this.log("Error clearing conversation history:", error) - throw new Error( - `Failed to clear conversation history: ${error instanceof Error ? error.message : "Unknown error"}`, - ) - } - } - - async stopChatAgent(agentId: string): Promise { - this.log("Stopping chat agent:", agentId) - - try { - await this.client.mutate({ - mutation: DELETE_AGENT_MUTATION, - variables: { id: agentId }, - errorPolicy: "all", - fetchPolicy: "no-cache", - }) - } catch (error) { - this.log("Error stopping chat agent:", error) - throw new Error( - `Failed to stop chat agent: ${error instanceof Error ? error.message : "Unknown error"}`, - ) - } - } - - getClient(): ApolloClient { - return this.client - } - - async pingAgent(agentId: string): Promise { - try { - await this.sendMessage(agentId, "ping") - return true - } catch { - return false - } - } -} diff --git a/hypermode-chat/src/app/page.tsx b/hypermode-chat/src/app/page.tsx index 8a3aeb3..f56f304 100644 --- a/hypermode-chat/src/app/page.tsx +++ b/hypermode-chat/src/app/page.tsx @@ -2,38 +2,15 @@ import React, { useEffect, useState } from "react" import { ChatInterface, Avatar } from "@aichatkit/ui" -import { Conversation } from "@aichatkit/types" +import { CardAction } from "@aichatkit/types" import { PlusIcon, SendIcon, XIcon } from "lucide-react" import { useApolloClient } from "@apollo/client" import { LocalStorageAdapter } from "@aichatkit/localstorage-adapter" -import { CustomAgentAdapter } from "./chat-agent-adapter" - -const formatTimestamp = () => { - return new Date().toLocaleTimeString([], { - hour: "2-digit", - minute: "2-digit", - }) -} - -const initialConversations: Conversation[] = [ - { - id: "1", - title: "New Agent Chat", - messages: [ - { - id: "1", - content: - "Hello! I'm your AI assistant powered by a Hypermode agent backend. I can remember our conversation and help you with various tasks. How can I assist you today?", - role: "assistant" as const, - timestamp: formatTimestamp(), - }, - ], - }, -] +import { ApolloAdapter } from "@aichatkit/apollo-adapter" export default function HypermodeChatDemo() { const apolloClient = useApolloClient() - const [networkAdapter, setNetworkAdapter] = useState(null) + const [networkAdapter, setNetworkAdapter] = useState(null) const [storageAdapter, setStorageAdapter] = useState(null) const [ready, setReady] = useState(false) const [error, setError] = useState(null) @@ -41,22 +18,23 @@ export default function HypermodeChatDemo() { useEffect(() => { const initAdapters = async () => { try { - const agentAdapter = new CustomAgentAdapter({ - // @ts-ignore - apolloClient: apolloClient, - debug: process.env.NODE_ENV === "development", + // Use the standard ApolloAdapter from ChatKit + const apolloAdapter = new ApolloAdapter({ + // @ts-expect-error - need to make apollo a peer dependency + apolloClient, }) const localStorageAdapter = new LocalStorageAdapter({}) await localStorageAdapter.initialize() + // Set up network callbacks for backend synchronization localStorageAdapter.setNetworkCallbacks({ - getConversationHistory: (agentId: string) => agentAdapter.getConversationHistory(agentId), + getConversationItems: (agentId: string) => apolloAdapter.getConversationItems(agentId), clearConversationHistory: (agentId: string) => - agentAdapter.clearConversationHistory(agentId), + apolloAdapter.clearConversationHistory(agentId), }) - setNetworkAdapter(agentAdapter) + setNetworkAdapter(apolloAdapter) setStorageAdapter(localStorageAdapter) setReady(true) setError(null) @@ -69,6 +47,31 @@ export default function HypermodeChatDemo() { initAdapters() }, [apolloClient]) + const handleCardAction = (action: CardAction) => { + console.log("Card action triggered:", action) + + switch (action.action) { + case "show_facts": + // Handle showing all facts + alert(`Showing all facts: ${JSON.stringify(action.data, null, 2)}`) + break + case "search_entity": + // Handle entity search + alert(`Searching for entity: ${action.data?.entity}`) + break + case "view_details": + // Handle viewing fact details + alert(`Viewing details for: ${action.data?.fact}`) + break + default: + if (action.type === "link") { + window.open(action.action, "_blank") + } else { + console.log("Unhandled card action:", action) + } + } + } + if (error) { return (
@@ -103,25 +106,31 @@ export default function HypermodeChatDemo() { return (
} newConversationIcon={} deleteConversationIcon={} userAvatar={} assistantAvatar={} + inputPlaceholder="Ask me to remember facts or search for information..." chatAreaClassName="hypermode-scrollbar" - // headerContent={ - // <> - // } + onCardAction={handleCardAction} + headerContent={ +
+
+ + Knowledge Agent +
+
+ } sidebarHeaderContent={
-
Agent Chat
+
Knowledge Chat
Powered by Hypermode Agents