|
|
|
@ -150,6 +150,7 @@ func (g *Gui) LoadJSON() {
|
|
|
|
|
log.Println(fmt.Sprintf("can't open file: %s", err))
|
|
|
|
|
return err
|
|
|
|
|
}
|
|
|
|
|
defer file.Close()
|
|
|
|
|
|
|
|
|
|
i, err := UnMarshalJSON(file)
|
|
|
|
|
if err != nil {
|
|
|
|
@ -215,7 +216,7 @@ func (g *Gui) SaveJSONToFile(file string) error {
|
|
|
|
|
enc := json.NewEncoder(&buf)
|
|
|
|
|
enc.SetIndent("", " ")
|
|
|
|
|
|
|
|
|
|
if err := enc.Encode(g.makeJSON(g.Tree.GetRoot())); err != nil {
|
|
|
|
|
if err := enc.Encode(g.MakeJSON(g.Tree.OriginRoot)); err != nil {
|
|
|
|
|
log.Println(fmt.Sprintf("can't marshal json: %s", err))
|
|
|
|
|
return err
|
|
|
|
|
}
|
|
|
|
@ -228,7 +229,7 @@ func (g *Gui) SaveJSONToFile(file string) error {
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func (g *Gui) makeJSON(node *tview.TreeNode) interface{} {
|
|
|
|
|
func (g *Gui) MakeJSON(node *tview.TreeNode) interface{} {
|
|
|
|
|
ref := node.GetReference().(Reference)
|
|
|
|
|
children := node.GetChildren()
|
|
|
|
|
|
|
|
|
@ -236,22 +237,25 @@ func (g *Gui) makeJSON(node *tview.TreeNode) interface{} {
|
|
|
|
|
case Object:
|
|
|
|
|
i := make(map[string]interface{})
|
|
|
|
|
for _, n := range children {
|
|
|
|
|
i[n.GetText()] = g.makeJSON(n)
|
|
|
|
|
i[n.GetText()] = g.MakeJSON(n)
|
|
|
|
|
}
|
|
|
|
|
return i
|
|
|
|
|
case Array:
|
|
|
|
|
var i []interface{}
|
|
|
|
|
for _, n := range children {
|
|
|
|
|
i = append(i, g.makeJSON(n))
|
|
|
|
|
i = append(i, g.MakeJSON(n))
|
|
|
|
|
}
|
|
|
|
|
return i
|
|
|
|
|
case Key:
|
|
|
|
|
if len(node.GetChildren()) == 0 {
|
|
|
|
|
return ""
|
|
|
|
|
}
|
|
|
|
|
v := node.GetChildren()[0]
|
|
|
|
|
if v.GetReference().(Reference).JSONType == Value {
|
|
|
|
|
return g.parseValue(v)
|
|
|
|
|
}
|
|
|
|
|
return map[string]interface{}{
|
|
|
|
|
node.GetText(): g.makeJSON(v),
|
|
|
|
|
node.GetText(): g.MakeJSON(v),
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -339,14 +343,14 @@ func (g *Gui) NaviPanel() {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func (g *Gui) EditWithEditor() {
|
|
|
|
|
g.App.Suspend(func() {
|
|
|
|
|
f, err := ioutil.TempFile("", "tson")
|
|
|
|
|
if err != nil {
|
|
|
|
|
log.Println(fmt.Sprintf("can't create temp file: %s", err))
|
|
|
|
|
g.Message(err.Error(), "main", func() {})
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
defer os.RemoveAll(f.Name())
|
|
|
|
|
f.Close()
|
|
|
|
|
|
|
|
|
|
if err := g.SaveJSONToFile(f.Name()); err != nil {
|
|
|
|
|
log.Println(fmt.Sprintf("can't write to temp file: %s", err))
|
|
|
|
@ -354,15 +358,21 @@ func (g *Gui) EditWithEditor() {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if b := g.App.Suspend(func() {
|
|
|
|
|
editor := os.Getenv("EDITOR")
|
|
|
|
|
if editor == "" {
|
|
|
|
|
log.Println(fmt.Sprintf("$EDITOR is empty: %s", err))
|
|
|
|
|
g.Message(err.Error(), "main", func() {})
|
|
|
|
|
msg := fmt.Sprint("$EDITOR is empty")
|
|
|
|
|
log.Println(msg)
|
|
|
|
|
g.Message(msg, "main", func() {})
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
cmd := exec.Command(editor, f.Name())
|
|
|
|
|
var args []string
|
|
|
|
|
if editor == "vim" {
|
|
|
|
|
args = append(args, []string{"-c", "set ft=json", f.Name()}...)
|
|
|
|
|
} else {
|
|
|
|
|
args = append(args, f.Name())
|
|
|
|
|
}
|
|
|
|
|
cmd := exec.Command(editor, args...)
|
|
|
|
|
|
|
|
|
|
// Start the command with a pty.
|
|
|
|
|
ptmx, err := pty.Start(cmd)
|
|
|
|
@ -371,7 +381,11 @@ func (g *Gui) EditWithEditor() {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
// Make sure to close the pty at the end.
|
|
|
|
|
defer func() { _ = ptmx.Close() }() // Best effort.
|
|
|
|
|
defer func() {
|
|
|
|
|
if err := ptmx.Close(); err != nil {
|
|
|
|
|
log.Printf("can't close pty: %s", err)
|
|
|
|
|
}
|
|
|
|
|
}()
|
|
|
|
|
|
|
|
|
|
// Handle pty size.
|
|
|
|
|
ch := make(chan os.Signal, 1)
|
|
|
|
@ -392,28 +406,34 @@ func (g *Gui) EditWithEditor() {
|
|
|
|
|
g.Message(err.Error(), "main", func() {})
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
defer func() { _ = terminal.Restore(int(os.Stdin.Fd()), oldState) }() // Best effort.
|
|
|
|
|
|
|
|
|
|
// Copy stdin to the pty and the pty to stdout.
|
|
|
|
|
go func() {
|
|
|
|
|
io.Copy(ptmx, os.Stdin)
|
|
|
|
|
defer func() {
|
|
|
|
|
if err := terminal.Restore(int(os.Stdin.Fd()), oldState); err != nil {
|
|
|
|
|
log.Printf("can't restore terminal: %s", err)
|
|
|
|
|
}
|
|
|
|
|
}()
|
|
|
|
|
|
|
|
|
|
// Copy stdin to the pty and the pty to stdout.
|
|
|
|
|
go io.Copy(ptmx, os.Stdin)
|
|
|
|
|
io.Copy(os.Stdout, ptmx)
|
|
|
|
|
|
|
|
|
|
i, err := UnMarshalJSON(f)
|
|
|
|
|
f, err = os.Open(f.Name())
|
|
|
|
|
if err != nil {
|
|
|
|
|
log.Println(fmt.Sprintf("can't read from file: %s", err))
|
|
|
|
|
log.Println(fmt.Sprintf("can't open file: %s", err))
|
|
|
|
|
g.Message(err.Error(), "main", func() {})
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
defer f.Close()
|
|
|
|
|
|
|
|
|
|
g.Tree.UpdateView(g, i)
|
|
|
|
|
}); !b {
|
|
|
|
|
log.Println(fmt.Sprintf("can't edit: %s", err))
|
|
|
|
|
i, err := UnMarshalJSON(f)
|
|
|
|
|
if err != nil {
|
|
|
|
|
log.Println(fmt.Sprintf("can't read from file: %s", err))
|
|
|
|
|
g.Message(err.Error(), "main", func() {})
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
os.RemoveAll(f.Name())
|
|
|
|
|
g.Tree.UpdateView(g, i)
|
|
|
|
|
})
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func UnMarshalJSON(in io.Reader) (interface{}, error) {
|
|
|
|
|