fix(tasks): add a max length to task Description (and record the DTO validation audit)
Maintainers usually reply within 1 day
Nobody has claimed this yet.
Assessment
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Newbie friendliness
- 68/100
Research direction
Start with TaskItemValidator and ProjectValidator to follow the existing description-length rule pattern, then review the controller validation paths noted in the issue. Add validator tests under TaskFlow.Api.Tests/Validators/ and controller tests covering PUT and PATCH rejection with no task changes. Done means all acceptance criteria pass, including POST/PUT/PATCH behavior, and dotnet test plus dotnet format --verify-no-changes pass.
Written by the indexing model from the issue text.
Description
Groomed 2026-10-30 — ready for implementation.
Waits for the monorepo move (#397). This changes the API, so it is built after the assistant moves into this repo and the MCP change ships in the same PR (checked by the integration and error-code tests).
Original Description
Problem
UpdateTaskItemDto and PatchTaskItemDto have fields with no DTO-level validator. #207 (PR #363) added validators for CreateTaskItemDto, UpdateTaskItemDto and PatchTaskItemDto, but each covers only TimezoneOffsetMinutes.
During validation of #207 the reviewer noted that other fields, for example Title length and Description length, are not checked at the DTO level. In PATCH, Title appears to be checked only through the TaskItem model validator (TaskItemValidator) after the changes are applied to the entity.
This has not been verified as a real gap. The TaskItem validator may already cover these fields, in which case the only difference is where the error is raised. This issue is to find out.
What to check
- For each field on
CreateTaskItemDto,UpdateTaskItemDtoandPatchTaskItemDto, list which rule (if any) validates it today, and where (DTO validator,TaskItemValidator, EF constraint, or none). - Identify any field where invalid input can reach the database, or cause a 500, or be accepted by one endpoint and rejected by another. Examples to try: over-long Title or Description, empty or whitespace-only Title on PATCH,
BlockedReasonlength,DueDateextremes. - Compare the three endpoints (POST, PUT, PATCH) for consistent behavior on the same invalid input.
Outcome
- If every field is already covered by
TaskItemValidator, close this issue with a short table of findings. - If there are gaps, add the missing rules (in
Validators/, following the.InclusiveBetween/WithMessagepattern used for the offset) and tests underTaskFlow.Api.Tests/Validators/, or split out one issue per gap.
Context
Raised as a note-only observation by the implementation-validator during /feature-factory 207 (PR #363). Out of scope there.
Audit findings (2026-10-30, by reading the code; no requests were sent)
TaskItemValidator validates the entity after the DTO is mapped onto it. It runs on create (TaskItemsController.cs, around line 192) and in ApplyUpdateAsync (around line 437), so POST, PUT and PATCH are covered the same way. The three DTO validators cover only TimezoneOffsetMinutes, which is fine.
| Field | Validated by | Gap |
|---|---|---|
| Title | TaskItemValidator: not empty, max 100 |
none |
| Status, Priority | TaskItemValidator: IsInEnum |
none |
| BlockedReason | TaskItemValidator: max 200, only while Blocked |
none |
| Description | nothing (no rule in TaskItemValidator, no length constraint in TaskDbContext) |
no length limit on POST, PUT or PATCH |
| DueDate | nothing | no range check; extremes are covered by #238 |
| ParentTaskItemId, ProjectId | controller checks | not examined here |
Comparable text fields are bounded: Project description 2000, Note content 2000, JournalNote content 2000, JournalLogEntry content 2000, JournalEntry summary 10000. Task Description is the only unbounded user text field.
Stored data check (2026-10-30, via the TaskFlow MCP list_tasks, 11 tasks, detailed format): the longest description is about 110 characters (task #68). Caveats: the MCP's target instance was not confirmed to be production, and the detailed format may truncate descriptions.
User Story
As a task owner, I want an over-long task description to be rejected with a clear message, so that task data stays bounded like every other text field and an accidental paste cannot bloat the database or the responses.
Acceptance Criteria
- Given a POST with a
Descriptionlonger than 2000 characters, then the response is 400 with the message "Description must not exceed 2000 characters." and no task is created. - Given a PUT with a
Descriptionlonger than 2000 characters, then the response is 400 with the same message and the task is unchanged. - Given a PATCH with a
Descriptionlonger than 2000 characters, then the response is 400 with the same message and the task is unchanged. - Given a
Descriptionof exactly 2000 characters, null, or empty, then POST, PUT and PATCH accept it. - Given the rule, then it lives in
TaskItemValidator(Validators/), not in the three DTO validators, so one rule covers every endpoint and the parent auto-complete path. Errors keep theBadRequest(validationResult.Errors)shape. - Given the validator, then unit tests under
TaskFlow.Api.Tests/Validators/cover 2000 accepted, 2001 rejected, null and empty accepted, with the exact message. Controller tests cover PUT and PATCH rejection with the task unchanged. - Given the finished change, then
dotnet testanddotnet format --verify-no-changespass, and backend line coverage stays at 75% or above.
Edge Cases
- Existing data above the limit. PUT resends Description, so a stored description longer than 2000 characters would make every later update of that task fail until it is shortened. The MCP check found nothing near the limit, but it could not be confirmed against production. Check production data (for example with the MCP against the live instance) before merging.
- Parent auto-complete.
TryAutoCompleteParentAsyncvalidates the parent entity (around line 575). A parent with an over-limit legacy description would fail validation there. Confirm what the user sees. - Counting.
MaximumLengthcounts UTF-16 code units, not characters as the user perceives them. 2000 is the same unit the other validators use; do not change it. - Frontend. Check how the task forms surface a 400 on Description. Adding a
maxLengthattribute is optional and not required by this story. - The message and rule follow
ProjectValidator(Description max 2000).
Out of Scope
- DueDate range or wire format (#238).
- Title, Status, Priority and BlockedReason rules (already covered).
- Changing the
TimezoneOffsetMinutesrules from #207. - Changing the error shape (
BadRequest(validationResult.Errors)is the convention; see #364). - Global FluentValidation auto-validation.
- Adding a database column constraint or migration.
- ParentTaskItemId and ProjectId validation.
- Dominant language
- C#
- Stars
- 1
- Forks
- 0
- Avg merge
- 2h 2m
- Merged PRs (30d)
- 98
Getting set up
- Ships a Dockerfile or Docker Compose file
- No pull request template
- Read the contributing guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from nevridge/TaskFlow
-
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
Maintainers usually reply within 1 day
-
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
Maintainers usually reply within 1 day
-
Difficulty 2/5 1-3 hours Newbie friendliness 68/100
Maintainers usually reply within 1 day
-
bug
Difficulty 2/5 1-3 hours Newbie friendliness 65/100
Maintainers usually reply within 1 day
-
tech-debt
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
Maintainers usually reply within 1 day
All issues in nevridge/TaskFlow
Similar issues
-
Difficulty 2/5 1-3 hours Newbie friendliness 74/100
juandresrodca/AdminForge#54 ·
-
要トリアージ 辞書
Difficulty 1/5 1-3 hours Newbie friendliness 86/100
yksr-melt/Meltype#1625 · 1 reaction ·
Maintainers usually reply within 1 day
-
Docs typoOpen
Difficulty 1/5 Under an hour Newbie friendliness 78/100
MonoGame/docs.monogame.github.io#328 · 1 comment ·
-
Difficulty 2/5 1-3 hours Newbie friendliness 70/100
space-wizards/RobustToolbox#7197 ·
Maintainers usually reply within 1 day
-
documentation high priority
Difficulty 2/5 1-3 hours Newbie friendliness 76/100
lachydotmcg/capri-desktop#201 ·
Maintainers usually reply within 1 day