Skip to content

Move customerNumber from request root into each consignment's product#61

Merged
crakter merged 2 commits into
masterfrom
claude/brave-bardeen-S4zZM
Jun 1, 2026
Merged

Move customerNumber from request root into each consignment's product#61
crakter merged 2 commits into
masterfrom
claude/brave-bardeen-S4zZM

Conversation

@crakter
Copy link
Copy Markdown
Owner

@crakter crakter commented Jun 1, 2026

Summary

Bring's Booking API expects customerNumber inside consignments[].product.customerNumber, but the SDK was emitting it at the request root. Bring's gateway reads from the product slot, finds nothing, and rejects every consignment with BOOK-INPUT-019 "Customer number must be provided". The BookingRequest constructor invariant (non-empty customerNumber) prevented a local failure but couldn't help the wire shape — every live booking would fail.

This was masked because the existing BookingApiTest only validated the (incorrect) root placement against a mock client.

Change

  • BookingRequest::toArray() no longer emits customerNumber at the root. Instead, it injects the field into each consignment's product object at serialization time.
  • The public SDK shape is unchanged: callers still pass customerNumber once on BookingRequest. The repetition Bring's schema demands per consignment is an implementation detail.
  • Test updated to pin the field at consignments[0].product.customerNumber AND to assert it is NOT present at the root, locking in the correct shape against the live API.

Confirmed against https://developer.bring.com/api/booking/ — the schema lists customerNumber as a required property of the product object inside each consignment.

Test plan

  • vendor/bin/phpunit — 198 tests, all green
  • vendor/bin/phpstan analyse — no errors
  • BookingApiTest now asserts the field at the product level and explicitly forbids the root placement

Generated by Claude Code

Bring's Booking API expects customerNumber inside
consignments[].product.customerNumber. The SDK was emitting it at
the request root, which Bring's gateway silently ignores — it
reads from the product slot, finds nothing, and rejects every
consignment with BOOK-INPUT-019 "Customer number must be
provided". The constructor invariant (non-empty customerNumber)
prevented the local failure but couldn't help the wire shape.

The public SDK shape is unchanged: customerNumber stays a single
request-level field on BookingRequest. At toArray() time we
inject it into each consignment's product object, so callers
keep modelling it once even though Bring's schema repeats it per
consignment.

The existing BookingApiTest only checked the (incorrect) root
placement against a mock client, so the bug went unnoticed. The
assertion is updated to pin the field to consignments[0].product
and to assert it is NOT present at the root, locking in the
correct shape against the live API.

Confirmed against https://developer.bring.com/api/booking/ —
schema lists customerNumber as a required property of the
product object inside each consignment.
Copy link
Copy Markdown

@gemini-code-assist gemini-code-assist Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request updates the serialization of BookingRequest to nest the customerNumber inside each consignment's product object rather than placing it at the request root, aligning with the expectations of Bring's Booking API. The corresponding unit tests have been updated to reflect this structural change. Feedback was provided to replace the array union operator (+) with direct array assignment to improve readability and prevent potential confusion regarding array merging behavior in PHP.

$consignments = array_map(
static function (Consignment $c) use ($customerNumber): array {
$arr = $c->toArray();
$arr['product'] = ['customerNumber' => $customerNumber] + (array) $arr['product'];
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Using the array union operator (+) for merging arrays can be non-intuitive in PHP because the left-hand side takes precedence (unlike array_merge where the right-hand side overwrites). To improve readability and avoid potential confusion for future maintainers, it is more idiomatic to use direct array assignment.

                $product = (array) $arr['product'];
                $product['customerNumber'] = $customerNumber;
                $arr['product'] = $product;

@crakter crakter merged commit 2d97b59 into master Jun 1, 2026
18 checks passed
@crakter crakter deleted the claude/brave-bardeen-S4zZM branch June 1, 2026 20:18
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.

2 participants