Dyrected
Examples & RecipesRecipe Library

Build a field editor directly into a page

Let a signed-in customer edit a complaint draft on their dashboard without rebuilding document state or nested field paths.

This generated recipe is review-ready source material. Use it from the runtime where it appears in the sidebar and search results.

Let a signed-in customer edit a complaint draft on their dashboard without rebuilding document state or nested field paths.

Use this when

  • build a custom field editor in my app
  • edit a dyrected document inside a customer dashboard
  • mount dyrected form state in a customer route
  • edit nested customer complaint fields without the admin page

Dyrected concepts

createDyrectedFormController, DyrectedFormProvider, DyrectedFieldPathProvider, useDyrectedForm, useField

Additional packages: @dyrected/admin, @dyrected/react

Decisions and cautions

Use this recipe only when its runtime matches the project you are documenting or building. Cloud recipes must stay inside the managed content backend boundary. Self-hosted recipes may use the server runtime, database, hooks, and infrastructure you control.

Complete recipe

This is the canonical source compiled and behavior-tested by @dyrected/knowledge.

import {
  DyrectedFieldPathProvider,
  DyrectedFormProvider,
  useDyrectedForm,
  useField,
} from "@dyrected/react";
import { createDyrectedFormController } from "@dyrected/admin/public";

const controller = createDyrectedFormController({
  collection: "customers",
  fields: [
    { name: "fullName", type: "text", label: "Full name" },
    { name: "email", type: "email", label: "Email address" },
    {
      name: "complaintDraft",
      type: "object",
      label: "Complaint draft",
      fields: [
        { name: "orderNumber", type: "text", label: "Order number" },
        { name: "subject", type: "text", label: "Subject" },
        { name: "message", type: "textarea", label: "Complaint message" },
      ],
    },
  ],
  initialValues: {
    fullName: "Amara Okafor",
    email: "[email protected]",
    complaintDraft: {
      orderNumber: "ORD-2048",
      subject: "Damaged package on arrival",
      message: "The shipping box arrived wet and the product inside is scratched.",
    },
  },
});

function CustomerIdentityCard() {
  const fullName = useField("fullName");
  const email = useField("email");

  return (
    <section className="space-y-4">
      <input
        value={String(fullName.value ?? "")}
        onChange={(event) => fullName.setValue(event.target.value)}
      />

      <input
        type="email"
        value={String(email.value ?? "")}
        onChange={(event) => email.setValue(event.target.value)}
      />
    </section>
  );
}

function ComplaintDraftEditor() {
  const orderNumber = useField("orderNumber");
  const subject = useField("subject");
  const message = useField("message");

  return (
    <section className="space-y-4">
      <input
        value={String(orderNumber.value ?? "")}
        onChange={(event) => orderNumber.setValue(event.target.value)}
      />

      <input
        value={String(subject.value ?? "")}
        onChange={(event) => subject.setValue(event.target.value)}
      />

      <textarea
        value={String(message.value ?? "")}
        onChange={(event) => message.setValue(event.target.value)}
      />
    </section>
  );
}

function CustomerComplaintPage() {
  const form = useDyrectedForm();

  return (
    <form
      className="space-y-6"
      onSubmit={(event) => {
        event.preventDefault();
        void form.submit();
      }}
    >
      <h1>Complaint draft for signed-in customer</h1>

      <CustomerIdentityCard />

      <DyrectedFieldPathProvider path="complaintDraft">
        <ComplaintDraftEditor />
      </DyrectedFieldPathProvider>

      <button type="submit" disabled={form.isSubmitting}>
        Save complaint draft
      </button>
    </form>
  );
}

export default function CustomerComplaintRoute() {
  return (
    <DyrectedFormProvider controller={controller}>
      <CustomerComplaintPage />
    </DyrectedFormProvider>
  );
}

On this page

Dyrected| Cloud

Get your backend ready in minutes

Use a managed database, storage, APIs, and admin dashboard without setting up the infrastructure yourself.

Set Up My Backend