6 Commits

Author SHA1 Message Date
31c9ed52cb preparing for 1.0 2024-06-14 05:53:22 -07:00
28d0d041b0 lint and check fmt on docker build 2024-06-14 05:47:35 -07:00
278cb73053 fmt 2024-06-14 05:47:29 -07:00
ea0c84547f add example script 2024-06-14 05:39:08 -07:00
a852d938e7 ignore binary 2024-06-14 05:39:03 -07:00
a660203e8f fix call stack depth bug to show log location correctly 2024-06-14 05:38:29 -07:00
8 changed files with 114 additions and 8 deletions

1
.gitignore vendored
View File

@@ -1 +1,2 @@
.aider* .aider*
cmd/example/example

39
Dockerfile Normal file
View File

@@ -0,0 +1,39 @@
# First stage: Use the golangci-lint image to run the linter
FROM golangci/golangci-lint:latest as lint
# Set the Current Working Directory inside the container
WORKDIR /app
# Copy the go.mod file and the rest of the application code
COPY go.mod ./
COPY . .
# Run golangci-lint
RUN golangci-lint run
RUN sh -c 'test -z "$(gofmt -l .)"'
# Second stage: Use the official Golang image to run tests
FROM golang:1.22 as test
# Set the Current Working Directory inside the container
WORKDIR /app
# Copy the go.mod file and the rest of the application code
COPY go.mod ./
COPY . .
# Run tests
RUN go test -v ./...
# Final stage: Combine the linting and testing stages
FROM golang:1.22 as final
# Ensure that the linting stage succeeded
WORKDIR /app
COPY --from=lint /app .
COPY --from=test /app .
# Set the final CMD to something minimal since we only needed to verify lint and tests during build
CMD ["echo", "Build and tests passed successfully!"]

14
LICENSE Normal file
View File

@@ -0,0 +1,14 @@
DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
Version 2, December 2004
Copyright (C) 2004 Sam Hocevar <sam@hocevar.net>
Everyone is permitted to copy and distribute verbatim or modified
copies of this license document, and changing it is allowed as long
as the name is changed.
DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. You just DO WHAT THE FUCK YOU WANT TO.

View File

@@ -12,3 +12,6 @@ fmt:
lint: lint:
golangci-lint run golangci-lint run
sh -c 'test -z "$$(gofmt -l .)"' sh -c 'test -z "$$(gofmt -l .)"'
docker:
docker build --progress plain .

View File

@@ -11,15 +11,18 @@ stdlib `log/slog` default handler, and solve the 90% case for logging.
## Current Status ## Current Status
Pre-1.0, not working yet. Released v1.0.0 2024-06-14. Works as intended. No known bugs.
## Features ## Features
- if output is a tty, outputs pretty color logs - if output is a tty, outputs pretty color logs
- if output is not a tty, outputs json - if output is not a tty, outputs json
- supports delivering logs via tcp RELP (e.g. to remote rsyslog using imrelp)
- supports delivering each log message via a webhook - supports delivering each log message via a webhook
## Planned Features
- supports delivering logs via tcp RELP (e.g. to remote rsyslog using imrelp)
## Installation ## Installation
To use simplelog, first ensure your project is set up with Go modules: To use simplelog, first ensure your project is set up with Go modules:
@@ -36,7 +39,9 @@ go get sneak.berlin/go/simplelog
## Usage ## Usage
Below is an example of how to use SimpleLog in a Go application. This example is provided in the form of a `main.go` file, which demonstrates logging at various levels using structured logging syntax. Below is an example of how to use SimpleLog in a Go application. This
example is provided in the form of a `main.go` file, which demonstrates
logging at various levels using structured logging syntax.
```go ```go
package main package main
@@ -54,3 +59,7 @@ func main() {
slog.Error("Failed to save data", slog.String("reason", "permission denied")) slog.Error("Failed to save data", slog.String("reason", "permission denied"))
} }
``` ```
## License
[WTFPL](./LICENSE)

26
cmd/example/main.go Normal file
View File

@@ -0,0 +1,26 @@
package main
import (
"log/slog"
_ "sneak.berlin/go/simplelog"
)
func main() {
// log structured data with slog as usual:
slog.Info(
"User login attempt",
slog.String("user", "JohnDoe"),
slog.Int("attempt", 3),
)
slog.Warn(
"Configuration mismatch",
slog.String("expected", "config.json"),
slog.String("found", "config.dev.json"),
)
slog.Error(
"Failed to save data",
slog.String("reason", "permission denied"),
)
}

View File

@@ -16,7 +16,10 @@ func NewConsoleHandler() *ConsoleHandler {
return &ConsoleHandler{} return &ConsoleHandler{}
} }
func (c *ConsoleHandler) Handle(ctx context.Context, record slog.Record) error { func (c *ConsoleHandler) Handle(
ctx context.Context,
record slog.Record,
) error {
timestamp := time.Now().UTC().Format("2006-01-02T15:04:05.000Z07:00") timestamp := time.Now().UTC().Format("2006-01-02T15:04:05.000Z07:00")
var colorFunc func(format string, a ...interface{}) string var colorFunc func(format string, a ...interface{}) string
@@ -32,16 +35,28 @@ func (c *ConsoleHandler) Handle(ctx context.Context, record slog.Record) error {
} }
// Get the caller information // Get the caller information
_, file, line, ok := runtime.Caller(5) _, file, line, ok := runtime.Caller(4)
if !ok { if !ok {
file = "???" file = "???"
line = 0 line = 0
} }
fmt.Println(colorFunc("%s [%s] %s:%d: %s", timestamp, record.Level, file, line, record.Message)) fmt.Println(
colorFunc(
"%s [%s] %s:%d: %s",
timestamp,
record.Level,
file,
line,
record.Message,
),
)
return nil return nil
} }
func (c *ConsoleHandler) Enabled(ctx context.Context, level slog.Level) bool { func (c *ConsoleHandler) Enabled(
ctx context.Context,
level slog.Level,
) bool {
return true return true
} }

View File

@@ -15,7 +15,6 @@ type Event struct {
Data json.RawMessage `json:"data"` Data json.RawMessage `json:"data"`
} }
func NewEvent(level, message string, data json.RawMessage) Event { func NewEvent(level, message string, data json.RawMessage) Event {
return Event{ return Event{
ID: uuid.New(), ID: uuid.New(),