feat: Add QR code scanner for event tickets - #57
Conversation
- Add validate_ticket_for_checkin() endpoint for ticket validation - Add checkin_ticket() endpoint for processing check-ins - Include comprehensive error handling and validation - Support for checking ticket status, booking confirmation, and duplicate check-ins - Return detailed ticket information including add-ons and event details
- Add html5-qrcode package for QR code scanning functionality - Update package.json and yarn.lock with new dependencies - Enable QR code scanning capabilities for ticket validation
- Create useTicketValidation composable for reusable ticket validation logic - Handle ticket validation and check-in API calls - Manage loading states and error handling - Provide centralized state management for scanner components
- Add QRScanner component with html5-qrcode integration - Add EventSelector component for event selection - Add TicketDetailsModal component for ticket validation display - Include comprehensive error handling and user feedback - Support both QR scanning and manual ticket ID entry
- Add CheckInScanner page with complete scanner interface - Update router to include /checkin-scanner route - Integrate all scanner components with audio feedback - Include event selection and ticket validation workflow
- Add beep.wav for successful scan feedback - Add beep-fail.wav for error feedback - Provide audio cues for better user experience during scanning
- Update components.d.ts with new component type definitions - Include QRScanner, EventSelector, and TicketDetailsModal components - Ensure proper TypeScript support for all new scanner components
|
Hi 👋 Can you add a demo video? |
| def validate_ticket_for_checkin(ticket_id: str) -> dict: | ||
| try: |
There was a problem hiding this comment.
Let's use frappe.only_for and check if they have "Frontdesk Manager" role (you will have to create this role too)
- Replace return statements with frappe.throw() for consistent error handling - Simplify error responses by using Frappe's built-in error handling - Remove redundant error response objects in favor of exceptions
- Add Frontdesk Manager role to fixtures in hooks.py - Grant Frontdesk Manager permissions for Event Check In doctype
EventSelector improvements: - Switch from createResource to createListResource for better data handling - Remove status column and related logic for cleaner UI - Add auto-loading and filtering for published events - Simplify refresh button with icon-left prop QRScanner improvements: - Simplify stop button with icon-left prop - Remove redundant template structure
CheckInScanner improvements: - Simplify event selection display with single button - Remove complex card layout in favor of clean button interface - Add arrow-left icon for better UX Router improvements: - Update route path from /checkin-scanner to /check-in - Update route name from checkin-scanner to check-in for consistency
- Remove unused error parameter in useTicketValidation onError handler - Add LucideX icon component to component types for UI consistency
- Add frappe.only_for("Frontdesk Manager", True) to validate_ticket_for_checkin
- Add frappe.only_for("Frontdesk Manager", True) to checkin_ticket
- Restrict ticket validation and check-in operations to Frontdesk Manager role only
- Remove try-catch wrapper and simplify error handling - Change validation to check for existing check-ins on the same date instead of any time - Update check-in creation to include date field - Improve error messages to be more specific about date-based check-ins - Remove track-based logic from check-in process
- Replace track field with date field in doctype definition - Add date field to Python class with proper typing - Implement before_insert hook to auto-set date to today if not provided - Update field order and remove track-related configuration
- Add unplugin-auto-import dependency for better development experience - Update yarn.lock with new dependency versions - Update components.d.ts to reflect removed unused icon imports - Clean up auto-generated component declarations
- Create singleton pattern for shared state across components - Add audio feedback for success and error states - Implement modal state management within composable - Add comprehensive error handling with specific toast messages - Integrate ticket validation and check-in logic in one place - Add proper cleanup and state management
- Remove props-based communication in favor of composable integration - Add duplicate scan prevention with 2-second timeout - Improve error handling with specific toast messages - Add proper scanner cleanup on component unmount - Integrate with ticket validation composable for unified state management - Remove unused icon imports and simplify component interface - Add global CSS to hide scanner info icon for cleaner UI
- Remove props-based state management in favor of composable integration - Add safe property access with optional chaining throughout template - Simplify component interface by removing unnecessary props - Improve button layout with better responsive design - Integrate with ticket validation composable for unified state management - Remove unused imports and clean up component structure
- Simplify CheckInScanner page by removing complex state management - Remove track-based check-in button and logic from FE Event doctype - Update EventSelector styling for better mobile experience - Clean up unused imports and simplify component interfaces - Integrate all components with the new composable pattern - Remove legacy track-based check-in functionality
There was a problem hiding this comment.
Pull Request Overview
This PR implements a comprehensive QR code-based event check-in system that enables event organizers to scan and validate attendee tickets. The feature includes backend validation APIs, frontend scanner components with audio feedback, and support for multiple event management.
Key Changes:
- Backend API endpoints for ticket validation and check-in processing with duplicate prevention
- QR scanner interface with manual ticket ID entry fallback and real-time camera scanning
- Event selector for multi-event support with responsive UI and status indicators
Reviewed Changes
Copilot reviewed 13 out of 17 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| dashboard/src/router.js | Adds check-in route for scanner page |
| dashboard/src/pages/CheckInScanner.vue | Main scanner page with event selection and ticket validation interface |
| dashboard/src/composables/useTicketValidation.js | Singleton composable for ticket validation and check-in logic with audio feedback |
| dashboard/src/components/TicketDetailsModal.vue | Modal displaying ticket information and check-in controls |
| dashboard/src/components/QRScanner.vue | QR code scanner component with manual entry fallback |
| dashboard/src/components/EventSelector.vue | Event selection interface with loading and empty states |
| dashboard/package.json | Adds html5-qrcode and unplugin-auto-import dependencies |
| buzz/hooks.py | Adds Frontdesk Manager role to fixtures and reformats code |
| buzz/events/doctype/fe_event/fe_event.py | Removes deprecated check_in method and reformats imports |
| buzz/events/doctype/fe_event/fe_event.js | Removes old check-in button implementation |
| buzz/events/doctype/event_check_in/event_check_in.py | Adds date field auto-population logic |
| buzz/events/doctype/event_check_in/event_check_in.json | Replaces track field with date field and adds Frontdesk Manager permissions |
| buzz/api.py | Adds validate_ticket_for_checkin and checkin_ticket API endpoints |
Tip: Customize your code reviews with copilot-instructions.md. Create the file or learn how to get started.
| let errorData = JSON.stringify(error); | ||
| if (errorData.includes("Ticket not found")) { | ||
| toast.error("Ticket not found"); | ||
| } else if ( | ||
| errorData.includes("This ticket is not confirmed and cannot be used for check-in") | ||
| ) { | ||
| toast.error("This ticket is not confirmed and cannot be used for check-in"); | ||
| } else if (errorData.includes("This ticket was already checked in today")) { | ||
| toast.error("This ticket was already checked in today."); | ||
| } else { | ||
| toast.error("Error validating ticket"); |
There was a problem hiding this comment.
Error handling relies on string matching of JSON-serialized error messages, which is fragile and may fail if the error format changes. Consider using error codes or structured error responses from the API instead of string matching. Additionally, the toast message on line 58 ends with a period while others don't, creating inconsistency.
| let errorData = JSON.stringify(error); | |
| if (errorData.includes("Ticket not found")) { | |
| toast.error("Ticket not found"); | |
| } else if ( | |
| errorData.includes("This ticket is not confirmed and cannot be used for check-in") | |
| ) { | |
| toast.error("This ticket is not confirmed and cannot be used for check-in"); | |
| } else if (errorData.includes("This ticket was already checked in today")) { | |
| toast.error("This ticket was already checked in today."); | |
| } else { | |
| toast.error("Error validating ticket"); | |
| const message = error?.message || ""; | |
| if (message === "Ticket not found") { | |
| toast.error("Ticket not found."); | |
| } else if ( | |
| message === "This ticket is not confirmed and cannot be used for check-in" | |
| ) { | |
| toast.error("This ticket is not confirmed and cannot be used for check-in."); | |
| } else if (message === "This ticket was already checked in today") { | |
| toast.error("This ticket was already checked in today."); | |
| } else { | |
| toast.error("Error validating ticket."); |
|
CI failing @Inventor77 |
…straints to avoid unplugin-utils@0.3.1 engine mismatch (requires Node >=20.19.0)
…k-in - refine QR scanner behavior in dashboard/src/components/QRScanner.vue - adjust buzz/api.py endpoints/logic to support check-in flow
|
Linters failing again @Inventor77 |
- Add theme toggle functionality to Navbar component - Update BuzzLogo component with improved SVG design - Enhance dark/light mode support across components
- Add QR code scanning functionality using html5-qrcode library - Implement manual ticket ID entry as fallback option - Add duplicate scan prevention with 2-second timeout - Support multiple QR code formats (ticket ID, URLs with ticket parameter) - Add scanner controls (start/stop) and processing overlay - Improve mobile experience with custom styling overrides
- Add comprehensive ticket validation modal with multiple states - Support valid ticket display with attendee details and add-ons - Handle already checked-in tickets with warning state - Display error states for invalid tickets - Add check-in functionality with loading states - Format date/time display for check-in times - Improve UI with proper icons and color coding for different states
- Add ticket validation resource with success/error handling - Implement check-in resource for ticket processing - Add audio feedback with success and error sounds - Implement debounced toast notifications to prevent spam - Add comprehensive error handling for different ticket states - Support singleton pattern for state management across components - Add loading states for validation and check-in processes
- Remove booking status validation from ticket check-in - Remove redundant success flags from API responses - Remove booking amount/currency from ticket validation response - Simplify check-in flow by removing unnecessary validation checks
- Remove lastScanResult state and use validationResult directly - Simplify TicketDetailsModal by removing redundant success checks - Remove unused LucideAlertTriangle import - Streamline UI logic by removing unnecessary conditional rendering - Update CheckInScanner to use validationResult instead of lastScanResult
- Add Frontdesk Manager role validation to CheckInScanner page - Display access denied message for unauthorized users - Import LucideShieldX icon for security UI - Prevent scanner access without proper permissions
1f30ccb to
42abf1c
Compare
🎫 Event Check-in Scanner Feature
This PR introduces a comprehensive QR code-based check-in system for event ticket validation, enabling event organizers to efficiently scan and validate attendee tickets at event entrances.
✨ Features Added
Backend API
Ticket Validation API (
validate_ticket_for_checkin)Check-in Processing API (
checkin_ticket)Frontend Components
QR Scanner Component (
QRScanner.vue)Event Selector Component (
EventSelector.vue)Ticket Details Modal (
TicketDetailsModal.vue)User Experience
Audio Feedback
Responsive Design
🔧 Technical Implementation
Dependencies Added
html5-qrcode- QR code scanning libraryNew Files Created
dashboard/src/pages/CheckInScanner.vue- Main scanner pagedashboard/src/components/QRScanner.vue- QR scanning componentdashboard/src/components/EventSelector.vue- Event selectiondashboard/src/components/TicketDetailsModal.vue- Ticket details displaydashboard/src/composables/useTicketValidation.js- Reusable validation logicdashboard/src/assets/audio/- Audio feedback filesAPI Endpoints
buzz.api.validate_ticket_for_checkin(ticket_id)- Validate ticketbuzz.api.checkin_ticket(ticket_id)- Process check-in🚀 Usage
/dashboard/checkin-scanner🎯 Benefits
🧪 Testing
📱 Mobile Support
The scanner is fully optimized for mobile devices with:
Ready for review and testing! 🎉