goodies API

goodies

package

API reference for the goodies package.

I
interface

ErrorHandler

ErrorHandler is the protocol for handling errors, use this to implement
custom error handling logic.

pkg/v1/goodies/cleanup_queue.go:18-21
type ErrorHandler interface

Methods

HandleError
Method

Parameters

args ...interface{}

Returns

error
func HandleError(...)
S
struct
Implements: ErrorHandler

NoErrorHandler

NoErrorHandler is a default error handler that does nothing, useful when
you don’t need to handle errors.

pkg/v1/goodies/cleanup_queue.go:25-25
type NoErrorHandler struct

Methods

HandleError
Method

Parameters

args ...interface{}

Returns

error
func (*NoErrorHandler) HandleError(args ...interface{}) error
{
	return nil
}
T
type

ErrorHandlerFn

ErrorHandlerFn is an error handler that implements the ErrorHandler
protocol, use this to create custom error handling logic.

pkg/v1/goodies/cleanup_queue.go:33-33
type ErrorHandlerFn func(args ...interface{}) error
S
struct

CleanupQueue

CleanupQueue is a priority queue that runs cleanup tasks in order of
priority and uses the defined error handler to handle errors.

pkg/v1/goodies/cleanup_queue.go:41-43
type CleanupQueue struct

Methods

Add
Method

Add adds a new task to the cleanup queue.

Parameters

task func(args ...interface{}) error
args []interface{}
priority int
errorHandler ErrorHandler
ignoreErrorHandlerFailure bool
func (*CleanupQueue) Add(task func(args ...interface{}) error, args []interface{}, priority int, errorHandler ErrorHandler, ignoreErrorHandlerFailure bool)
{
	cleanupTask := &CleanupTask{
		Task:                      task,
		Args:                      args,
		Priority:                  priority,
		ErrorHandler:              errorHandler,
		IgnoreErrorHandlerFailure: ignoreErrorHandlerFailure,
	}
	heap.Push(&q.tasks, cleanupTask)
}
Run
Method

Run runs the cleanup queue and executes all the tasks in order of priority. It returns an error if any of the tasks encounter an error, including the error handler function, unless the task is marked to ignore error handler failures.

Returns

error
func (*CleanupQueue) Run() error
{
	for q.tasks.Len() > 0 {
		task := heap.Pop(&q.tasks).(*CleanupTask)
		err := task.Task(task.Args...)
		if err != nil {
			errHandle := task.ErrorHandler.HandleError(task.Args...)
			if errHandle != nil {
				if !task.IgnoreErrorHandlerFailure {
					return fmt.Errorf("error handling failed: %v", errHandle)
				}
			}
		}
	}
	return nil
}

Fields

Name Type Description
tasks cleanupHeap
F
function

NewCleanupQueue

NewCleanupQueue creates a new cleanup queue.

Returns

pkg/v1/goodies/cleanup_queue.go:46-50
func NewCleanupQueue() *CleanupQueue

{
	q := &CleanupQueue{}
	heap.Init(&q.tasks)
	return q
}
S
struct

CleanupTask

CleanupTask is a task that defines a cleanup task to be run in the cleanup
queue. It has a priority, a task to run, a list of arguments, an error
handler to handle errors, and a flag to ignore error handler failures.

pkg/v1/goodies/cleanup_queue.go:55-62
type CleanupTask struct

Fields

Name Type Description
Priority int
Task func(args ...interface{}) error
Args []interface{}
ErrorHandler ErrorHandler
IgnoreErrorHandlerFailure bool
index int
T
type

cleanupHeap

pkg/v1/goodies/cleanup_queue.go:96-96
type cleanupHeap []*CleanupTask
S
struct

EventManager

EventManager is a simple event manager that allows subscribing to events
and notifying them, so that multiple parts of the code can be notified
when an event happens and act accordingly.

pkg/v1/goodies/event_manager.go:18-22
type EventManager struct

Methods

Subscribe
Method

Subscribe subscribes to an event type and returns a subscription ID, use this ID to unsubscribe from the event later.

Parameters

eventType string
handler EventHandler

Returns

int
func (*EventManager) Subscribe(eventType string, handler EventHandler) int
{
	em.mu.Lock()
	defer em.mu.Unlock()

	if em.listeners[eventType] == nil {
		em.listeners[eventType] = make(map[int]EventHandler)
	}

	em.nextID++
	id := em.nextID
	em.listeners[eventType][id] = handler
	return id
}
Example
subID := eventManager.Subscribe("testEvent", func(data interface{}) {
	fmt.Println("Event happened:", data)
})
fmt.Println("Subscribed with ID:", subID)
Unsubscribe
Method

Unsubscribe unsubscribes from an event type using its subscription ID

Parameters

eventType string
id int
func (*EventManager) Unsubscribe(eventType string, id int)
{
	em.mu.Lock()
	defer em.mu.Unlock()

	if handlers, ok := em.listeners[eventType]; ok {
		delete(handlers, id)
	}
}
Example
subID := eventManager.Subscribe("testEvent", func(data interface{}) {
	fmt.Println("Event happened:", data)
})
fmt.Println("Subscribed with ID:", subID)
eventManager.Unsubscribe("testEvent", subID)
Notify
Method

Notify notifies an event type with some data, all the handlers subscribed to the event type will be called with the data.

Parameters

eventType string
data interface{}
func (*EventManager) Notify(eventType string, data interface{})
{
	em.mu.RLock()
	defer em.mu.RUnlock()

	if handlers, ok := em.listeners[eventType]; ok {
		for _, handler := range handlers {
			handler(data)
		}
	}
}
Example
eventManager.Notify("testEvent", "testData")

Fields

Name Type Description
mu sync.RWMutex
listeners map[string]map[int]EventHandler
nextID int
T
type

EventHandler

EventHandler is the protocol for handling events, use this to implement
custom event handling logics for your application.

pkg/v1/goodies/event_manager.go:26-26
type EventHandler func(interface{})
F
function

NewEventManager

NewEventManager creates a new event manager.

Returns

pkg/v1/goodies/event_manager.go:37-41
func NewEventManager() *EventManager

{
	return &EventManager{
		listeners: make(map[string]map[int]EventHandler),
	}
}

Example

eventManager := goodies.NewEventManager()
eventManager.Subscribe("testEvent", func(data interface{}) {
	fmt.Println("Event happened:", data)
})
eventManager.Notify("testEvent", "testData")
I
interface

ValidatorType

ValidatorType defines the protocol for a validation method. Implement this
to create custom validation methods for your integrity checks.

pkg/v1/goodies/integrity_check.go:25-27
type ValidatorType interface

Methods

Hash
Method

Parameters

data io.Reader

Returns

string
error
func Hash(...)
S
struct
Implements: ValidatorType

SHA1Validator

SHA1Validator is an implementation of the validation method using SHA-1

pkg/v1/goodies/integrity_check.go:30-30
type SHA1Validator struct

Methods

Hash
Method

Parameters

data io.Reader

Returns

string
error
func (SHA1Validator) Hash(data io.Reader) (string, error)
{
	h := sha1.New()
	if _, err := io.Copy(h, data); err != nil {
		return "", err
	}
	return hex.EncodeToString(h.Sum(nil)), nil
}
S
struct
Implements: ValidatorType

SHA256Validator

SHA256Validator is an implementation of the validation method using SHA-256

pkg/v1/goodies/integrity_check.go:41-41
type SHA256Validator struct

Methods

Hash
Method

Parameters

data io.Reader

Returns

string
error
func (SHA256Validator) Hash(data io.Reader) (string, error)
{
	h := sha256.New()
	if _, err := io.Copy(h, data); err != nil {
		return "", err
	}
	return hex.EncodeToString(h.Sum(nil)), nil
}
S
struct
Implements: ValidatorType

MD5Validator

MD5Validator is an implementation of the validation method using MD5

pkg/v1/goodies/integrity_check.go:52-52
type MD5Validator struct

Methods

Hash
Method

Parameters

data io.Reader

Returns

string
error
func (MD5Validator) Hash(data io.Reader) (string, error)
{
	h := md5.New()
	if _, err := io.Copy(h, data); err != nil {
		return "", err
	}
	return hex.EncodeToString(h.Sum(nil)), nil
}
S
struct

IntegrityCheckResult

IntegrityCheckResult represents the result of an integrity check

pkg/v1/goodies/integrity_check.go:63-68
type IntegrityCheckResult struct

Fields

Name Type Description
TotalRequested int
Passed int
Failed int
FailedChecks []FailedCheck
S
struct

FailedCheck

FailedCheck represents a failed integrity check

pkg/v1/goodies/integrity_check.go:71-75
type FailedCheck struct

Fields

Name Type Description
ResourcePath string
RequestedHash string
DetectedHash string
F
function

CheckIntegrity

CheckIntegrity performs an integrity check of the provided data using the
provided validation method and returns the result. If a validation fails
the result will contain the failed checks.

The prefix parameter specifies the base path to be used for each file check.

Parameters

data
[]byte
method
prefix
string

Returns

pkg/v1/goodies/integrity_check.go:100-113
func CheckIntegrity(data []byte, method ValidatorType, prefix string) (IntegrityCheckResult, error)

{
	pairings := make(map[string]string)
	lines := strings.Split(string(data), "\n")
	for _, line := range lines {
		parts := strings.SplitN(line, " ", 2)
		if len(parts) != 2 {
			return IntegrityCheckResult{}, fmt.Errorf("invalid line format: %s", line)
		}
		pairings[parts[0]] = parts[1]
	}

	// Perform the integrity check using the provided validation method
	return checkIntegrity(pairings, method, prefix)
}

Example

data := []byte("batman.txt 8c555f537cd1fe3f1239ebf7b6d639bc0d576bda\nrobin.txt 4e58c66d2ef2b9a60c7ea2bc03253d8b01874b52")
result, err := CheckIntegrity(data, SHA1Validator{}, "files/")

if err != nil {
	fmt.Printf("Error: %v\n", err)
}

fmt.Printf("Total requested: %d\n", result.TotalRequested)
fmt.Printf("Passed: %d\n", result.Passed)
fmt.Printf("Failed: %d\n", result.Failed)
for _, failedCheck := range result.FailedChecks {
	fmt.Printf("Resource: %s\n", failedCheck.ResourcePath)
	fmt.Printf("Requested: %s\n", failedCheck.RequestedHash)
	fmt.Printf("Detected: %s\n", failedCheck.DetectedHash)
}
F
function

checkIntegrity

checkIntegrity performs the integrity check of the file data using
the provided validation method.

Parameters

pairings
map[string]string
method
prefix
string

Returns

pkg/v1/goodies/integrity_check.go:117-144
func checkIntegrity(pairings map[string]string, method ValidatorType, prefix string) (IntegrityCheckResult, error)

{
	var result IntegrityCheckResult

	for resourcePath, requestedHash := range pairings {
		// If a prefix is provided, we have to join it with the resource path to
		// ensure the file is found in the place the developer expects.
		fullPath := filepath.Join(prefix, resourcePath)
		detectedHash, err := calculateHash(fullPath, method)
		if err != nil {
			fmt.Printf("Error calculating hash for %s: %v\n", fullPath, err)
			continue
		}

		result.TotalRequested++
		if requestedHash == detectedHash {
			result.Passed++
		} else {
			result.Failed++
			result.FailedChecks = append(result.FailedChecks, FailedCheck{
				ResourcePath:  fullPath,
				RequestedHash: requestedHash,
				DetectedHash:  detectedHash,
			})
		}
	}

	return result, nil
}
F
function

calculateHash

calculateHash calculates the hash of a file using the provided validation
method and returns it as a string.

Parameters

filePath
string
method

Returns

string
error
pkg/v1/goodies/integrity_check.go:148-156
func calculateHash(filePath string, method ValidatorType) (string, error)

{
	file, err := os.Open(filePath)
	if err != nil {
		return "", err
	}
	defer file.Close()

	return method.Hash(file)
}