Как создавать поездки с общим маршрутом

В этом документе описывается, как создать совместную поездку, задать правильные поля и назначить ее транспортному средству для выполнения. Предполагается, что вы настроили Fleet Engine, создали транспортные средства, у вас есть работающее приложение для водителей и, возможно, приложение для пользователей. Вы также должны быть знакомы с различными сценариями поездок по запросу. Ознакомьтесь со следующими руководствами:

Основы создания поездок

В этом разделе описываются сведения о запросе, необходимые для создания поездки в Fleet Engine. Вы отправляете запрос на создание с помощью gRPC или REST.

  • Метод CreateTrip(): gRPC или REST.
  • Сообщение CreateTripRequest: только gRPC

Поля поездки

Чтобы создать поездку в Fleet Engine, используйте следующие поля. Для разных типов поездок можно использовать разные поля: с одним или несколькими пунктами назначения, последовательные или совместные. Необязательные поля можно заполнить при создании поездки или позже, при ее обновлении.

Поля поездки
Название Обязательно? Описание
parent Да Строка, содержащая идентификатор проекта. Этот идентификатор должен быть таким же, как и во всей интеграции Fleet Engine, с теми же ролями сервисного аккаунта.
trip_id Да Строка, которую вы создаете для уникальной идентификации этой поездки. Для идентификаторов поездок действуют определенные ограничения, указанные в справочной документации.
trip_type Да Задайте для TripType одно из следующих значений в зависимости от типа поездки:
  • Один пункт назначения. Укажите SHARED или EXCLUSIVE.
  • Multi-destination (Несколько пунктов назначения): EXCLUSIVE.
  • Back-to-back: установите значение EXCLUSIVE.
  • Общий пул. Задайте значение SHARED.
pickup_point Да Пункт отправления.
Промежуточные пункты Да

Только для поездок с несколькими пунктами назначения. Список промежуточных пунктов назначения, которые водитель посещает между посадкой и высадкой. Как и в случае с dropoff_point, это поле также можно задать позже, вызвав UpdateTrip, но поездка с несколькими пунктами назначения по определению содержит промежуточные пункты назначения.

vehicle_waypoints Да

Только для совместных поездок. В этом поле можно чередовать путевые точки из разных поездок. Он содержит все оставшиеся путевые точки для назначенного транспортного средства, а также путевые точки посадки и высадки для этой поездки. Чтобы задать это поле, вызовите метод CreateTrip или UpdateTrip. Вы также можете обновить путевые точки транспортного средства через поле waypoints с помощью вызова UpdateVehicle. Из соображений конфиденциальности сервис не возвращает эту информацию при вызовах GetTrip.

number_of_passengers Нет Количество пассажиров.
dropoff_point Нет Пункт назначения поездки.
vehicle_id Нет Идентификатор транспортного средства, назначенного для поездки.

Пример: создание совместной поездки

В приведенном ниже примере интеграции серверной части показано, как создать поездку и назначить ее транспортному средству в качестве совместной поездки.

// Vehicle with VEHICLE_ID ID is already created and it is assigned Trip A.

static final String PROJECT_ID = "my-rideshare-co-gcp-project";
static final String TRIP_ID = "shared-trip-A";
static final String VEHICLE_ID = "your-vehicle-id";
static final String TRIP_A_ID = "trip-a-id";
static final String TRIP_B_ID = "trip-b-id";

TripServiceBlockingStub tripService = TripService.newBlockingStub(channel);

String parent = "providers/" + PROJECT_ID;

LatLng tripBPickup =
    LatLng.newBuilder().setLatitude(-12.12314).setLongitude(88.142123).build();
LatLng tripBDropoff =
    LatLng.newBuilder().setLatitude(-14.12314).setLongitude(90.142123).build();

TerminalLocation tripBPickupTerminalLocation =
    TerminalLocation.newBuilder().setPoint(tripBPickup).build();
TerminalLocation tripBDropoffTerminalLocation =
    TerminalLocation.newBuilder().setPoint(tripBDropoff).build();

// TripA already exists and it's assigned to a vehicle with VEHICLE_ID ID.
Trip tripB = Trip.newBuilder()
    .setTripType(TripType.SHARED)
    .setVehicleId(VEHICLE_ID)
    .setPickupPoint(tripBPickupTerminalLocation)
    .setDropoffPoint(tripBDropoffTerminalLocation)
    .addAllVehicleWaypoints(
        // This is where you define the arrival order for unvisited waypoints.
        // If you don't specify an order, then the Fleet Engine adds Trip B's
        // waypoints to the end of Trip A's.
        ImmutableList.of(
            // Trip B's pickup point.
            TripWaypoint.newBuilder()
                .setLocation(tripBPickupTerminalLocation)
                .setTripId(TRIP_B_ID)
                .setWaypointType(WaypointType.PICKUP_WAYPOINT_TYPE)
                .build(),
            // Trip A's drop-off point.
            TripWaypoint.newBuilder()
                .setLocation(tripA.getDropoffPoint())
                .setTripId(TRIP_A_ID)
                .setWaypointType(WaypointType.DROP_OFF_WAYPOINT_TYPE)
                .build(),
            // Trip B's drop-off point.
            TripWaypoint.newBuilder()
                .setLocation(tripBDropoffTerminalLocation)
                .setTripId(TRIP_B_ID)
                .setWaypointType(WaypointType.DROP_OFF_WAYPOINT_TYPE)
                .build()))
    .build();

// Create Trip request
CreateTripRequest createTripRequest = CreateTripRequest.newBuilder()
    .setParent(parent)
    .setTripId(TRIP_B_ID)
    .setTrip(tripB)
    .build();

try {
  // createdTrip.remainingWaypoints will contain shared-pool waypoints.
  // [tripB.pickup, tripA.dropoff, tripB.dropoff]
  Trip createdTrip = tripService.createTrip(createTripRequest);
} catch (StatusRuntimeException e) {
  Status s = e.getStatus();
  switch (s.getCode()) {
    case ALREADY_EXISTS:
      break;
    case PERMISSION_DENIED:
      break;
  }
  return;
}

Как обновлять совместные поездки

Чтобы Fleet Engine мог рассчитывать время прибытия и отслеживать поездку, ее нужно назначить транспортному средству. Это можно сделать как при создании поездки, так и позже, при ее обновлении.

Для совместных поездок необходимо указать порядок непосещенных путевых точек в коллекции путевых точек транспортного средства (Trip.vehicle_waypoints). Fleet Engine использует этот список для автоматического обновления путевых точек для всех поездок в совместном пуле.

Рассмотрим две поездки с совместным пулом: поездку А и поездку Б.

  • Поездка А направляется к месту высадки.
  • Затем тому же транспортному средству назначается поездка Б.

В одном запросе UpdateTripRequest для поездки Б вы задаете vehicleId, а также устанавливаете для Trip.vehicle_waypoints оптимальный порядок путевых точек: посадка Б → высадка А → высадка Б.

  • Вызов getVehicle() возвращает remainingWaypoints, содержащий:
    B Посадка → A Высадка → B Высадка.
  • Обратный вызов getTrip() или onTripRemainingWaypointsUpdated для поездки А возвращает remainingWaypoints, содержащий:
    посадку B → высадку A.
  • Обратный вызов getTrip() или onTripRemainingWaypointsUpdated для поездки Б возвращает remainingWaypoints, содержащий:
    Посадка для Б → Высадка для А → Высадка для Б.

Пример

В следующем примере интеграции серверной части показано, как обновить поездку, добавив идентификатор транспортного средства и путевые точки для двух совместных поездок.

static final String PROJECT_ID = "my-rideshare-co-gcp-project";
static final String TRIP_A_ID = "share-trip-A";
static final String TRIP_B_ID = "share-trip-B";
static final String VEHICLE_ID = "Vehicle";

String tripName = "providers/" + PROJECT_ID + "/trips/" + TRIP_B_ID;

// Get Trip A and Trip B objects from either the Fleet Engine or storage.
Trip tripA = …;
Trip tripB = …;

TripServiceBlockingStub tripService = TripService.newBlockingStub(channel);

// The trip settings to update.
Trip trip = Trip.newBuilder()
    .setVehicleId(VEHICLE_ID)
    .addAllVehicleWaypoints(
        // This is where you define the arrival order for unvisited waypoints.
        // If you don't specify an order, then the Fleet Engine adds Trip B's
        // waypoints to the end of Trip A's.
        ImmutableList.of(
            // Trip B's pickup point.
            TripWaypoint.newBuilder()
                .setLocation(tripB.getPickupPoint())
                .setTripId(TRIP_B_ID)
                .setWaypointType(WaypointType.PICKUP_WAYPOINT_TYPE)
                .build(),
            // Trip A's drop-off point.
            TripWaypoint.newBuilder()
                .setLocation(tripA.getDropoffPoint())
                .setTripId(TRIP_A_ID)
                .setWaypointType(WaypointType.DROP_OFF_WAYPOINT_TYPE)
                .build(),
            // Trip B's drop-off point.
            TripWaypoint.newBuilder()
                .setLocation(tripB.getDropoffPoint())
                .setTripId(TRIP_B_ID)
                .setWaypointType(WaypointType.DROP_OFF_WAYPOINT_TYPE)
                .build()))
    .build();

// The trip update request.
UpdateTripRequest updateTripRequest = UpdateTripRequest.newBuilder()
    .setName(tripName)
    .setTrip(trip)
    .setUpdateMask(FieldMask.newBuilder()
        .addPaths("vehicle_id")
        .addPaths("vehicle_waypoints"))
    .build();

// Error handling. If Fleet Engine has both a trip and vehicle with the IDs,
// and if the credentials validate, and if the given vehicle_waypoints list
// is valid, then the service updates the trip.
try {
  Trip updatedTrip = tripService.updateTrip(updateTripRequest);
} catch (StatusRuntimeException e) {
  Status s = e.getStatus();
  switch (s.getCode()) {
    case NOT_FOUND:          // Either the trip or vehicle does not exist.
      break;
    case PERMISSION_DENIED:
      break;
    case INVALID_REQUEST:    // vehicle_waypoints is invalid.
      break;
  }
  return;
}

Дальнейшие действия