Commit graph

20 commits

Author SHA1 Message Date
John Mizerek
add3842db3 Return priceMap from platform_images mode
order.online embeds displayPrice alongside images — now extracted and
returned so items missing prices from image-based menus get filled in.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-15 02:36:01 -07:00
John Mizerek
436f83d67e Fix: use queryTimed instead of undefined $pdo for ImageExtension update
$pdo doesn't exist in this file — all DB queries use queryTimed/queryOne
from helpers.php.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-15 02:08:26 -07:00
John Mizerek
5d34d8378b Fix: set ImageExtension after downloading item images in saveWizard
downloadItemImage() saved files to disk but never updated the DB column,
so items appeared to have no images despite files existing on disk.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-15 01:57:39 -07:00
John Mizerek
280394f5e0 Move app from /opt to /var/www/payfrit-api (standard Linux web dir)
- Moved directory on both dev and biz servers
- Updated nginx configs on both servers
- Added appRoot() helper, uploadsRoot() uses it
- No more hardcoded /opt/payfrit-api paths in codebase

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 22:32:55 -07:00
John Mizerek
aa986507fd Remove all Lucee references — uploads now live under /opt/payfrit-api
- Moved uploads from Lucee webroot to /opt/payfrit-api/uploads/
- Updated nginx on both dev and biz to alias /uploads/ to new path
- Replaced luceeWebroot() with uploadsRoot() helper
- Temp files now use /opt/payfrit-api/temp/
- No more /opt/lucee or /var/www/biz.payfrit.com references

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 22:26:52 -07:00
John Mizerek
28d86ba6e5 Fix production webroot path — both servers use /opt/lucee/tomcat/webapps/ROOT
Added luceeWebroot() helper to avoid repeating the path. The previous
fix incorrectly used /var/www/biz.payfrit.com for production, but both
dev and biz use the same Lucee webroot.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 22:19:10 -07:00
John Mizerek
4a4a098551 Fix upload paths to use Lucee webroot and accept uppercase OTP keys
Upload endpoints were saving files to PHP's DOCUMENT_ROOT instead of
the Lucee webroot where the Android app loads them from. Also fix
verifyLoginOTP and verifyOTP to accept both UUID/OTP and uuid/otp keys.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 22:04:27 -07:00
John Mizerek
3d9084d848 Add platform_images mode with stealth Playwright for order.online
- Stealth Playwright bypasses Cloudflare bot protection
- Multiple selector strategies for menu item cards
- Fuzzy name matching (exact, normalized, partial)
- Background-image extraction as fallback
- Script auto-created at /opt/playwright/platform-images.js

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 20:22:10 -07:00
John Mizerek
24849c01e4 Fetch contact/about page during discovery for business info
- Detect contact/about/location/hours links on main page
- Fetch contact page and extract phone, address, hours
- Phone: regex for US phone formats + tel: links
- Address: US street address pattern (number + street type)
- Hours: day + time range patterns from plain text
- Overrides bad JSON-LD data with actual contact page info

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 18:26:19 -07:00
John Mizerek
b48f20011d Fix address parsing: proper US format detection (Street, City, ST ZIP)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 18:11:41 -07:00
John Mizerek
1df69463a8 Fix discovery business info extraction
- Prefer title tag for name over JSON-LD (sites often put address in LD name)
- Parse full address string into components (addressLine1, city, state, zip)
- Handle newlines in addresses (Squarespace puts newlines in JSON-LD)
- Convert 24h hours to 12h format
- Strip country suffix from addresses

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 18:09:54 -07:00
John Mizerek
a14213151f Extract per-menu schedule in extract_page mode
- Claude prompt now asks for menuSchedule (days/times this menu is served)
- Separates menu schedule from overall business hours
- Returns menuSchedule in response for frontend to use

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 17:45:05 -07:00
John Mizerek
571930ed25 Extract business info during discovery phase
- Parse JSON-LD structured data (Restaurant, FoodEstablishment, etc.)
- Extract phone from tel: links, address from og: meta tags
- Return businessInfo in discovery response so sub-pages don't need it

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 17:34:55 -07:00
John Mizerek
4ac13de09d Add discovery + multi-page extract modes for setup wizard
- Discovery mode: quick Playwright crawl returns detected menu sub-pages
- Extract_page mode: processes single menu page through Claude individually
- More aggressive HTML stripping: removes SVG, nav, footer, form, attributes
- Increased truncation limit from 100KB to 200KB for generic fallback path
- Enables interactive wizard flow: discover → confirm → extract each page

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 17:03:54 -07:00
John Mizerek
552c404cf6 Server-side address parsing: split combined address into components
Claude returns address as one string with country suffix.
Now strips "United States/USA", extracts ZIP, state, splits
address line and city server-side before sending to wizard.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 16:45:34 -07:00
John Mizerek
a7464545df Support multiple menus in wizard import (Brunch/Lunch/Dinner)
- Updated Claude prompt to detect separate menus vs categories
- Added platformImageMap and subPagesVisited parsing from Playwright
- Bumped Playwright wait from 5s to 10s for sub-page crawling
- saveWizard.php creates separate Menus rows and assigns categories/items
  to the correct menu based on each item's "menu" field

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 16:29:38 -07:00
John Mizerek
08ef54976f Port Twilio SMS integration from CFML to PHP
Add sendSMS() to helpers.php using Twilio REST API with cURL,
credentials loaded from config/twilio.json. Wire into sendOTP,
loginOTP, and sendLoginOTP endpoints, replacing TODO stubs.
SMS is auto-skipped on dev environments.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 16:02:34 -07:00
John Mizerek
4d806d4e1e Port admin, cron, and receipt endpoints from CFML to PHP
- admin/quickTasks: list, create, save, delete
- admin/scheduledTasks: list, save, delete, toggle, run, runDue
- cron: expireStaleChats, expireTabs
- receipt: public order receipt page (no auth, UUID-secured)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-14 15:57:25 -07:00
John Mizerek
bd913bb46d Fix PUBLIC_ROUTES case-sensitivity bug in runAuth (strtolower path vs mixed-case routes) 2026-03-14 15:11:04 -07:00
John Mizerek
1f81d98c52 Initial PHP API migration from CFML
Complete port of all 163 API endpoints from Lucee/CFML to PHP 8.3.
Shared helpers in api/helpers.php (DB, auth, request/response, security).
PDO prepared statements throughout. Same JSON response shapes as CFML.
2026-03-14 14:26:59 -07:00