2026-02-28 22:47:30 +00:00
// Last modified: 2026-02-28 22:43:40 GMT
2026-02-28 18:03:12 +00:00
package cmd
2026-02-28 18:28:27 +00:00
2026-02-28 19:56:23 +00:00
import (
"fmt"
"os"
"path/filepath"
2026-02-28 22:47:30 +00:00
"time"
2026-02-28 19:56:23 +00:00
"github.com/fatih/color"
"github.com/spf13/cobra"
2026-02-28 20:52:03 +00:00
"gmgauthier.com/grokkit/config"
2026-02-28 19:56:23 +00:00
"gmgauthier.com/grokkit/internal/grok"
)
2026-02-28 18:28:27 +00:00
var editCmd = & cobra . Command {
Use : "edit FILE INSTRUCTION" ,
2026-02-28 20:17:12 +00:00
Short : "Edit a file in-place with Grok (safe preview + backup)" ,
Args : cobra . ExactArgs ( 2 ) ,
2026-02-28 18:28:27 +00:00
Run : func ( cmd * cobra . Command , args [ ] string ) {
2026-02-28 19:56:23 +00:00
filePath := args [ 0 ]
2026-02-28 20:17:12 +00:00
instruction := args [ 1 ]
2026-02-28 19:56:23 +00:00
2026-02-28 20:52:03 +00:00
modelFlag , _ := cmd . Flags ( ) . GetString ( "model" )
model := config . GetModel ( modelFlag )
2026-02-28 20:17:12 +00:00
if _ , err := os . Stat ( filePath ) ; os . IsNotExist ( err ) {
color . Red ( "File not found: %s" , filePath )
2026-02-28 19:56:23 +00:00
os . Exit ( 1 )
}
2026-02-28 20:17:12 +00:00
original , _ := os . ReadFile ( filePath )
2026-02-28 19:56:23 +00:00
backupPath := filePath + ".bak"
2026-02-28 20:17:12 +00:00
_ = os . WriteFile ( backupPath , original , 0644 )
2026-02-28 19:56:23 +00:00
client := grok . NewClient ( )
messages := [ ] map [ string ] string {
2026-02-28 22:47:30 +00:00
{ "role" : "system" , "content" : fmt . Sprintf ( "You are an expert programmer. The VERY FIRST LINE of the returned file MUST be a header comment in this exact format: '// Last modified: %s'. Then return the complete updated file content. No explanations, no markdown, no diffs, no extra text." , time . Now ( ) . Format ( "2006-01-02 15:04:05 MST" ) ) } ,
2026-02-28 20:17:12 +00:00
{ "role" : "user" , "content" : fmt . Sprintf ( "File: %s\n\nOriginal content:\n%s\n\nTask: %s" , filepath . Base ( filePath ) , original , instruction ) } ,
2026-02-28 19:56:23 +00:00
}
2026-02-28 20:17:12 +00:00
color . Yellow ( "Asking Grok to %s..." , instruction )
2026-02-28 20:52:03 +00:00
raw := client . Stream ( messages , model )
2026-02-28 20:31:02 +00:00
newContent := grok . CleanCodeResponse ( raw )
2026-02-28 19:56:23 +00:00
2026-02-28 20:31:02 +00:00
// Nice unified diff preview
color . Cyan ( "\nProposed changes:" )
fmt . Println ( "--- a/" + filepath . Base ( filePath ) )
fmt . Println ( "+++ b/" + filepath . Base ( filePath ) )
// simple diff output (you can make it fancier later)
fmt . Print ( newContent )
2026-02-28 19:56:23 +00:00
2026-02-28 20:31:02 +00:00
fmt . Print ( "\n\nApply these changes? (y/n): " )
2026-02-28 19:56:23 +00:00
var confirm string
fmt . Scanln ( & confirm )
2026-02-28 20:17:12 +00:00
if confirm != "y" && confirm != "Y" {
color . Yellow ( "Changes discarded. Backup saved as %s" , backupPath )
2026-02-28 19:56:23 +00:00
return
}
2026-02-28 20:17:12 +00:00
_ = os . WriteFile ( filePath , [ ] byte ( newContent ) , 0644 )
color . Green ( "✅ Applied successfully! Backup: %s" , backupPath )
2026-02-28 18:28:27 +00:00
} ,
2026-02-28 22:29:16 +00:00
}