Skip to content

Commit

Permalink
chore: extract common aws logic across cloud api (#7245)
Browse files Browse the repository at this point in the history
Create base classes for all cloud API resources to share common logic
across AWS platforms

## Checklist

- [x] Title matches [Winglang's style
guide](https://www.winglang.io/contributing/start-here/pull_requests#how-are-pull-request-titles-formatted)
- [x] Description explains motivation and solution
- [x] Tests added (always)
- [x] Docs updated (only required for features)
- [x] Added `pr/e2e-full` label if this feature requires end-to-end
testing

*By submitting this pull request, I confirm that my contribution is made
under the terms of the [Wing Cloud Contribution
License](https://github.com/winglang/wing/blob/main/CONTRIBUTION_LICENSE.md)*.

---------

Signed-off-by: monada-bot[bot] <[email protected]>
Co-authored-by: monada-bot[bot] <[email protected]>
  • Loading branch information
eladb and monadabot authored Jan 19, 2025
1 parent 630c00b commit 023ab50
Show file tree
Hide file tree
Showing 61 changed files with 3,095 additions and 1,359 deletions.
2,768 changes: 2,344 additions & 424 deletions docs/api/04-standard-library/aws/api-reference.md

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion docs/api/04-standard-library/cloud/website.md
Original file line number Diff line number Diff line change
Expand Up @@ -501,7 +501,7 @@ The website's custom domain object.

### IWebsite <a name="IWebsite" id="@winglang/sdk.cloud.IWebsite"></a>

- *Implemented By:* <a href="#@winglang/sdk.cloud.Website">Website</a>, <a href="#@winglang/sdk.cloud.IWebsite">IWebsite</a>
- *Implemented By:* <a href="#@winglang/sdk.aws.Website">Website</a>, <a href="#@winglang/sdk.cloud.Website">Website</a>, <a href="#@winglang/sdk.cloud.IWebsite">IWebsite</a>

Base interface for a website.

Expand Down
2 changes: 1 addition & 1 deletion docs/api/04-standard-library/std/resource.md
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ Operations to lift on the object.

- *Extends:* <a href="#@winglang/sdk.std.ILiftable">ILiftable</a>

- *Implemented By:* <a href="#@winglang/sdk.aws.BucketRef">BucketRef</a>, <a href="#@winglang/sdk.aws.Domain">Domain</a>, <a href="#@winglang/sdk.aws.FunctionRef">FunctionRef</a>, <a href="#@winglang/sdk.aws.QueueRef">QueueRef</a>, <a href="#@winglang/sdk.aws.SecretRef">SecretRef</a>, <a href="#@winglang/sdk.cloud.Api">Api</a>, <a href="#@winglang/sdk.cloud.Bucket">Bucket</a>, <a href="#@winglang/sdk.cloud.Counter">Counter</a>, <a href="#@winglang/sdk.cloud.Domain">Domain</a>, <a href="#@winglang/sdk.cloud.Endpoint">Endpoint</a>, <a href="#@winglang/sdk.cloud.Function">Function</a>, <a href="#@winglang/sdk.cloud.OnDeploy">OnDeploy</a>, <a href="#@winglang/sdk.cloud.Queue">Queue</a>, <a href="#@winglang/sdk.cloud.Schedule">Schedule</a>, <a href="#@winglang/sdk.cloud.Secret">Secret</a>, <a href="#@winglang/sdk.cloud.Service">Service</a>, <a href="#@winglang/sdk.cloud.Topic">Topic</a>, <a href="#@winglang/sdk.cloud.Website">Website</a>, <a href="#@winglang/sdk.sim.Container">Container</a>, <a href="#@winglang/sdk.sim.Policy">Policy</a>, <a href="#@winglang/sdk.sim.Resource">Resource</a>, <a href="#@winglang/sdk.sim.State">State</a>, <a href="#@winglang/sdk.std.AutoIdResource">AutoIdResource</a>, <a href="#@winglang/sdk.std.Resource">Resource</a>, <a href="#@winglang/sdk.std.Test">Test</a>, <a href="#@winglang/sdk.std.TestRunner">TestRunner</a>, <a href="#@winglang/sdk.ui.Button">Button</a>, <a href="#@winglang/sdk.ui.Field">Field</a>, <a href="#@winglang/sdk.ui.FileBrowser">FileBrowser</a>, <a href="#@winglang/sdk.ui.HttpClient">HttpClient</a>, <a href="#@winglang/sdk.ui.Section">Section</a>, <a href="#@winglang/sdk.ui.Table">Table</a>, <a href="#@winglang/sdk.ui.ValueField">ValueField</a>, <a href="#@winglang/sdk.ui.VisualComponent">VisualComponent</a>, <a href="#@winglang/sdk.aws.IAwsFunction">IAwsFunction</a>, <a href="#@winglang/sdk.aws.IAwsInflightHost">IAwsInflightHost</a>, <a href="#@winglang/sdk.cloud.IApiEndpointHandler">IApiEndpointHandler</a>, <a href="#@winglang/sdk.cloud.IBucketEventHandler">IBucketEventHandler</a>, <a href="#@winglang/sdk.cloud.IFunctionHandler">IFunctionHandler</a>, <a href="#@winglang/sdk.cloud.IOnDeployHandler">IOnDeployHandler</a>, <a href="#@winglang/sdk.cloud.IQueueSetConsumerHandler">IQueueSetConsumerHandler</a>, <a href="#@winglang/sdk.cloud.IScheduleOnTickHandler">IScheduleOnTickHandler</a>, <a href="#@winglang/sdk.cloud.IServiceHandler">IServiceHandler</a>, <a href="#@winglang/sdk.cloud.IServiceStopHandler">IServiceStopHandler</a>, <a href="#@winglang/sdk.cloud.ITopicOnMessageHandler">ITopicOnMessageHandler</a>, <a href="#@winglang/sdk.sim.IResourceFactory">IResourceFactory</a>, <a href="#@winglang/sdk.sim.ISimulatorInflightHost">ISimulatorInflightHost</a>, <a href="#@winglang/sdk.sim.ISimulatorResource">ISimulatorResource</a>, <a href="#@winglang/sdk.std.IHostedLiftable">IHostedLiftable</a>, <a href="#@winglang/sdk.std.IInflight">IInflight</a>, <a href="#@winglang/sdk.std.IInflightHost">IInflightHost</a>, <a href="#@winglang/sdk.std.IResource">IResource</a>, <a href="#@winglang/sdk.std.ITestHandler">ITestHandler</a>, <a href="#@winglang/sdk.ui.IButtonHandler">IButtonHandler</a>, <a href="#@winglang/sdk.ui.IFieldHandler">IFieldHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserDeleteHandler">IFileBrowserDeleteHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserGetHandler">IFileBrowserGetHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserListHandler">IFileBrowserListHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserPutHandler">IFileBrowserPutHandler</a>, <a href="#@winglang/sdk.ui.IHttpClientGetApiSpecHandler">IHttpClientGetApiSpecHandler</a>, <a href="#@winglang/sdk.ui.IHttpClientGetUrlHandler">IHttpClientGetUrlHandler</a>, <a href="#@winglang/sdk.ui.ITableScanHandler">ITableScanHandler</a>, <a href="#@winglang/sdk.util.IPredicateHandler">IPredicateHandler</a>
- *Implemented By:* <a href="#@winglang/sdk.aws.Api">Api</a>, <a href="#@winglang/sdk.aws.Bucket">Bucket</a>, <a href="#@winglang/sdk.aws.BucketRef">BucketRef</a>, <a href="#@winglang/sdk.aws.Counter">Counter</a>, <a href="#@winglang/sdk.aws.Domain">Domain</a>, <a href="#@winglang/sdk.aws.Function">Function</a>, <a href="#@winglang/sdk.aws.FunctionRef">FunctionRef</a>, <a href="#@winglang/sdk.aws.Queue">Queue</a>, <a href="#@winglang/sdk.aws.QueueRef">QueueRef</a>, <a href="#@winglang/sdk.aws.Secret">Secret</a>, <a href="#@winglang/sdk.aws.SecretRef">SecretRef</a>, <a href="#@winglang/sdk.aws.Service">Service</a>, <a href="#@winglang/sdk.aws.Topic">Topic</a>, <a href="#@winglang/sdk.aws.Website">Website</a>, <a href="#@winglang/sdk.cloud.Api">Api</a>, <a href="#@winglang/sdk.cloud.Bucket">Bucket</a>, <a href="#@winglang/sdk.cloud.Counter">Counter</a>, <a href="#@winglang/sdk.cloud.Domain">Domain</a>, <a href="#@winglang/sdk.cloud.Endpoint">Endpoint</a>, <a href="#@winglang/sdk.cloud.Function">Function</a>, <a href="#@winglang/sdk.cloud.OnDeploy">OnDeploy</a>, <a href="#@winglang/sdk.cloud.Queue">Queue</a>, <a href="#@winglang/sdk.cloud.Schedule">Schedule</a>, <a href="#@winglang/sdk.cloud.Secret">Secret</a>, <a href="#@winglang/sdk.cloud.Service">Service</a>, <a href="#@winglang/sdk.cloud.Topic">Topic</a>, <a href="#@winglang/sdk.cloud.Website">Website</a>, <a href="#@winglang/sdk.sim.Container">Container</a>, <a href="#@winglang/sdk.sim.Policy">Policy</a>, <a href="#@winglang/sdk.sim.Resource">Resource</a>, <a href="#@winglang/sdk.sim.State">State</a>, <a href="#@winglang/sdk.std.AutoIdResource">AutoIdResource</a>, <a href="#@winglang/sdk.std.Resource">Resource</a>, <a href="#@winglang/sdk.std.Test">Test</a>, <a href="#@winglang/sdk.std.TestRunner">TestRunner</a>, <a href="#@winglang/sdk.ui.Button">Button</a>, <a href="#@winglang/sdk.ui.Field">Field</a>, <a href="#@winglang/sdk.ui.FileBrowser">FileBrowser</a>, <a href="#@winglang/sdk.ui.HttpClient">HttpClient</a>, <a href="#@winglang/sdk.ui.Section">Section</a>, <a href="#@winglang/sdk.ui.Table">Table</a>, <a href="#@winglang/sdk.ui.ValueField">ValueField</a>, <a href="#@winglang/sdk.ui.VisualComponent">VisualComponent</a>, <a href="#@winglang/sdk.aws.IAwsFunction">IAwsFunction</a>, <a href="#@winglang/sdk.aws.IAwsInflightHost">IAwsInflightHost</a>, <a href="#@winglang/sdk.aws.IAwsService">IAwsService</a>, <a href="#@winglang/sdk.cloud.IApiEndpointHandler">IApiEndpointHandler</a>, <a href="#@winglang/sdk.cloud.IBucketEventHandler">IBucketEventHandler</a>, <a href="#@winglang/sdk.cloud.IFunctionHandler">IFunctionHandler</a>, <a href="#@winglang/sdk.cloud.IOnDeployHandler">IOnDeployHandler</a>, <a href="#@winglang/sdk.cloud.IQueueSetConsumerHandler">IQueueSetConsumerHandler</a>, <a href="#@winglang/sdk.cloud.IScheduleOnTickHandler">IScheduleOnTickHandler</a>, <a href="#@winglang/sdk.cloud.IServiceHandler">IServiceHandler</a>, <a href="#@winglang/sdk.cloud.IServiceStopHandler">IServiceStopHandler</a>, <a href="#@winglang/sdk.cloud.ITopicOnMessageHandler">ITopicOnMessageHandler</a>, <a href="#@winglang/sdk.sim.IResourceFactory">IResourceFactory</a>, <a href="#@winglang/sdk.sim.ISimulatorInflightHost">ISimulatorInflightHost</a>, <a href="#@winglang/sdk.sim.ISimulatorResource">ISimulatorResource</a>, <a href="#@winglang/sdk.std.IHostedLiftable">IHostedLiftable</a>, <a href="#@winglang/sdk.std.IInflight">IInflight</a>, <a href="#@winglang/sdk.std.IInflightHost">IInflightHost</a>, <a href="#@winglang/sdk.std.IResource">IResource</a>, <a href="#@winglang/sdk.std.ITestHandler">ITestHandler</a>, <a href="#@winglang/sdk.ui.IButtonHandler">IButtonHandler</a>, <a href="#@winglang/sdk.ui.IFieldHandler">IFieldHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserDeleteHandler">IFileBrowserDeleteHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserGetHandler">IFileBrowserGetHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserListHandler">IFileBrowserListHandler</a>, <a href="#@winglang/sdk.ui.IFileBrowserPutHandler">IFileBrowserPutHandler</a>, <a href="#@winglang/sdk.ui.IHttpClientGetApiSpecHandler">IHttpClientGetApiSpecHandler</a>, <a href="#@winglang/sdk.ui.IHttpClientGetUrlHandler">IHttpClientGetUrlHandler</a>, <a href="#@winglang/sdk.ui.ITableScanHandler">ITableScanHandler</a>, <a href="#@winglang/sdk.util.IPredicateHandler">IPredicateHandler</a>

A liftable object that needs to be registered on the host as part of the lifting process.

Expand Down
1 change: 0 additions & 1 deletion packages/@winglang/platform-awscdk/src/api.inflight.ts

This file was deleted.

31 changes: 3 additions & 28 deletions packages/@winglang/platform-awscdk/src/api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,10 @@ import {
import { CfnPermission } from "aws-cdk-lib/aws-lambda";
import { Construct } from "constructs";
import { App } from "./app";
import { cloud, core, std } from "@winglang/sdk";
import { cloud, std } from "@winglang/sdk";
import {
ApiEndpointHandler,
IAwsApi,
Api as AwsApi,
STAGE_NAME,
} from "@winglang/sdk/lib/shared-aws/api";
import { createApiDefaultResponse } from "@winglang/sdk/lib/shared-aws/api.default";
Expand All @@ -21,15 +21,7 @@ import { isAwsCdkFunction } from "./function";
/**
* AWS Implementation of `cloud.Api`.
*/
export class Api extends cloud.Api implements IAwsApi {
/** @internal */
public static _toInflightType(): string {
return core.InflightClient.forType(
__filename.replace("api", "api.inflight"),
"ApiClient"
);
}

export class Api extends AwsApi {
private readonly api: WingRestApi;
private readonly handlers: Record<string, cloud.Function> = {};
private readonly endpoint: cloud.Endpoint;
Expand Down Expand Up @@ -230,23 +222,6 @@ export class Api extends cloud.Api implements IAwsApi {
return handler;
}

/** @internal */
public onLift(host: std.IInflightHost, ops: string[]): void {
host.addEnvironment(this.urlEnvName(), this.url);
super.onLift(host, ops);
}

/** @internal */
public _liftedState(): Record<string, string> {
return {
$url: `process.env["${this.urlEnvName()}"]`,
};
}

private urlEnvName(): string {
return `API_${this.node.addr.slice(-8)}`;
}

public get restApiArn(): string {
return this.api.api.arnForExecuteApi();
}
Expand Down
1 change: 0 additions & 1 deletion packages/@winglang/platform-awscdk/src/bucket.inflight.ts

This file was deleted.

65 changes: 3 additions & 62 deletions packages/@winglang/platform-awscdk/src/bucket.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,14 +10,12 @@ import { LambdaDestination } from "aws-cdk-lib/aws-s3-notifications";
import { Construct } from "constructs";
import { App } from "./app";
import { cloud, std } from "@winglang/sdk";
import { calculateBucketPermissions } from "@winglang/sdk/lib/shared-aws/permissions";
import { IAwsBucket } from "@winglang/sdk/lib/shared-aws/bucket";
import { Bucket as AwsBucket } from "@winglang/sdk/lib/shared-aws/bucket";
import {
IAwsCdkFunction,
addPolicyStatements,
isAwsCdkFunction,
} from "./function";
import { LiftMap, lift, InflightClient } from "@winglang/sdk/lib/core";
import { lift } from "@winglang/sdk/lib/core";

const EVENTS = {
[cloud.BucketEventType.DELETE]: EventType.OBJECT_REMOVED,
Expand All @@ -30,15 +28,7 @@ const EVENTS = {
*
* @inflight `@winglang/sdk.cloud.IBucketClient`
*/
export class Bucket extends cloud.Bucket implements IAwsBucket {
/** @internal */
public static _toInflightType(): string {
return InflightClient.forType(
__filename.replace("bucket", "bucket.inflight"),
"BucketClient"
);
}

export class Bucket extends AwsBucket {
private readonly bucket: S3Bucket;
private readonly public: boolean;
private readonly forceDestroy: boolean;
Expand Down Expand Up @@ -116,27 +106,6 @@ export class Bucket extends cloud.Bucket implements IAwsBucket {
return fn;
}

/** @internal */
public get _liftMap(): LiftMap {
return {
[cloud.BucketInflightMethods.DELETE]: [],
[cloud.BucketInflightMethods.GET]: [],
[cloud.BucketInflightMethods.GET_JSON]: [],
[cloud.BucketInflightMethods.LIST]: [],
[cloud.BucketInflightMethods.PUT]: [],
[cloud.BucketInflightMethods.PUT_JSON]: [],
[cloud.BucketInflightMethods.PUBLIC_URL]: [],
[cloud.BucketInflightMethods.EXISTS]: [],
[cloud.BucketInflightMethods.TRY_GET]: [],
[cloud.BucketInflightMethods.TRY_GET_JSON]: [],
[cloud.BucketInflightMethods.TRY_DELETE]: [],
[cloud.BucketInflightMethods.SIGNED_URL]: [],
[cloud.BucketInflightMethods.METADATA]: [],
[cloud.BucketInflightMethods.COPY]: [],
[cloud.BucketInflightMethods.RENAME]: [],
};
}

public onCreate(
inflight: cloud.IBucketEventHandler,
opts?: cloud.BucketOnCreateOptions
Expand Down Expand Up @@ -212,34 +181,6 @@ export class Bucket extends cloud.Bucket implements IAwsBucket {
this.onUpdate(inflight, opts);
}

public onLift(host: std.IInflightHost, ops: string[]): void {
if (!isAwsCdkFunction(host)) {
throw new Error("Expected 'host' to implement IAwsCdkFunction");
}

addPolicyStatements(
host.awscdkFunction,
calculateBucketPermissions(this.bucket.bucketArn, ops)
);

// The bucket name needs to be passed through an environment variable since
// it may not be resolved until deployment time.
host.addEnvironment(this.envName(), this.bucket.bucketName);

super.onLift(host, ops);
}

/** @internal */
public _liftedState(): Record<string, string> {
return {
$bucketName: `process.env["${this.envName()}"]`,
};
}

private envName(): string {
return `BUCKET_NAME_${this.node.addr.slice(-8)}`;
}

public get bucketArn(): string {
return this.bucket.bucketArn;
}
Expand Down
1 change: 0 additions & 1 deletion packages/@winglang/platform-awscdk/src/counter.inflight.ts

This file was deleted.

57 changes: 4 additions & 53 deletions packages/@winglang/platform-awscdk/src/counter.ts
Original file line number Diff line number Diff line change
@@ -1,28 +1,17 @@
import { RemovalPolicy } from "aws-cdk-lib";
import { AttributeType, BillingMode, Table } from "aws-cdk-lib/aws-dynamodb";
import { Construct } from "constructs";
import { cloud, std } from "@winglang/sdk";
import { calculateCounterPermissions } from "@winglang/sdk/lib/shared-aws/permissions";
import { IAwsCounter, COUNTER_HASH_KEY } from "@winglang/sdk/lib/shared-aws/counter";
import { addPolicyStatements, isAwsCdkFunction } from "./function";
import { InflightClient, LiftMap } from "@winglang/sdk/lib/core";
import { cloud } from "@winglang/sdk";
import { Counter as AwsCounter, COUNTER_HASH_KEY } from "@winglang/sdk/lib/shared-aws/counter";

/**
* AWS implementation of `cloud.Counter`.
*
* @inflight `@winglang/sdk.cloud.ICounterClient`
*/
export class Counter extends cloud.Counter implements IAwsCounter {
/** @internal */
public static _toInflightType(): string {
return InflightClient.forType(
__filename.replace("counter", "counter.inflight"),
"CounterClient"
);
}

export class Counter extends AwsCounter {
private readonly table: Table;

constructor(scope: Construct, id: string, props: cloud.CounterProps = {}) {
super(scope, id, props);

Expand All @@ -32,44 +21,6 @@ export class Counter extends cloud.Counter implements IAwsCounter {
removalPolicy: RemovalPolicy.DESTROY,
});
}

/** @internal */
public get _liftMap(): LiftMap {
return {
[cloud.CounterInflightMethods.INC]: [],
[cloud.CounterInflightMethods.DEC]: [],
[cloud.CounterInflightMethods.PEEK]: [],
[cloud.CounterInflightMethods.SET]: [],
};
}

public onLift(host: std.IInflightHost, ops: string[]): void {
if (!isAwsCdkFunction(host)) {
throw new Error("Expected 'host' to implement 'isAwsCdkFunction' method");
}

addPolicyStatements(
host.awscdkFunction,
calculateCounterPermissions(this.table.tableArn, ops)
);

host.addEnvironment(this.envName(), this.table.tableName);

super.onLift(host, ops);
}

/** @internal */
public _liftedState(): Record<string, string> {
return {
$tableName: `process.env["${this.envName()}"]`,
$initial: `${this.initial}`,
};
}

private envName(): string {
return `DYNAMODB_TABLE_NAME_${this.node.addr.slice(-8)}`;
}

public get dynamoTableArn(): string {
return this.table.tableArn;
}
Expand Down

This file was deleted.

33 changes: 4 additions & 29 deletions packages/@winglang/platform-awscdk/src/endpoint.ts
Original file line number Diff line number Diff line change
@@ -1,20 +1,12 @@
import { CfnOutput } from "aws-cdk-lib";
import { Construct } from "constructs";
import { cloud, std } from "@winglang/sdk";
import { InflightClient } from "@winglang/sdk/lib/core";
import { cloud } from "@winglang/sdk";
import { Endpoint as AwsEndpoint } from "@winglang/sdk/lib/shared-aws/endpoint";
import { CfnOutput } from "aws-cdk-lib";

/**
* AWS implementation of `cloud.Endpoint`.
*/
export class Endpoint extends cloud.Endpoint {
/** @internal */
public static _toInflightType(): string {
return InflightClient.forType(
__filename.replace("endpoint", "endpoint.inflight"),
"EndpointClient"
);
}

export class Endpoint extends AwsEndpoint {
constructor(
scope: Construct,
id: string,
Expand All @@ -27,21 +19,4 @@ export class Endpoint extends cloud.Endpoint {
value: this.url,
});
}

/** @internal */
public onLift(host: std.IInflightHost, ops: string[]): void {
host.addEnvironment(this.urlEnvName(), this.url);
super.onLift(host, ops);
}

/** @internal */
public _liftedState(): Record<string, string> {
return {
$url: `process.env["${this.urlEnvName()}"]`,
};
}

private urlEnvName(): string {
return `ENDPOINT_NAME_${this.node.addr.slice(-8)}`;
}
}

This file was deleted.

Loading

0 comments on commit 023ab50

Please sign in to comment.