Skip to content

Commit 6038e6e

Browse files
committed
feat: base integration for circuit breaker
1 parent a6fe2d9 commit 6038e6e

File tree

2 files changed

+39
-4
lines changed

2 files changed

+39
-4
lines changed

src/handlers/handlerUtils.ts

Lines changed: 38 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -751,19 +751,35 @@ export async function tryTargetsRecursively(
751751
];
752752
// end: merge inherited config with current target config (preference given to current)
753753

754+
const circuitBreakerConfigId = c.get('circuitBreakerConfigId');
755+
if (circuitBreakerConfigId) {
756+
const healthyTargets = (currentTarget.targets || [])
757+
.map((t: any, index: number) => ({
758+
...t,
759+
originalIndex: index,
760+
}))
761+
.filter((t: any) => !t.isClosed);
762+
763+
if (healthyTargets.length) {
764+
currentTarget.targets = healthyTargets;
765+
}
766+
}
767+
754768
let response;
755769

756770
switch (strategyMode) {
757771
case StrategyModes.FALLBACK:
758772
for (const [index, target] of currentTarget.targets.entries()) {
773+
const originalIndex = target.originalIndex || index;
774+
currentJsonPath = `${currentJsonPath}.targets[${originalIndex}]`;
759775
response = await tryTargetsRecursively(
760776
c,
761777
target,
762778
request,
763779
requestHeaders,
764780
fn,
765781
method,
766-
`${currentJsonPath}.targets[${index}]`,
782+
currentJsonPath,
767783
currentInheritedConfig
768784
);
769785
if (response?.headers.get('x-portkey-gateway-exception') === 'true') {
@@ -791,8 +807,9 @@ export async function tryTargetsRecursively(
791807

792808
let randomWeight = Math.random() * totalWeight;
793809
for (const [index, provider] of currentTarget.targets.entries()) {
810+
const originalIndex = provider.originalIndex || index;
794811
if (randomWeight < provider.weight) {
795-
currentJsonPath = currentJsonPath + `.targets[${index}]`;
812+
currentJsonPath = currentJsonPath + `.targets[${originalIndex}]`;
796813
response = await tryTargetsRecursively(
797814
c,
798815
provider,
@@ -836,28 +853,30 @@ export async function tryTargetsRecursively(
836853
throw new RouterError(conditionalRouter.message);
837854
}
838855

856+
const originalIndex = finalTarget.originalIndex || finalTarget.index;
839857
response = await tryTargetsRecursively(
840858
c,
841859
finalTarget,
842860
request,
843861
requestHeaders,
844862
fn,
845863
method,
846-
`${currentJsonPath}.targets[${finalTarget.index}]`,
864+
`${currentJsonPath}.targets[${originalIndex}]`,
847865
currentInheritedConfig
848866
);
849867
break;
850868
}
851869

852870
case StrategyModes.SINGLE:
871+
const originalIndex = currentTarget.targets[0].originalIndex || 0;
853872
response = await tryTargetsRecursively(
854873
c,
855874
currentTarget.targets[0],
856875
request,
857876
requestHeaders,
858877
fn,
859878
method,
860-
`${currentJsonPath}.targets[0]`,
879+
`${currentJsonPath}.targets[${originalIndex}]`,
861880
currentInheritedConfig
862881
);
863882
break;
@@ -873,6 +892,14 @@ export async function tryTargetsRecursively(
873892
currentJsonPath,
874893
method
875894
);
895+
if (circuitBreakerConfigId) {
896+
await c.get('handleCircuitBreakerResponse')(
897+
response,
898+
circuitBreakerConfigId,
899+
currentJsonPath,
900+
c
901+
);
902+
}
876903
} catch (error: any) {
877904
// tryPost always returns a Response.
878905
// TypeError will check for all unhandled exceptions.
@@ -898,6 +925,13 @@ export async function tryTargetsRecursively(
898925
);
899926
} else {
900927
response = error.response;
928+
if (circuitBreakerConfigId) {
929+
await c.get('recordCircuitBreakerFailure')(
930+
env(c),
931+
circuitBreakerConfigId,
932+
currentJsonPath
933+
);
934+
}
901935
}
902936
}
903937
break;

src/types/requestBody.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -197,6 +197,7 @@ export interface Targets {
197197

198198
defaultInputGuardrails?: HookObject[];
199199
defaultOutputGuardrails?: HookObject[];
200+
originalIndex?: number;
200201
}
201202

202203
/**

0 commit comments

Comments
 (0)