1 điểm bởi GN⁺ 2023-09-11 | 1 bình luận | Chia sẻ qua WhatsApp
  • Để tránh tình trạng pizza ở điểm tiếp tế bị hết tại Gravel Worlds Long Voyage ở Nebraska, tôi đã tạo một hệ thống tự động đặt trước pizza Casey's dựa trên vị trí GPS của xe đạp
  • Cấu trúc hoạt động là geofence của AWS Location phát hiện thiết bị theo dõi GPS rời khỏi khu vực, rồi Lambda thực hiện đơn đặt hàng online theo ETA của điểm dừng tiếp theo
  • Vì Casey's không có API đặt hàng công khai, tôi dùng Playwright để screen scraping trang web React của họ, và cấu hình để nhận kết quả đơn hàng qua thông báo đẩy trên iPhone và Apple Watch
  • Trong cuộc đua thực tế, tôi nhận được thông báo đặt hàng thành công nhưng cửa hàng không có bản ghi đơn nào, cho thấy một false positive trong tự động hóa trình duyệt trên đám mây
  • Sau đó tôi đổi sang lưu video thao tác của trình duyệt lên S3, và đơn thử nghiệm đã thành công, nhưng trong môi trường Lambda thì chỉ kiểm thử cục bộ là không đủ để đảm bảo độ ổn định

Vì sao tôi muốn đảm bảo có pizza giữa cuộc đua

  • Tôi tham gia cuộc đua xe đạp Gravel Worlds Long Voyage ở Nebraska vào mùa thu hoạch tại Midwest
  • Năm trước, các tay đua nhanh hơn đến trước đã lấy hết pizza Casey's ở điểm tiếp tế, nên khi tôi tới nơi thì không còn chiếc nào
  • Mục tiêu năm nay là đặt trước pizza nóng mới ra lò đúng vào thời điểm dừng chân
  • Tôi định bổ sung vào hệ thống GPS tracker serverless sẵn có một cơ chế chạy script đặt hàng khi rời khỏi một geofence nhất định

Cách tôi dùng GPS và Lambda để kích hoạt đơn hàng

  • Thiết kế tổng thể là geofence của AWS Location giám sát thiết bị theo dõi GPS
    • Khi thiết bị rời geofence, nó sẽ kích hoạt một hàm Lambda
    • Lambda tính ETA đến điểm dừng tiếp theo
    • Dựa trên thời gian đó để đặt pizza Casey's
  • Casey's không có API công khai cho đặt hàng online, nên tôi chọn screen scraping trang web
    • Trang web của Casey's là một ứng dụng React phức tạp render phía client
    • Thay vì scraper thông thường, tôi dùng Playwright
    • Việc chạy Playwright trên Lambda khó đến mức tôi còn phải viết riêng một bài khác về nó
  • Để kiểm tra trạng thái đơn hàng, tôi cấu hình gửi thông báo đẩy tới điện thoại và đồng hồ khi thành công hoặc thất bại
    • Việc làm cho Web Push hoạt động trên thiết bị iOS cũng đủ phức tạp để thành một bài viết riêng

Kết quả tại hiện trường khác với thông báo thành công

  • Geofence dùng để kích hoạt đặt hàng được đặt quanh mốc 180 dặm của cuộc đua
  • Tôi dự định nhận pizza ở mốc 200 dặm
  • Khi rời geofence, đồng hồ của tôi nhận được thông báo đẩy rằng đơn pizza đã đặt thành công
  • Nhưng khi đến điểm dừng, quầy không có đơn hàng nào và cửa hàng cũng không lưu lại bản ghi đặt hàng
  • Sau khi kiểm tra tài khoản, tôi xác nhận không hề có đơn thực tế nào được tạo; đó chỉ là một false positive với thông báo thành công
  • Tại chỗ vẫn còn vài miếng pizza làm sẵn, nên tôi mua chúng
  • Sau đó, suốt quãng đường còn lại để hoàn thành cuộc đua 300 dặm, tôi cứ nghĩ mãi về việc hàm Lambda đã sai ở đâu

Video ghi lại thay cho log đã để lộ manh mối

  • Sau cuộc đua, tôi kiểm tra log nhưng không có thông tin nào cho thấy nguyên nhân thất bại
  • Trên log, mọi thứ trông như đã âm thầm thành công nên gần như không có đầu mối để debug
  • Vài ngày sau, tôi sửa Lambda để ghi video thao tác trình duyệt và tải nó lên bucket S3
  • Khi thử lại với thay đổi này, đơn hàng thực sự thành công và tôi đã nhận được một chiếc Hawaiian pizza như bình thường
  • Nguyên nhân chính xác vẫn chưa được xác định
    • Có thể Lambda đã kết thúc xử lý ngay sau khi form.submit() cuối cùng được chạy trong trình duyệt Playwright nhúng
    • Có thể trang đặt hàng online chưa kịp xác nhận phản hồi thành công từ trình duyệt nên không hoàn tất đơn hàng
    • Phần thời gian bổ sung để xử lý và tải video lên có thể đã cho trình duyệt đủ thời gian để dọn dẹp hoàn tất

Nếu làm lại lần nữa, tôi sẽ thay đổi gì

  • Việc screen scraping ổn định một ứng dụng React client bằng trình duyệt chạy trên đám mây là điều khả thi nhưng rất khó
  • Nếu làm lại, tôi có thể cân nhắc reverse engineering ứng dụng native của Casey's để gọi trực tiếp API nội bộ
  • Cần một quy trình làm việc tốt hơn để mô phỏng các hành vi địa không gian
    • Ban đầu tôi tạo geofence quanh nhà để thử nghiệm
    • Nhưng việc 11 giờ đêm lại phải đi bộ ra ngoài để test nhanh chóng trở nên quá phiền
  • Không nên cắt giảm kiểm thử trong môi trường thực tế
    • Trước cuộc đua, phần lớn việc thử nghiệm là chạy hàm trên máy trạm cục bộ
    • Điều đó tạo ra cảm giác tự tin sai lầm rằng nếu chạy được ở local thì trên Lambda cũng sẽ hoạt động đúng
  • Nếu bạn lo Casey's hết pizza, một cách khác là nới khoảng cách với nhóm phía trước lên hơn 30 phút để cửa hàng có thời gian làm thêm các miếng pizza mới
  • Mã nguồn đã được công khai trên GitHub: https://github.com/mattdsteele/spot-tracker-tracker/…

1 bình luận

 
GN⁺ 2023-09-11
Ý kiến trên Hacker News
  • Colin có thể vừa giao hàng vừa làm pizza cho bạn: https://youtu.be/YjyJRTM0knE?si=fes2lbRntUlciPSH

    • Buồn cười thật, nhưng ý tưởng trong video YouTube này thực ra từng là mô hình kinh doanh của một startup được SoftBank đầu tư, và họ đã nhận 500 triệu USD vốn đầu tư
      Khiếm khuyết chí mạng trong kế hoạch tưởng như kín kẽ đó là khi xe tải đi qua chỗ xóc trên đường, pizza bay lung tung và mất sạch topping: https://gizmodo.com/zume-softbank-ai-pizza-delivery-stellar-...
    • Hóa ra bỏ GIL thì sẽ thành thế này
      Video này làm tôi cười to nhất trong số những gì đã xem trên YouTube năm nay
    • Tôi không biết sự liều lĩnh của Colin là diễn như Electroboom, hay đúng là liều lĩnh như những gì ta thấy
      Đến giờ tôi vẫn không phân định được, và kỳ lạ là vì thế mà xem hơi khó chịu. Tất nhiên chắc anh ấy sẽ không đăng video nào mà mọi chuyện hỏng thật nặng
    • Trời ơi, cả tối Chủ nhật của tôi biến mất
      Tôi đã xem suốt 2 tiếng rưỡi video người này đào đường hầm từ nhà ra nhà kho, đúng là một kênh rất thú vị
  • Rất hay. Cảm giác như một cách diễn giải pizzatool theo kiểu thế kỷ 21
    https://donhopkins.medium.com/the-story-of-sun-microsystems-...
    Nhân tiện, tiệm pizza Waypoint Pizza ở Tiburon nếu nhờ khéo thì họ cũng giao ra trên mặt nước ở San Francisco Bay. Khá hữu ích trong những cuộc đua thuyền buồm kỳ quặc và không quá nghiêm túc như Three Bridge Fiasco

    • Giao pizza bình thường cũng có thể tốn thêm 5–10 đô, nên tôi tò mò nếu nhờ khéo thì giao trên mặt nước sẽ tốn khoảng bao nhiêu
  • Dean Karnazes từng làm việc tương tự trong một cuộc đua ultrarunning mà không cần công nghệ
    Nghe nói ông ấy cuộn pizza như burrito rồi vừa cầm vừa chạy: https://gffmag.com/the-raw-endurance-of-ultramarathon-man-de...

    • Chạy đường dài sức bền về cơ bản gần như là một hành vi ăn uống
  • Nếu là website React thì rất có khả năng nghĩa là có một API có thể dùng trực tiếp
    Có thể vẫn cần đăng nhập để lấy token, nhưng cách đó vững chắc hơn nhiều

    • Đồng ý. Tôi luôn bối rối vì sao người ta không theo dõi rồi phát lại network request thay vì scrape màn hình
      Rẻ hơn nhiều và vững chắc hơn nhiều, hay là tôi đang bỏ lỡ điều gì?
  • Tôi thật sự rất thích bài này
    Có nhiều yếu tố hay: một vấn đề kỹ thuật thú vị, pizza, khiến tôi phải tra xem “s-tier” nghĩa là gì, chỉ riêng tiền đề đã buồn cười mà còn thêm cả hài hước, rồi cả phần mea culpa cuối bài và suy đoán nguyên nhân bug. Lý thuyết đó nghe cũng có vẻ hợp lý, nhưng chưa chắc chắn

    • Tôi thì hoàn toàn không thích. Cảm giác như một thiết bị Rube Goldberg không hoạt động, được dựng bằng 100 lớp trừu tượng, keo dán đám mây và các giải pháp chắp vá
      Cứ như gom hết những mặt tệ của công nghệ hiện đại lại một chỗ
  • Thành thật mà nói thì khá ngầu. Tôi tự hỏi liệu có thể làm điều tương tự với các dịch vụ như Deliveroo không
    Vào một ngày X cụ thể, nếu điều kiện khớp, chẳng hạn khi đang làm thêm giờ và còn cách nhà khoảng Z, thì đặt trước đơn hàng Y đã định sẵn — nghe có vẻ khả thi

    • Vì sao lại phải nói dối rằng việc này khá ngầu? Việc cố tình nói rõ như vậy nghe hơi lạ
    • Kết nối với fitness tracker, để pizza chỉ được giao ở mức vừa đủ duy trì thâm hụt calo nhằm tiếp tục giảm cân
    • Các dịch vụ đặt đồ ăn có lẽ nên có API tốt cho những mục đích như thế này
      Có lý do gì để không cho phép tích hợp dễ dàng việc đặt món và thanh toán vào các kiểu hack như IFTTT đâu?
  • Tôi có ký ức đẹp khi lớn lên cùng pizza của Casey's
    Mỗi lần quay lại Midwest tôi đều mua ăn; khó nói chính xác là gì, nhưng nó có một sức hút riêng

    • Có phải vì nhiều dầu hơn không? Pizza ăn sáng là đỉnh nhất. Nhất là thường vào ngày hôm sau khi đã uống Busch Light
  • À, cuối cùng là nó không chạy được nhỉ
    Nếu phát hiện ra ở mốc 200 dặm thì chắc khá là nặng nề

  • Phần mềm, xe đạp và pizza — đúng là những thứ tôi thích trong đời
    Tôi rất thích dự án và bài viết này, và nó còn gợi cho tôi vài ý tưởng tương tự

    • Đây cũng là những thứ tôi thích. OP, bạn và tôi nên lập một câu lạc bộ
  • Nếu là tôi thì có lẽ tôi sẽ gọi điện rảnh tay, hoặc nhờ một người bạn gọi hộ rồi dùng tin nhắn để kích hoạt
    Và cứ gọi là “giao hàng”, nhưng thực ra không phải là đến lấy mang đi sao?