Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 2 additions & 3 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
VERSION=0.0.7
GITCOMMIT?=$(shell git describe --dirty --always)
LDFLAGS=-ldflags "-w -s -X main.version=${VERSION} -X main.commit=${GITCOMMIT}"
LDFLAGS=-ldflags "-w -s -X main.version=${VERSION}"

all: check-diff

.PHONY: check-diff
.PHONY: check-diff lint check linux

check-diff: *.go
go build $(LDFLAGS) -o check-diff
Expand Down
97 changes: 97 additions & 0 deletions check.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
package main

import (
"bytes"
"crypto/sha256"
"fmt"
"os"
"os/exec"
"os/user"
"path/filepath"
"strings"

"github.com/mackerelio/checkers"
"github.com/monitoring-forge/saferio"
)

func (opt *Opt) cmd(file *os.File) error {
cmd := exec.Command(opt.Command, opt.Args...)
var stderr bytes.Buffer
cmd.Stdout = file
cmd.Stderr = &stderr
if err := cmd.Start(); err != nil {
return err
}
err := cmd.Wait()
if err != nil {
return fmt.Errorf("%w - %s", err, stderr.String())
}
return nil
}

func (opt *Opt) check() *checkers.Checker {

hasher := sha256.New()
fmt.Fprintf(hasher, "%s\x00%s\x00%s", opt.Identifier, opt.Command, strings.Join(opt.Args, "\x00"))

curUser, err := user.Current()
if err != nil {
return checkers.Critical(err.Error())
}

prevFileName := fmt.Sprintf("check-diff-%s-%x", curUser.Uid, hasher.Sum(nil))
newFile, err := os.CreateTemp(opt.Workdir, "check-diff-")
if err != nil {
return checkers.Critical(err.Error())
}

defer func() {
_ = newFile.Close()
_ = os.Remove(newFile.Name())
}()

err = opt.cmd(newFile)
if err != nil {
return checkers.Critical(err.Error())
}

err = newFile.Close()
if err != nil {
return checkers.Critical(err.Error())
}
Comment thread
kazeburo marked this conversation as resolved.

if !saferio.FileExists(opt.Workdir, prevFileName) {
err = os.Rename(newFile.Name(), filepath.Join(opt.Workdir, prevFileName))
if err != nil {
return checkers.Critical(err.Error())
}
if len(opt.Args) > 0 {
return checkers.Ok(fmt.Sprintf("first time execution command: '%s %s'", opt.Command, strings.Join(opt.Args, " ")))
}
return checkers.Ok(fmt.Sprintf("first time execution command: '%s'", opt.Command))
}

diff, err := diff(filepath.Join(opt.Workdir, prevFileName), newFile.Name())
if err != nil {
return checkers.Critical(err.Error())
}

err = os.Rename(newFile.Name(), filepath.Join(opt.Workdir, prevFileName))
if err != nil {
return checkers.Critical(err.Error())
}
Comment thread
kazeburo marked this conversation as resolved.

if diff == "" {
msg, err := buildNoDifferenceMsg(filepath.Join(opt.Workdir, prevFileName))
if err != nil {
return checkers.Critical(err.Error())
}
return checkers.Ok(msg)
}

diffMsg := buildDiffMsg(diff)
if opt.Warn {
return checkers.Warning(diffMsg)
}
return checkers.Critical(diffMsg)
}
16 changes: 8 additions & 8 deletions main_test.go → check_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,19 +84,19 @@ func createTempFile(t *testing.T, content string) (*os.File, func()) {
}
}

func TestRun(t *testing.T) {
func TestCheck(t *testing.T) {
opt, file := getCmdOpt(t, "echo", []string{"Hello, World!"})
defer file.Close()
ckr := opt.run()
ckr := opt.check()
if ckr.Status != checkers.OK {
t.Errorf("Expected OK status, got %v", ckr.Status)
}
if !strings.Contains(ckr.Message, "first time execution command") {
t.Errorf("Expected first time execution message, got %q", ckr.Message)
}

// Run again to check for no difference
ckr = opt.run()
// Check again to check for no difference
ckr = opt.check()
if ckr.Status != checkers.OK {
t.Errorf("Expected OK status, got %v", ckr.Status)
}
Expand All @@ -105,16 +105,16 @@ func TestRun(t *testing.T) {
}
}

func TestRunWithDifference(t *testing.T) {
func TestCheckWithDifference(t *testing.T) {
opt, file := getCmdOpt(t, "date", []string{})
defer file.Close()
// First run to create the initial state
opt.run()
// First check to create the initial state
opt.check()

// Change the command to produce a different output
time.Sleep(2 * time.Second) // Ensure the date command produces a different output
opt.Command = "date"
ckr := opt.run()
ckr := opt.check()
if ckr.Status != checkers.CRITICAL {
t.Errorf("Expected CRITICAL status, got %v", ckr.Status)
}
Expand Down
30 changes: 16 additions & 14 deletions diff.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,17 @@ package main

import (
"bufio"
"errors"
"fmt"
"io"
"strings"

"github.com/cubicdaiya/gonp"
"github.com/monitoring-forge/saferio"
)

func getLines(filename string) ([]string, error) {
file, err := openRD(filename)
file, err := saferio.OpenRD(filename)
if err != nil {
return nil, err
}
Expand All @@ -29,23 +31,23 @@ func getLines(filename string) ([]string, error) {
}

func diff(prev, current string) (string, error) {
prevLines, err := getLines(prev)
if err != nil {
return "", err
}
newLines, err := getLines(current)
if err != nil {
return "", err
}
prevLines, err := getLines(prev)
if err != nil {
return "", err
}
newLines, err := getLines(current)
if err != nil {
return "", err
}

d := gonp.New(prevLines, newLines)
d.Compose()
d := gonp.New(prevLines, newLines)
d.Compose()

return d.SprintUniHunks(d.UnifiedHunks()), nil
return d.SprintUniHunks(d.UnifiedHunks()), nil
}

func buildNoDifferenceMsg(filename string) (string, error) {
file, err := openRD(filename)
file, err := saferio.OpenRD(filename)
if err != nil {
return "", err
}
Expand All @@ -57,7 +59,7 @@ func buildNoDifferenceMsg(filename string) (string, error) {
}
b := make([]byte, 128)
count, err := file.Read(b)
if err != nil && err != io.EOF {
if err != nil && !errors.Is(err, io.EOF) {
return "", err
}
o := string(strings.TrimRight(string(b[0:count]), "\r\n"))
Expand Down
2 changes: 2 additions & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -11,5 +11,7 @@ require github.com/cubicdaiya/gonp v1.0.4

require (
github.com/mackerelio/golib v1.2.2
github.com/monitoring-forge/flagrun v0.0.7
github.com/monitoring-forge/saferio v0.0.2
golang.org/x/sys v0.47.0 // indirect
)
4 changes: 4 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,9 @@ github.com/mackerelio/checkers v0.2.1 h1:vRXzAT+CEyaLjSrHVxKUBjyWq1kfo8QcI8ZoSKZ
github.com/mackerelio/checkers v0.2.1/go.mod h1:CW3k/5bvHhxDrfKgWvMvNH0R51zco141ZVxlI7o/KAc=
github.com/mackerelio/golib v1.2.2 h1:fQfW1o2KvPyIsAH/7+M2J0gpf2jLu+NyYpDCN79zxW4=
github.com/mackerelio/golib v1.2.2/go.mod h1:itcSOfrsT5XvkzflFPebT43RrliaKDz2T6YGYt3jclw=
github.com/monitoring-forge/flagrun v0.0.7 h1:6UpM8waZzN0KiZJJ2xHP64TncdmMKHE6W2HBxJwhAZA=
github.com/monitoring-forge/flagrun v0.0.7/go.mod h1:yAwxGIEx81wU4JOMp6hz7SdSYWgT/Hr4JXEdHlEn1mw=
github.com/monitoring-forge/saferio v0.0.2 h1:DJ4D4e7tBuMze4Ez7N7l7pGPAJ/oFsC0mwh+dg5UkwE=
github.com/monitoring-forge/saferio v0.0.2/go.mod h1:N2nfAMrgYrax2CdwKIIWIjy5tIrlQFtJJWzKess30KY=
golang.org/x/sys v0.47.0 h1:o7XGOvZQCADBQQ4Y7VNq2dRWQR7JmOUW8Kxx4ZsNgWs=
golang.org/x/sys v0.47.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw=
Loading
Loading