google / wire: это вариант использования для одноэлементного шаблона?

#go #dependency-injection

#Вперед #внедрение зависимости

Вопрос:

Следующий фрагмент объявляет два инициализатора google / wire, которые имеют общую зависимость. Каков наилучший способ обеспечить создание только одного экземпляра конфигурации?

Я мог бы передать общую зависимость функции InitializeStorageHandler, но это помешало бы назначению DI, если я правильно понимаю.

Конечно, я мог бы также использовать одноэлементный шаблон. Я не уверен, что это «правильный способ» выполнения чего-либо. Существует ли лучшая практика?

 package api

import (
    "../storage"
    "../config"
    "github.com/google/wire"
)

func InitializeServer() (*Server, error) {
    panic(wire.Build(config.NewConfiguration, NewServer))
}

func InitializeStorageHandler() *StorageHandler {
    panic(wire.Build(config.NewConfiguration, storage.NewStorage, storage.NewService, NewStorageHandler))
}
  

Ответ №1:

Конечно, я мог бы также использовать одноэлементный шаблон

Это соответствовало бы wire, как в выпуске 77, в котором упоминается, что «Wire в значительной степени предназначен для предоставления одиночных файлов».

Как обсуждалось в выпуске 21:

На данный момент Wire намеренно не имеет понятия о подкомпонентах.
В беседе с командой Dagger мы обнаружили, что подкомпоненты и области применения вносят изрядную сложность.

Как вы говорите, вы можете получить почти такое же поведение, вернув синглтоны из первого инжектора, который их создает, а затем передать их более поздним инжекторам. Преимущество этого заключается в том, что поток данных становится явным, что для приведенных нами примеров выглядело как чистый выигрыш.
Тем не менее, нам очень любопытно посмотреть, как люди будут использовать Wire в реальных приложениях: если это не масштабируется, нам, возможно, придется вернуться.

После более пристального изучения вашего примера я понял, что сам компонент поддерживает состояние (деталь, о которой я забыл в Dagger). Мое объяснение выше по-прежнему в значительной степени применимо: мы хотим, чтобы состояние было явным.

В таком случае ознакомьтесь с «Как одноэлементный шаблон работает с Golang» от Джефферсона Отони Лима: sync.Once или init() функция может помочь безопасно создать одноэлементный шаблон «На ходу».