package main import ( "bytes" "encoding/json" "os" "path/filepath" "strings" "testing" "github.com/xuri/excelize/v2" ) func TestRunCommandAcceptsShortConfigVarsAndPrintsSummary(t *testing.T) { dir := t.TempDir() dataPath := filepath.Join(dir, "data.xlsx") templatePath := filepath.Join(dir, "template.xlsx") configPath := filepath.Join(dir, "task.json") writeCLIWorkbook(t, dataPath, "Daily", [][]string{ {"name", "done"}, {"张三", "完成日报"}, }) writeCLIWorkbook(t, templatePath, "日报", [][]string{ {"批次", "{{batch}}"}, {"员工", "{{name}}"}, {"完成", "{{done}}"}, }) writeCLIJSON(t, configPath, map[string]any{ "data": map[string]any{ "type": "excel", "path": dataPath, "sheet": "Daily", }, "template": map[string]any{ "path": templatePath, }, "output": map[string]any{ "path": filepath.Join(dir, "out", "日报_{{batch}}_{{name}}.xlsx"), }, }) var stdout bytes.Buffer var stderr bytes.Buffer exitCode := run([]string{"run", "-c", configPath, "--var", "batch=早班"}, &stdout, &stderr) if exitCode != 0 { t.Fatalf("exit code = %d, stderr=%q", exitCode, stderr.String()) } if stderr.Len() != 0 { t.Fatalf("expected empty stderr, got %q", stderr.String()) } if !strings.Contains(stdout.String(), "generated 1 file(s)") || !strings.Contains(stdout.String(), "日报_早班_张三.xlsx") { t.Fatalf("unexpected stdout: %q", stdout.String()) } } func TestRunCommandRejectsBadVarSyntax(t *testing.T) { var stdout bytes.Buffer var stderr bytes.Buffer exitCode := run([]string{"run", "-c", "task.json", "--var", "badvar"}, &stdout, &stderr) if exitCode != 2 { t.Fatalf("exit code = %d, want 2", exitCode) } if !strings.Contains(stderr.String(), "docfill:") || !strings.Contains(stderr.String(), "invalid --var") { t.Fatalf("unexpected stderr: %q", stderr.String()) } } func TestRunCommandRejectsUnexpectedArgs(t *testing.T) { var stdout bytes.Buffer var stderr bytes.Buffer exitCode := run([]string{"run", "-c", "task.json", "extra"}, &stdout, &stderr) if exitCode != 2 { t.Fatalf("exit code = %d, want 2", exitCode) } if stdout.Len() != 0 { t.Fatalf("expected empty stdout, got %q", stdout.String()) } if !strings.Contains(stderr.String(), "unexpected argument") { t.Fatalf("unexpected stderr: %q", stderr.String()) } } func writeCLIWorkbook(t *testing.T, path, sheet string, rows [][]string) { t.Helper() f := excelize.NewFile() defer f.Close() defaultSheet := f.GetSheetName(0) if defaultSheet != sheet { if err := f.SetSheetName(defaultSheet, sheet); err != nil { t.Fatalf("set sheet name: %v", err) } } for r, row := range rows { for c, value := range row { cell, err := excelize.CoordinatesToCellName(c+1, r+1) if err != nil { t.Fatalf("cell name: %v", err) } if err := f.SetCellValue(sheet, cell, value); err != nil { t.Fatalf("set cell: %v", err) } } } if err := f.SaveAs(path); err != nil { t.Fatalf("save workbook: %v", err) } } func writeCLIJSON(t *testing.T, path string, value any) { t.Helper() data, err := json.MarshalIndent(value, "", " ") if err != nil { t.Fatalf("marshal json: %v", err) } if err := os.WriteFile(path, data, 0o644); err != nil { t.Fatalf("write json: %v", err) } }