sanity
Version:
Sanity is a real-time content infrastructure with a scalable, hosted backend featuring a Graph Oriented Query Language (GROQ), asset pipelines and fast edge caches
51 lines (43 loc) • 1.75 kB
text/typescript
import {escapeRegExp} from 'lodash'
import {type NormalizedWorkspace} from './types'
/**
* Recursively creates a matching expression.
* A list over normalized workspaces, like
* ```
* [
* {workspace: {…}, name: 'default', basePath: '/studio/deep/shared/test'},
* {workspace: {…}, name: 'playground', basePath: '/studio/deep/shared/playground'}
* {workspace: {…}, name: 'staging', basePath: '/studio/deep/shared/staging'}
* ]
* ```
* Becomes a Regex like `/^(\/studio(\/deep(\/shared(\/|$))?(\/|$))?(\/|$))?$/i`
* @internal
*/
export function createCommonBasePathRegex(workspaces: NormalizedWorkspace[]): RegExp {
const workspaceSegments = workspaces.map((workspace) =>
// gets the segments from the basePath
workspace.basePath
// removes the leading `/`
.substring(1)
.split('/'),
)
// this common base path is used to check if we should redirect. it's the base
// path that is common between all the workspaces.
const commonBasePath = workspaceSegments.reduce((commonSegments, segments) => {
for (let i = 0; i < commonSegments.length; i++) {
const commonSegment = commonSegments[i]
const segment = segments[i].toLowerCase()
if (commonSegment !== segment) {
return commonSegments.slice(0, i)
}
}
return commonSegments
})
// recursively creates a matching expression
// `/foo/bar/baz` becomes `(\/foo(\/bar(\/baz(\/|$))?(\/|$))?(\/|$))?`
function createCommonBasePathRegexRecursively([first, ...rest]: string[]): string {
if (!first) return ''
return `(\\/${escapeRegExp(first)}${createCommonBasePathRegexRecursively(rest)}(\\/|$))?`
}
return new RegExp(`^${createCommonBasePathRegexRecursively(commonBasePath)}$`, 'i')
}