diff --git a/package-lock.json b/package-lock.json
index 56bd8b2..b2f0afb 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -6,13 +6,14 @@
"packages": {
"": {
"name": "codecause.dev",
- "version": "1.0.1",
+ "version": "1.0.2",
"dependencies": {
+ "@lit-labs/router": "^0.1.4",
"@lit/task": "^1.0.3",
- "@vaadin/router": "^2.0.1",
"lit": "^3.3.2",
"three": "^0.182.0",
"three-stdlib": "^2.36.1",
+ "urlpattern-polyfill": "^10.1.0",
"uuid": "^13.0.0"
},
"devDependencies": {
@@ -31,8 +32,8 @@
"vite-plugin-eslint": "^1.8.1"
},
"engines": {
- "node": ">=20",
- "npm": ">=9.6.3"
+ "node": ">=24",
+ "npm": ">=11.6.2"
}
},
"node_modules/@babel/code-frame": {
@@ -66,6 +67,7 @@
"integrity": "sha512-H3mcG6ZDLTlYfaSNi0iOKkigqMFvkTKlGUYlD8GW7nNOYRrevuA46iTypPyv+06V3fEmvvazfntkBU34L0azAw==",
"dev": true,
"license": "MIT",
+ "peer": true,
"dependencies": {
"@babel/code-frame": "^7.28.6",
"@babel/generator": "^7.28.6",
@@ -2292,6 +2294,15 @@
"@jridgewell/sourcemap-codec": "^1.4.14"
}
},
+ "node_modules/@lit-labs/router": {
+ "version": "0.1.4",
+ "resolved": "https://registry.npmjs.org/@lit-labs/router/-/router-0.1.4.tgz",
+ "integrity": "sha512-xURH6fOPE0MYfXa1nyl+qTIhZRVWkFa2oggTRodKAI2q/HjA2Va7HEKe7fMm8DdnFE+zEI2aUGnStawKpVh3lQ==",
+ "license": "BSD-3-Clause",
+ "dependencies": {
+ "lit": "^2.0.0 || ^3.0.0"
+ }
+ },
"node_modules/@lit-labs/ssr-dom-shim": {
"version": "1.5.1",
"resolved": "https://registry.npmjs.org/@lit-labs/ssr-dom-shim/-/ssr-dom-shim-1.5.1.tgz",
@@ -2770,6 +2781,7 @@
"integrity": "sha512-03ruubjWyOHlmljCVoxSuNDdmfZDzsrrz0P2LeJsOXr+ZwFQ+0yQIwNCwt/GYhV7Z31fgtXJTAEs+FYlEL851g==",
"dev": true,
"license": "MIT",
+ "peer": true,
"dependencies": {
"@types/estree": "*",
"@types/json-schema": "*"
@@ -2875,6 +2887,7 @@
"integrity": "sha512-nm3cvFN9SqZGXjmw5bZ6cGmvJSyJPn0wU9gHAZZHDnZl2wF9PhHv78Xf06E0MaNk4zLVHL8hb2/c32XvyJOLQg==",
"dev": true,
"license": "MIT",
+ "peer": true,
"dependencies": {
"@typescript-eslint/scope-manager": "8.53.1",
"@typescript-eslint/types": "8.53.1",
@@ -3106,36 +3119,6 @@
"dev": true,
"license": "ISC"
},
- "node_modules/@vaadin/router": {
- "version": "2.0.1",
- "resolved": "https://registry.npmjs.org/@vaadin/router/-/router-2.0.1.tgz",
- "integrity": "sha512-Rs3FQhc8CECrigF8dbaQk7Q3+/BXIjUMd5vapMIphW09WdDxZB88yQ1C/WXV08Z2skPqMP+6ooLde6ItjygleQ==",
- "license": "Apache-2.0",
- "dependencies": {
- "@vaadin/vaadin-usage-statistics": "^2.1.3",
- "path-to-regexp": "^6.3.0",
- "type-fest": "^5.2.0"
- }
- },
- "node_modules/@vaadin/vaadin-development-mode-detector": {
- "version": "2.0.7",
- "resolved": "https://registry.npmjs.org/@vaadin/vaadin-development-mode-detector/-/vaadin-development-mode-detector-2.0.7.tgz",
- "integrity": "sha512-9FhVhr0ynSR3X2ao+vaIEttcNU5XfzCbxtmYOV8uIRnUCtNgbvMOIcyGBvntsX9I5kvIP2dV3cFAOG9SILJzEA==",
- "license": "Apache-2.0"
- },
- "node_modules/@vaadin/vaadin-usage-statistics": {
- "version": "2.1.3",
- "resolved": "https://registry.npmjs.org/@vaadin/vaadin-usage-statistics/-/vaadin-usage-statistics-2.1.3.tgz",
- "integrity": "sha512-8r4TNknD7OJQADe3VygeofFR7UNAXZ2/jjBFP5dgI8+2uMfnuGYgbuHivasKr9WSQ64sPej6m8rDoM1uSllXjQ==",
- "hasInstallScript": true,
- "license": "Apache-2.0",
- "dependencies": {
- "@vaadin/vaadin-development-mode-detector": "^2.0.0"
- },
- "engines": {
- "node": "^12.20.0 || ^14.13.1 || >=16.0.0"
- }
- },
"node_modules/@vitejs/plugin-legacy": {
"version": "7.2.1",
"resolved": "https://registry.npmjs.org/@vitejs/plugin-legacy/-/plugin-legacy-7.2.1.tgz",
@@ -3180,6 +3163,7 @@
"integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==",
"dev": true,
"license": "MIT",
+ "peer": true,
"bin": {
"acorn": "bin/acorn"
},
@@ -3360,6 +3344,7 @@
}
],
"license": "MIT",
+ "peer": true,
"dependencies": {
"baseline-browser-mapping": "^2.9.0",
"caniuse-lite": "^1.0.30001759",
@@ -3682,6 +3667,7 @@
"integrity": "sha512-LEyamqS7W5HB3ujJyvi0HQK/dtVINZvd5mAAp9eT5S/ujByGjiZLCzPcHVzuXbpJDJF/cxwHlfceVUDZ2lnSTw==",
"dev": true,
"license": "MIT",
+ "peer": true,
"dependencies": {
"@eslint-community/eslint-utils": "^4.8.0",
"@eslint-community/regexpp": "^4.12.1",
@@ -3742,6 +3728,7 @@
"integrity": "sha512-82GZUjRS0p/jganf6q1rEO25VSoHH0hKPCTrgillPjdI/3bgBhAE1QzHrHTizjpRvy6pGAvKjDJtk2pF9NDq8w==",
"dev": true,
"license": "MIT",
+ "peer": true,
"bin": {
"eslint-config-prettier": "bin/cli.js"
},
@@ -4832,12 +4819,6 @@
"dev": true,
"license": "MIT"
},
- "node_modules/path-to-regexp": {
- "version": "6.3.0",
- "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-6.3.0.tgz",
- "integrity": "sha512-Yhpw4T9C6hPpgPeA28us07OJeqZ5EzQTkbfwuhsUg0c237RomFoETJgmp2sa3F/41gfLE6G5cqcYwznmeEeOlQ==",
- "license": "MIT"
- },
"node_modules/path-type": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz",
@@ -4861,6 +4842,7 @@
"integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==",
"dev": true,
"license": "MIT",
+ "peer": true,
"engines": {
"node": ">=12"
},
@@ -4919,6 +4901,7 @@
"integrity": "sha512-UOnG6LftzbdaHZcKoPFtOcCKztrQ57WkHDeRD9t/PTQtmT0NHSeWWepj6pS0z/N7+08BHFDQVUrfmfMRcZwbMg==",
"dev": true,
"license": "MIT",
+ "peer": true,
"bin": {
"prettier": "bin/prettier.cjs"
},
@@ -5153,6 +5136,7 @@
"deprecated": "This version is no longer supported. Please see https://eslint.org/version-support for other options.",
"dev": true,
"license": "MIT",
+ "peer": true,
"dependencies": {
"@eslint-community/eslint-utils": "^4.2.0",
"@eslint-community/regexpp": "^4.6.1",
@@ -5775,24 +5759,13 @@
"dev": true,
"license": "MIT"
},
- "node_modules/tagged-tag": {
- "version": "1.0.0",
- "resolved": "https://registry.npmjs.org/tagged-tag/-/tagged-tag-1.0.0.tgz",
- "integrity": "sha512-yEFYrVhod+hdNyx7g5Bnkkb0G6si8HJurOoOEgC8B/O0uXLHlaey/65KRv6cuWBNhBgHKAROVpc7QyYqE5gFng==",
- "license": "MIT",
- "engines": {
- "node": ">=20"
- },
- "funding": {
- "url": "https://github.com/sponsors/sindresorhus"
- }
- },
"node_modules/terser": {
"version": "5.46.0",
"resolved": "https://registry.npmjs.org/terser/-/terser-5.46.0.tgz",
"integrity": "sha512-jTwoImyr/QbOWFFso3YoU3ik0jBBDJ6JTOQiy/J2YxVJdZCc+5u7skhNwiOR3FQIygFqVUPHl7qbbxtjW2K3Qg==",
"dev": true,
"license": "BSD-2-Clause",
+ "peer": true,
"dependencies": {
"@jridgewell/source-map": "^0.3.3",
"acorn": "^8.15.0",
@@ -5817,7 +5790,8 @@
"version": "0.182.0",
"resolved": "https://registry.npmjs.org/three/-/three-0.182.0.tgz",
"integrity": "sha512-GbHabT+Irv+ihI1/f5kIIsZ+Ef9Sl5A1Y7imvS5RQjWgtTPfPnZ43JmlYI7NtCRDK9zir20lQpfg8/9Yd02OvQ==",
- "license": "MIT"
+ "license": "MIT",
+ "peer": true
},
"node_modules/three-stdlib": {
"version": "2.36.1",
@@ -5905,27 +5879,13 @@
"node": ">= 0.8.0"
}
},
- "node_modules/type-fest": {
- "version": "5.4.1",
- "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-5.4.1.tgz",
- "integrity": "sha512-xygQcmneDyzsEuKZrFbRMne5HDqMs++aFzefrJTgEIKjQ3rekM+RPfFCVq2Gp1VIDqddoYeppCj4Pcb+RZW0GQ==",
- "license": "(MIT OR CC0-1.0)",
- "dependencies": {
- "tagged-tag": "^1.0.0"
- },
- "engines": {
- "node": ">=20"
- },
- "funding": {
- "url": "https://github.com/sponsors/sindresorhus"
- }
- },
"node_modules/typescript": {
"version": "5.9.3",
"resolved": "https://registry.npmjs.org/typescript/-/typescript-5.9.3.tgz",
"integrity": "sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw==",
"dev": true,
"license": "Apache-2.0",
+ "peer": true,
"bin": {
"tsc": "bin/tsc",
"tsserver": "bin/tsserver"
@@ -6043,6 +6003,12 @@
"punycode": "^2.1.0"
}
},
+ "node_modules/urlpattern-polyfill": {
+ "version": "10.1.0",
+ "resolved": "https://registry.npmjs.org/urlpattern-polyfill/-/urlpattern-polyfill-10.1.0.tgz",
+ "integrity": "sha512-IGjKp/o0NL3Bso1PymYURCJxMPNAf/ILOpendP9f5B6e1rTJgdgiOvgfoT8VxCAdY+Wisb9uhGaJJf3yZ2V9nw==",
+ "license": "MIT"
+ },
"node_modules/uuid": {
"version": "13.0.0",
"resolved": "https://registry.npmjs.org/uuid/-/uuid-13.0.0.tgz",
@@ -6062,6 +6028,7 @@
"integrity": "sha512-w+N7Hifpc3gRjZ63vYBXA56dvvRlNWRczTdmCBBa+CotUzAPf5b7YMdMR/8CQoeYE5LX3W4wj6RYTgonm1b9DA==",
"dev": true,
"license": "MIT",
+ "peer": true,
"dependencies": {
"esbuild": "^0.27.0",
"fdir": "^6.5.0",
diff --git a/package.json b/package.json
index 5713e9f..f097db8 100644
--- a/package.json
+++ b/package.json
@@ -15,11 +15,12 @@
"format": "prettier --write ."
},
"dependencies": {
+ "@lit-labs/router": "^0.1.4",
"@lit/task": "^1.0.3",
- "@vaadin/router": "^2.0.1",
"lit": "^3.3.2",
"three": "^0.182.0",
"three-stdlib": "^2.36.1",
+ "urlpattern-polyfill": "^10.1.0",
"uuid": "^13.0.0"
},
"devDependencies": {
diff --git a/src/app.ts b/src/app.ts
index d2e9db8..28b1db1 100644
--- a/src/app.ts
+++ b/src/app.ts
@@ -1,26 +1,20 @@
import { LitElement, html, css, type TemplateResult } from 'lit';
-import { customElement, query } from 'lit/decorators.js';
-import { Router } from '@vaadin/router';
+import { customElement } from 'lit/decorators.js';
import { routes } from './routes';
import './components/header/header';
import './components/footer/footer';
+import { Router } from '@lit-labs/router';
@customElement('app-root')
export class AppRoot extends LitElement {
- @query('#outlet')
- private _outlet!: HTMLElement | null;
-
- firstUpdated(): void {
- const router = new Router(this._outlet);
- router.setRoutes(routes);
- }
+ private _router = new Router(this, routes);
render(): TemplateResult {
return html`
-
+ ${this._router.outlet()}
`;
diff --git a/src/main.ts b/src/main.ts
index 36c3352..c6a4b34 100644
--- a/src/main.ts
+++ b/src/main.ts
@@ -1 +1,2 @@
+import 'urlpattern-polyfill';
import './app';
diff --git a/src/views/about-view.ts b/src/pages/about.ts
similarity index 95%
rename from src/views/about-view.ts
rename to src/pages/about.ts
index 0019fbb..b9c8736 100644
--- a/src/views/about-view.ts
+++ b/src/pages/about.ts
@@ -1,8 +1,8 @@
import { LitElement, html, css, type TemplateResult } from 'lit';
import { customElement } from 'lit/decorators.js';
-@customElement('about-view')
-export class AboutView extends LitElement {
+@customElement('about-page')
+export class AboutPage extends LitElement {
render(): TemplateResult {
return html`
About Us
@@ -84,6 +84,6 @@ export class AboutView extends LitElement {
declare global {
interface HTMLElementTagNameMap {
- 'about-view': AboutView;
+ 'about-page': AboutPage;
}
}
diff --git a/src/views/home-view.ts b/src/pages/home.ts
similarity index 97%
rename from src/views/home-view.ts
rename to src/pages/home.ts
index e65d998..06c8a6e 100644
--- a/src/views/home-view.ts
+++ b/src/pages/home.ts
@@ -19,8 +19,8 @@ const PERSON_IMAGES: readonly {
{ alt: 'person-4', path: person4, id: '4' },
];
-@customElement('home-view')
-export class HomeView extends LitElement {
+@customElement('home-page')
+export class HomePage extends LitElement {
connectedCallback(): void {
super.connectedCallback();
this.dispatchEvent(
@@ -203,6 +203,6 @@ export class HomeView extends LitElement {
declare global {
interface HTMLElementTagNameMap {
- 'home-view': HomeView;
+ 'home-page': HomePage;
}
}
diff --git a/src/views/not-found-view.ts b/src/pages/not-found.ts
similarity index 93%
rename from src/views/not-found-view.ts
rename to src/pages/not-found.ts
index 21583c3..4274b4e 100644
--- a/src/views/not-found-view.ts
+++ b/src/pages/not-found.ts
@@ -1,8 +1,8 @@
import { LitElement, css, html, type TemplateResult } from 'lit';
import { customElement } from 'lit/decorators.js';
-@customElement('not-found-view')
-export class NotFoundView extends LitElement {
+@customElement('not-found-page')
+export class NotFoundPage extends LitElement {
connectedCallback(): void {
super.connectedCallback();
this.dispatchEvent(
@@ -78,6 +78,6 @@ export class NotFoundView extends LitElement {
declare global {
interface HTMLElementTagNameMap {
- 'not-found-view': NotFoundView;
+ 'not-found-page': NotFoundPage;
}
}
diff --git a/src/views/projects-view.ts b/src/pages/projects.ts
similarity index 97%
rename from src/views/projects-view.ts
rename to src/pages/projects.ts
index 2481e79..cd66a6b 100644
--- a/src/views/projects-view.ts
+++ b/src/pages/projects.ts
@@ -15,8 +15,8 @@ type Repo = {
stargazers_count: number;
};
-@customElement('projects-view')
-export class ProjectsView extends LitElement {
+@customElement('projects-page')
+export class ProjectsPage extends LitElement {
connectedCallback(): void {
super.connectedCallback();
this._githubReposTask.run();
@@ -172,6 +172,6 @@ export class ProjectsView extends LitElement {
declare global {
interface HTMLElementTagNameMap {
- 'projects-view': ProjectsView;
+ 'projects-page': ProjectsPage;
}
}
diff --git a/src/routes.ts b/src/routes.ts
index 46b7de5..dec8bd2 100644
--- a/src/routes.ts
+++ b/src/routes.ts
@@ -1,58 +1,42 @@
-import type {
- ActionResult,
- Route,
- RouteContext,
- Commands,
-} from '@vaadin/router';
import { APP_TITLE } from './utils/constants';
+import { html } from 'lit';
+import type { RouteConfig } from '@lit-labs/router';
-export const routes: Route[] = [
+export const routes: RouteConfig[] = [
{
path: '/',
- async action(
- this: Route,
- _context: RouteContext,
- commands: Commands
- ): Promise {
- await import('./views/home-view');
+ render: () => html``,
+ enter: async (): Promise => {
+ await import('./pages/home.ts');
document.title = `${APP_TITLE} | Inspiring innovation, empowering collaboration, enabling progress, and driving impact through code`;
- return commands.component('home-view');
+ return true;
},
},
{
path: '/about',
- async action(
- this: Route,
- _context: RouteContext,
- commands: Commands
- ): Promise {
- await import('./views/about-view');
+ render: () => html``,
+ enter: async (): Promise => {
+ await import('./pages/about.ts');
document.title = `${APP_TITLE} | About`;
- return commands.component('about-view');
+ return true;
},
},
{
path: '/projects',
- async action(
- this: Route,
- _context: RouteContext,
- commands: Commands
- ): Promise {
- await import('./views/projects-view');
+ render: () => html``,
+ enter: async (): Promise => {
+ await import('./pages/projects.ts');
document.title = `${APP_TITLE} | Projects`;
- return commands.component('projects-view');
+ return true;
},
},
{
- path: '(.*)',
- async action(
- this: Route,
- _context: RouteContext,
- commands: Commands
- ): Promise {
- await import('./views/not-found-view');
+ path: '/*',
+ render: () => html``,
+ enter: async (): Promise => {
+ await import('./pages/not-found.ts');
document.title = `${APP_TITLE} | Page not found`;
- return commands.component('not-found-view');
+ return true;
},
},
];