@@ -46,6 +46,21 @@ interface MenuItem {
46
46
icon ?: React . ReactNode ;
47
47
}
48
48
49
+ /** ---------- Base URL helpers ---------- */
50
+ /** Normalizes NEXT_PUBLIC_BASE_URL into either "" or "/something" (no trailing slash). */
51
+ const getBasePath = ( ) => {
52
+ const raw = process . env . NEXT_PUBLIC_BASE_URL ?? "" ;
53
+ const trimmed = raw . replace ( / ^ \/ + | \/ + $ / g, "" ) ; // strip leading/trailing slashes
54
+ return trimmed ? `/${ trimmed } ` : "" ;
55
+ } ;
56
+
57
+ /** Joins base path with a relative path like "virtual-keys" or "/virtual-keys" -> "/base/virtual-keys" */
58
+ const withBase = ( relativePath : string ) => {
59
+ const base = getBasePath ( ) ; // "" or "/ui" (no trailing slash)
60
+ const rel = relativePath . replace ( / ^ \/ + / , "" ) ; // drop any leading slash
61
+ return `${ base } /${ rel } ` . replace ( / \/ { 2 , } / g, "/" ) ; // collapse accidental doubles
62
+ } ;
63
+
49
64
const Sidebar2 : React . FC < SidebarProps > = ( { accessToken, userRole, defaultSelectedKey, collapsed = false } ) => {
50
65
const menuItems : MenuItem [ ] = [
51
66
{ key : "1" , page : "api-keys" , label : "Virtual Keys" , icon : < KeyOutlined style = { { fontSize : 18 } } /> } ,
@@ -217,25 +232,31 @@ const Sidebar2: React.FC<SidebarProps> = ({ accessToken, userRole, defaultSelect
217
232
return "1" ;
218
233
} ;
219
234
235
+ // Match Virtual Keys path with base prefix (e.g., "/virtual-keys" or "/ui/virtual-keys")
236
+ const virtualKeysPath = withBase ( "virtual-keys" ) ;
237
+
220
238
const selectedMenuKey =
221
- pathname === "/dashboard/virtual-keys"
239
+ pathname === virtualKeysPath
222
240
? "1"
223
241
: pageParam
224
242
? findMenuItemKey ( pageParam )
225
243
: defaultSelectedKey
226
244
? findMenuItemKey ( defaultSelectedKey )
227
245
: "1" ;
228
246
229
- // Root-only routing helper: always replace everything after the domain
230
- const rootWithPage = ( p : string ) => ( { pathname : "/" , query : { page : p } } ) ;
247
+ // Root-only routing helper: always replace everything after the domain, honoring base path
248
+ const rootWithPage = ( p : string ) => ( {
249
+ pathname : getBasePath ( ) || "/" ,
250
+ query : { page : p } ,
251
+ } ) ;
231
252
232
253
// Convert to AntD Menu items:
233
- // - "Virtual Keys" still routes to / virtual-keys
234
- // - All other items (and children) route to "/?page=<page>"
254
+ // - "Virtual Keys" routes to "/<BASE>/ virtual-keys"
255
+ // - All other items (and children) route to "/<BASE>/ ?page=<page>"
235
256
const antdItems = filteredMenuItems . map ( ( item ) => {
236
257
const isVirtualKeys = item . key === "1" ;
237
258
const label = isVirtualKeys ? (
238
- < Link href = "/ virtual-keys"> Virtual Keys</ Link >
259
+ < Link href = { withBase ( " virtual-keys") } > Virtual Keys</ Link >
239
260
) : (
240
261
< Link href = { rootWithPage ( item . page ) } > { item . label } </ Link >
241
262
) ;
0 commit comments