1 // Copyright (C) 2021 Simon Ruderich
3 // This program is free software: you can redistribute it and/or modify
4 // it under the terms of the GNU General Public License as published by
5 // the Free Software Foundation, either version 3 of the License, or
6 // (at your option) any later version.
8 // This program is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 // GNU General Public License for more details.
13 // You should have received a copy of the GNU General Public License
14 // along with this program. If not, see <http://www.gnu.org/licenses/>.
26 "github.com/google/go-cmp/cmp"
27 "github.com/google/go-cmp/cmp/cmpopts"
29 "ruderich.org/simon/safcm"
30 "ruderich.org/simon/safcm/cmd/safcm-remote/log"
31 "ruderich.org/simon/safcm/cmd/safcm-remote/run"
34 type testRunner struct {
43 func (r *testRunner) Run(cmd *exec.Cmd) error {
44 stdout, stderr, resErr := r.check("run", cmd)
45 _, err := cmd.Stdout.Write(stdout)
49 _, err = cmd.Stderr.Write(stderr)
55 func (r *testRunner) CombinedOutput(cmd *exec.Cmd) ([]byte, error) {
56 stdout, stderr, err := r.check("combinedOutput", cmd)
58 // stdout also contains stderr
59 r.t.Fatalf("%s: CombinedOutput: stderr != nil, but %v",
64 func (r *testRunner) check(method string, cmd *exec.Cmd) (
65 []byte, []byte, error) {
67 if len(r.expCmds) == 0 {
68 r.t.Fatalf("%s: %s: empty expCmds", r.name, method)
70 if len(r.resStdout) == 0 {
71 r.t.Fatalf("%s: %s: empty resStdout", r.name, method)
73 if len(r.resStderr) == 0 {
74 r.t.Fatalf("%s: %s: empty resStderr", r.name, method)
76 if len(r.resError) == 0 {
77 r.t.Fatalf("%s: %s: empty resError", r.name, method)
81 r.expCmds = r.expCmds[1:]
82 if !reflect.DeepEqual(exp, cmd) {
83 r.t.Errorf("%s: %s: %s", r.name, method,
84 cmp.Diff(exp, cmd, cmpopts.IgnoreUnexported(
89 var stdout, stderr []byte
92 stdout, r.resStdout = r.resStdout[0], r.resStdout[1:]
93 stderr, r.resStderr = r.resStderr[0], r.resStderr[1:]
94 err, r.resError = r.resError[0], r.resError[1:]
96 return stdout, stderr, err
99 type syncTestResult struct {
106 func prepareSync(req safcm.MsgSyncReq, runner *testRunner) (
107 *Sync, *syncTestResult) {
109 res := &syncTestResult{
110 ch: make(chan string),
120 res.dbg = append(res.dbg, x)
125 logger := log.NewLogger(logPrefix,
126 func(level safcm.LogLevel, format string, a ...interface{}) {
127 res.ch <- fmt.Sprintf("%d: %s", level,
128 fmt.Sprintf(format, a...))
132 cmd: run.NewCmd(runner, logger),
137 func (s *syncTestResult) Wait() []string {
141 // All expected commands must have been executed
142 if len(s.runner.expCmds) != 0 {
143 s.runner.t.Errorf("%s: expCmds left: %v",
144 s.runner.name, s.runner.expCmds)
146 if len(s.runner.resStdout) != 0 {
147 s.runner.t.Errorf("%s: resStdout left: %v",
148 s.runner.name, s.runner.resStdout)
150 if len(s.runner.resStderr) != 0 {
151 s.runner.t.Errorf("%s: resStderr left: %v",
152 s.runner.name, s.runner.resStderr)
154 if len(s.runner.resError) != 0 {
155 s.runner.t.Errorf("%s: resError left: %v",
156 s.runner.name, s.runner.resError)