Example #1
0
func (s *Service) handleLuaLoad(msg sarif.Message) {
	gen := false
	name := strings.TrimPrefix(strings.TrimPrefix(msg.Action, "lua/load"), "/")
	if name == "" {
		name, gen = sarif.GenerateId(), true
	}
	if _, ok := s.Machines[name]; ok {
		s.destroyMachine(name)
	}

	m, err := s.createMachine(name)
	if err != nil {
		s.ReplyInternalError(msg, err)
		return
	}

	var ctp ContentPayload
	if err := msg.DecodePayload(&ctp); err != nil {
		s.ReplyBadRequest(msg, err)
		return
	}
	text := msg.Text
	if ctp.Content.Url != "" {
		ct, err := content.Get(ctp.Content)
		if err != nil {
			s.ReplyBadRequest(msg, err)
		}
		text = string(ct.Data)
	}

	var gp interface{}
	msg.DecodePayload(&gp)
	out, err, _ := m.Do(text, gp)
	if err != nil {
		s.ReplyBadRequest(msg, err)
		s.destroyMachine(name)
		return
	}

	if !gen {
		f, err := os.Create(s.cfg.ScriptDir + "/" + name + ".lua")
		if err == nil {
			_, err = f.Write([]byte(text))
			defer f.Close()
		}
		if err != nil {
			s.ReplyInternalError(msg, err)
			s.destroyMachine(name)
			return
		}
	}

	s.Reply(msg, sarif.CreateMessage("lua/loaded", &MsgMachineStatus{
		name,
		"up",
		out,
	}))
}
Example #2
0
func (app *App) Edit() {
	// Request document from given action
	action := flag.Arg(1)
	putAction := flag.Arg(2)

	msg, ok := <-app.Client.Request(sarif.CreateMessage(action, nil))
	if !ok {
		app.Log.Fatalln("No response received at " + action)
	}
	if msg.IsAction("err") {
		app.Log.Fatalln(msg.Action + ": " + msg.Text)
	}

	rawPayload := false
	var ctp ContentPayload
	app.Must(msg.DecodePayload(&ctp))

	// Extract content from response
	var err error
	if ctp.Content.Url != "" {
		ct, err := content.Get(ctp.Content)
		app.Must(err)
		ctp.Content.Data = ct.Data
	} else if len(msg.Payload.Raw) > 0 {
		var p interface{}
		msg.DecodePayload(&p)
		ctp.Content.Data, err = json.MarshalIndent(p, "", "    ")
		app.Must(err)
		rawPayload = true
	} else {
		ctp.Content.Data = []byte(msg.Text)
	}

	// Create temp file with content
	f, err := tempFile(os.TempDir(), "tars-", "-"+ctp.Content.Name)
	app.Must(err)
	defer func() {
		f.Close()
		os.Remove(f.Name())
	}()
	_, err = f.Write(ctp.Content.Data)
	app.Must(err)
	app.Must(f.Sync())
	fi, err := f.Stat()
	app.Must(err)
	lastMod := fi.ModTime()

	// Start editor and continuously check progress
	editor := os.Getenv("EDITOR")
	cmd := exec.Command(editor, f.Name())
	cmd.Stdin = os.Stdin
	cmd.Stdout = os.Stdout
	cmd.Stderr = os.Stderr
	app.Must(cmd.Start())

	stop := make(chan bool, 2)
	go func() {
		app.Must(cmd.Wait())
		stop <- true
	}()

	lastErr := ""
	run := true
	for run {
		select {
		case <-time.After(time.Second):
		case <-stop:
			run = false
		}

		fi, err := f.Stat()
		app.Must(err)
		if lastMod.Before(fi.ModTime()) && putAction != "" {
			lastMod = fi.ModTime()
			_, err := f.Seek(0, 0)
			app.Must(err)
			data, err := ioutil.ReadAll(f)
			app.Must(err)

			lastErr = ""
			req := sarif.CreateMessage(putAction, nil)
			if rawPayload {
				var temp interface{}
				err := json.Unmarshal(data, &temp)
				if err == nil {
					req.Payload.Raw = data
				}
			} else {
				req.EncodePayload(ContentPayload{content.PutData(data)})
			}
			msg, ok := <-app.Client.Request(req)

			if !ok {
				lastErr = "Could not save: no response received at " + ctp.Content.PutAction
			} else if msg.IsAction("err") {
				lastErr = msg.Action + ": " + msg.Text
			}
		}
	}

	if lastErr != "" {
		app.Log.Fatalln(lastErr)
	}
}