Skip to content

Commit 0af9aae

Browse files
committed
Fix UI issue in routing rules page
Present indicative message when external routing service is used or when no routing rules exist in file based routing
1 parent eabda99 commit 0af9aae

File tree

3 files changed

+69
-8
lines changed

3 files changed

+69
-8
lines changed

gateway-ha/src/main/java/io/trino/gateway/ha/resource/GatewayWebAppResource.java

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@
1818
import io.trino.gateway.ha.clustermonitor.ClusterStats;
1919
import io.trino.gateway.ha.config.HaGatewayConfiguration;
2020
import io.trino.gateway.ha.config.ProxyBackendConfiguration;
21+
import io.trino.gateway.ha.config.RoutingRulesConfiguration;
22+
import io.trino.gateway.ha.config.RulesType;
2123
import io.trino.gateway.ha.config.UIConfiguration;
2224
import io.trino.gateway.ha.domain.Result;
2325
import io.trino.gateway.ha.domain.RoutingRule;
@@ -73,6 +75,8 @@ public class GatewayWebAppResource
7375
private final QueryHistoryManager queryHistoryManager;
7476
private final BackendStateManager backendStateManager;
7577
private final ResourceGroupsManager resourceGroupsManager;
78+
private final boolean isRulesEngineEnabled;
79+
private final RulesType ruleType;
7680
// TODO Avoid putting mutable objects in fields
7781
private final UIConfiguration uiConfiguration;
7882
private final RoutingRulesManager routingRulesManager;
@@ -92,6 +96,9 @@ public GatewayWebAppResource(
9296
this.resourceGroupsManager = requireNonNull(resourceGroupsManager, "resourceGroupsManager is null");
9397
this.uiConfiguration = configuration.getUiConfiguration();
9498
this.routingRulesManager = requireNonNull(routingRulesManager, "routingRulesManager is null");
99+
RoutingRulesConfiguration routingRules = configuration.getRoutingRules();
100+
isRulesEngineEnabled = routingRules.isRulesEngineEnabled();
101+
ruleType = routingRules.getRulesType();
95102
}
96103

97104
@POST
@@ -446,6 +453,10 @@ public Response readExactMatchSourceSelector()
446453
public Response getRoutingRules()
447454
throws IOException
448455
{
456+
if (isRulesEngineEnabled && ruleType == RulesType.EXTERNAL) {
457+
return Response.status(Response.Status.NO_CONTENT)
458+
.entity(Result.fail("Routing rules are managed by an external service")).build();
459+
}
449460
List<RoutingRule> routingRulesList = routingRulesManager.getRoutingRules();
450461
return Response.ok(Result.ok(routingRulesList)).build();
451462
}

webapp/src/api/base.ts

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,14 @@ export class ClientApi {
1717
if (res.status === 401 || res.status === 403) {
1818
this.authErrorHandler()
1919
}
20+
else if (res.status === 204) {
21+
// handle the case of Response.Status.NO_CONTENT when External Routing Service is used
22+
return { isExternalRouting: true };
23+
}
24+
else if (res.status >= 500) {
25+
const resJson = await res.json();
26+
this.serverErrorHandler(resJson.msg);
27+
}
2028
else if (res.status !== 200) {
2129
Toast.error({
2230
content: Locale.Error.Network,
@@ -119,6 +127,14 @@ export class ClientApi {
119127
accessStore.updateToken("");
120128
throw new Error(Locale.Auth.Expiration);
121129
}
130+
serverErrorHandler(msg: string): void {
131+
Toast.error({
132+
content: msg,
133+
duration: 5,
134+
theme: "light"
135+
});
136+
throw new Error(msg);
137+
}
122138
}
123139

124140
export const api = new ClientApi();

webapp/src/components/routing-rules.tsx

Lines changed: 42 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { useEffect, useState } from "react";
22
import { routingRulesApi, updateRoutingRulesApi } from "../api/webapp/routing-rules.ts";
33
import { RoutingRulesData } from "../types/routing-rules";
4-
import { Button, Card, Form, Toast } from "@douyinfe/semi-ui";
4+
import { Button, Card, Form, Toast, Spin } from "@douyinfe/semi-ui";
55
import { FormApi } from "@douyinfe/semi-ui/lib/es/form";
66
import { Role, useAccessStore } from "../store";
77
import Locale from "../locales";
@@ -10,20 +10,30 @@ export function RoutingRules() {
1010
const [rules, setRules] = useState<RoutingRulesData[]>([]);
1111
const [editingStates, setEditingStates] = useState<boolean[]>([]);
1212
const [formApis, setFormApis] = useState<(FormApi<any> | null)[]>([]);
13+
const [isExternalRouting, setIsExternalRouting] = useState(false);
14+
const [isLoading, setIsLoading] = useState(true);
1315
const access = useAccessStore();
1416

1517
useEffect(() => {
1618
fetchRoutingRules();
1719
}, []);
1820

1921
const fetchRoutingRules = () => {
22+
setIsLoading(true);
2023
routingRulesApi()
2124
.then(data => {
22-
setRules(data);
23-
setEditingStates(new Array(data.length).fill(false));
24-
setFormApis(new Array(data.length).fill(null));
25+
if (data.isExternalRouting) {
26+
setIsExternalRouting(true);
27+
} else {
28+
setRules(data);
29+
setEditingStates(new Array(data.length).fill(false));
30+
setFormApis(new Array(data.length).fill(null));
31+
setIsExternalRouting(false);
32+
}
2533
}).catch(() => {
2634
Toast.error(Locale.RoutingRules.ErrorFetch);
35+
}).finally(() => {
36+
setIsLoading(false);
2737
});
2838
};
2939

@@ -80,8 +90,32 @@ export function RoutingRules() {
8090
};
8191

8292
return (
83-
<div>
84-
{rules.map((rule, index) => (
93+
<>
94+
{isLoading ? (
95+
<div style={{
96+
display: 'flex',
97+
justifyContent: 'center',
98+
alignItems: 'center',
99+
paddingTop: '40px'
100+
}}>
101+
<Spin size="large" />
102+
</div>
103+
) : rules.length === 0 ? (
104+
<div style={{
105+
display: 'flex',
106+
justifyContent: 'center',
107+
alignItems: 'flex-start',
108+
paddingTop: '40px',
109+
fontSize: '16px',
110+
color: '#666'
111+
}}>
112+
{isExternalRouting ?
113+
"No routing rules available. Routing rules are managed by an external service." :
114+
"No routing rules configured. Add rules to manage query routing."
115+
}
116+
</div>
117+
) : (
118+
rules.map((rule, index) => (
85119
<div key={index} style={{marginBottom: '20px'}}>
86120
<Card
87121
shadows='always'
@@ -170,7 +204,7 @@ export function RoutingRules() {
170204
</Form>
171205
</Card>
172206
</div>
173-
))}
174-
</div>
207+
)))}
208+
</>
175209
);
176210
}

0 commit comments

Comments
 (0)