Small routing primitives for pattern matching and file-path derived routes.
The current public package is intentionally small. It exports:
PathRouterPathRouterUtils
bun i @denshya/routerPathRouter is a lightweight URL pattern matcher.
You add routes to its public routes array and then call match(path).
import { PathRouter } from "@denshya/router"
const router = new PathRouter<string>()
router.routes.push(
{ pattern: "/", filePath: "home", resource: "home" },
{ pattern: "/products/:id", filePath: "product", resource: "product" },
{ pattern: "/404", filePath: "404", resource: "not-found" },
)
router.match("/products/42")
// => {
// route: { pattern: "/products/:id", filePath: "product", resource: "product" },
// params: { id: "42" }
// }match(path) returns either null or a PathRouteMatch<T>:
interface PathRouteMatch<T> {
route: {
pattern: string
filePath: string
resource: T
}
params: Record<string, string>
}PathRouterUtils.patternFromFilePath(...) helps turn file paths into route patterns.
The docs app inside the Tama repository uses it to convert markdown files into routes.
import { PathRouter, PathRouterUtils } from "@denshya/router"
const config = {
root: "/docs",
entry: "index",
}
const fileRouter = new PathRouter<() => Promise<unknown>>()
const filePath = "/docs/learn/index"
const pattern = PathRouterUtils.patternFromFilePath(filePath, config)
fileRouter.routes.push({
filePath,
pattern,
resource: () => import("./learn/index.md"),
})Typical file inputs can map to patterns such as:
indexto//guides/indexto/guides/products/[id]or similar naming after your own preprocessing step to a URL pattern you choose
PathRouterUtils only converts paths based on the root and entry settings.
Any naming convention beyond that remains your application's responsibility.
routesis public on purpose so applications can generate routes however they want.- Matching is based on
URLPattern. - This package does not include navigation state, active link helpers, or browser history integration. Use
@denshya/navigationfor that layer.
Use @denshya/router together with @denshya/navigation when you want:
- route matching in one package
- browser history state in another package
- a modular Tama routing stack without a framework-owned router