Skip to content

Commit

Permalink
Merge pull request #1309 from aligent/feature/add-allow-list
Browse files Browse the repository at this point in the history
Add allow list and option to block all requests
  • Loading branch information
TheOrangePuff authored Feb 14, 2024
2 parents 05e2f9b + 92cb3cf commit 448a865
Show file tree
Hide file tree
Showing 2 changed files with 118 additions and 56 deletions.
165 changes: 111 additions & 54 deletions packages/graphql-mesh-server/lib/fargate.ts
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,11 @@ export interface MeshServiceProps {
* Defaults to 3
*/
blockedIpv6Priority?: number;
/**
* If true, block all access to the endpoint. Use in conjunction with allowedIps to block public access
* @default false
*/
blockAll?: boolean;
/**
* List of AWS Managed rules to add to the WAF
*/
Expand All @@ -97,9 +102,14 @@ export interface MeshServiceProps {
*/
rateLimitPriority?: number;
/**
* List of IPv4 addresses that can bypass rate limiting.
* The waf allowed ip rule priority.
* Defaults to 2
*/
allowedIpPriority?: number;
/**
* List of IPv4 addresses that can bypass all WAF block lists.
*/
rateLimitBypassList?: string[];
allowedIps?: string[];
/**
* Pass custom cpu scaling steps
* Default value:
Expand Down Expand Up @@ -253,8 +263,8 @@ export class MeshService extends Construct {
this.service = fargateService.service;
this.loadBalancer = fargateService.loadBalancer;

const rateLimitBypassList = new CfnIPSet(this, "RateLimitBypassList", {
addresses: props.rateLimitBypassList || [],
const allowedIpList = new CfnIPSet(this, "allowList", {
addresses: props.allowedIps || [],
ipAddressVersion: "IPV4",
scope: "REGIONAL",
description: "List of IPs that are whitelisted from rate limiting",
Expand All @@ -274,47 +284,108 @@ export class MeshService extends Construct {
description: "List of IPv6s blocked by WAF",
});

const defaultRules: CfnWebACL.RuleProperty[] = [
{
name: "IPBlockList",
priority: 2 || props.blockedIpPriority,
statement: {
ipSetReferenceStatement: {
arn: blockedIpList.attrArn,
const defaultRules: CfnWebACL.RuleProperty[] = props.blockAll
? [
{
name: "BlockNonAllowedIps",
priority: props.allowedIpPriority || 2,
statement: {
notStatement: {
statement: {
ipSetReferenceStatement: {
arn: allowedIpList.attrArn,
ipSetForwardedIpConfig: {
fallbackBehavior: "MATCH",
headerName: "X-Forwarded-For",
position: "FIRST",
},
},
},
},
},
visibilityConfig: {
cloudWatchMetricsEnabled: true,
metricName: "IPAllowList",
sampledRequestsEnabled: true,
},
action: {
block: {},
},
},
},
visibilityConfig: {
cloudWatchMetricsEnabled: true,
metricName: "IPBlockList",
sampledRequestsEnabled: true,
},
action: {
block: {},
},
},
{
name: "IPv6BlockList",
priority: 3 || props.blockedIpPriority,
statement: {
ipSetReferenceStatement: {
arn: blockedIpv6List.attrArn,
]
: [
{
name: "IPAllowList",
priority: props.allowedIpPriority || 2,
statement: {
ipSetReferenceStatement: {
arn: allowedIpList.attrArn,
ipSetForwardedIpConfig: {
fallbackBehavior: "MATCH",
headerName: "X-Forwarded-For",
position: "FIRST",
},
},
},
visibilityConfig: {
cloudWatchMetricsEnabled: true,
metricName: "IPAllowList",
sampledRequestsEnabled: true,
},
action: {
allow: {},
},
},
},
visibilityConfig: {
cloudWatchMetricsEnabled: true,
metricName: "IPv6BlockList",
sampledRequestsEnabled: true,
},
action: {
block: {},
},
},
];
{
name: "IPBlockList",
priority: props.blockedIpPriority || 3,
statement: {
ipSetReferenceStatement: {
arn: blockedIpList.attrArn,
ipSetForwardedIpConfig: {
fallbackBehavior: "MATCH",
headerName: "X-Forwarded-For",
position: "FIRST",
},
},
},
visibilityConfig: {
cloudWatchMetricsEnabled: true,
metricName: "IPBlockList",
sampledRequestsEnabled: true,
},
action: {
block: {},
},
},
{
name: "IPv6BlockList",
priority: (props.blockedIpPriority || 3) + 1,
statement: {
ipSetReferenceStatement: {
arn: blockedIpv6List.attrArn,
ipSetForwardedIpConfig: {
fallbackBehavior: "MATCH",
headerName: "X-Forwarded-For",
position: "FIRST",
},
},
},
visibilityConfig: {
cloudWatchMetricsEnabled: true,
metricName: "IPv6BlockList",
sampledRequestsEnabled: true,
},
action: {
block: {},
},
},
];

if (props.rateLimit) {
if (props.rateLimit && !props.blockAll) {
defaultRules.push({
name: "RateLimit",
priority: 10 || props.rateLimitPriority,
priority: props.rateLimitPriority || 10,
statement: {
rateBasedStatement: {
aggregateKeyType: "FORWARDED_IP",
Expand All @@ -323,20 +394,6 @@ export class MeshService extends Construct {
fallbackBehavior: "MATCH",
headerName: "X-Forwarded-For",
},
scopeDownStatement: {
notStatement: {
statement: {
ipSetReferenceStatement: {
arn: rateLimitBypassList.attrArn,
ipSetForwardedIpConfig: {
fallbackBehavior: "MATCH",
headerName: "X-Forwarded-For",
position: "FIRST",
},
},
},
},
},
},
},
visibilityConfig: {
Expand Down
9 changes: 7 additions & 2 deletions packages/graphql-mesh-server/lib/graphql-mesh-server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,11 @@ export type MeshHostingProps = {
* Defaults to 3
*/
blockedIpv6Priority?: number;
/**
* If true, block all access to the endpoint. Use in conjunction with allowedIps to block public access
* @default false
*/
blockAll?: boolean;
/**
* List of AWS Managed rules to add to the WAF
*/
Expand All @@ -122,9 +127,9 @@ export type MeshHostingProps = {
*/
rateLimitPriority?: number;
/**
* List of IPv4 addresses that can bypass rate limiting.
* List of IPv4 addresses that can bypass all WAF block lists.
*/
rateLimitBypassList?: string[];
allowedIps?: string[];
/**
* Enable / disable container insights
* Defaults to true
Expand Down

0 comments on commit 448a865

Please sign in to comment.