// Package cryptocli — Go-клиент crypto-service по UDS. На M1 — заглушка, // возвращает ErrNotImplemented. Реальная реализация — после // генерации gRPC-стабов из proto (когда прокси откроет proto-tooling // и Go-зависимости). package cryptocli import ( "context" "errors" "net" "time" "git.zetit.ru/zuevav/Bridge-and-Join-s/internal/m2mcore" ) // ErrNotImplemented возвращается клиентом до подключения реального gRPC. var ErrNotImplemented = errors.New("cryptocli: не реализовано (ждём gRPC-стабы из proto)") // Client — клиент crypto-service по Unix Domain Socket. type Client struct { socketPath string dialer net.Dialer timeout time.Duration } // Option настраивает Client. type Option func(*Client) // WithTimeout задаёт таймаут на одну операцию. func WithTimeout(t time.Duration) Option { return func(c *Client) { c.timeout = t } } // NewClient создаёт клиента к UDS. На M1 — без реального gRPC. // Используется как заглушка, реализующая m2mcore.CryptoVerifier. func NewClient(socketPath string, opts ...Option) *Client { c := &Client{socketPath: socketPath, timeout: 5 * time.Second} for _, o := range opts { o(c) } return c } // VerifyXMLDSig вызывает CryptoService.VerifyXMLDSig. На M1 — stub. func (c *Client) VerifyXMLDSig(ctx context.Context, _ []byte) (m2mcore.CertInfo, error) { // На M1 проверяем только доступность сокета и возвращаем // ErrNotImplemented. Это позволяет m2m-core логировать «crypto-service // доступен, но криптография ещё не подключена» отдельно от «сокета // нет совсем». dctx, cancel := context.WithTimeout(ctx, c.timeout) defer cancel() conn, err := c.dialer.DialContext(dctx, "unix", c.socketPath) if err != nil { return m2mcore.CertInfo{}, err } _ = conn.Close() return m2mcore.CertInfo{}, ErrNotImplemented } // Ensure Client реализует m2mcore.CryptoVerifier. var _ m2mcore.CryptoVerifier = (*Client)(nil)