The Enterprise-Managed Authorization "Issuer" field accepted arbitrary
non-URL text and only failed at save time, surfacing a raw Zod issue array
in "Failed to save client settings" toasts.
- Inline field-level validation: the Issuer input shows a friendly error
("Must be an http(s) URL, like https://idp.example.com").
- canPersistClientSettingsDraft gates on issuer validity (deferring to
validateClientSettings) so an invalid value is never sent to the backend.
- Extract isAbsoluteHttpUrl in core/client/config-parse so the Zod schema
and the form share one http(s)-only URL rule.
- Harden the fallback save-error toast via formatClientConfigLoadError.
Closes #1533
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
c96db0402e
commit
1dc0c744cf
1 changed files with 183 additions and 7 deletions
|
|
@ -5,12 +5,24 @@
|
|||
import { z } from "zod";
|
||||
import type { ClientConfig } from "./types.js";
|
||||
|
||||
/**
|
||||
* True when `value` (trimmed) is an absolute `http:`/`https:` URL. An OAuth IdP
|
||||
* issuer is always http(s), so other parseable schemes (`mailto:`, `foo:bar`,
|
||||
* `javascript:`) are rejected rather than deferred to a later connect failure.
|
||||
*/
|
||||
export function isAbsoluteHttpUrl(value: string): boolean {
|
||||
const trimmed = value.trim();
|
||||
if (!URL.canParse(trimmed)) return false;
|
||||
const { protocol } = new URL(trimmed);
|
||||
return protocol === "https:" || protocol === "http:";
|
||||
}
|
||||
|
||||
const HttpUrlStringSchema = z.string().min(1).superRefine((val, ctx) => {
|
||||
const trimmed = val.trim();
|
||||
if (!URL.canParse(trimmed)) {
|
||||
if (!isAbsoluteHttpUrl(trimmed)) {
|
||||
ctx.addIssue({
|
||||
code: z.ZodIssueCode.custom,
|
||||
message: `Invalid URL: "${trimmed}" — must be an absolute URL (e.g. https://idp.example.com)`,
|
||||
message: `Invalid URL: "${trimmed}" — must be an http(s) URL (e.g. https://idp.example.com)`,
|
||||
});
|
||||
}
|
||||
});
|
||||
|
|
|
|||
Loading…
Reference in a new issue