package grpcapi import ( "context" "crypto/sha256" "testing" "galaxy/gateway/internal/session" "connectrpc.com/connect" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" ) func TestExecuteCommandRejectsPayloadHashWithInvalidLength(t *testing.T) { t.Parallel() delegate := &recordingEdgeGatewayService{} server, runGateway := newTestGateway(t, ServerDependencies{ Service: delegate, SessionCache: staticSessionCache{lookupFunc: func(context.Context, string) (session.Record, error) { return newActiveSessionRecord(), nil }}, }) defer runGateway.stop(t) addr := waitForListenAddr(t, server) client := newEdgeClient(t, addr) req := newValidExecuteCommandRequest() req.PayloadHash = []byte("short") _, err := client.ExecuteCommand(context.Background(), connect.NewRequest(req)) require.Error(t, err) assert.Equal(t, connect.CodeInvalidArgument, connect.CodeOf(err)) assert.Equal(t, "payload_hash must be a 32-byte SHA-256 digest", connectErrorMessage(t, err)) assert.Zero(t, delegate.executeCalls) } func TestExecuteCommandRejectsPayloadHashMismatch(t *testing.T) { t.Parallel() delegate := &recordingEdgeGatewayService{} server, runGateway := newTestGateway(t, ServerDependencies{ Service: delegate, SessionCache: staticSessionCache{lookupFunc: func(context.Context, string) (session.Record, error) { return newActiveSessionRecord(), nil }}, }) defer runGateway.stop(t) addr := waitForListenAddr(t, server) client := newEdgeClient(t, addr) req := newValidExecuteCommandRequest() sum := sha256.Sum256([]byte("other")) req.PayloadHash = sum[:] _, err := client.ExecuteCommand(context.Background(), connect.NewRequest(req)) require.Error(t, err) assert.Equal(t, connect.CodeInvalidArgument, connect.CodeOf(err)) assert.Equal(t, "payload_hash does not match payload_bytes", connectErrorMessage(t, err)) assert.Zero(t, delegate.executeCalls) } func TestSubscribeEventsRejectsPayloadHashWithInvalidLength(t *testing.T) { t.Parallel() delegate := &recordingEdgeGatewayService{} server, runGateway := newTestGateway(t, ServerDependencies{ Service: delegate, SessionCache: staticSessionCache{lookupFunc: func(context.Context, string) (session.Record, error) { return newActiveSessionRecord(), nil }}, }) defer runGateway.stop(t) addr := waitForListenAddr(t, server) client := newEdgeClient(t, addr) req := newValidSubscribeEventsRequest() req.PayloadHash = []byte("short") err := subscribeEventsError(t, context.Background(), client, req) require.Error(t, err) assert.Equal(t, connect.CodeInvalidArgument, connect.CodeOf(err)) assert.Equal(t, "payload_hash must be a 32-byte SHA-256 digest", connectErrorMessage(t, err)) assert.Zero(t, delegate.subscribeCalls) } func TestSubscribeEventsRejectsPayloadHashMismatch(t *testing.T) { t.Parallel() delegate := &recordingEdgeGatewayService{} server, runGateway := newTestGateway(t, ServerDependencies{ Service: delegate, SessionCache: staticSessionCache{lookupFunc: func(context.Context, string) (session.Record, error) { return newActiveSessionRecord(), nil }}, }) defer runGateway.stop(t) addr := waitForListenAddr(t, server) client := newEdgeClient(t, addr) req := newValidSubscribeEventsRequest() sum := sha256.Sum256([]byte("other")) req.PayloadHash = sum[:] err := subscribeEventsError(t, context.Background(), client, req) require.Error(t, err) assert.Equal(t, connect.CodeInvalidArgument, connect.CodeOf(err)) assert.Equal(t, "payload_hash does not match payload_bytes", connectErrorMessage(t, err)) assert.Zero(t, delegate.subscribeCalls) }