@kensio/yulin 1.21.26 → 1.21.27
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/service/eventbridge/bus/sim-event-bus-name.d.ts +4 -0
- package/dist/service/eventbridge/bus/sim-event-bus-name.js +17 -12
- package/dist/service/eventbridge/cfn/bus/sim-cfn-event-bus-creator.js +8 -1
- package/dist/service/eventbridge/cfn/bus/sim-cfn-event-bus-properties.d.ts +5 -0
- package/dist/service/eventbridge/cfn/bus/sim-cfn-event-bus-properties.js +14 -1
- package/dist/service/eventbridge/cfn/rule/sim-cfn-event-rule-creator.js +2 -0
- package/dist/service/eventbridge/cfn/rule/sim-cfn-event-rule-target-delivery.d.ts +15 -0
- package/dist/service/eventbridge/cfn/rule/sim-cfn-event-rule-target-delivery.js +53 -0
- package/dist/service/eventbridge/cfn/rule/sim-cfn-event-rule-targets.d.ts +4 -0
- package/dist/service/eventbridge/cfn/rule/sim-cfn-event-rule-targets.js +7 -3
- package/dist/service/eventbridge/command/authorize/sim-event-bridge-authorizer.d.ts +5 -0
- package/dist/service/eventbridge/command/authorize/sim-event-bridge-authorizer.js +7 -0
- package/dist/service/eventbridge/command/bus/sim-event-bridge-create-event-bus.d.ts +7 -1
- package/dist/service/eventbridge/command/bus/sim-event-bridge-create-event-bus.js +7 -1
- package/dist/service/eventbridge/command/bus/sim-event-bridge-partner-bus.d.ts +24 -0
- package/dist/service/eventbridge/command/bus/sim-event-bridge-partner-bus.js +44 -0
- package/dist/service/eventbridge/command/bus/sim-event-bridge-unsimulated-bus-input.js +0 -5
- package/dist/service/eventbridge/command/put-events/sim-event-bridge-authorized-entries.js +8 -0
- package/dist/service/eventbridge/command/sim-event-bridge-command.types.d.ts +1 -0
- package/dist/service/eventbridge/command/sim-event-bridge-commands.d.ts +6 -0
- package/dist/service/eventbridge/command/sim-event-bridge-commands.js +19 -1
- package/dist/service/eventbridge/command/source/sim-event-bridge-describe-event-source.d.ts +35 -0
- package/dist/service/eventbridge/command/source/sim-event-bridge-describe-event-source.js +46 -0
- package/dist/service/eventbridge/command/source/sim-event-bridge-put-partner-events.d.ts +41 -0
- package/dist/service/eventbridge/command/source/sim-event-bridge-put-partner-events.js +82 -0
- package/dist/service/eventbridge/command/source/source.command.d.ts +59 -0
- package/dist/service/eventbridge/command/source/source.command.js +1 -0
- package/dist/service/eventbridge/command/target/sim-event-bridge-target-commands.js +2 -0
- package/dist/service/eventbridge/command/target/sim-event-bridge-unsimulated-target-input.js +2 -12
- package/dist/service/eventbridge/command/target/target.command.d.ts +8 -5
- package/dist/service/eventbridge/delivery/sim-aws-event-bridge-delivery-targets.d.ts +6 -1
- package/dist/service/eventbridge/delivery/sim-aws-event-bridge-delivery-targets.js +16 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-dead-letter-attributes.d.ts +9 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-dead-letter-attributes.js +47 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-dead-letter-queue.d.ts +24 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-dead-letter-queue.js +28 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-delivery-attempt.d.ts +41 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-delivery-attempt.js +97 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-delivery-queue.js +7 -37
- package/dist/service/eventbridge/delivery/sim-event-bridge-delivery-retries.test-support.d.ts +25 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-delivery-retries.test-support.js +60 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-delivery.d.ts +22 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-failing-targets.test-support.d.ts +23 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-failing-targets.test-support.js +28 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-no-delivery-targets.d.ts +5 -1
- package/dist/service/eventbridge/delivery/sim-event-bridge-no-delivery-targets.js +9 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-queue-message.d.ts +28 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-queue-message.js +45 -0
- package/dist/service/eventbridge/delivery/sim-event-bridge-target-delivery.d.ts +4 -1
- package/dist/service/eventbridge/delivery/sim-event-bridge-target-delivery.js +19 -14
- package/dist/service/eventbridge/index.d.ts +2 -0
- package/dist/service/eventbridge/index.js +2 -0
- package/dist/service/eventbridge/routing/sim-event-bridge-router.js +1 -0
- package/dist/service/eventbridge/sdk/sim-event-bridge-sdk-command-router.js +4 -0
- package/dist/service/eventbridge/sim-event-bridge-inspection.d.ts +10 -0
- package/dist/service/eventbridge/sim-event-bridge-inspection.js +9 -0
- package/dist/service/eventbridge/sim-event-bridge-partners.d.ts +38 -0
- package/dist/service/eventbridge/sim-event-bridge-partners.js +43 -0
- package/dist/service/eventbridge/sim-event-bridge.d.ts +12 -12
- package/dist/service/eventbridge/sim-event-bridge.js +14 -11
- package/dist/service/eventbridge/source/sim-partner-event-source-name.d.ts +28 -0
- package/dist/service/eventbridge/source/sim-partner-event-source-name.js +62 -0
- package/dist/service/eventbridge/source/sim-partner-event-source-store.d.ts +18 -0
- package/dist/service/eventbridge/source/sim-partner-event-source-store.js +29 -0
- package/dist/service/eventbridge/source/sim-partner-event-source.d.ts +46 -0
- package/dist/service/eventbridge/source/sim-partner-event-source.js +43 -0
- package/dist/service/eventbridge/target/sim-event-target-dead-letter-config.d.ts +28 -0
- package/dist/service/eventbridge/target/sim-event-target-dead-letter-config.js +42 -0
- package/dist/service/eventbridge/target/sim-event-target-retry-policy.d.ts +28 -0
- package/dist/service/eventbridge/target/sim-event-target-retry-policy.js +53 -0
- package/dist/service/eventbridge/target/sim-event-target.d.ts +17 -0
- package/dist/service/eventbridge/target/sim-event-target.js +19 -0
- package/docs/services/eventbridge/README.md +223 -6
- package/package.json +1 -1
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import { BackgroundTasks } from "../../../util/background/background.js";
|
|
2
|
+
import { SimClockControl } from "../../../util/clock/sim-clock-control.js";
|
|
3
|
+
import { SimControllableClock } from "../../../util/clock/sim-controllable-clock.js";
|
|
4
|
+
import { SimFixedClock } from "../../../util/clock/sim-clock.js";
|
|
5
|
+
import { SimEventBridge } from "../sim-event-bridge.js";
|
|
6
|
+
import { SimEventBridgeFailingTargets, } from "./sim-event-bridge-failing-targets.test-support.js";
|
|
7
|
+
const startedAt = new Date("2026-10-07T09:00:00.000Z");
|
|
8
|
+
/**
|
|
9
|
+
* A simulated EventBridge whose targets fail as the options say.
|
|
10
|
+
*/
|
|
11
|
+
export function retrySimulation(options) {
|
|
12
|
+
const clock = new SimControllableClock({
|
|
13
|
+
base: new SimFixedClock(startedAt),
|
|
14
|
+
});
|
|
15
|
+
const background = new BackgroundTasks({ clock });
|
|
16
|
+
const targets = new SimEventBridgeFailingTargets(clock, options);
|
|
17
|
+
return {
|
|
18
|
+
eventBridge: new SimEventBridge({ background, deliveryTargets: targets }),
|
|
19
|
+
clock: new SimClockControl({ clock, background }),
|
|
20
|
+
attempts: targets.attempts,
|
|
21
|
+
deadLetters: targets.deadLetters,
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Add a rule with one target carrying the given retry policy and a
|
|
26
|
+
* dead-letter queue, and put one matching event.
|
|
27
|
+
*/
|
|
28
|
+
export async function putOrder(simulation, target) {
|
|
29
|
+
const { eventBridge } = simulation;
|
|
30
|
+
await eventBridge.putRule({
|
|
31
|
+
input: {
|
|
32
|
+
Name: "orders",
|
|
33
|
+
EventPattern: JSON.stringify({ source: ["orders.service"] }),
|
|
34
|
+
},
|
|
35
|
+
});
|
|
36
|
+
await eventBridge.putTargets({
|
|
37
|
+
input: {
|
|
38
|
+
Rule: "orders",
|
|
39
|
+
Targets: [
|
|
40
|
+
{
|
|
41
|
+
Id: "fulfilment",
|
|
42
|
+
Arn: "arn:aws:sqs:us-east-1:888888888888:fulfilment",
|
|
43
|
+
...target,
|
|
44
|
+
},
|
|
45
|
+
],
|
|
46
|
+
},
|
|
47
|
+
});
|
|
48
|
+
await eventBridge.putEvents({
|
|
49
|
+
input: {
|
|
50
|
+
Entries: [
|
|
51
|
+
{
|
|
52
|
+
Source: "orders.service",
|
|
53
|
+
DetailType: "OrderPlaced",
|
|
54
|
+
Detail: JSON.stringify({ orderId: "order-1" }),
|
|
55
|
+
},
|
|
56
|
+
],
|
|
57
|
+
},
|
|
58
|
+
});
|
|
59
|
+
await simulation.clock.advanceBy({ milliseconds: 0 });
|
|
60
|
+
}
|
|
@@ -37,6 +37,28 @@ export interface SimEventBridgeDeliveryTargets {
|
|
|
37
37
|
* EventBridge.
|
|
38
38
|
*/
|
|
39
39
|
deliver(request: SimEventBridgeDeliveryRequest): Promise<void>;
|
|
40
|
+
/**
|
|
41
|
+
* Send an event EventBridge gave up delivering to its target's dead-letter
|
|
42
|
+
* queue, refusing if the queue does not admit EventBridge.
|
|
43
|
+
*/
|
|
44
|
+
deadLetter(request: SimEventBridgeDeadLetterRequest): Promise<void>;
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Which of a target's retry limits ran out, as the dead-letter message's
|
|
48
|
+
* `EXHAUSTED_RETRY_CONDITION` names it.
|
|
49
|
+
*/
|
|
50
|
+
export type SimEventBridgeExhaustedRetryCondition = "MaximumEventAgeInSeconds" | "MaximumRetryAttempts";
|
|
51
|
+
/**
|
|
52
|
+
* One event on its way to a target's dead-letter queue, and why.
|
|
53
|
+
*
|
|
54
|
+
* A failure EventBridge does not retry, such as a target that is missing or
|
|
55
|
+
* refuses EventBridge, carries no exhausted condition.
|
|
56
|
+
*/
|
|
57
|
+
export interface SimEventBridgeDeadLetterRequest {
|
|
58
|
+
readonly delivery: SimEventBridgeDeliveryRequest;
|
|
59
|
+
readonly error: unknown;
|
|
60
|
+
readonly retryAttempts: number;
|
|
61
|
+
readonly exhaustedCondition: SimEventBridgeExhaustedRetryCondition | undefined;
|
|
40
62
|
}
|
|
41
63
|
/**
|
|
42
64
|
* What a target's policy is asked about, as IAM condition values.
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import type { SimClock } from "../../../util/clock/sim-clock.js";
|
|
2
|
+
import type { SimEventBridgeDeadLetterRequest, SimEventBridgeDeliveryTargets } from "./sim-event-bridge-delivery.js";
|
|
3
|
+
/**
|
|
4
|
+
* How a set of failing targets behaves.
|
|
5
|
+
*/
|
|
6
|
+
export interface SimEventBridgeFailingTargetsOptions {
|
|
7
|
+
readonly succeedsOnAttempt?: number;
|
|
8
|
+
readonly error?: Error;
|
|
9
|
+
readonly deadLetterRefused?: boolean;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Targets that fail with an error until a given attempt, and whose
|
|
13
|
+
* dead-letter queue takes or refuses what it is sent, keeping both.
|
|
14
|
+
*/
|
|
15
|
+
export declare class SimEventBridgeFailingTargets implements SimEventBridgeDeliveryTargets {
|
|
16
|
+
private readonly clock;
|
|
17
|
+
private readonly options;
|
|
18
|
+
readonly attempts: Date[];
|
|
19
|
+
readonly deadLetters: SimEventBridgeDeadLetterRequest[];
|
|
20
|
+
constructor(clock: SimClock, options: SimEventBridgeFailingTargetsOptions);
|
|
21
|
+
deliver(): Promise<void>;
|
|
22
|
+
deadLetter(request: SimEventBridgeDeadLetterRequest): Promise<void>;
|
|
23
|
+
}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Targets that fail with an error until a given attempt, and whose
|
|
3
|
+
* dead-letter queue takes or refuses what it is sent, keeping both.
|
|
4
|
+
*/
|
|
5
|
+
export class SimEventBridgeFailingTargets {
|
|
6
|
+
clock;
|
|
7
|
+
options;
|
|
8
|
+
attempts = [];
|
|
9
|
+
deadLetters = [];
|
|
10
|
+
constructor(clock, options) {
|
|
11
|
+
this.clock = clock;
|
|
12
|
+
this.options = options;
|
|
13
|
+
}
|
|
14
|
+
deliver() {
|
|
15
|
+
this.attempts.push(this.clock.now());
|
|
16
|
+
if (this.attempts.length === this.options.succeedsOnAttempt) {
|
|
17
|
+
return Promise.resolve();
|
|
18
|
+
}
|
|
19
|
+
return Promise.reject(this.options.error ?? new Error("fulfilment is unavailable"));
|
|
20
|
+
}
|
|
21
|
+
deadLetter(request) {
|
|
22
|
+
if (this.options.deadLetterRefused === true) {
|
|
23
|
+
return Promise.reject(new Error("dead-letter queue refused"));
|
|
24
|
+
}
|
|
25
|
+
this.deadLetters.push(request);
|
|
26
|
+
return Promise.resolve();
|
|
27
|
+
}
|
|
28
|
+
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { SimEventBridgeDeliveryRequest, SimEventBridgeDeliveryTargets } from "./sim-event-bridge-delivery.js";
|
|
1
|
+
import type { SimEventBridgeDeadLetterRequest, SimEventBridgeDeliveryRequest, SimEventBridgeDeliveryTargets } from "./sim-event-bridge-delivery.js";
|
|
2
2
|
/**
|
|
3
3
|
* The targets of a simulated EventBridge built on its own, which are none.
|
|
4
4
|
*
|
|
@@ -13,4 +13,8 @@ export declare class SimEventBridgeNoDeliveryTargets implements SimEventBridgeDe
|
|
|
13
13
|
* Refuse the delivery, saying why there was nowhere to make it.
|
|
14
14
|
*/
|
|
15
15
|
deliver(request: SimEventBridgeDeliveryRequest): Promise<void>;
|
|
16
|
+
/**
|
|
17
|
+
* Refuse the dead letter, saying why there was nowhere to send it.
|
|
18
|
+
*/
|
|
19
|
+
deadLetter(request: SimEventBridgeDeadLetterRequest): Promise<void>;
|
|
16
20
|
}
|
|
@@ -17,4 +17,13 @@ export class SimEventBridgeNoDeliveryTargets {
|
|
|
17
17
|
`${request.target.arn.value} was not reached. Reach EventBridge ` +
|
|
18
18
|
`through SimAws for a rule that delivers.`));
|
|
19
19
|
}
|
|
20
|
+
/**
|
|
21
|
+
* Refuse the dead letter, saying why there was nowhere to send it.
|
|
22
|
+
*/
|
|
23
|
+
deadLetter(request) {
|
|
24
|
+
return Promise.reject(new SimEventBridgeTargetNotFound(`This simulated EventBridge has no queues to send dead letters to, ` +
|
|
25
|
+
`so the dead-letter queue of target ${request.delivery.target.id} ` +
|
|
26
|
+
`was not reached. Reach EventBridge through SimAws for a ` +
|
|
27
|
+
`dead-letter queue that receives.`));
|
|
28
|
+
}
|
|
20
29
|
}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import type { SimAwsAccountRegionContainer } from "../../aws/sim-aws-account-region-scope.js";
|
|
2
|
+
import { type SimEventBridgeDeliverySource } from "./sim-event-bridge-delivery.js";
|
|
3
|
+
/**
|
|
4
|
+
* One SQS message attribute, as SendMessage takes it.
|
|
5
|
+
*/
|
|
6
|
+
export interface SimEventBridgeStringAttribute {
|
|
7
|
+
readonly DataType: string;
|
|
8
|
+
readonly StringValue: string;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* One message EventBridge sends to a queue, and the queue it is for.
|
|
12
|
+
*/
|
|
13
|
+
export interface SimEventBridgeQueueMessage {
|
|
14
|
+
readonly queueName: string;
|
|
15
|
+
readonly queueArn: string;
|
|
16
|
+
readonly body: string;
|
|
17
|
+
readonly attributes?: Readonly<Record<string, SimEventBridgeStringAttribute>>;
|
|
18
|
+
readonly source: SimEventBridgeDeliverySource;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Send a message to a queue as EventBridge, if the queue admits it for the
|
|
22
|
+
* rule.
|
|
23
|
+
*
|
|
24
|
+
* A target queue and a dead-letter queue are reached the same way. Both are
|
|
25
|
+
* sent to as `events.amazonaws.com`, and both need the queue policy to admit
|
|
26
|
+
* that principal for the rule.
|
|
27
|
+
*/
|
|
28
|
+
export declare function sendEventBridgeQueueMessage(scope: SimAwsAccountRegionContainer, message: SimEventBridgeQueueMessage): Promise<void>;
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { simScopeIamAuthZ } from "../../iam/authorize/sim-iam-region-auth-z.js";
|
|
2
|
+
import { SimSqsServiceSendAuthorizer } from "../../sqs/command/authorize/sim-sqs-service-send-authorizer.js";
|
|
3
|
+
import { SimEventBridgeDeliveryNotPermitted, SimEventBridgeTargetNotFound, } from "../error/sim-event-bridge-delivery.error.js";
|
|
4
|
+
import { simEventBridgeServicePrincipal, } from "./sim-event-bridge-delivery.js";
|
|
5
|
+
/**
|
|
6
|
+
* Send a message to a queue as EventBridge, if the queue admits it for the
|
|
7
|
+
* rule.
|
|
8
|
+
*
|
|
9
|
+
* A target queue and a dead-letter queue are reached the same way. Both are
|
|
10
|
+
* sent to as `events.amazonaws.com`, and both need the queue policy to admit
|
|
11
|
+
* that principal for the rule.
|
|
12
|
+
*/
|
|
13
|
+
export async function sendEventBridgeQueueMessage(scope, message) {
|
|
14
|
+
const { queueArn, source } = message;
|
|
15
|
+
const queue = scope.sqs().findQueue(message.queueName);
|
|
16
|
+
if (queue === undefined) {
|
|
17
|
+
throw new SimEventBridgeTargetNotFound(`${queueArn} is not a simulated SQS queue.`);
|
|
18
|
+
}
|
|
19
|
+
const decision = new SimSqsServiceSendAuthorizer({
|
|
20
|
+
iam: simScopeIamAuthZ(scope),
|
|
21
|
+
}).authorize({
|
|
22
|
+
queue,
|
|
23
|
+
servicePrincipal: simEventBridgeServicePrincipal,
|
|
24
|
+
...source,
|
|
25
|
+
});
|
|
26
|
+
if (decision.isDenied) {
|
|
27
|
+
throw new SimEventBridgeDeliveryNotPermitted(`The queue policy of ${queueArn} does not allow ` +
|
|
28
|
+
`${simEventBridgeServicePrincipal} to send to it for ` +
|
|
29
|
+
`${source.sourceArn}. Grant sqs:SendMessage with the queue's ` +
|
|
30
|
+
`Policy attribute.`);
|
|
31
|
+
}
|
|
32
|
+
// Sent through the ordinary SendMessage path, so a delivered event is the
|
|
33
|
+
// same thing an SDK caller would have sent, and is authorized again on the
|
|
34
|
+
// way in.
|
|
35
|
+
await scope.sqs().sendMessage({
|
|
36
|
+
input: {
|
|
37
|
+
QueueUrl: queue.arn.url,
|
|
38
|
+
MessageBody: message.body,
|
|
39
|
+
MessageAttributes: message.attributes,
|
|
40
|
+
},
|
|
41
|
+
}, {
|
|
42
|
+
caller: { kind: "service", service: simEventBridgeServicePrincipal },
|
|
43
|
+
...source,
|
|
44
|
+
});
|
|
45
|
+
}
|
|
@@ -1,10 +1,12 @@
|
|
|
1
|
+
import type { BackgroundScheduler } from "../../../util/background/background.js";
|
|
1
2
|
import type { SimEventBridgeDeliveryRequest, SimEventBridgeDeliveryTargets } from "./sim-event-bridge-delivery.js";
|
|
2
3
|
import type { SimEventBridgeDeliveryFailure } from "./sim-event-bridge-delivery-failures.js";
|
|
3
4
|
interface SimEventBridgeTargetDeliveryProperties {
|
|
4
5
|
readonly endpoints: SimEventBridgeDeliveryTargets;
|
|
6
|
+
readonly background: BackgroundScheduler;
|
|
5
7
|
}
|
|
6
8
|
/**
|
|
7
|
-
* Makes one delivery and keeps whatever went wrong.
|
|
9
|
+
* Makes one delivery, with its retries, and keeps whatever went wrong.
|
|
8
10
|
*
|
|
9
11
|
* A failure is recorded rather than thrown, because these run as background
|
|
10
12
|
* tasks and one left rejected would fail an unrelated
|
|
@@ -14,6 +16,7 @@ interface SimEventBridgeTargetDeliveryProperties {
|
|
|
14
16
|
*/
|
|
15
17
|
export declare class SimEventBridgeTargetDelivery {
|
|
16
18
|
private readonly endpoints;
|
|
19
|
+
private readonly background;
|
|
17
20
|
private readonly failures;
|
|
18
21
|
constructor(properties: SimEventBridgeTargetDeliveryProperties);
|
|
19
22
|
/**
|
|
@@ -1,6 +1,7 @@
|
|
|
1
|
+
import { SimEventBridgeDeliveryAttempt } from "./sim-event-bridge-delivery-attempt.js";
|
|
1
2
|
import { SimEventBridgeDeliveryFailures } from "./sim-event-bridge-delivery-failures.js";
|
|
2
3
|
/**
|
|
3
|
-
* Makes one delivery and keeps whatever went wrong.
|
|
4
|
+
* Makes one delivery, with its retries, and keeps whatever went wrong.
|
|
4
5
|
*
|
|
5
6
|
* A failure is recorded rather than thrown, because these run as background
|
|
6
7
|
* tasks and one left rejected would fail an unrelated
|
|
@@ -10,9 +11,11 @@ import { SimEventBridgeDeliveryFailures } from "./sim-event-bridge-delivery-fail
|
|
|
10
11
|
*/
|
|
11
12
|
export class SimEventBridgeTargetDelivery {
|
|
12
13
|
endpoints;
|
|
14
|
+
background;
|
|
13
15
|
failures = new SimEventBridgeDeliveryFailures();
|
|
14
16
|
constructor(properties) {
|
|
15
17
|
this.endpoints = properties.endpoints;
|
|
18
|
+
this.background = properties.background;
|
|
16
19
|
}
|
|
17
20
|
/**
|
|
18
21
|
* Every delivery that could not be made.
|
|
@@ -24,18 +27,20 @@ export class SimEventBridgeTargetDelivery {
|
|
|
24
27
|
* Send one event to one target.
|
|
25
28
|
*/
|
|
26
29
|
async deliver(request) {
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
30
|
+
await new SimEventBridgeDeliveryAttempt({
|
|
31
|
+
request,
|
|
32
|
+
endpoints: this.endpoints,
|
|
33
|
+
background: this.background,
|
|
34
|
+
record: (error) => {
|
|
35
|
+
this.failures.record({
|
|
36
|
+
ruleName: request.ruleName,
|
|
37
|
+
ruleArn: request.ruleArn,
|
|
38
|
+
targetId: request.target.id,
|
|
39
|
+
targetArn: request.target.arn.value,
|
|
40
|
+
eventId: request.event.id,
|
|
41
|
+
error,
|
|
42
|
+
});
|
|
43
|
+
},
|
|
44
|
+
}).start();
|
|
40
45
|
}
|
|
41
46
|
}
|
|
@@ -12,4 +12,6 @@ export { SimEventRuleName } from "./rule/sim-event-rule-name.js";
|
|
|
12
12
|
export { SimEventRuleState } from "./rule/sim-event-rule-state.js";
|
|
13
13
|
export { SimEventPattern } from "./pattern/sim-event-pattern.js";
|
|
14
14
|
export type { SimEventBusReceipt } from "./bus/sim-event-bus.js";
|
|
15
|
+
export { partnerEventSourceArn, SimPartnerEventSource, type SimPartnerEventSourceState, } from "./source/sim-partner-event-source.js";
|
|
16
|
+
export { isPartnerEventSourceName, SimPartnerEventSourceName, } from "./source/sim-partner-event-source-name.js";
|
|
15
17
|
export { SimEventBridgeAccessDeniedException, SimEventBridgeError, SimEventBridgeInvalidEventPatternException, SimEventBridgeResourceAlreadyExistsException, SimEventBridgeResourceNotFoundException, SimEventBridgeUnsimulatedInputException, SimEventBridgeValidationException, } from "./error/sim-event-bridge.error.js";
|
|
@@ -10,4 +10,6 @@ export { eventRuleArn } from "./rule/sim-event-rule-arn.js";
|
|
|
10
10
|
export { SimEventRuleName } from "./rule/sim-event-rule-name.js";
|
|
11
11
|
export { SimEventRuleState } from "./rule/sim-event-rule-state.js";
|
|
12
12
|
export { SimEventPattern } from "./pattern/sim-event-pattern.js";
|
|
13
|
+
export { partnerEventSourceArn, SimPartnerEventSource, } from "./source/sim-partner-event-source.js";
|
|
14
|
+
export { isPartnerEventSourceName, SimPartnerEventSourceName, } from "./source/sim-partner-event-source-name.js";
|
|
13
15
|
export { SimEventBridgeAccessDeniedException, SimEventBridgeError, SimEventBridgeInvalidEventPatternException, SimEventBridgeResourceAlreadyExistsException, SimEventBridgeResourceNotFoundException, SimEventBridgeUnsimulatedInputException, SimEventBridgeValidationException, } from "./error/sim-event-bridge.error.js";
|
|
@@ -22,6 +22,10 @@ export class SimEventBridgeSdkCommandRouter {
|
|
|
22
22
|
"ListEventBusesCommand",
|
|
23
23
|
async (command, context) => await simEventBridge.listEventBuses(command, simSdkCallerOptions(context)),
|
|
24
24
|
],
|
|
25
|
+
[
|
|
26
|
+
"DescribeEventSourceCommand",
|
|
27
|
+
async (command, context) => await simEventBridge.describeEventSource(command, simSdkCallerOptions(context)),
|
|
28
|
+
],
|
|
25
29
|
[
|
|
26
30
|
"PutEventsCommand",
|
|
27
31
|
async (command, context) => await simEventBridge.putEvents(command, simSdkCallerOptions(context)),
|
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
import type { SimEventBusStore } from "./bus/sim-event-bus-store.js";
|
|
2
|
+
import type { SimEventBridgeCommands } from "./command/sim-event-bridge-commands.js";
|
|
3
|
+
import type { SimEventBridgeDeliveryFailure } from "./delivery/sim-event-bridge-delivery-failures.js";
|
|
2
4
|
import type { SimEventBusReceipt } from "./bus/sim-event-bus.js";
|
|
3
5
|
import type { SimEventBus } from "./bus/sim-event-bus.js";
|
|
4
6
|
import type { SimEventBridgeEvent } from "./event/sim-event-bridge-event.js";
|
|
@@ -20,6 +22,14 @@ export declare abstract class SimEventBridgeInspection {
|
|
|
20
22
|
protected abstract readonly buses: SimEventBusStore;
|
|
21
23
|
protected abstract readonly rules: SimEventRuleStore;
|
|
22
24
|
protected abstract readonly targets: SimEventTargetStore;
|
|
25
|
+
protected abstract readonly commands: SimEventBridgeCommands;
|
|
26
|
+
/**
|
|
27
|
+
* Every event this scope's rules could not get to a target.
|
|
28
|
+
*
|
|
29
|
+
* Real EventBridge tells the caller nothing about a failed delivery, and
|
|
30
|
+
* neither does this. A target that is unexpectedly empty is explained here.
|
|
31
|
+
*/
|
|
32
|
+
get deliveryFailures(): readonly SimEventBridgeDeliveryFailure[];
|
|
23
33
|
/**
|
|
24
34
|
* Find an event bus by name.
|
|
25
35
|
*
|
|
@@ -10,6 +10,15 @@ import { defaultEventBusName } from "./bus/sim-event-bus-name.js";
|
|
|
10
10
|
* job that happens to live on the same object.
|
|
11
11
|
*/
|
|
12
12
|
export class SimEventBridgeInspection {
|
|
13
|
+
/**
|
|
14
|
+
* Every event this scope's rules could not get to a target.
|
|
15
|
+
*
|
|
16
|
+
* Real EventBridge tells the caller nothing about a failed delivery, and
|
|
17
|
+
* neither does this. A target that is unexpectedly empty is explained here.
|
|
18
|
+
*/
|
|
19
|
+
get deliveryFailures() {
|
|
20
|
+
return this.commands.router.deliveryFailures;
|
|
21
|
+
}
|
|
13
22
|
/**
|
|
14
23
|
* Find an event bus by name.
|
|
15
24
|
*
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import type { BackgroundScheduler } from "../../util/background/background.js";
|
|
2
|
+
import type { SimAwsAccountRegionScope } from "../aws/sim-aws-account-region-scope.js";
|
|
3
|
+
import type { SimPutPartnerEventsCommand, SimPutPartnerEventsCommandOutput } from "./command/source/source.command.js";
|
|
4
|
+
import { SimEventBridgeInspection } from "./sim-event-bridge-inspection.js";
|
|
5
|
+
import { SimPartnerEventSource } from "./source/sim-partner-event-source.js";
|
|
6
|
+
import type { SimPartnerEventSourceStore } from "./source/sim-partner-event-source-store.js";
|
|
7
|
+
/**
|
|
8
|
+
* What a test does as a SaaS partner sending events to a simulated Account.
|
|
9
|
+
*
|
|
10
|
+
* A partner such as Stripe works from its own Account, which is outside the
|
|
11
|
+
* simulation. It creates a partner event source shared with the receiving
|
|
12
|
+
* Account, and puts events onto it. Both are simulator accessors here rather
|
|
13
|
+
* than SDK commands, because the receiving Account's own clients never send
|
|
14
|
+
* either request.
|
|
15
|
+
*/
|
|
16
|
+
export declare abstract class SimEventBridgePartners extends SimEventBridgeInspection {
|
|
17
|
+
protected abstract readonly partnerSources: SimPartnerEventSourceStore;
|
|
18
|
+
protected abstract readonly background: BackgroundScheduler;
|
|
19
|
+
protected abstract readonly accountRegionScope: SimAwsAccountRegionScope;
|
|
20
|
+
/**
|
|
21
|
+
* Share a partner event source with this Account and Region, as the
|
|
22
|
+
* partner's CreatePartnerEventSource does.
|
|
23
|
+
*
|
|
24
|
+
* The source starts pending. Creating a bus with the same `Name` and
|
|
25
|
+
* `EventSourceName` activates it, and that bus then receives what
|
|
26
|
+
* `putPartnerEvents` sends.
|
|
27
|
+
*/
|
|
28
|
+
addPartnerEventSource(name: string): SimPartnerEventSource;
|
|
29
|
+
/**
|
|
30
|
+
* Put events onto partner event buses as their partner would, taking the
|
|
31
|
+
* shape of the partner's PutPartnerEvents request.
|
|
32
|
+
*
|
|
33
|
+
* Each entry's `Source` has to name a source `addPartnerEventSource` shared
|
|
34
|
+
* with this scope. The event goes to the bus of the same name, or nowhere if
|
|
35
|
+
* that bus has not been created yet.
|
|
36
|
+
*/
|
|
37
|
+
putPartnerEvents(command: SimPutPartnerEventsCommand): Promise<SimPutPartnerEventsCommandOutput>;
|
|
38
|
+
}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import { SimEventBridgeInspection } from "./sim-event-bridge-inspection.js";
|
|
2
|
+
import { SimPartnerEventSource } from "./source/sim-partner-event-source.js";
|
|
3
|
+
import { SimPartnerEventSourceName } from "./source/sim-partner-event-source-name.js";
|
|
4
|
+
/**
|
|
5
|
+
* What a test does as a SaaS partner sending events to a simulated Account.
|
|
6
|
+
*
|
|
7
|
+
* A partner such as Stripe works from its own Account, which is outside the
|
|
8
|
+
* simulation. It creates a partner event source shared with the receiving
|
|
9
|
+
* Account, and puts events onto it. Both are simulator accessors here rather
|
|
10
|
+
* than SDK commands, because the receiving Account's own clients never send
|
|
11
|
+
* either request.
|
|
12
|
+
*/
|
|
13
|
+
export class SimEventBridgePartners extends SimEventBridgeInspection {
|
|
14
|
+
/**
|
|
15
|
+
* Share a partner event source with this Account and Region, as the
|
|
16
|
+
* partner's CreatePartnerEventSource does.
|
|
17
|
+
*
|
|
18
|
+
* The source starts pending. Creating a bus with the same `Name` and
|
|
19
|
+
* `EventSourceName` activates it, and that bus then receives what
|
|
20
|
+
* `putPartnerEvents` sends.
|
|
21
|
+
*/
|
|
22
|
+
addPartnerEventSource(name) {
|
|
23
|
+
const source = new SimPartnerEventSource({
|
|
24
|
+
name: SimPartnerEventSourceName.of(name, "Name"),
|
|
25
|
+
accountRegionScope: this.accountRegionScope,
|
|
26
|
+
createdAt: this.background.now(),
|
|
27
|
+
});
|
|
28
|
+
this.partnerSources.add(source);
|
|
29
|
+
return source;
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Put events onto partner event buses as their partner would, taking the
|
|
33
|
+
* shape of the partner's PutPartnerEvents request.
|
|
34
|
+
*
|
|
35
|
+
* Each entry's `Source` has to name a source `addPartnerEventSource` shared
|
|
36
|
+
* with this scope. The event goes to the bus of the same name, or nowhere if
|
|
37
|
+
* that bus has not been created yet.
|
|
38
|
+
*/
|
|
39
|
+
async putPartnerEvents(command) {
|
|
40
|
+
await this.background.sequence();
|
|
41
|
+
return this.commands.putPartnerEvents.handle(command);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
@@ -4,13 +4,14 @@ import type { SimAwsAccountRegionScope } from "../aws/sim-aws-account-region-sco
|
|
|
4
4
|
import type { SimIamInterServiceAuthZ } from "../iam/authorize/sim-iam-inter-service-auth-z.js";
|
|
5
5
|
import { SimEventBusStore } from "./bus/sim-event-bus-store.js";
|
|
6
6
|
import type * as simEventBridgeCommands from "./command/sim-event-bridge-command.types.js";
|
|
7
|
+
import { SimEventBridgeCommands } from "./command/sim-event-bridge-commands.js";
|
|
7
8
|
import type { SimEventBridgeRequestOptions } from "./command/sim-event-bridge-request-options.js";
|
|
8
9
|
import { SimEventRuleStore } from "./rule/sim-event-rule-store.js";
|
|
9
10
|
import { SimEventTargetStore } from "./target/sim-event-target-store.js";
|
|
10
11
|
import type { SimEventBridgeDeliveryTargets } from "./delivery/sim-event-bridge-delivery.js";
|
|
11
|
-
import type { SimEventBridgeDeliveryFailure } from "./delivery/sim-event-bridge-delivery-failures.js";
|
|
12
12
|
import { SimEventBridgeCfnResourceFactory } from "./cfn/sim-event-bridge-cfn-resource-factory.js";
|
|
13
|
-
import {
|
|
13
|
+
import { SimEventBridgePartners } from "./sim-event-bridge-partners.js";
|
|
14
|
+
import { SimPartnerEventSourceStore } from "./source/sim-partner-event-source-store.js";
|
|
14
15
|
interface SimEventBridgeProperties {
|
|
15
16
|
readonly accountRegionScope?: SimAwsAccountRegionScope;
|
|
16
17
|
readonly iam?: SimIamInterServiceAuthZ;
|
|
@@ -36,22 +37,17 @@ interface SimEventBridgeProperties {
|
|
|
36
37
|
* matches nothing is gone. A rule carrying a schedule instead fires on the
|
|
37
38
|
* simulation's own clock, so advancing time is what sends its event.
|
|
38
39
|
*/
|
|
39
|
-
export declare class SimEventBridge extends
|
|
40
|
+
export declare class SimEventBridge extends SimEventBridgePartners {
|
|
40
41
|
protected readonly buses: SimEventBusStore;
|
|
41
42
|
protected readonly rules: SimEventRuleStore;
|
|
42
43
|
protected readonly targets: SimEventTargetStore;
|
|
43
|
-
|
|
44
|
-
|
|
44
|
+
protected readonly partnerSources: SimPartnerEventSourceStore;
|
|
45
|
+
protected readonly commands: SimEventBridgeCommands;
|
|
46
|
+
protected readonly background: BackgroundScheduler;
|
|
47
|
+
protected readonly accountRegionScope: SimAwsAccountRegionScope;
|
|
45
48
|
private readonly sdkRouter;
|
|
46
49
|
private readonly cfnFactory;
|
|
47
50
|
constructor(properties?: SimEventBridgeProperties);
|
|
48
|
-
/**
|
|
49
|
-
* Every event this scope's rules could not get to a target.
|
|
50
|
-
*
|
|
51
|
-
* Real EventBridge tells the caller nothing about a failed delivery, and
|
|
52
|
-
* neither does this. A target that is unexpectedly empty is explained here.
|
|
53
|
-
*/
|
|
54
|
-
get deliveryFailures(): readonly SimEventBridgeDeliveryFailure[];
|
|
55
51
|
/**
|
|
56
52
|
* Handle a CreateEventBus Command from the SDK.
|
|
57
53
|
*/
|
|
@@ -68,6 +64,10 @@ export declare class SimEventBridge extends SimEventBridgeInspection {
|
|
|
68
64
|
* Handle a ListEventBuses Command from the SDK.
|
|
69
65
|
*/
|
|
70
66
|
listEventBuses(command: simEventBridgeCommands.SimListEventBusesCommand, options?: SimEventBridgeRequestOptions): Promise<simEventBridgeCommands.SimListEventBusesCommandOutput>;
|
|
67
|
+
/**
|
|
68
|
+
* Handle a DescribeEventSource Command from the SDK.
|
|
69
|
+
*/
|
|
70
|
+
describeEventSource(command: simEventBridgeCommands.SimDescribeEventSourceCommand, options?: SimEventBridgeRequestOptions): Promise<simEventBridgeCommands.SimDescribeEventSourceCommandOutput>;
|
|
71
71
|
/**
|
|
72
72
|
* Handle a PutEvents Command from the SDK.
|
|
73
73
|
*/
|
|
@@ -8,7 +8,8 @@ import { SimEventRuleStore } from "./rule/sim-event-rule-store.js";
|
|
|
8
8
|
import { SimEventTargetStore } from "./target/sim-event-target-store.js";
|
|
9
9
|
import { SimEventBridgeCfnResourceFactory } from "./cfn/sim-event-bridge-cfn-resource-factory.js";
|
|
10
10
|
import { SimEventBridgeSdkCommandRouter } from "./sdk/sim-event-bridge-sdk-command-router.js";
|
|
11
|
-
import {
|
|
11
|
+
import { SimEventBridgePartners } from "./sim-event-bridge-partners.js";
|
|
12
|
+
import { SimPartnerEventSourceStore } from "./source/sim-partner-event-source-store.js";
|
|
12
13
|
/**
|
|
13
14
|
* Simulated EventBridge. Handles SDK commands. Emulates AWS behaviour and
|
|
14
15
|
* state.
|
|
@@ -22,12 +23,14 @@ import { SimEventBridgeInspection } from "./sim-event-bridge-inspection.js";
|
|
|
22
23
|
* matches nothing is gone. A rule carrying a schedule instead fires on the
|
|
23
24
|
* simulation's own clock, so advancing time is what sends its event.
|
|
24
25
|
*/
|
|
25
|
-
export class SimEventBridge extends
|
|
26
|
+
export class SimEventBridge extends SimEventBridgePartners {
|
|
26
27
|
buses;
|
|
27
28
|
rules = new SimEventRuleStore();
|
|
28
29
|
targets = new SimEventTargetStore();
|
|
30
|
+
partnerSources = new SimPartnerEventSourceStore();
|
|
29
31
|
commands;
|
|
30
32
|
background;
|
|
33
|
+
accountRegionScope;
|
|
31
34
|
sdkRouter = new SimEventBridgeSdkCommandRouter(this);
|
|
32
35
|
cfnFactory = new SimEventBridgeCfnResourceFactory({
|
|
33
36
|
eventBridge: this,
|
|
@@ -37,26 +40,19 @@ export class SimEventBridge extends SimEventBridgeInspection {
|
|
|
37
40
|
const { accountRegionScope = simAwsAccountRegionScopeFactory.make(), background = new BackgroundTasks(), } = properties;
|
|
38
41
|
const iam = simIamInRegion(properties.iam, accountRegionScope.regionName);
|
|
39
42
|
this.background = background;
|
|
43
|
+
this.accountRegionScope = accountRegionScope;
|
|
40
44
|
this.buses = new SimEventBusStore(SimEventBus.default({ accountRegionScope, createdAt: background.now() }));
|
|
41
45
|
this.commands = new SimEventBridgeCommands({
|
|
42
46
|
buses: this.buses,
|
|
43
47
|
rules: this.rules,
|
|
44
48
|
targets: this.targets,
|
|
49
|
+
partnerSources: this.partnerSources,
|
|
45
50
|
deliveryTargets: properties.deliveryTargets,
|
|
46
51
|
iam,
|
|
47
52
|
background,
|
|
48
53
|
accountRegionScope,
|
|
49
54
|
});
|
|
50
55
|
}
|
|
51
|
-
/**
|
|
52
|
-
* Every event this scope's rules could not get to a target.
|
|
53
|
-
*
|
|
54
|
-
* Real EventBridge tells the caller nothing about a failed delivery, and
|
|
55
|
-
* neither does this. A target that is unexpectedly empty is explained here.
|
|
56
|
-
*/
|
|
57
|
-
get deliveryFailures() {
|
|
58
|
-
return this.commands.router.deliveryFailures;
|
|
59
|
-
}
|
|
60
56
|
/**
|
|
61
57
|
* Handle a CreateEventBus Command from the SDK.
|
|
62
58
|
*/
|
|
@@ -85,6 +81,13 @@ export class SimEventBridge extends SimEventBridgeInspection {
|
|
|
85
81
|
await this.background.sequence();
|
|
86
82
|
return this.commands.buses.listEventBuses(command, options);
|
|
87
83
|
}
|
|
84
|
+
/**
|
|
85
|
+
* Handle a DescribeEventSource Command from the SDK.
|
|
86
|
+
*/
|
|
87
|
+
async describeEventSource(command, options) {
|
|
88
|
+
await this.background.sequence();
|
|
89
|
+
return this.commands.eventSources.handle(command, options);
|
|
90
|
+
}
|
|
88
91
|
/**
|
|
89
92
|
* Handle a PutEvents Command from the SDK.
|
|
90
93
|
*/
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Whether a string has the shape of a partner event source name.
|
|
3
|
+
*
|
|
4
|
+
* A partner event bus takes the name of its source, so this is also the one
|
|
5
|
+
* shape of bus name that may carry a `/`.
|
|
6
|
+
*/
|
|
7
|
+
export declare function isPartnerEventSourceName(value: string): boolean;
|
|
8
|
+
/**
|
|
9
|
+
* The name of one partner event source.
|
|
10
|
+
*
|
|
11
|
+
* A SaaS partner names the source when it creates it, in the form
|
|
12
|
+
* `aws.partner/<partner>/<name>`. The receiving Account never chooses the
|
|
13
|
+
* name. It creates a bus under the same one.
|
|
14
|
+
*/
|
|
15
|
+
export declare class SimPartnerEventSourceName {
|
|
16
|
+
readonly value: string;
|
|
17
|
+
private constructor();
|
|
18
|
+
/**
|
|
19
|
+
* Read a partner event source name from request input, refusing one real
|
|
20
|
+
* EventBridge would refuse.
|
|
21
|
+
*/
|
|
22
|
+
static of(value: string, parameterName: string): SimPartnerEventSourceName;
|
|
23
|
+
/**
|
|
24
|
+
* The partner that created the source, which is the segment after
|
|
25
|
+
* `aws.partner`.
|
|
26
|
+
*/
|
|
27
|
+
get partner(): string;
|
|
28
|
+
}
|