網頁

2023/11/2

Golang uber Fx ParamTags, ResultTags group tag

Go語言依賴套件uber-go/fxParamTagsResultTag group tag用法。


當依賴參數類型為slice時,可用group tag來標注。


範例環境:

  • Go 1.19


事前要求

參考「Golang uber Fx annotate ParamTags, ResultTags name tag」了解Fx name tag基本用法。


範例

例如下面NewSchedulerService接收slice參數類型[]Scheduler,所以用fx.ParamTags(`group:"scheduler"`)標註參數為"scheduler" group;而依賴的兩個建構式NewCleanupSchedulerNewSyncScheduler則用fx.ResultTags(`group:"scheduler"`)標注回傳結果屬於"scheduler" group。

由於Scheduler為介面,實作分別為CleanupSchedulerSyncScheduler,所以必須將兩者的建構式以fx.As(new(Scheduler))標註回傳結果為Scheduler,如此NewSchedulerService才能從參數[]Scheduler中收到這兩個實例。

main.go

package main

import (
    "fmt"

    "go.uber.org/fx"
)

type Scheduler interface {
    Run()
}

type CleanupScheduler struct {
}

func NewCleanupScheduler() *CleanupScheduler {
    return &CleanupScheduler{}
}

func (sch CleanupScheduler) Run() {
    fmt.Println("start cleanup...")
}

type SyncScheduler struct {
}

func NewSyncScheduler() *SyncScheduler {
    return &SyncScheduler{}
}

func (sch SyncScheduler) Run() {
    fmt.Println("start sync...")
}

func main() {
    fx.New(
        fx.Provide(
            fx.Annotate(
                NewCleanupScheduler,
                fx.As(new(Scheduler)),
                fx.ResultTags(`group:"scheduler"`),
            ),
        ),
        fx.Provide(
            fx.Annotate(
                NewSyncScheduler,
                fx.As(new(Scheduler)),
                fx.ResultTags(`group:"scheduler"`),
            ),
        ),
        fx.Provide(
            fx.Annotate(
                NewSchedulerService,
                fx.ParamTags(`group:"scheduler"`),
            ),
        ),
        fx.Invoke(func(a *SchedulerService) {
            a.Do()
        }),
    ).Run()
}

type SchedulerService struct {
    schedulers []Scheduler
}

func NewSchedulerService(schedulers []Scheduler) *SchedulerService {
    return &SchedulerService{
        schedulers: schedulers,
    }
}

func (svc SchedulerService) Do() {
    for _, sch := range svc.schedulers {
        go sch.Run()
    }
}

github



測試

執行程式後輸出以下:

[Fx] PROVIDE    main.Scheduler[group = "scheduler"] <;= fx.Annotate(main.NewCleanupScheduler(), fx.ResultTags(["group:\"scheduler\""]), fx.As([[main.Scheduler]])
[Fx] PROVIDE    main.Scheduler[group = "scheduler"] <;= fx.Annotate(main.NewSyncScheduler(), fx.ResultTags(["group:\"scheduler\""]), fx.As([[main.Scheduler]])
[Fx] PROVIDE    *main.SchedulerService <;= fx.Annotate(main.NewSchedulerService(), fx.ParamTags(["group:\"scheduler\""])
[Fx] PROVIDE    fx.Lifecycle <;= go.uber.org/fx.New.func1()
[Fx] PROVIDE    fx.Shutdowner <;= go.uber.org/fx.(*App).shutdowner-fm()
[Fx] PROVIDE    fx.DotGraph <;= go.uber.org/fx.(*App).dotGraph-fm()
[Fx] INVOKE             main.main.func1()
[Fx] RUN        provide: fx.Annotate(main.NewCleanupScheduler(), fx.ResultTags(["group:\"scheduler\""]), fx.As([[main.Scheduler]])
[Fx] RUN        provide: fx.Annotate(main.NewSyncScheduler(), fx.ResultTags(["group:\"scheduler\""]), fx.As([[main.Scheduler]])
[Fx] RUN        provide: fx.Annotate(main.NewSchedulerService(), fx.ParamTags(["group:\"scheduler\""])
start cleanup...
start sync...
[Fx] RUNNING


沒有留言:

張貼留言