Skip to content

fix(middleware-sdk-s3-control): do not validate for FIPS in S3 Outposts #3027

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Nov 18, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,31 +1,38 @@
import { getOutpostEndpoint } from "./getOutpostEndpoint";

describe(getOutpostEndpoint.name, () => {
const mockRegion = "region";
const mockDnsSuffix = "mockDnsSuffix";
const mockHostname = `s3-control.${mockRegion}.${mockDnsSuffix}`;
const mockInput = { isCustomEndpoint: false, useFipsEndpoint: false };

it("returns hostname if custom endpoint is set", () => {
const mockHostname = "mock.hostname.com";
expect(getOutpostEndpoint(mockHostname, { ...mockInput, isCustomEndpoint: true })).toStrictEqual(mockHostname);
});

describe("returns outpost endpoint", () => {
it("uses region from hostname if regionOverride if provided", () => {
expect(getOutpostEndpoint(mockHostname, mockInput)).toStrictEqual(`s3-outposts.${mockRegion}.${mockDnsSuffix}`);
});
const mockRegion = "region";
const mockDnsSuffix = "mockDnsSuffix";

const testOutpostEndpoint = (useFipsEndpoint: boolean) => {
const mockHostname = `s3-control${useFipsEndpoint ? "-fips" : ""}.${mockRegion}.${mockDnsSuffix}`;
it("uses region from hostname if regionOverride if provided", () => {
expect(getOutpostEndpoint(mockHostname, { ...mockInput, useFipsEndpoint })).toStrictEqual(
`s3-outposts${useFipsEndpoint ? "-fips" : ""}.${mockRegion}.${mockDnsSuffix}`
);
});

it("uses region from regionOverride if provided", () => {
const mockRegionOverride = "mockRegionOverride";
expect(
getOutpostEndpoint(mockHostname, { ...mockInput, useFipsEndpoint, regionOverride: mockRegionOverride })
).toStrictEqual(`s3-outposts${useFipsEndpoint ? "-fips" : ""}.${mockRegionOverride}.${mockDnsSuffix}`);
});
};

it("uses region from regionOverride if provided", () => {
const mockRegionOverride = "mockRegionOverride";
expect(getOutpostEndpoint(mockHostname, { ...mockInput, regionOverride: mockRegionOverride })).toStrictEqual(
`s3-outposts.${mockRegionOverride}.${mockDnsSuffix}`
);
describe("with FIPS", () => {
testOutpostEndpoint(true);
});

it(`adds suffix "-fips" if useFipsEndpoint is set`, () => {
expect(getOutpostEndpoint(mockHostname, { ...mockInput, useFipsEndpoint: true })).toStrictEqual(
`s3-outposts-fips.${mockRegion}.${mockDnsSuffix}`
);
describe("without FIPS", () => {
testOutpostEndpoint(false);
});
});
});
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
const REGEX_S3CONTROL_HOSTNAME = /^(.+\.)?s3-control[.-]([a-z0-9-]+)\./;
const REGEX_S3CONTROL_HOSTNAME = /^(.+\.)?s3-control(-fips)?[.-]([a-z0-9-]+)\./;

export interface GetOutpostEndpointOptions {
isCustomEndpoint?: boolean;
Expand All @@ -10,15 +10,17 @@ export const getOutpostEndpoint = (
hostname: string,
{ isCustomEndpoint, regionOverride, useFipsEndpoint }: GetOutpostEndpointOptions
): string => {
const [matched, prefix, region] = hostname.match(REGEX_S3CONTROL_HOSTNAME)!;
// hostname prefix will be ignored even if presents
return isCustomEndpoint
? hostname
: [
`s3-outposts${useFipsEndpoint ? "-fips" : ""}`,
regionOverride || region,
hostname.replace(new RegExp(`^${matched}`), ""),
]
.filter((part) => part !== undefined)
.join(".");
if (isCustomEndpoint) {
return hostname;
}

const [matched, prefix, fips, region] = hostname.match(REGEX_S3CONTROL_HOSTNAME)!;
// hostname prefix will be ignored even if it is present
return [
`s3-outposts${useFipsEndpoint ? "-fips" : ""}`,
regionOverride || region,
hostname.replace(new RegExp(`^${matched}`), ""),
]
.filter((part) => part !== undefined)
.join(".");
};
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,7 @@ const validateOutpostsArn = (
clientRegion,
clientSigningRegion: signingRegion,
useFipsEndpoint,
allowFipsRegion: true,
});
validateNoDualstack(useDualstackEndpoint);
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -169,8 +169,8 @@ describe("getProcessArnablesMiddleware", () => {
expect(context).toMatchObject({ signing_service: "s3-outposts", signing_region: "us-gov-east-1" });
});

it("should validate when arn region is fips region", async () => {
expect.assertions(1);
it("should compute hostname for fips region", async () => {
expect.assertions(4);
const clientRegion = "us-gov-east-1";
const hostname = `s3-control.${clientRegion}.amazonaws.com`;
const options = setupPluginOptions({
Expand All @@ -181,36 +181,14 @@ describe("getProcessArnablesMiddleware", () => {
});
const stack = getStack(hostname, options);
const handler = stack.resolve((() => {}) as any, {});
try {
await handler({
input: {
Name: "arn:aws-us-gov:s3-outposts:fips-us-gov-east-1:123456789012:outpost:op-01234567890123456:accesspoint:myaccesspoint",
},
});
} catch (e) {
expect(e.message).toContain("FIPS region is not supported");
}
});

it("should update endpoint, headers and context correctly if client is fips region", async () => {
expect.assertions(4);
const clientRegion = "fip-us-gov-east-1";
const hostname = `s3-control.${clientRegion}.amazonaws.com`;
const options = setupPluginOptions({
region: clientRegion,
useArnRegion: true,
regionInfoProvider: () => Promise.resolve({ hostname, partition: "aws-us-gov" }),
});
const stack = getStack(hostname, options);
const handler = stack.resolve((() => {}) as any, {});
const {
output: { request, context, input },
} = (await handler({
input: {
Name: "arn:aws-us-gov:s3-outposts:us-gov-east-1:123456789012:outpost:op-01234567890123456:accesspoint:myaccesspoint",
},
})) as any;
expect(request.hostname).toBe("s3-outposts.us-gov-east-1.amazonaws.com");
expect(request.hostname).toBe("s3-outposts-fips.us-gov-east-1.amazonaws.com");
expect(request.headers).toMatchObject({ "x-amz-outpost-id": "op-01234567890123456" });
expect(input.AccountId).toBe("123456789012");
expect(context).toMatchObject({ signing_service: "s3-outposts", signing_region: "us-gov-east-1" });
Expand Down Expand Up @@ -391,8 +369,8 @@ describe("getProcessArnablesMiddleware", () => {
expect(context).toMatchObject({ signing_service: "s3-outposts", signing_region: "us-gov-east-1" });
});

it("should validate when arn region is fips region", async () => {
expect.assertions(1);
it("should compute hostname for fips region", async () => {
expect.assertions(4);
const clientRegion = "us-gov-east-1";
const hostname = `s3-control.${clientRegion}.amazonaws.com`;
const options = setupPluginOptions({
Expand All @@ -403,16 +381,17 @@ describe("getProcessArnablesMiddleware", () => {
});
const stack = getStack(hostname, options);
const handler = stack.resolve((() => {}) as any, {});
try {
await handler({
input: {
Bucket:
"arn:aws-us-gov:s3-outposts:fips-us-gov-east-1:123456789012:outpost:op-01234567890123456:bucket:mybucket",
},
});
} catch (e) {
expect(e.message).toContain("FIPS region is not supported");
}
const {
output: { request, context, input },
} = (await handler({
input: {
Bucket: "arn:aws-us-gov:s3-outposts:us-gov-east-1:123456789012:outpost:op-01234567890123456:bucket:mybucket",
},
})) as any;
expect(request.hostname).toBe("s3-outposts-fips.us-gov-east-1.amazonaws.com");
expect(request.headers).toMatchObject({ "x-amz-outpost-id": "op-01234567890123456" });
expect(input.AccountId).toBe("123456789012");
expect(context).toMatchObject({ signing_service: "s3-outposts", signing_region: "us-gov-east-1" });
});

it("should update endpoint, headers and context correctly if client is fips region", async () => {
Expand Down