Skip to content

feat(contact-properties): implement contact-properties namespace#1

Merged
rafa-thayto merged 3 commits into
mainfrom
feat/contact-properties
Feb 19, 2026
Merged

feat(contact-properties): implement contact-properties namespace#1
rafa-thayto merged 3 commits into
mainfrom
feat/contact-properties

Conversation

@rafa-thayto

@rafa-thayto rafa-thayto commented Feb 19, 2026

Copy link
Copy Markdown
Contributor

Summary

  • Adds resend contact-properties top-level command with five subcommands: create, get, list, update, delete
  • Help text is written for both human and AI agent/CI consumers (structured error codes, exact JSON output shapes, flag descriptions)
  • Corrects spec-doc inaccuracies against the live SDK: field is key not name; allowed types are string|number only; update only accepts fallbackValue (cannot rename or retype after creation)
  • Refactors codebase-wide: drops the redundant 'braille' default arg from every createSpinner call (34 files) and extracts repeated data! dereferences to named locals in list/get commands
  • Fixes a TypeScript error in create.ts: p.select takes one type argument, not two
  • Updates CLAUDE.md with learned conventions and SDK gotchas

Test Plan

  • bun test — 288 tests across 42 files, all passing
  • bun run build — compiles to dist/resend with no type errors
  • bunx tsc --noEmit — zero TypeScript errors
  • resend contact-properties --help — shows all subcommands with full help text
  • resend contact-properties create --key company_name --type string --json — creates a property, returns {"object":"contact_property","id":"..."}
  • resend contact-properties list --json — returns {"object":"list","has_more":false,"data":[...]}
  • resend contact-properties update <id> --fallback-value "Acme" --json — returns {"object":"contact_property","id":"..."}
  • resend contact-properties update <id> --clear-fallback-value --json — sets fallback to null
  • resend contact-properties delete <id> --yes --json — returns {"object":"contact_property","id":"...","deleted":true}
  • Non-interactive guard: omitting --key or --type in a pipe exits with code 1 and {"error":{"code":"missing_key"}} / {"error":{"code":"missing_type"}}

Notes

update intentionally exposes only --fallback-value / --clear-fallback-value. The SDK's UpdateContactPropertyOptions does not support renaming or retyping a property — the spec doc was incorrect on this point. Renaming would silently break any broadcasts referencing the old key name.

Adds create, get, list, update, delete subcommands under
`resend contact-properties`. Registered in src/cli.ts.

SDK field is `key` (not `name`); types are `string|number` only;
update only accepts fallbackValue — cannot rename or retype after
creation. Separate --clear-fallback-value flag handles null-setting.

33 tests across 5 files; all 288 suite tests passing.
'braille' is already the default in createSpinner — passing it
explicitly across 19 command files was pure noise.
After the if(error){outputError(...)} guard, data is always non-null.
Using data! multiple times in a block is noisy — extract const d/list = data!
and reference it cleanly. Also drops the redundant 'braille' spinner arg
from these files.

Affected: domains/get, domains/create, domains/list, broadcasts/list,
contacts/list, contacts/segments, contacts/topics, api-keys/create, api-keys/list.
@rafa-thayto rafa-thayto force-pushed the feat/contact-properties branch from cf28557 to df9f6b3 Compare February 19, 2026 16:39
@rafa-thayto rafa-thayto merged commit 8bb6d8f into main Feb 19, 2026
0 of 9 checks passed
dielduarte added a commit that referenced this pull request Jun 25, 2026
Felipe review (#1): getJwtExp cast the decoded payload without guards, so a
malformed access token would throw a cryptic error or store NaN/undefined as
the expiry, leaving the credential in an inconsistent state. Validate segment
count, JSON payload, and numeric exp, throwing a clear re-login message.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant