예제 #1
0
def book_order(request):
    """
    Book an order: send it to the dispatcher to get an order assignment,
    then pass the assignment to the station manager.
    """
    order_id = int(request.POST["order_id"])
    logging.info("book_order_task: %d" % order_id)
    order = get_object_or_404(Order, id=order_id)
    passenger = order.passenger

    # if this is the first order of this passenger, connect him with the station that originated the order
    if order.originating_station and passenger.orders.count() == 1:
        logging.info("assigning passenger %s to station %s" % (passenger, order.originating_station))
        passenger.originating_station = order.originating_station
        if not passenger.default_station:
            passenger.default_station = order.originating_station

        passenger.save()

    sorry_msg = ugettext_noop("We're sorry, but we could not find a taxi for you") # use dummy ugettext for makemessages)

    # check if dispatching should stop and return an answer to the user
    if (utc_now() - order.create_date).seconds > ORDER_HANDLE_TIMEOUT:
        try:
            order.change_status(new_status=TIMED_OUT)
            send_msg_to_passenger(passenger, translate_to_lang(sorry_msg, order.language_code))
            logging.warning("order time out: %d" % order_id)
            response = HttpResponse(ORDER_TIMEOUT)
        except UpdateStatusError:
            logging.error("book_order failed: cannot set order [%d] status to %s" % (order.id, "TIME_OUT"))
    else:
        try:
            # choose an assignment for the order and push it to the relevant workstation
            order_assignment = dispatcher.assign_order(order)
            push_order(order_assignment)
            enqueue_redispatch_orders(order_assignment, ORDER_TEASER_TIMEOUT, redispatch_pending_orders)
            response = HttpResponse(ORDER_HANDLED)

        except NoWorkStationFoundError:
            try:
                order.change_status(new_status=FAILED)
                send_msg_to_passenger(passenger, translate_to_lang(sorry_msg, order.language_code)) # use dummy ugettext for makemessages

                log_event(EventType.ORDER_FAILED, order=order, passenger=order.passenger)
                logging.warning("no matching workstation found for: %d" % order_id)
                response = HttpResponse(NO_MATCHING_WORKSTATIONS_FOUND)
            except UpdateStatusError:
                logging.error("book_order failed: cannot set order [%d] status to %s" % (order.id, "FAILED"))

        except Exception, e:
            try:
                order.change_status(new_status=ERROR)
                send_msg_to_passenger(passenger, translate_to_lang(ugettext_noop("We're sorry, but we have encountered an error while handling your request")
                             , order.language_code)) # use dummy ugettext for makemessages
                log_event(EventType.ORDER_ERROR, order=order, passenger=order.passenger)
                logging.error("book_order: OrderError: %d" % order_id)
                raise # handle exception in decorator 
            except UpdateStatusError:
                logging.error("book_order failed: cannot set order [%d] status to %s" % (order.id, "ERROR"))
예제 #2
0
def get_tracker_msg_for_order(order, last_assignment=None):
    msg = {}

    # new order, still pending
    if order.status == PENDING:
        msg.update({"pk": order.id,
                    "status": PENDING,
                    "from_raw": order.from_raw,
                    "to_raw": order.to_raw,
                    })

    # order is assigned, get status from the most recent assignment
    elif order.status == ASSIGNED:
        if not last_assignment:
            try:
                last_assignment = OrderAssignment.objects.filter(order=order).order_by('-create_date')[0]
            except IndexError:
                logging.error("tracker msg error: cannot get last assignment of order %d" % order.id)

        if last_assignment and last_assignment.status in [PENDING, ASSIGNED]:
            msg.update({"pk": order.id,
                        "status": last_assignment.status,
                        "from_raw": order.from_raw,
                        "to_raw": order.to_raw,
                        "info": translate_to_lang(STATUS_MESSAGES[last_assignment.status], order.language_code),
                        "station": last_assignment.station.name,
                        })

    # order has final status
    elif order.status == ACCEPTED:
        pickup_hour = order.modify_date + datetime.timedelta(minutes=order.pickup_time)
        msg.update({"pk": order.id,
                    "status": ACCEPTED,
                    "from_raw": order.from_raw,
                    "to_raw": order.to_raw,
                    "info": translate_to_lang(STATUS_MESSAGES[ACCEPTED], order.language_code),
                    "station": order.station_name,
                    "station_phone": str(order.station.phones.all()[0]),
                    "pickup_time_sec": order.get_pickup_time(),
                    "pickup_hour": pickup_hour.strftime("%H:%M"),
                    })

    elif order.status in [TIMED_OUT, FAILED, ERROR]:
        msg.update({"pk": order.id,
                    "status": FAILED,
                    "from_raw": order.from_raw,
                    "to_raw": order.to_raw,
                    "info": translate_to_lang(STATUS_MESSAGES[FAILED], order.language_code),
                    })

    return msg
예제 #3
0
 def _notify_order_passenger(order):
     logging.info("Ride status update: notifying passenger about taxi location for order: %s" % order)
     msg = translate_to_lang(_("To view your taxi: "), order.language_code)
     url = " http://%s%s" % (settings.DEFAULT_DOMAIN,
                            reverse("ordering.passenger_controller.track_order", kwargs={"order_id": order.id}))
     msg += url
     send_msg_to_passenger(order.passenger, msg)
예제 #4
0
def handle_approved_orders(sender, signal_type, order, status, **kwargs):
    from common.util import notify_by_email, send_mail_as_noreply
    from common.langsupport.util import translate_to_lang
    from ordering.models import APPROVED
    from sharing.passenger_controller import get_passenger_ride_email

    logging.info("handle_approved_orders: %s" % status)
    if status == APPROVED:

        # send confirmation email
        passenger = order.passenger
        if passenger.user and passenger.user.email:
            msg = get_passenger_ride_email(order)
            send_mail_as_noreply(passenger.user.email, translate_to_lang("WAYbetter Order Confirmation", order.language_code), html=msg)
            notify_by_email("Order Confirmation [%s]%s" % (order.id, " (DEBUG)" if order.debug else ""), html=msg)
예제 #5
0
def handle_approved_orders(sender, signal_type, order, status, **kwargs):
    from common.util import notify_by_email, send_mail_as_noreply
    from common.langsupport.util import translate_to_lang
    from ordering.models import APPROVED
    from sharing.passenger_controller import get_passenger_ride_email

    logging.info("handle_approved_orders: %s" % status)
    if status == APPROVED:

        # send confirmation email
        passenger = order.passenger
        if passenger.user and passenger.user.email:
            msg = get_passenger_ride_email(order)
            send_mail_as_noreply(passenger.user.email,
                                 translate_to_lang(
                                     "WAYbetter Order Confirmation",
                                     order.language_code),
                                 html=msg)
            notify_by_email("Order Confirmation [%s]%s" %
                            (order.id, " (DEBUG)" if order.debug else ""),
                            html=msg)
예제 #6
0
def accept_order(order, pickup_time, station):
    try:
        order.pickup_time = pickup_time
        order.station = station
        order.future_pickup = True
        order.save()

        # only change status after updating order values so that signal handler will see updated order
        order.change_status(ASSIGNED, ACCEPTED)

        enqueue_update_future_pickup(order, order.pickup_time*60)

        msg = translate_to_lang(
            ugettext_noop("Pickup at %(from)s in %(time)d minutes.\nStation: %(station_name)s, %(station_phone)s"),
            order.language_code) %\
              {"from": order.from_raw,
               "time": pickup_time,
               "station_name": order.station_name,
               "station_phone": station.phones.all()[0].local_phone} # use dummy ugettext for makemessages

        send_msg_to_passenger(order.passenger, msg)
    except UpdateStatusError:
        logging.error("accept_order failed [%d]: cannot mark order as %s" % (order.id, "ACCEPTED"))
예제 #7
0
def accept_order(order, pickup_time, station):
    try:
        order.pickup_time = pickup_time
        order.station = station
        order.future_pickup = True
        order.save()

        # only change status after updating order values so that signal handler will see updated order
        order.change_status(ASSIGNED, ACCEPTED)

        enqueue_update_future_pickup(order, order.pickup_time * 60)

        msg = translate_to_lang(
            ugettext_noop("Pickup at %(from)s in %(time)d minutes.\nStation: %(station_name)s, %(station_phone)s"),
            order.language_code) %\
              {"from": order.from_raw,
               "time": pickup_time,
               "station_name": order.station_name,
               "station_phone": station.phones.all()[0].local_phone} # use dummy ugettext for makemessages

        send_msg_to_passenger(order.passenger, msg)
    except UpdateStatusError:
        logging.error("accept_order failed [%d]: cannot mark order as %s" %
                      (order.id, "ACCEPTED"))
예제 #8
0
def get_tracker_msg_for_order(order, last_assignment=None):
    msg = {}

    # new order, still pending
    if order.status == PENDING:
        msg.update({
            "pk": order.id,
            "status": PENDING,
            "from_raw": order.from_raw,
            "to_raw": order.to_raw,
        })

    # order is assigned, get status from the most recent assignment
    elif order.status == ASSIGNED:
        if not last_assignment:
            try:
                last_assignment = OrderAssignment.objects.filter(
                    order=order).order_by('-create_date')[0]
            except IndexError:
                logging.error(
                    "tracker msg error: cannot get last assignment of order %d"
                    % order.id)

        if last_assignment and last_assignment.status in [PENDING, ASSIGNED]:
            msg.update({
                "pk":
                order.id,
                "status":
                last_assignment.status,
                "from_raw":
                order.from_raw,
                "to_raw":
                order.to_raw,
                "info":
                translate_to_lang(STATUS_MESSAGES[last_assignment.status],
                                  order.language_code),
                "station":
                last_assignment.station.name,
            })

    # order has final status
    elif order.status == ACCEPTED:
        pickup_hour = order.modify_date + datetime.timedelta(
            minutes=order.pickup_time)
        msg.update({
            "pk":
            order.id,
            "status":
            ACCEPTED,
            "from_raw":
            order.from_raw,
            "to_raw":
            order.to_raw,
            "info":
            translate_to_lang(STATUS_MESSAGES[ACCEPTED], order.language_code),
            "station":
            order.station_name,
            "station_phone":
            str(order.station.phones.all()[0]),
            "pickup_time_sec":
            order.get_pickup_time(),
            "pickup_hour":
            pickup_hour.strftime("%H:%M"),
        })

    elif order.status in [TIMED_OUT, FAILED, ERROR]:
        msg.update({
            "pk":
            order.id,
            "status":
            FAILED,
            "from_raw":
            order.from_raw,
            "to_raw":
            order.to_raw,
            "info":
            translate_to_lang(STATUS_MESSAGES[FAILED], order.language_code),
        })

    return msg
예제 #9
0
def book_order(request):
    """
    Book an order: send it to the dispatcher to get an order assignment,
    then pass the assignment to the station manager.
    """
    order_id = int(request.POST["order_id"])
    logging.info("book_order_task: %d" % order_id)
    order = get_object_or_404(Order, id=order_id)
    passenger = order.passenger

    # if this is the first order of this passenger, connect him with the station that originated the order
    if order.originating_station and passenger.orders.count() == 1:
        logging.info("assigning passenger %s to station %s" %
                     (passenger, order.originating_station))
        passenger.originating_station = order.originating_station
        if not passenger.default_station:
            passenger.default_station = order.originating_station

        passenger.save()

    sorry_msg = ugettext_noop(
        "We're sorry, but we could not find a taxi for you"
    )  # use dummy ugettext for makemessages)

    # check if dispatching should stop and return an answer to the user
    if (utc_now() - order.create_date).seconds > ORDER_HANDLE_TIMEOUT:
        try:
            order.change_status(new_status=TIMED_OUT)
            send_msg_to_passenger(
                passenger, translate_to_lang(sorry_msg, order.language_code))
            logging.warning("order time out: %d" % order_id)
            response = HttpResponse(ORDER_TIMEOUT)
        except UpdateStatusError:
            logging.error(
                "book_order failed: cannot set order [%d] status to %s" %
                (order.id, "TIME_OUT"))
    else:
        try:
            # choose an assignment for the order and push it to the relevant workstation
            order_assignment = dispatcher.assign_order(order)
            push_order(order_assignment)
            enqueue_redispatch_orders(order_assignment, ORDER_TEASER_TIMEOUT,
                                      redispatch_pending_orders)
            response = HttpResponse(ORDER_HANDLED)

        except NoWorkStationFoundError:
            try:
                order.change_status(new_status=FAILED)
                send_msg_to_passenger(passenger,
                                      translate_to_lang(
                                          sorry_msg, order.language_code)
                                      )  # use dummy ugettext for makemessages

                log_event(EventType.ORDER_FAILED,
                          order=order,
                          passenger=order.passenger)
                logging.warning("no matching workstation found for: %d" %
                                order_id)
                response = HttpResponse(NO_MATCHING_WORKSTATIONS_FOUND)
            except UpdateStatusError:
                logging.error(
                    "book_order failed: cannot set order [%d] status to %s" %
                    (order.id, "FAILED"))

        except Exception, e:
            try:
                order.change_status(new_status=ERROR)
                send_msg_to_passenger(
                    passenger,
                    translate_to_lang(
                        ugettext_noop(
                            "We're sorry, but we have encountered an error while handling your request"
                        ), order.language_code
                    ))  # use dummy ugettext for makemessages
                log_event(EventType.ORDER_ERROR,
                          order=order,
                          passenger=order.passenger)
                logging.error("book_order: OrderError: %d" % order_id)
                raise  # handle exception in decorator
            except UpdateStatusError:
                logging.error(
                    "book_order failed: cannot set order [%d] status to %s" %
                    (order.id, "ERROR"))