You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于React Router v6的多步骤表单导航优化方案咨询

Solution for Dynamic Multi-Step Form Navigation with React Router v6

1. Refactor Routes to Use Dynamic Parameters

Replace hardcoded form routes with a dynamic segment to support any form ID from your backend config:

<Routes>
  <Route path="/" element={<Layout />}>
    <Route index element={<Pages.Home />} />
    <Route path="form" element={<FormProvider><FormLayout /></FormProvider>}>
      {/* Dynamic route for all form steps */}
      <Route path=":formId" element={<FormRenderer />} />
      {/* Redirect to the first form step when accessing /form */}
      <Route index element={<Navigate to={getFirstFormId(formConfig)} />} />
    </Route>
    <Route path="*" element={<Pages.NotFound />} />
  </Route>
</Routes>

2. Build a Form Renderer Component

Map form IDs from the config to your actual form components:

// Map form IDs to their corresponding components
const formComponentMap = {
  form1: Forms.Form1,
  form2: Forms.Form2,
  form3: Forms.Form3
};

const FormRenderer = () => {
  const { formId } = useParams();
  const FormComponent = formComponentMap[formId];

  // Fallback if form ID doesn't exist in the map
  if (!FormComponent) return <Pages.NotFound />;

  return <FormComponent />;
};

3. Store Form Config in Context

Fetch and store the backend config in your FormContext to avoid redundant fetching/lookups:

const FormProvider = ({ children }) => {
  const [formConfig, setFormConfig] = useState({});
  const [formData, setFormData] = useState({});

  // Fetch config from backend on mount
  useEffect(() => {
    fetch('/api/form-config')
      .then(res => res.json())
      .then(setFormConfig);
  }, []);

  const contextValue = useMemo(() => ({
    formConfig,
    formData,
    setFormData
  }), [formConfig, formData]);

  return <FormContext.Provider value={contextValue}>{children}</FormContext.Provider>;
};

4. Create a Reusable Hook for Current Form Info

Centralize the logic to get the current form's navigation data:

const useCurrentForm = () => {
  const { formId } = useParams();
  const { formConfig } = useFormContext();
  return formConfig[formId] || {};
};

5. Update FormLayout for Dynamic Navigation

Use the custom hook to get navigation details without syncing URL state:

const FormLayout = () => {
  const currentForm = useCurrentForm();
  const navigate = useNavigate();

  const handleNavigate = (targetFormId) => {
    navigate(`/form/${targetFormId}`);
  };

  return (
    <div>
      <h2>{currentForm.title}</h2>
      <Outlet />
      <div className="form-nav">
        {currentForm.prev && (
          <button onClick={() => handleNavigate(currentForm.prev)}>Back</button>
        )}
        <button onClick={() => {
          currentForm.next 
            ? handleNavigate(currentForm.next) 
            : console.log('Submit form data'); // Replace with submission logic
        }}>
          {currentForm.next ? 'Next' : 'Submit'}
        </button>
      </div>
    </div>
  );
};

Helper Function to Find First Form Step

Add this helper to redirect to the initial form step when accessing /form:

const getFirstFormId = (config) => {
  return Object.keys(config).find(key => config[key].prev === null) || '';
};

Why This Works:

  • No URL-to-JSON sync: Uses React Router's useParams() to get the current form ID directly, eliminating the need to track page state in context.
  • Dynamic routes: The :formId segment adapts to any form IDs defined in the backend config, so you don't need to update routes when steps change.
  • No redundancy: The useCurrentForm hook centralizes config lookup logic, so components don't repeat code to match URLs to JSON.
  • Backend control: Changing the JSON (reordering steps, updating titles, adding/removing steps) automatically reflects in the UI without frontend code changes.

内容的提问来源于stack exchange,提问作者mik3wk

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 18:34:56