gastownhall/beads · error · publicCreateValidationError

create: issue comments and dependencies must be supplied…

Error message

create: issue comments and dependencies must be supplied through request fields

What it means

ValidatePublicCreateRequest rejects a create request whose embedded Issue carries Comments or Dependencies. These must be supplied through the dedicated request fields (request.Comments / request.Dependencies), not nested inside the issue payload, so the store can write them with correct provenance and ordering.

Solutions

  1. Clear request.Issue.Comments and request.Issue.Dependencies and pass them via the CreateRequest's dedicated Comments/Dependencies fields instead
  2. Strip nested comments/dependencies when converting a loaded issue into a create request
  3. Only pass these fields when you actually intend to create them alongside the issue

Example fix

// before
issue.Comments = loadedComments
req := publicops.CreateRequest{Actor: actor, Issue: issue}
// after
issue.Comments = nil
issue.Dependencies = nil
req := publicops.CreateRequest{Actor: actor, Issue: issue, Comments: loadedComments}
Defensive patterns

Strategy: validation

Validate before calling

func issuePayloadClean(i *types.Issue) bool { return len(i.Comments) == 0 && len(i.Dependencies) == 0 }

Prevention

When it happens

Trigger: Calling ExecuteCreate with a CreateRequest whose request.Issue.Comments or request.Issue.Dependencies slices are non-empty.

Common situations: Constructing a types.Issue struct copied from an existing issue (which often carries comments/deps) and reusing it in a create request; API migration from an older nested style.

Related errors


AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30). Data as JSON: /api/errors/165ecb28c9e5b350. Report an issue: GitHub.

Appendix: source

Thrown at internal/storage/issueops/public_create.go:35

// create request for the domain create use case.
type PublicCreateContext struct {
	IssuePrefix     string
	AllowedPrefixes string
	CustomStatuses  []string
	CustomTypes     []string
}

// ValidatePublicCreateRequest checks public-create invariants independent of
// database configuration.
func ValidatePublicCreateRequest(request publicops.CreateRequest) error {
	if request.Actor == "" || request.Issue == nil {
		return publicCreateValidationError(fmt.Errorf("create: actor and issue are required"))
	}
	if err := types.CheckFieldLen("actor", request.Actor); err != nil {
		return publicCreateValidationError(fmt.Errorf("create: %w", err))
	}
	if len(request.Issue.Comments) > 0 || len(request.Issue.Dependencies) > 0 {
		return publicCreateValidationError(fmt.Errorf("create: issue comments and dependencies must be supplied through request fields"))
	}
	for _, field := range []struct{ name, value string }{{"assignee", request.Issue.Assignee}, {"owner", request.Issue.Owner}} {
		if err := types.CheckFieldLen(field.name, field.value); err != nil {
			return publicCreateValidationError(err)
		}
	}
	for _, label := range request.Issue.Labels {
		if err := types.CheckFieldLen("label", label); err != nil {
			return publicCreateValidationError(err)
		}
	}
	if err := types.CheckFieldLen("parent ID", request.ParentID); err != nil {
		return publicCreateValidationError(fmt.Errorf("create: %w", err))
	}
	return validatePublicCreateDependencies(request)
}

// PreparePublicCreateRequest snapshots, normalizes, and validates a public

View on GitHub (pinned to 71377f2769)