💿 Open up the app and show all the features💿 Build a little todo list from scratch- normal forms
- ship it, it works and the UX is fine
- iterate to useFetcher to show why you'd bring it in
- useFetcher is the thing that turns your remix app from a "website" to a "web app", if you're into that terminology.
- still just forms!
- progressive enhancement is about two things
- how the app goes from basic functionality to fancy
- progressive enhancement is about two things
- normal forms
- how the developer is able to iterate their code from basic to fancy
View router.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import "./index.css"; | |
import React from "react"; | |
import ReactDOM from "react-dom"; | |
import { | |
DataBrowserRouter, | |
Route, | |
useLoaderData, | |
Form, | |
useNavigation, | |
} from "react-router-dom"; |
View routes
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/routes | |
/__landing.tsx -> (layout: __landing.*) | |
/__landing.index.tsx -> / | |
/__landing.company.tsx -> /company | |
/__landing.company.team.tsx -> /company/team | |
/__landing.company.careers.tsx -> /company/careers | |
/__landing.docs.doc.$.tsx -> /docs/* | |
/__auth.tsx -> (layout: _auth.*) | |
/__auth.login.tsx -> /login | |
/__auth.signup.tsx -> /signup |
View remix-meetup-webapps.md
View pending-link.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
function useIsPendingPathname(to) { | |
let { location } = useTransition(); | |
let { pathname } = useResolvedPath(to); | |
return location?.pathname === pathname; | |
} | |
function useIsSlowTransition(ms = 300) { | |
let transition = useTransition(); | |
let [isSlow, setIsSlow] = useState(false); |
View people.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { useEffect, useRef } from "react"; | |
import { | |
Form, | |
useFetcher, | |
useLoaderData, | |
useTransition, | |
} from "remix"; | |
import { arc } from "~/arc.server"; | |
export async function loader() { |
View twitter.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// hard, buggy, incomplete, slower | |
<button | |
onClick={async () => { | |
setLoading(true); | |
let result = await updateProject({ | |
status: "active" | |
}); | |
setLoading(false); | |
setResult(result); | |
}} |
View action.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
export let action: ActionFunction = async ({ request, params }) => { | |
let session = await requireAuthSession(request); | |
await ensureUserAccount(session.get("auth")); | |
let data = Object.fromEntries(await request.formData()); | |
invariant(typeof data._action === "string", "_action should be string"); | |
switch (data._action) { | |
case Actions.CREATE_TASK: | |
case Actions.UPDATE_TASK_NAME: { |
View index.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import type { LoaderFunction, ActionFunction } from "remix"; | |
import { useLoaderData, useFetcher } from "remix"; | |
import invariant from "tiny-invariant"; | |
import cuid from "cuid"; | |
import React from "react"; | |
import type { Task, User } from "@prisma/client"; | |
import { requireAuthSession } from "~/util/magic-auth"; | |
import { ensureUserAccount } from "~/util/account"; | |
import { placeCaretAtEnd } from "~/components/range"; | |
import { getBacklog } from "~/models/backlog"; |
View server.mjs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { createServer } from "http"; | |
createServer(async (req, res) => { | |
if (req.url === "/app.js") { | |
res.setHeader("Content-Type", "application/javascript; charset=UTF-8"); | |
res.setHeader("Cache-Control", "max-age=10"); | |
res.write(`console.log("lol")`); | |
res.end(); | |
return; | |
} |
View session-stuff.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// root.tsx | |
import { getUserSession, requireUser, logout } from "~/session"; | |
export function loader({ request }) { | |
// use case: know if the user is logged in, no redirect to /login | |
let userSession = await getUserSession(request); | |
let isAuthenticated = userSession.has("userId"); | |
return { isAuthenticated }; | |
} |
NewerOlder