Step 4: Product mapping

The next step after registering your plugin is to map the product counterparts between Bókun extranet and external system. Each product in Bókun can be mapped to one external product only and vice versa.

In order to accomplish mapping, the same product has to exist on both Bókun extranet as well as the plugin side. There are two different API calls, both of which have to be implemented by the Inventory plugin.

gRPC service interfaces

gRPC-enabled plugins must implement the following API calls:

rpc SearchProducts(SearchProductsRequest) returns (stream io.bokun.inventory.common.api.grpc.BasicProductInfo) {}

The above call (further referred as searchProduct) may return multiple products, based on search criteria. This only requires basic product information to be supplied.

rpc GetProductById(GetProductByIdRequest) returns (io.bokun.inventory.common.api.grpc.ProductDescription) {}

The above call (further referred as getProductById) must return extended information about a single product requested.

REST URLs

REST-enabled plugins must implement the following API calls:

POST /product/search

The above call (further referred as searchProducts) may return multiple products, based on search criteria. This only requires basic product information to be supplied.

POST /product/getById

The above call (further referred as getProductById) must return extended information about a single product requested.

 

searchProducts call

searchProducts call takes a single SearchProductsRequest (in gRPC) or SearchProductsRequest (in REST) as an input parameter and returns a number of BasicProductInfos as its result.

 

SearchProductsRequest/SearchProductRequest have the following attributes:

Attribute
Mandatory
Notes
parameters
Plugin configuration parameters, as specified in Step 3. plugin configuration
productName
If specified, result set should only contain products matching given product name (substring match)
country
ISO ALPHA-2 country code. If specified, the result set should only contain products from given country
city
If specified, result set should only contain products matching given city name (substring match) this product is applicable for. If the product is not applicable to any city, this attribute can be ignored

If none of {productName, country, city} are specified, searchProducts should simply return a list of all available products.

BasicProductInfo object has the following attributes:

Attribute
Mandatory
Notes
id
Product ID on external system. Must be unique: no other product should return this id. Inventory service will maintain active bimap of external-to-internal references.
name
Product name on the external system
description
Product description on the external system
pricingCategories
Product categories (such as Adult, Child, etc.) this product is sold at - as referred by the remote system. Should have at least one element in the collection.
cities
Should list all cities (plain text format) this product is served at. Only optional if product is not applicable to a city. Multiple entries could be used for multi-city product
countries
Should list all countries (ISO ALPHA-2 codes) this product is for. If this product does not refer to any country, the field might remain unset, otherwise mandatory. The most typical case is having one country in the list
 

getProductById call

getProductById implements retrieval of the most detailed information about a given product. This information is used for the mapping between products as well it could be used as a template for creating a new product in Bókun. This call takes in GetProductByIdRequest as a parameter and returns ProductDescription.

 

GetProductByIdRequest has the following attributes:

Attribute
Mandatory
Notes
parameters
Plugin configuration parameters, as specified in Step 3. plugin configuration
externalId
Product id on the external system

ProductDescription has the following attributes:

Attribute
Mandatory
Notes
id
Product id on the external system. Must correspond to GetProductByIdRequest::externalId as well as BasicProductInfo::id
name
Product name on the external system. Must match BasicProductInfo::name
description
Product description on the external system. Must match BasicProductInfo::description
pricingCategories
Product categories (such as Adult, Child, etc.) this product is sold at - as referred by the remote system. Should have at least one element in the collection. Must match BasicProductInfo::pricingCategories
rates
Product rates (such as daily rate, weekly rate, etc.). Even if the remote system does not support the concept of rates, plugin must provide some default/mock rate for mapping
openingHours (gRPC only), allYearOpeningHours,seasonalOpeningHours
Opening hours when this product is available (similar to ship opening hours). Note that these are not departure times. Note: only one of {allYearOpeningHours, seasonalOpeningHours} may be present but not both. This is enforced in gRPC API by static proto construct; REST may have it enforced in runtime.
bookingType
If DATE, then this product does not have any start times. If DATE_AND_TIME, then this product is bookable for certain times within available days. If PASS, then this product is bookable so that participants could consume this product at any given day (providing ticket is not expired).
customPickupPlaceAllowed
see notes
Whether customer can be picked up at an arbitrary place, specified during the booking process. Mandatory if meetingType is one of {MEET_ON_LOCATION_OR_PICK_UP, PICK_UP}, otherwise irrelevant/ignored.
pickupMinutesBefore
see notes
How many minutes somebody should be picked up before the event takes place. Mandatory if meetingType is one of {MEET_ON_LOCATION_OR_PICK_UP, PICK_UP}, otherwise irrelevant/ignored.
pickupPlaces
see notes
A collection of predefined pick up places, supported by vendor. Mandatory (should have at least one entry) if meetingType is one of {MEET_ON_LOCATION_OR_PICK_UP, PICK_UP} and customPickupPlaceAllowed is false.
dropoffAvailable
Whether drop off is available for this product.
customDropoffPlaceAllowed
see notes
Whether customer can be dropped off at arbitrary place, specified during the booking process. Mandatory if dropoffAvailable is true, otherwise irrelevant/ignored.
dropoffPlaces
A collection of predefined drop off places, supported by vendor. Mandatory (should have at least one entry) if dropoffAvailable is true and customDropoffPlaceAllowed is false.
productCategory
Currently only experience type of products (aka activities) are supported hence the system expects ACTIVITIES here.
ticketSupport
Should specify what kind of tickets does this integration support (per booking or per person or none).
countries
Should list all countries (ISO ALPHA-2 codes) this product is for. If this product does not refer to any country, the field might remain unset, otherwise mandatory. The most typical case is having one country in the list. Must match BasicProductInfo::countries
cities
Should list all cities (plain text format) this product is served at. Only optional if product is not applicable to a city. Multiple entries could be used for multi-city product. Must match BasicProductInfo::cities
startTimes
see notes
Plugin should specify a collection of product start time(s), if bookingType=DATE_AND_TIME. Otherwise ignored
ticketType
see notes
What kind of tickets does this product generate? Currently supported types: • QR codeData Matrix • Binary Mandatory unless ticketSupport is set to TICKETS_NOT_REQUIRED. Binary tickets currently only support application/pdf content type meaning the plugin should send tickets in PDF format
meetingType
How are passengers arriving to the event (are they picked up or should arrive independently)?
enforcedLeadPassengerFields
A list of personal details fields this plugin requires to be filled for the lead passenger. If unset, no customer fields are forced during the booking process.
enfoorcedTravellerFields
A list of personal details fields this plugin requires to be filled for each traveller who is not lead passenger. If unset, no customer fields are forced during the booking process
extras
A list of extras available to book with this product

Binary ticket data object differences

Binary ticket data type, if supported by the plugin, has slight differences in terms of how it should be served using different transport protocol.

gRPC supports bytes type which is an arbitrary sequence of bytes, and which perfectly fits the purpose of serving application/pdf content.

REST has no such native byte stream support. As a result of this, REST object attribute counterpart (BinaryTicket::ticketContent) expects Base64-encoded byte stream instead.

Mapping process

Once the product information is returned to the Bókun platform, it will show a screen, similar to the one below:

The vendor (or Bókun support staff) would then go about mapping selected external products against local counterparts. Mapping specifics are not covered in this document as it is out of scope for plugin development. No API call is made for the mapping as Inventory service covers this without any additional involvement of the plugin.

Note: automatic price import as well as some other fields (such as start times) are not implemented in Bókun just yet, even though this information is provided by the plugin API. Make sure you go over product settings in Bókun platform to ensure all product properties are set correctly after mapping.

Did this answer your question?
😞
😐
🤩