DGS-444, DGS-446: courier request pickup time slots + response parsing fix - #150
Closed
GantasG wants to merge 4 commits into
Closed
DGS-444, DGS-446: courier request pickup time slots + response parsing fix#150GantasG wants to merge 4 commits into
GantasG wants to merge 4 commits into
Conversation
GantasG
force-pushed
the
DGS-446-courier-request-pickup-time-slots
branch
from
August 31, 2026 09:42
8ddf281 to
1fe1ed6
Compare
…ontract DPD's live pickupOrderSave_ endpoint now rejects any pickup time that is not one of its fixed pickupTimeFrom/pickupTimeTo slots, and answers with a JSON object instead of the legacy plain-text response. Request side (DGS-446 + DGS-444): - The free-form 'Desired pick-up time' / 'Last pick-up time' datetime inputs are replaced with a pick-up date field and two slot dropdowns constrained to DPD's whitelists, so an invalid value can no longer be submitted. - Defaults are slot-aligned (next available slot today, or tomorrow 08:00) instead of the raw 'now + 30 min' value DPD always rejected. - CourierRequestValidator rejects non-whitelisted slots server-side. - The API request now carries pickupDate/pickupTimeFrom/pickupTimeTo alongside the legacy pickupTime/senderWorkUntil datetimes, which are kept for DPD endpoints still running the old contract and for the module's own entity. Response side (DGS-446): - CourierRequestResponseParser accepts both response shapes: the legacy '<p>DONE' / '402 Error:' strings and the new JSON object, whose body->message (or errlog) is surfaced to the merchant. Previously the JSON object reached strpos() and fatally crashed the admin page on PHP 8. Requires invertus/dpdbaltics-api with CourierRequestRequest slot setters (see the companion dpdbaltics-api PR); composer.lock to be bumped once that lands on the developer branch.
GantasG
force-pushed
the
DGS-446-courier-request-pickup-time-slots
branch
from
August 31, 2026 09:47
1fe1ed6 to
ef461e8
Compare
actions/cache@v1 is auto-failed by GitHub since its shutdown, so both jobs died before running on any PR. Bump checkout/cache/auto-commit to current versions, pin PHP 7.4 (autoindex and header-stamp are PHP 5/7-era tools), and install with --prefer-source because the lock file's legacy.zip dist URLs are no longer served by GitHub.
Author
|
Closing — wrong repo: the live merchants run the module from DPDBaltics/PrestaShop (v3.3.1, the version in DGS-444/DGS-446). The fix is being re-applied and re-verified there. The companion API-package PR Invertus/dpdbaltics-api#6 stays open — DPDBaltics/PrestaShop depends on the same invertus/dpdbaltics-api package. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Tickets
pickupTime, DPD API now requirespickupTimeFrom/pickupTimeTo(Critical)One branch for both: they share the root-cause chain, and the slot work that fixes DGS-446 subsumes DGS-444.
What changed
Request side:
CourierRequestValidator::validatePickupTimeSlots()re-checks the whitelist server-side (a tampered POST gets a clear error, not an API round-trip).pickupDate/pickupTimeFrom/pickupTimeToalongside the legacypickupTime/senderWorkUntildatetimes — kept for DPD endpoints still on the old contract (EE/LV) and for the module's ownDPDCourierRequestentity, whose stored columns are composed from the slot fields.Response side (the crash):
CourierRequestResponseParseraccepts both response shapes: legacy<p>DONE/402 Error:strings and the new JSON object, whosebody->message(orerrlog) is surfaced to the merchant. Previously thestdClassreachedstrpos()and fatally crashed the admin page on PHP 8 (TypeError, uncatchable by the controller'scatch (Exception)).Depends on
CourierRequestRequest(the payload is built by that package'sjsonSerialize(), so the new params can't reach the wire from module code alone). Merge that intodeveloperfirst, thencomposer update invertus/dpdbaltics-apihere to bumpcomposer.lock(will push that bump once the api PR lands). Until then a freshcomposer installof this branch runs the old DTO and courier submit would fatal on the missing setters.Reproduction & verification (local PS 8.2.7 / PHP 8.1, DPD live endpoint stubbed with wiremock replaying the exact live rejection)
Both bugs reproduced on
mainbefore the fix:2026-08-31 11:35:26(raw now+30min, no slot) — DGS-444 confirmed.pickupTimeonly) → HTTP 500 withstrpos(): Argument #1 ($haystack) must be of type string, stdClass given— DGS-446 confirmed byte-for-byte.After the fix, against the same stubs:
12:00).<p>DONE): 'Successful creation' confirmation, record saved with composed datetimes, list view unchanged.pick_up_time_from=11:35rejected server-side with the whitelist message, no API call.Captured outgoing request after the fix (wiremock):
Unit tests added (run green on PHP 7.2 via the module's PHPUnit 5.7):
CourierRequestResponseParserTest(8 tests, incl. the stdClass regression fixture DGS-446 asks for),PickupTimeSlotUtilityTest(4),CourierRequestValidatorTest(6). The pre-existingtests/Unitsuite is broken onmain(network-dependent API tests,_PS_VERSION_undefined) — untouched.Browser QA: BO form smoke + interaction pass done on PS 8.2.7 (defaults, valid submit, DPD-rejection submit, tampered-value submit, success submit). Module list view after save verified. FO untouched by this change.
Verdict: ship with follow-ups (the two items below).
Needs human verification
integracijos.dpd.lt) with production credentials. The new param names (pickupDate/pickupTimeFrom/pickupTimeTo) match DPD's current API data model and the live error message, but DPD's ws-mapper docs for the new contract aren't public, and the sandbox doesn't enforce it (per both tickets), so the exact wire naming is unverified against production. If DPD expects different naming, the module now shows DPD's answer instead of crashing, so the failure mode is a readable error.DONEstrings as success and any JSON object as a surfaced error. If the live endpoint starts answering success as JSON, the success branch needs the shape added.Confidence: 75%
Notes
wiremock/mappings/carries the stub replaying DPD's live rejection — the workspace's wiremock container mounts this dir, so the repro stays reproducible for QA.pick_up_time/sender_work_untilcolumns still store full datetimes composed from the slot fields.