feat(booking): add list selection for web scanner and camera checkout for mobile - #2788
Conversation
WalkthroughThe PR adds scanner-based partial checkout to Companion and no-scan quick actions for individual booking assets in the web scanner. It adds checkout validation, submission handling, synthetic scanned-item atoms, responsive pending-asset actions, and updated tests. ChangesPartial booking actions
Estimated code review effort: 4 (Complex) | ~45 minutes Sequence Diagram(s)sequenceDiagram
participant BookingDetail
participant CompanionScanner
participant partialCheckoutBooking
BookingDetail->>CompanionScanner: open checkout scanner
CompanionScanner->>CompanionScanner: validate scanned assets
CompanionScanner->>partialCheckoutBooking: submit selected assets
partialCheckoutBooking-->>CompanionScanner: return checkout result
CompanionScanner->>BookingDetail: navigate after success
Possibly related PRs
Suggested labels: Suggested reviewers: 🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@apps/companion/app/`(tabs)/scanner.tsx:
- Line 207: Update the kit-linked scan branch around isBookingCheckoutMode so
checkout uses the same eligibility rules as the single-asset checkout path:
exclude members that are CHECKED_OUT or IN_CUSTODY, while retaining the existing
CHECKED_OUT requirement for check-in. Adjust the related “Not Checked Out” and
“Already Covered” user-facing messages in the kit-member handling to describe
checkout-specific failures when isBookingCheckoutMode is true, including the
corresponding flow near the single-asset branch.
- Around line 2033-2101: Update handleBookingCheckout so the success alert’s
navigation callback only clears scanner state and routes to the booking detail
when result?.isComplete is true; for partial checkouts, keep the operator on the
scanner while preserving the successful submission feedback and updated booking
state.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro Plus
Run ID: 96af5a67-2d00-4924-8285-6b77f9dcd15b
📒 Files selected for processing (8)
apps/companion/app/(tabs)/bookings/[id].tsxapps/companion/app/(tabs)/scanner.tsxapps/webapp/app/atoms/qr-scanner.tsapps/webapp/app/components/scanner/drawer/uses/partial-checkin-drawer.test.tsxapps/webapp/app/components/scanner/drawer/uses/partial-checkin-drawer.tsxapps/webapp/app/components/scanner/drawer/uses/partial-checkout-drawer.test.tsxapps/webapp/app/components/scanner/drawer/uses/partial-checkout-drawer.tsxapps/webapp/app/components/scanner/drawer/uses/pending-items-list.tsx
…or booking checkout
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@apps/companion/app/`(tabs)/scanner.tsx:
- Around line 2105-2114: After a successful partial checkout in the submission
flow around result?.isComplete, immediately update local bookingCtx.bookedAssets
entries corresponding to the submitted asset IDs to status CHECKED_OUT before
calling fetchBookingCtx(). Preserve fetchBookingCtx() as reconciliation, and add
a regression test covering an immediate kit rescan to ensure already checked-out
members are not queued.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro Plus
Run ID: cf6d1d50-660e-49d4-a447-5bd6b523667a
📒 Files selected for processing (1)
apps/companion/app/(tabs)/scanner.tsx
| if (result?.isComplete) { | ||
| InteractionManager.runAfterInteractions(() => { | ||
| pushIntoTab( | ||
| "/(tabs)/bookings", | ||
| `/(tabs)/bookings/${bookingId}` | ||
| ); | ||
| }); | ||
| } else { | ||
| fetchBookingCtx(); | ||
| } |
There was a problem hiding this comment.
🎯 Functional Correctness | 🟠 Major | ⚡ Quick win
Keep kit eligibility current after a partial checkout.
When result?.isComplete is false, Line 2113 starts fetchBookingCtx() but leaves bookingCtx.bookedAssets stale until the request resolves. The camera can accept a kit scan in that interval. The kit branch at Lines 900-912 can then queue members that assetIds already checked out.
Update the local bookedAssets statuses to CHECKED_OUT after a successful submission, then keep fetchBookingCtx() as reconciliation. Add a regression test that rescans a kit immediately after a partial checkout.
Proposed fix
Haptics.notificationAsync(Haptics.NotificationFeedbackType.Success);
playScanSound();
+ const checkedOutAssetIds = new Set(assetIds);
+ setBookingCtx((prev) =>
+ prev
+ ? {
+ ...prev,
+ bookedAssets: prev.bookedAssets.map((asset) =>
+ checkedOutAssetIds.has(asset.id)
+ ? { ...asset, status: "CHECKED_OUT" }
+ : asset
+ ),
+ }
+ : prev
+ );
const msg = result?.isComplete📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| if (result?.isComplete) { | |
| InteractionManager.runAfterInteractions(() => { | |
| pushIntoTab( | |
| "/(tabs)/bookings", | |
| `/(tabs)/bookings/${bookingId}` | |
| ); | |
| }); | |
| } else { | |
| fetchBookingCtx(); | |
| } | |
| const checkedOutAssetIds = new Set(assetIds); | |
| setBookingCtx((prev) => | |
| prev | |
| ? { | |
| ...prev, | |
| bookedAssets: prev.bookedAssets.map((asset) => | |
| checkedOutAssetIds.has(asset.id) | |
| ? { ...asset, status: "CHECKED_OUT" } | |
| : asset | |
| ), | |
| } | |
| : prev | |
| ); | |
| if (result?.isComplete) { | |
| InteractionManager.runAfterInteractions(() => { | |
| pushIntoTab( | |
| "/(tabs)/bookings", | |
| `/(tabs)/bookings/${bookingId}` | |
| ); | |
| }); | |
| } else { | |
| fetchBookingCtx(); | |
| } |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@apps/companion/app/`(tabs)/scanner.tsx around lines 2105 - 2114, After a
successful partial checkout in the submission flow around result?.isComplete,
immediately update local bookingCtx.bookedAssets entries corresponding to the
submitted asset IDs to status CHECKED_OUT before calling fetchBookingCtx().
Preserve fetchBookingCtx() as reconciliation, and add a regression test covering
an immediate kit rescan to ensure already checked-out members are not queued.
Summary
Introduces list-based selection ("Check out/in without scanning") for individual assets in the web booking scanner drawers, and adds a camera "Scan to Check Out" option for booking checkout in the mobile companion app.
Key Changes
Closes: #2655
Summary by CodeRabbit