I got some issues with my solidjs (Vanilla JS) code. I try to build a small three page Website, just to print out some Information. I use vitejs, solidjs and tailwindcss. I was able to build the relevant sections, some reactivity and my desired three sites. All on its own works well. The thing I can't manage is Routing.
My index.html looks for the App.jsx. Within the App.jsx I do the relevant imports, load and display my components and render everything. It looks something like this:
import { render } from "solid-js/web";
import { Router, Route } from "@solidjs/router";
import "./app.css";
const root = document.getElementById("root");
import Header from "./components/Header";
import Footer from "./components/Footer";
import Home from "./pages/Home";
import Impressum from "./pages/Impressum";
import NotFound from "./pages/404";
function App() {
return (
<>
<Header />
<Router>
<Route path="/" component={Home} />
<Route path="/impressum" component={Impressum} />
<Route path="*404" component={NotFound} />
</Router>
<Footer />
</>
);
}
render(() => <App />, root);
In the Header component is a navigation bar with links. I also import A from solidjs/router in it. It looks something like this (I don't show the styles and other functionality which works fine):
import { createSignal, onCleanup, onMount, createEffect } from "solid-js";
import { A } from "@solidjs/router";
//import LinkList from "./LinkList";
import { Collapse, Dropdown, Ripple, initTWE } from "tw-elements";
import logo from "../assets/logo.svg";
[...]
<nav>
<ul>
<li><A href ="/">Home</A></li>
<li><A href ="/impressum">Impressum</A></li>
</ul>
</nav>
Running the dev server gives me the following error:
Uncaught Error: and 'use' router primitives can be only used inside a Route.
I tried different wrappers, asked chatGPT and have been on Google for hours. I can't figure out what is wrong. I'm not very long into programming. Also English isn't my native language...
As the warning states, you can use an A
element or other elements that rely on the router API under a Route component.
The problem is that you have an A
component directly under the Router
component through the Header
component but it should be wrapped by a Route
first. So, you need to move those links under a component that is used for a path.
The idea is that the navigation items are always associated with a route. It is like links can exist inside a page.
import { A, Route, Router } from '@solidjs/router';
import { render } from 'solid-js/web';
function App() {
const Home = () => (
<div>
<ul>
<li><A href='/blog'>Blog</A></li>
<li><A href='/users'>Users</A></li>
</ul>
<div>This is home page!</div>
</div>
);
const Users = () => <div>Users</div>;
const Blog = () => <div>Blog</div>;
const NotFound = () => <div>NotFound</div>;
return (
<Router>
<Route path="/" component={Home} />
<Route path="/users" component={Users} />
<Route path="/blog" component={Blog} />
<Route path="*404" component={NotFound} />
</Router>
);
}
render(() => <App />, document.body);
Alternatively, you can use a layout component:
const Layout: Component<{ children: JSX.Element }> = (props) => {
return (
<div>
<ul>
<li><A href='/'>Home</A></li>
<li><A href='/blog'>Blog</A></li>
<li><A href='/users'>Users</A></li>
</ul>
{props.children}
</div>
);
};
const Home: Component<{}> = () => <Layout><div>This is Home page!</div></Layout>
The router above is intended to be used with server rendered app. If you are going to use it for SPA, make sure you use the hash mode router:
import { HashRouter } from "@solidjs/router";
Otherwise you will have page not found error when you refresh the page when you are on a sub-route.
PS: Solid Router has undergone some major updates, I believe for better SSR support, this is one of the changes that is brought about the latest update.