Phase 6 Plan 1: Timestamp Format and Bytes Encoding Annotations Summary
One-liner: Proto annotations and shared parsing for timestamp_format (RFC3339/Unix/Date) and bytes_encoding (base64/hex variants) with validation.
What Was Done#
Task 1: Proto Annotations (c143646)#
Added two new enums and field extensions to proto/sebuf/http/annotations.proto:
TimestampFormat enum (5 values):
TIMESTAMP_FORMAT_UNSPECIFIED(0) -- protojson default (RFC 3339)TIMESTAMP_FORMAT_RFC3339(1) -- explicit RFC 3339, self-documentingTIMESTAMP_FORMAT_UNIX_SECONDS(2) -- integer secondsTIMESTAMP_FORMAT_UNIX_MILLIS(3) -- integer millisecondsTIMESTAMP_FORMAT_DATE(4) -- date-only string "2024-01-15"
BytesEncoding enum (6 values):
BYTES_ENCODING_UNSPECIFIED(0) -- protojson default (standard base64)BYTES_ENCODING_BASE64(1) -- explicit standard base64 with paddingBYTES_ENCODING_BASE64_RAW(2) -- base64 without paddingBYTES_ENCODING_BASE64URL(3) -- URL-safe base64 with paddingBYTES_ENCODING_BASE64URL_RAW(4) -- URL-safe base64 without paddingBYTES_ENCODING_HEX(5) -- hexadecimal lowercase
Field extensions:
timestamp_format(50015) -- valid on google.protobuf.Timestamp fields onlybytes_encoding(50016) -- valid on bytes fields only
Task 2: Shared Annotation Parsing (dc11725)#
Created two Go files following the established annotation-per-file pattern:
timestamp_format.go exports:
GetTimestampFormat(field)-- returns TimestampFormat enum valueHasTimestampFormatAnnotation(field)-- true for non-default, non-RFC3339 formatsIsTimestampField(field)-- detects google.protobuf.Timestamp by FullNameValidateTimestampFormatAnnotation(field, messageName)-- rejects non-Timestamp fieldsTimestampFormatValidationError-- structured error type
bytes_encoding.go exports:
GetBytesEncoding(field)-- returns BytesEncoding enum valueHasBytesEncodingAnnotation(field)-- true for non-default, non-BASE64 encodingsValidateBytesEncodingAnnotation(field, messageName)-- rejects non-bytes fieldsBytesEncodingValidationError-- structured error type
Tests added to annotations_test.go:
- Extension descriptor tests (numbers 50015, 50016)
- Enum value tests (all 5 TimestampFormat + all 6 BytesEncoding values)
- String representation tests for debugging
- Validation error message format tests
Decisions Made#
| ID | Decision | Rationale |
|---|---|---|
| D-06-01-01 | Extension numbers 50015-50016 | Continue sequential numbering from 50014 (empty_behavior) |
| D-06-01-02 | UNSPECIFIED = protojson default | Consistent with all prior annotations (int64, enum, empty_behavior) |
| D-06-01-03 | Has* excludes RFC3339/BASE64 | Both RFC3339 and UNSPECIFIED produce identical protojson behavior; same for BASE64 |
| D-06-01-04 | Has* excludes BASE64 default | Parallel to HasTimestampFormatAnnotation excluding RFC3339 |
Deviations from Plan#
None -- plan executed exactly as written.
Verification Results#
| Check | Result |
|---|---|
Proto compiles (buf build) |
PASS |
| Go packages compile | PASS |
| Annotation tests pass | PASS (all new tests green) |
Lint clean (make lint-fix) |
PASS (0 issues) |
| Extension numbers unique (50015, 50016) | PASS |
Full test suite (go test ./...) |
PASS (zero regression) |
Next Phase Readiness#
Plans 06-02 through 06-04 can now use the shared annotation functions:
GetTimestampFormat()andGetBytesEncoding()for encoding decisionsHasTimestampFormatAnnotation()andHasBytesEncodingAnnotation()for detectionIsTimestampField()for type checkingValidateTimestampFormatAnnotation()andValidateBytesEncodingAnnotation()for generation-time validation
No blockers identified.
