Skip to content

Instantly share code, notes, and snippets.

@lucis
Created June 13, 2024 20:19
Show Gist options
  • Save lucis/767a25da176d010572665059c7c7f98a to your computer and use it in GitHub Desktop.
Save lucis/767a25da176d010572665059c7c7f98a to your computer and use it in GitHub Desktop.
Useful for HTMX integration with deco.cx
import { useSection } from "deco/hooks/useSection.ts";
import type { AppContext } from "../apps/site.ts";
import type { SectionProps } from "deco/mod.ts";
import { toFileUrl } from "std/path/mod.ts";
interface Props {
component: string;
props?: Record<string, unknown>;
}
export type ComponentProps<LoaderFunc, ActionFunc = LoaderFunc> = SectionProps<
LoaderFunc,
ActionFunc
>;
const ROOT = toFileUrl(Deno.cwd()).href;
export const useComponent = <T = Record<string, unknown>>(
component: string,
props?: T,
otherProps: { href?: string } = {},
) =>
useSection({
...otherProps,
props: {
props,
component: component.replace(ROOT, ""),
__resolveType: "site/sections/Component.tsx",
},
});
const identity = <T,>(x: T) => x;
export const loader = async (
{ component, props }: Props,
req: Request,
ctx: AppContext,
) => {
const { default: Component, loader, action } = await import(
`${ROOT}${component}`
);
return {
props: await (loader || action || identity)(props, req, ctx),
Component,
};
};
export const action = async (
{ component, props }: Props,
req: Request,
ctx: AppContext,
) => {
const { default: Component, action, loader } = await import(
`${ROOT}${component}`
);
return {
props: await (action || loader || identity)(props, req, ctx),
Component,
};
};
export default function Section(
// deno-lint-ignore no-explicit-any
{ Component, props }: { Component: any; props: any },
) {
return <Component {...props} />;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment