237 lines
5.7 KiB
Go
237 lines
5.7 KiB
Go
package commands
|
|
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
"strings"
|
|
|
|
"github.com/BlackRoad-OS/blackroad-cli/internal/api"
|
|
"github.com/olekukonko/tablewriter"
|
|
"github.com/spf13/cobra"
|
|
)
|
|
|
|
var memoryCmd = &cobra.Command{
|
|
Use: "memory",
|
|
Short: "Manage memory",
|
|
Long: "Query, log, and manage BlackRoad memory entries.",
|
|
}
|
|
|
|
var memoryQueryCmd = &cobra.Command{
|
|
Use: "query",
|
|
Short: "Query memory entries",
|
|
Run: func(cmd *cobra.Command, args []string) {
|
|
client, err := api.NewClient()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
search, _ := cmd.Flags().GetString("search")
|
|
action, _ := cmd.Flags().GetString("action")
|
|
tagsStr, _ := cmd.Flags().GetString("tags")
|
|
limit, _ := cmd.Flags().GetInt("limit")
|
|
|
|
var tags []string
|
|
if tagsStr != "" {
|
|
tags = strings.Split(tagsStr, ",")
|
|
}
|
|
|
|
entries, err := client.QueryMemory(search, action, tags, limit)
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
if len(entries) == 0 {
|
|
fmt.Println("No entries found")
|
|
return
|
|
}
|
|
|
|
table := tablewriter.NewWriter(os.Stdout)
|
|
table.SetHeader([]string{"Hash", "Action", "Entity", "Details", "Time"})
|
|
table.SetBorder(false)
|
|
table.SetHeaderColor(
|
|
tablewriter.Colors{tablewriter.FgCyanColor},
|
|
tablewriter.Colors{tablewriter.FgCyanColor},
|
|
tablewriter.Colors{tablewriter.FgCyanColor},
|
|
tablewriter.Colors{tablewriter.FgCyanColor},
|
|
tablewriter.Colors{tablewriter.FgCyanColor},
|
|
)
|
|
|
|
for _, e := range entries {
|
|
details := e.Details
|
|
if len(details) > 30 {
|
|
details = details[:27] + "..."
|
|
}
|
|
table.Append([]string{
|
|
e.Hash[:12],
|
|
e.Action,
|
|
e.Entity,
|
|
details,
|
|
e.Timestamp.Format("01-02 15:04"),
|
|
})
|
|
}
|
|
table.Render()
|
|
fmt.Printf("\n%s %d entries\n", cyan("Found:"), len(entries))
|
|
},
|
|
}
|
|
|
|
var memoryGetCmd = &cobra.Command{
|
|
Use: "get <hash>",
|
|
Short: "Get memory entry by hash",
|
|
Args: cobra.ExactArgs(1),
|
|
Run: func(cmd *cobra.Command, args []string) {
|
|
client, err := api.NewClient()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
entry, err := client.GetMemoryEntry(args[0])
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
fmt.Printf("%s %s\n", bold("Hash:"), entry.Hash)
|
|
fmt.Printf("%s %s\n", bold("Action:"), entry.Action)
|
|
fmt.Printf("%s %s\n", bold("Entity:"), entry.Entity)
|
|
if entry.Details != "" {
|
|
fmt.Printf("%s %s\n", bold("Details:"), entry.Details)
|
|
}
|
|
if len(entry.Tags) > 0 {
|
|
fmt.Printf("%s %s\n", bold("Tags:"), strings.Join(entry.Tags, ", "))
|
|
}
|
|
fmt.Printf("%s %s\n", bold("Timestamp:"), entry.Timestamp.Format("2006-01-02 15:04:05"))
|
|
},
|
|
}
|
|
|
|
var memoryLogCmd = &cobra.Command{
|
|
Use: "log <action> <entity> [details]",
|
|
Short: "Log a memory entry",
|
|
Long: `Log a memory entry to the BlackRoad memory system.
|
|
|
|
Actions: deployed, created, updated, fixed, configured, milestone, til, announce, progress
|
|
|
|
Examples:
|
|
blackroad memory log deployed auth-service "v2.0.0 to production"
|
|
blackroad memory log milestone api "1 million requests served"
|
|
blackroad memory log til security "Always validate JWT signatures"`,
|
|
Args: cobra.MinimumNArgs(2),
|
|
Run: func(cmd *cobra.Command, args []string) {
|
|
client, err := api.NewClient()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
action := args[0]
|
|
entity := args[1]
|
|
var details string
|
|
if len(args) > 2 {
|
|
details = strings.Join(args[2:], " ")
|
|
}
|
|
|
|
tagsStr, _ := cmd.Flags().GetString("tags")
|
|
var tags []string
|
|
if tagsStr != "" {
|
|
tags = strings.Split(tagsStr, ",")
|
|
}
|
|
|
|
entry, err := client.LogMemory(action, entity, details, tags)
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
printSuccess(fmt.Sprintf("Logged: %s (hash: %s)", entry.Entity, entry.Hash[:12]))
|
|
},
|
|
}
|
|
|
|
var memoryTilCmd = &cobra.Command{
|
|
Use: "til <category> <learning>",
|
|
Short: "Share a Today I Learned entry",
|
|
Args: cobra.MinimumNArgs(2),
|
|
Run: func(cmd *cobra.Command, args []string) {
|
|
client, err := api.NewClient()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
category := args[0]
|
|
learning := strings.Join(args[1:], " ")
|
|
|
|
entry, err := client.TIL(category, learning)
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
printSuccess(fmt.Sprintf("TIL shared: %s (hash: %s)", category, entry.Hash[:12]))
|
|
},
|
|
}
|
|
|
|
var memoryStatsCmd = &cobra.Command{
|
|
Use: "stats",
|
|
Short: "Show memory statistics",
|
|
Run: func(cmd *cobra.Command, args []string) {
|
|
client, err := api.NewClient()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
stats, err := client.MemoryStats()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
fmt.Printf("%s\n", bold("Memory Statistics"))
|
|
fmt.Printf("%s %d entries\n", cyan("Total:"), stats.Total)
|
|
},
|
|
}
|
|
|
|
var memoryVerifyCmd = &cobra.Command{
|
|
Use: "verify",
|
|
Short: "Verify hash chain integrity",
|
|
Run: func(cmd *cobra.Command, args []string) {
|
|
client, err := api.NewClient()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
valid, checked, err := client.VerifyChain()
|
|
if err != nil {
|
|
printError(err.Error())
|
|
return
|
|
}
|
|
|
|
if valid {
|
|
printSuccess(fmt.Sprintf("Chain valid! Checked %d entries", checked))
|
|
} else {
|
|
printError(fmt.Sprintf("Chain INVALID! Checked %d entries", checked))
|
|
}
|
|
},
|
|
}
|
|
|
|
func init() {
|
|
memoryCmd.AddCommand(memoryQueryCmd)
|
|
memoryCmd.AddCommand(memoryGetCmd)
|
|
memoryCmd.AddCommand(memoryLogCmd)
|
|
memoryCmd.AddCommand(memoryTilCmd)
|
|
memoryCmd.AddCommand(memoryStatsCmd)
|
|
memoryCmd.AddCommand(memoryVerifyCmd)
|
|
|
|
// Query flags
|
|
memoryQueryCmd.Flags().StringP("search", "s", "", "Search text")
|
|
memoryQueryCmd.Flags().StringP("action", "a", "", "Filter by action")
|
|
memoryQueryCmd.Flags().StringP("tags", "t", "", "Filter by tags (comma-separated)")
|
|
memoryQueryCmd.Flags().IntP("limit", "l", 50, "Maximum results")
|
|
|
|
// Log flags
|
|
memoryLogCmd.Flags().StringP("tags", "t", "", "Tags (comma-separated)")
|
|
}
|