Skip to content

URL construction and templates

UrlBuilder combines a base URL, path substitutions, and a query record. It does not send a request and does not perform general RFC URI-template expansion.

Builder

new UrlBuilder(baseURL: string, urlTemplateStyle?) exposes mutable baseURL and urlTemplateResolver. build(url: string, params?: UrlParams): string resolves both parts; resolveRequestUrl(request: FetchRequest) delegates to build. UrlBuilderCapable requires a urlBuilder. UrlParams.path and .query are optional Record<string, any> values.

combineURLs(baseURL, relativeURL) trims trailing/leading slash runs at the join. Empty relative URL returns the base unchanged; an absolute or protocol-relative second URL overrides the base. isAbsoluteURL recognizes an optional scheme followed by //, not every URI scheme (data: is not classified as absolute by this helper).

Query values go directly into new URLSearchParams(record): arrays become comma-separated strings, objects become their string representation, and null/undefined are not omitted. Pre-normalize values if you need repeated keys or omission. Existing query text is preserved and new parameters append before a fragment, choosing ?, &, or no extra separator after a trailing ?/&.

Template resolvers

Public APIBehavior
UrlTemplateStyle.UriTemplateDefault enum value 0; {id} placeholders.
UrlTemplateStyle.ExpressEnum value 1; :id at the start or after /.
getUrlTemplateResolver(style?)Express only for the Express enum, otherwise the shared URI resolver.
UriTemplateResolver, uriTemplateResolverClass and singleton implementing UrlTemplateResolver.
ExpressUrlTemplateResolver, expressUrlTemplateResolverCorresponding colon-style implementation.
extractPathParams(template)Parameter names in occurrence order, including repetitions.
resolve(template, pathParams?)encodeURIComponent of each value. Without a map/null, leaves template unchanged; with a map, a missing/undefined value throws Error.
urlTemplateRegexResolve(template, regex, params?)Same substitution rule for a caller-supplied capture group naming the key.
urlTemplateRegexExtract(template, regex)Loops through regex.exec; use a global regex so matching progresses.

A present null value is encoded as 'null'; slashes inside values become %2F. UrlResolveInterceptor applies the client's builder to exchange.request.url, then clears request.urlParams to avoid resolving twice. Its name/order constants are listed under interceptors. Missing template parameters fail before network I/O when a map is supplied.

Complete example

ts
import { UrlBuilder, UrlTemplateStyle } from '@ahoo-wang/fetcher';

const urls = new UrlBuilder(
  'https://api.example.com/v1',
  UrlTemplateStyle.UriTemplate,
);
const url = urls.build('/users/{id}?active=true#details', {
  path: { id: 'a/b' },
  query: { page: 2, q: 'hello world' },
});
console.assert(
  url ===
    'https://api.example.com/v1/users/a%2Fb?active=true&page=2&q=hello+world#details',
);

Public symbols and source

SymbolImplementation
UrlParamsurlBuilder.ts:27
UrlBuilderurlBuilder.ts:72
UrlBuilderCapableurlBuilder.ts:166
UrlTemplateStyleurlTemplateResolver.ts:20
getUrlTemplateResolverurlTemplateResolver.ts:63
UrlTemplateResolverurlTemplateResolver.ts:92
urlTemplateRegexResolveurlTemplateResolver.ts:151
urlTemplateRegexExtracturlTemplateResolver.ts:174
UriTemplateResolverurlTemplateResolver.ts:205
uriTemplateResolverurlTemplateResolver.ts:297
ExpressUrlTemplateResolverurlTemplateResolver.ts:316
expressUrlTemplateResolverurlTemplateResolver.ts:397
isAbsoluteURLurls.ts:27
combineURLsurls.ts:49

Package index

Released under the Apache License 2.0.