|
| 1 | +import { describe, it, expect, vi, beforeEach } from "vitest"; |
| 2 | +import type { ResourcesConfig } from "aws-amplify"; |
| 3 | +import type { CredentialsAndIdentityIdProvider, TokenProvider } from "@aws-amplify/core"; |
| 4 | +import { createServerRunner } from "./adapter"; |
| 5 | +import * as adapterCore from "aws-amplify/adapter-core"; |
| 6 | +import cookie from "cookie"; |
| 7 | + |
| 8 | +vi.mock("aws-amplify/adapter-core", () => ({ |
| 9 | + createUserPoolsTokenProvider: vi.fn(), |
| 10 | + createAWSCredentialsAndIdentityIdProvider: vi.fn(), |
| 11 | + runWithAmplifyServerContext: vi.fn(), |
| 12 | + createKeyValueStorageFromCookieStorageAdapter: vi.fn((adapter) => adapter), |
| 13 | +})); |
| 14 | + |
| 15 | +vi.mock("cookie", () => ({ |
| 16 | + default: { |
| 17 | + parse: vi.fn(), |
| 18 | + serialize: vi.fn(), |
| 19 | + }, |
| 20 | +})); |
| 21 | + |
| 22 | +describe("createServerRunner", () => { |
| 23 | + const mockAmplifyConfig: ResourcesConfig = { |
| 24 | + Storage: { |
| 25 | + S3: { |
| 26 | + bucket: "bucket", |
| 27 | + region: "us-east-1", |
| 28 | + }, |
| 29 | + }, |
| 30 | + }; |
| 31 | + |
| 32 | + const mockAuthConfig: ResourcesConfig = { |
| 33 | + ...mockAmplifyConfig, |
| 34 | + Auth: { |
| 35 | + Cognito: { |
| 36 | + identityPoolId: "123", |
| 37 | + userPoolId: "abc", |
| 38 | + userPoolClientId: "def", |
| 39 | + }, |
| 40 | + }, |
| 41 | + } |
| 42 | + const mockParsedConfig = mockAmplifyConfig; |
| 43 | + const mockOperation = vi.fn(); |
| 44 | + const mockResponse = { data: "test-response" }; |
| 45 | + let mockRequest: Request; |
| 46 | + let mockResponseHeaders: Headers; |
| 47 | + |
| 48 | + beforeEach(() => { |
| 49 | + vi.resetAllMocks(); |
| 50 | + mockRequest = new Request("https://example.com"); |
| 51 | + mockResponseHeaders = new Headers(); |
| 52 | + vi.mocked(adapterCore.runWithAmplifyServerContext).mockResolvedValue( |
| 53 | + mockResponse, |
| 54 | + ); |
| 55 | + vi.mocked(cookie.parse).mockReturnValue({}); |
| 56 | + vi.mocked(cookie.serialize).mockReturnValue("cookie=value"); |
| 57 | + }); |
| 58 | + |
| 59 | + it("creates a serverRunner with the provided config", () => { |
| 60 | + const { runWithAmplifyServerContext } = createServerRunner({ |
| 61 | + config: mockAmplifyConfig, |
| 62 | + }); |
| 63 | + expect(runWithAmplifyServerContext).toBeDefined(); |
| 64 | + expect(typeof runWithAmplifyServerContext).toBe("function"); |
| 65 | + }); |
| 66 | + |
| 67 | + it("runs operations with no Auth config", async () => { |
| 68 | + const { runWithAmplifyServerContext } = createServerRunner({ |
| 69 | + config: mockAmplifyConfig, |
| 70 | + }); |
| 71 | + |
| 72 | + const result = await runWithAmplifyServerContext({ |
| 73 | + serverContext: { |
| 74 | + request: mockRequest, |
| 75 | + responseHeaders: mockResponseHeaders, |
| 76 | + }, |
| 77 | + operation: mockOperation, |
| 78 | + }); |
| 79 | + |
| 80 | + expect(adapterCore.runWithAmplifyServerContext).toHaveBeenCalledWith( |
| 81 | + mockParsedConfig, |
| 82 | + {}, |
| 83 | + mockOperation, |
| 84 | + ); |
| 85 | + expect(result).toEqual(mockResponse); |
| 86 | + }); |
| 87 | + |
| 88 | + it("handles Auth config with no cookies", async () => { |
| 89 | + |
| 90 | + const { runWithAmplifyServerContext } = createServerRunner({ |
| 91 | + config: mockAuthConfig, |
| 92 | + }); |
| 93 | + |
| 94 | + const result = await runWithAmplifyServerContext({ |
| 95 | + serverContext: { |
| 96 | + request: mockRequest, |
| 97 | + responseHeaders: mockResponseHeaders, |
| 98 | + }, |
| 99 | + operation: mockOperation, |
| 100 | + }); |
| 101 | + |
| 102 | + expect(adapterCore.createUserPoolsTokenProvider).not.toHaveBeenCalled(); |
| 103 | + expect( |
| 104 | + adapterCore.createAWSCredentialsAndIdentityIdProvider, |
| 105 | + ).not.toHaveBeenCalled(); |
| 106 | + expect(adapterCore.runWithAmplifyServerContext).toHaveBeenCalledWith( |
| 107 | + mockAuthConfig, |
| 108 | + {}, |
| 109 | + mockOperation, |
| 110 | + ); |
| 111 | + expect(result).toEqual(mockResponse); |
| 112 | + }); |
| 113 | + |
| 114 | + it("handles Auth config with cookies", async () => { |
| 115 | + const mockCookies = { "auth-cookie": "value" }; |
| 116 | + vi.mocked(cookie.parse).mockReturnValue(mockCookies); |
| 117 | + |
| 118 | + const mockTokenProvider = { token: "mock-token" }; |
| 119 | + const mockCredentialsProvider = { credentials: "mock-credentials" }; |
| 120 | + |
| 121 | + vi.mocked(adapterCore.createUserPoolsTokenProvider).mockReturnValue( |
| 122 | + mockTokenProvider as unknown as TokenProvider, |
| 123 | + ); |
| 124 | + vi.mocked( |
| 125 | + adapterCore.createAWSCredentialsAndIdentityIdProvider, |
| 126 | + ).mockReturnValue(mockCredentialsProvider as unknown as CredentialsAndIdentityIdProvider); |
| 127 | + |
| 128 | + const mockRequestWithCookies = new Request("https://example.com", { |
| 129 | + headers: { Cookie: "auth-cookie=value" }, |
| 130 | + }); |
| 131 | + |
| 132 | + const { runWithAmplifyServerContext } = createServerRunner({ |
| 133 | + config: mockAuthConfig as ResourcesConfig, |
| 134 | + }); |
| 135 | + |
| 136 | + const result = await runWithAmplifyServerContext({ |
| 137 | + serverContext: { |
| 138 | + request: mockRequestWithCookies, |
| 139 | + responseHeaders: mockResponseHeaders, |
| 140 | + }, |
| 141 | + operation: mockOperation, |
| 142 | + }); |
| 143 | + |
| 144 | + expect(cookie.parse).toHaveBeenCalledWith("auth-cookie=value"); |
| 145 | + expect(adapterCore.createUserPoolsTokenProvider).toHaveBeenCalled(); |
| 146 | + expect( |
| 147 | + adapterCore.createAWSCredentialsAndIdentityIdProvider, |
| 148 | + ).toHaveBeenCalled(); |
| 149 | + |
| 150 | + expect(adapterCore.runWithAmplifyServerContext).toHaveBeenCalledWith( |
| 151 | + mockAuthConfig, |
| 152 | + { |
| 153 | + Auth: { |
| 154 | + tokenProvider: mockTokenProvider, |
| 155 | + credentialsProvider: mockCredentialsProvider, |
| 156 | + }, |
| 157 | + }, |
| 158 | + mockOperation, |
| 159 | + ); |
| 160 | + expect(result).toEqual(mockResponse); |
| 161 | + }); |
| 162 | +}); |
0 commit comments