Skip to content

fix: WorkItemAttachments.create() raises ValidationError on actual Plane response #33

@volodchenkov

Description

@volodchenkov

Calling client.work_items.attachments.create(...) against a live Plane instance raises:

pydantic.ValidationError: 1 validation error for WorkItemAttachment
asset
  Field required [type=missing, input_value={'upload_data': {...}, 'asset_id': '...', 'attachment': {...}, 'asset_url': '...'}, input_type=dict]

Plane returns a wrapper response, not a flat WorkItemAttachment:

{
  "upload_data": { "url": "...", "fields": { "...S3 multipart policy..." } },
  "asset_id": "427e...",
  "attachment": { "id": "427e...", "asset": "ws/uuid-name.ext", "is_uploaded": false, ... },
  "asset_url": "/api/assets/v2/.../attachments/427e.../"
}

But WorkItemAttachments.create() calls WorkItemAttachment.model_validate(response) directly on the wrapper — WorkItemAttachment is actually nested inside response["attachment"]. Hence the missing-asset validation error.

Reproduction:

from plane import PlaneClient
from plane.models.work_items import WorkItemAttachmentUploadRequest

client = PlaneClient(api_key="<key>", base_url="https://your-plane.example.io")
client.work_items.attachments.create(
    workspace_slug="ws", project_id="<uuid>", work_item_id="<uuid>",
    data=WorkItemAttachmentUploadRequest(name="x.txt", size=10),
)
# raises pydantic.ValidationError

Suggested fix: add a new WorkItemAttachmentCreateResponse model capturing the full wrapper and change WorkItemAttachments.create() to return it. Exposes both the attachment record and the upload data the caller needs for the S3 multipart
POST.

PR coming.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions