FastUI icon indicating copy to clipboard operation
FastUI copied to clipboard

DOCS: Create documentation for `ModelForm`

Open Zaubeerer opened this issue 1 year ago • 2 comments

Intro

If I understand c.ModelForm correctly, submit_url='/decisions/' should post to "/decisions/".

This may lead to the following errors:

  • 405 Method Not Allowed, if the post route does not exist
  • 422 Unprocessable Entity, if the payload or response doesn't have the right format (Pydantic model)

However, in the below MRE I don't understand why I get a 422.

Questions

  • [ ] (How) Can I get more information about the 422 error?
  • [ ] How to leverage PageEvent?
  • [ ] Is the request or the response model the problem?

Suggested Steps

  • [ ] Root Cause Analysis in this issue
  • [ ] PR to improve documentation (e.g. docstring for ModelForm)
  • [ ] PR to improve error messages related to 422 error messages

Further Information

https://github.com/pydantic/FastUI/blob/6b7c7cba5250eaf044bc312199fd877878334087/src/python-fastui/fastui/components/forms.py#L97

https://github.com/pydantic/FastUI/blob/6b7c7cba5250eaf044bc312199fd877878334087/src/python-fastui/fastui/events.py#L9

Minimal Reproducible Example (MRE)

from fastapi import FastAPI
from fastapi.responses import HTMLResponse
from fastui import AnyComponent, FastUI, prebuilt_html
from fastui import components as c
from fastui.events import PageEvent
from sqlmodel import SQLModel

app = FastAPI()


class Decision(SQLModel):
    name: str = "example decision"
    state_emotional: str = "curious"
    situation: str = "I have a decision to make"


@app.get("/api/new", response_model=FastUI, response_model_exclude_none=True)
def new_decision() -> list[AnyComponent]:
    return [
        c.Heading(text="New Decision", level=2),
        c.Paragraph(text="Create a new decision."),
        c.ModelForm[Decision](
            submit_url="/decisions/",
            # success_event=PageEvent(),
        ),
    ]


@app.post("/decisions/", response_model=Decision)
async def create_decision(
    *,
    decision: Decision,
    # session: Session = Depends(get_session),
):
    print(decision)
    # db_decision = Decision.from_orm(decision)
    # session.add(db_decision)
    # session.commit()
    # session.refresh(db_decision)
    return decision


@app.get("/{path:path}")
async def html_landing() -> HTMLResponse:
    """Simple HTML page which serves the React app, comes last as it matches all paths."""
    return HTMLResponse(prebuilt_html(title="FastUI: Decisions"))

Zaubeerer avatar Dec 19 '23 21:12 Zaubeerer

Solving this issue may solve #97, or at least make progress on it.

Zaubeerer avatar Dec 19 '23 22:12 Zaubeerer

@samuelcolvin, any short hint on this?

Would be happy to contribute the related PRs :)

Zaubeerer avatar Dec 21 '23 07:12 Zaubeerer