https://github.com/daichitakahashi/deps
Manage lifecycle of the application's dependencies and shutdown gracefully, with minimalistic API.
https://github.com/daichitakahashi/deps
dependency go golang goroutine graceful-shutdown
Last synced: 8 months ago
JSON representation
Manage lifecycle of the application's dependencies and shutdown gracefully, with minimalistic API.
- Host: GitHub
- URL: https://github.com/daichitakahashi/deps
- Owner: daichitakahashi
- License: mit
- Created: 2023-02-07T15:26:58.000Z (over 2 years ago)
- Default Branch: main
- Last Pushed: 2023-10-06T12:49:46.000Z (about 2 years ago)
- Last Synced: 2025-01-16T02:36:21.025Z (9 months ago)
- Topics: dependency, go, golang, goroutine, graceful-shutdown
- Language: Go
- Homepage:
- Size: 14.6 KB
- Stars: 0
- Watchers: 1
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- Changelog: CHANGELOG.md
- License: LICENSE
Awesome Lists containing this project
README
# deps
[](https://pkg.go.dev/github.com/daichitakahashi/deps)
[](https://daichitakahashi.github.io/deps/coverage.html)Manage lifecycle of the application's dependencies and shutdown gracefully, with minimalistic API.
## How to use
Create application entrypoint using `deps.New()` and describe dependencies with `Dependent()`.
```go
func main() {
root := deps.New()// Worker #1 (Web server)
go func(dep *deps.Dependency) {
var (
svr http.Server
err error
e = make(chan error, 1)
)
defer dep.Stop(&err) // request abort if err!=nilgo func() {
e <- svr.ListenAndServe()
}()
select {
case err = <-e:
log.Println("server stopped unexpectedly: ", err)
case <-dep.Aborted():
log.Println("start shutdown server")
// do not pass shutdown error to dep.Stop()
if shutdownErr := svr.Shutdown(dep.AbortContext()); shutdownErr != nil { // timeout=1m
log.Println("failed to shutdown server gracefully: ", shutdownErr)
}
}
}(root.Dependent())// Worker #2 (Periodic task runner or something)
go func(dep *deps.Dependency) {
defer dep.Stop(nil)// Start worker and describe shutdown flow as same as Worker #1...
}(root.Dependent())sig := make(chan os.Signal, 1)
signal.Notify(sig, os.Interrupt)select {
case <-root.AbortRequested():
log.Println("abort: server error")
case s := <-sig:
log.Printf("abort: signal received (%s)", s.String())
}
ctx, cancel := context.WithTimeout(context.Background(), time.Minute)
defer cancel()
err := root.Abort(ctx)
if err != nil {
log.Fatal(err)
}
}
```