Developing the backend

LoadingObjectManager performs all operations with objects (adding to the map, clustering, and so on) on the client side. However, information about these objects is stored on the server, and the manager sends requests to it to get needed data.

To achieve maximal performance when working with the manager, you must design the backend architecture correctly. First of all, you need to determine what format will be used for storing data on the server, and how requests from the client will be processed. You should also decide whether to use server data caching.

When creating LoadingObjectManager, the developer sets the mode that the manager will use for loading data. The manager supports two data loading modes: for the entire viewport simultaneously, and by tiles. The loading mode determines the frequency of server requests and the speed of data loading.

In addition, when creating the manager, the developer specifies how the manager will request data for the needed viewport: by geographic coordinates, or by tile numbers. The structure of data on the server may vary, depending on how data is requested.

Data storage on the server

Spatial databases are the most suitable for storing information about geographic objects. Many database management systems have extensions for accessing spatial objects. For example, MySQL has SPATIAL, and PostgreSQL has PostGIS. Spatial indexes are also supported by other standard databases, such as Oracle and MongoDB.

Data loading modes are described below, along with recommendations for organizing data structures with various request parameters.

Data loading modes

When an area of the map is shown on a page, the manager calculates which tiles are in this area, and requests data for these tiles from the server if necessary (for more information about tiles, see the section Background information).

The manager supports two data loading modes: it can request data for the entire viewport at once, or for separate tiles. The data loading mode is set on the client side when creating the manager, using the splitRequests parameter. This parameter can take the value true or false (default).

Data loading mode

Description

splitRequests = false

Data is requested for the entire map viewport simultaneously.

Advantages

  • Since the manager loads data immediately for the entire area in a single request, this mode reduces the number of requests to the server.

Disadvantages

  • The server response must be formed dynamically.
  • Organizing server caching of data is more complex than when using splitRequests = true.
Request example

http://my-server.ru/?bbox=55.12,36.42,55.02,36.94&callback=myCallback_55.12_36.42_55.02_36.94

Request example

http://my-server.ru/?tileBounds=1,1,5,6&z=5&callback=myCallback_1_1_5_6

splitRequests = true

Data for the entire map viewport is requested by separate tiles.

Advantages

  • The server response can be formed for each tile ahead of time.
  • It is not difficult to organize server data caching.

Disadvantages

  • The server is sent a separate request for each tile. This may lead to a heavy load on the server and increased data loading time on poor connections.
Request example

http://my-server.ru/?bbox=55.12,36.42,55.02,36.94&z=10&callback=myCallback_55.12_36.42_55.02_36.94

Request example

http://my-server.ru/?tileBounds=1,1,5,6&z=5&callback=myCallback_1_1_5_6

Request parameters

When creating the manager, the developer specifies the URL template that the manager will use for forming requests to the server. The template defines parameters describing the borders of the area that data should be loaded for.

The following set of parameters is available for each mode:

  • bbox — Geographic coordinates of the lower-left and upper-right corners of the area.
  • tileBounds — Numbers of the upper-left and lower-right tiles of the area.
  • x, y — Tile numbers on the x and y axes, respectively (this parameter is only available when splitRequests = true).
  • z — Zoom level.

In addition to the parameters listed, the client passes the server the callback parameter — the name of the function that the server should wrap the response in. For more information, see the section Server response format.

Alert

If data will be requested by tile numbers, the developer must be able to project geographic objects onto the tile plane. For more information on projections that can be used in Yandex Maps, see the section Background information.

Ways to request data from the server are covered below, along with recommendations for data storage for each method.

Request data for a separate tile by geographic coordinates (splitRequests = true)

Using this method, data is requested from the server for a separate tile by the geographic coordinates of its lower-left and upper-right corners. The coordinates are passed in the 'bbox' GET parameter.

Request example:

http://my-server.ru/?bbox=55.12,36.42,55.02,36.94&callback=...

Note

In addition to the bbox parameter, the client passes the server the callback parameter — the name of the function that the server should wrap the response in. For more information, see the section Server response format.

For this method of requesting data, the spatial database index can be set as the field containing geographic coordinates of tile corners.

Despite the fact that tile data is requested by the geographic coordinates of tile corners, it is relatively simple to set up data caching on the server. This is because the map is made up of a finite number of tiles, and the corners of each tile at a particular zoom level always have the same geographic coordinates. Thus, data can be cached on the server for each tile by specifying the geographic coordinates of its lower-left and upper-right corners as the caching key.

Request data for a separate tile by its number (splitRequests = true)

Data is requested from the server for a separate tile by its number. The request passes the parameters x and y, which are the tile numbers on the x and y axes, respectively.

Request example:

http://my-server.ru/?x=20&y=30&z=10&callback=...

Note

Besides the x and y parameters, the request must pass the z parameter, which is the zoom level. In addition, the client always passes the server the callback parameter, which is the name of the function that the server should wrap the response in. For more information, see the section Server response format.

When the client requests data by tiles, it forms a finite number of requests to the server (because the map is made up a finite number of tiles). To avoid accessing the database each time a new request is received from the client, the response can be cached for each request. As caching keys, the request parameters can be set: x, y, and z. Server caching can be implemented using memcached or, for example, redis.

Request data for the entire area by geographic coordinates (splitRequests = false)

In this case, the manager requests data from the server for the entire area at once by the geographic coordinates of its lower-left and upper-right corners.

The coordinates are specified in the bbox GET parameter.

Request example:

http://my-server.ru/?bbox=55.12,36.42,55.02,36.94&callback=...

Note

In addition to the bbox parameter, the client passes the server the callback parameter — the name of the function that the server should wrap the response in. For more information, see the section Server response format.

When data is requested from the server by the area's geographic coordinates, a field containing the latitude and longitude of the tile corners is set as the spatial database index. You can get a selection of objects that are in this area, and then create a JSON description for these objects that is returned to the client.

Request data for the entire area by tile numbers (splitRequests = false)

In this case, the manager requests data from the server for the entire visible area at once by the numbers of its upper-left and lower-right tiles. The tiles numbers are passed in the request in the tileBounds GET parameter.

Request example:

http://my-server.ru/?tileBounds=1,1,10,9&z=10&callback=..

Note

Besides the tileBounds parameter, the request must pass the z parameter, which is the zoom level. In addition, the client always passes the server the callback parameter, which is the name of the function that the server should wrap the response in. For more information, see the section Server response format.

Using this method of requesting data, you can set up a composite index in the database with the keys x, y, and z (for more information about creating composite indexes, see this article). Then you will be able to get a selection from the database based on the generated key, as with geocoordinates.

Depending on the user's actions on the map, the sizes of requested areas may vary. For this reason, it is optimal to cache the selection from the database by tiles. Since the server is passed the tileBounds parameter, which contains the numbers of the first and last tiles in the area, it is not difficult to determine the numbers of the rest of the tile in this area. Then when data is requested for some tiled area, «piece together» the response from the data for each tile that is in the area, and send the response to the client.

There are many tools available for implementing data caching on the server (for example, memcached or redis). As the caching key, you can use the parameters x, y, and z.

Server response format

The description of objects is given in JSON format. It should contain the coordinates and object IDs, as well as information about their geometries. It can also specify additional information about the objects being added, such as their balloon contents.

Example of a JSON description of objects
{
  "type": "FeatureCollection",
  "features": [
    {
      "type": "Feature",
      "id": 0,
      "geometry": {
        "type": "Point",
        "coordinates": [55.831903, 37.411961]
      },
      "properties": {
        "balloonContent": "Balloon content",
        "clusterCaption": "Placemark 1",
        "hintContent": "Hint text"
      }
    },
    {
      "type": "Feature",
      "id": 2,
      "geometry": {
        "type": "Point",
        "coordinates": [55.763338, 37.565466]
      },
      "properties": {
        "balloonContent": "Balloon content",
        "clusterCaption": "Placemark 2",
        "hintContent": "Hint text"
      }
    }
  ]
}

The ID uniquely identifies each object of the manager. You can use the ID to get access to the desired object and, for example, change its properties or options. Object IDs are required attributes, and the developer must create them independently.

Wrapping the response in a callback function

The server should return data wrapped in a callback function. The manager passes the server the name of this callback function in the 'callback' GET parameter:

'{data URL}?callback={callback function name}&...'

The name of the function is set on the client side when creating the manager, in the paddingTemplate parameter.

If the paddingTemplate parameter is set on the client, the names of the callback functions will be known ahead of time for every request to the server. So this name will not have to be defined on the server — when placing data in static files, the JSON description for a tile can be pre-wrapped in the set function. For example, if the template for the callback function name is defined as 'myCallback_%c', for the tile with the number [1,2] and z=5 this description can be created on the server:

myCallback_x_1_y_2_z_5({
  "type": "FeatureCollection",
  "features": [
    ... 
  ]
})

If the name of the callback function is not set when creating the manager, the manager will automatically generate new names for these functions each time before sending a request.

'{data URL}?callback=id_1234567'