OneLayer
Overview
OneLayer Flow is a part of the SkyPath SDK that provides a way to fetch and process data from the SkyPath platform for a specific area on the world map. The flow is designed to handle the complexity of data fetching, processing, and updating, providing a simple and efficient way to access and use the data in your application. The flow combines data from multiple sources: Nowcasting, Observations, Pireps, EDR, ADS-B
Startup and Initialization
Upon instantiation, Onelayer Flow sets up initial configurations and prepares the system for data fetching based on provided map polygon and other settings. It immediately subscribes to internal events to handle periodic updates and user-triggered changes.
To crate OneLayer Flow call createOneLayerFlow
factory method from sdk object.
See example:
// Initialize SDK
const sdk = await createSkyPathSDK(...);
// Create Observations Flow
const oneLayerFlow = sdk.createOneLayerFlow()
The createOneLayerFlow()
method doesn't take any arguments, all configuration for the flow is provided with updateConfig()
method.
Lifecycle Management
- Start: Allocates resources, setting up intervals and listeners for data updates;
- Update: Triggers an update of the data, fetching new data for relevant areas and settings;
- Stop: Temporarily stops all operations, keeps resources, and pauses updates / fetches;
- Terminate: Completely stops all operations, releases resources, and removes all listeners, effectively shutting down the flow;
Data Retrieval Process
Under the hood, OneLayer flow abstracts the complexity for communication with SkyPath platform API in efficient way handling necessary data transformations, mappings and access management:
- Data fetching: The data for the whole world map is being fetched based on the map polygon and settings set. It handles concurrent loading and ensures that only relevant data is fetched and in performant way;
- Data Merging: New data may be merged with already loaded areas of a world map, appending it to the stored values to reduce network load and computation time;
- Data enrichment: Once new data is available on the back-end side, the old data is being enriched with the fresh data;
Data update process is triggered automatically by the flow, but can also be triggered manually by the user by calling updateConfig()
method.
Automatic updates are triggered periodically every 1 minute.
Once data update is triggered and successfully completed, the flow emits data update event, which can be listened to by the user to update the UI or perform any other necessary actions. This can be done by subscribing to the event using onData
method that takes a callback function as an argument and returns OneLayerData object for current and previous data:
oneLayerFlow.onData((data, previousData) => {
// Use the data to update the UI
})
If an error occurs during the update process, the flow emits an error event, which can be listened to by the user to handle the error. This can be done by subscribing to the event using onError
method that takes a callback function as an argument and returns an Error object:
oneLayerFlow.onError((error) => {
// Handle the error
})
Tracking the processing status of the flow can be done by subscribing to the onIsProcessingChange
event. This event is emitted when the flow starts or stops processing data. The event returns a boolean
value indicating the processing status:
oneLayerFlow.onIsProcessingChange((isProcessing) => {
// Handle the processing status
})
Configuration
To update the flow with new settings, call updateConfig
method:
oneLayerFlow.updateConfig(config)
The updateConfig(config: Config)
method takes the following arguments where the polygon is a custom area on a world map and settings are the configuration for the flow:
Property | Description | Type | Default |
---|---|---|---|
polygon | Map viewport rectangle or a route corridor polygon | Polygon | null |
aircraftCategory | Aircraft category | AircraftCategory | "C60" |
isCorridorMode | Flag to indicate if the polygon is a route corridor or not | boolean | false |
forecastTs | a unix time stamp that can show you the future forcast up to 12 hours | unix time stamp / null | null |
nowcastingAlt | nowcasting source will show only one altitude using this value | nowcastingAlt | 35 |
hoursAgo | what's the experation of each report | hoursAgo | "1" |
Please note, that all properties are optional. If you provide partial configuration, for missing properties previous or default values will be used.
Example: If you first set aircraftCategory to C10
and then update the configuration without providing aircraftCategory
, the value will remain C10
.
You may also erase certain properties by setting them to null
if the flow supports it.
undefined
values are ignored and will not trigger any changes.
Requirements
We apply some requirements to the polygon size to ensure the performance of the flow. Depending if the polygon is a corridor or not, the flow will handle the polygon differently.
Default Mode
When dealing with default mode, meaning isCorridorMode
is false
, flow relates polygon to 1 of 3 sizes:
- Small: smaller than continental U.S.
- Medium: from small to large
- Large: larger than the 2x continental U.S.
For each size, the flow applies different handling strategies to ensure the performance of the flow.
- Small
- Medium
- Large
- All severity data is loaded.
- Full polygon is loaded.
- Smooth severity data is excluded.
- Full polygon is loaded.
- Smooth severity data is excluded
- Only middle area is loaded.
Corridor Mode
When dealing with corridor mode, meaning isCorridorMode
is true
, there are only one limitation - the polygon size should be less than 2,500,000
nautical miles, otherwise, the flow will not load the data and will emit an error.
- Smooth severity data is excluded.
- Corridor polygon is loaded.
Filtering Data
Some of the data proved by the flow can be filtered based on the severity level. The severity level is a number from 0 to 4, where 0 is the smoothest and 4 is the most severe.
As Well as altitude, the altitude is a number that represents the altitude of thousands of feet. From 5 to 52.
The filter can be applied by calling getOneLayerHexagonsDataSlice
method:
import { GeoUtils } from '@yamasee/skypath-sdk-web';
const filteredData = GeoUtils.getOneLayerHexagonsDataSlice({
data, // oneLayerFlow.onData((data) => { the data provided by onData }
filters: {
altitudeFrom, // number, 5-52 lower from altitudeTo
altitudeTo, // number, 5-52 heigher from altitudeFrom
severity, // minimal severity number, 0-4. e.g. 2 will show only 2, 3 and 4
},
});
Parsing Data for Mapbox
If your application uses deck.gl
to display the data, you can use the prepareOneLayerHexagonsDataForMapHexagons
/ getHexagonsFeatureCollection
methods from the GeoUtils
class to parse the data for the deck.gl GeoJsonLayer.
import { GeoUtils } from '@yamasee/skypath-sdk-web';
import { GeoJsonLayer } from 'deck.gl';
const layerData =() => {
const hexagons = GeoUtils.prepareOneLayerHexagonsDataForMapHexagons({
data, // `filteredData` or oneLayerFlow.onData((data) => { the data provided by onData },
});
return GeoUtils.getHexagonsFeatureCollection(Object.values(hexagons));
};
const layer = () =>
new GeoJsonLayer({
...ONELAYER_GEOJSON_LAYER_CONFIG,
data: layerData,
});
Examples
Basic usage
// Import the SDK
import createSkyPathSDK, { GeoUtils } from "@yamasee/skypath-sdk-web";
import { GeoJsonLayer } from 'deck.gl';
// Init with your credentials
const sdk = await createSkyPathSDK(...);
let flowData = null;
// Create Observations Flow
const oneLayerFlow = sdk.createOneLayerFlow()
// Subscribe to the data update event
oneLayerFlow.onData((data) => {
// Use the data to update the UI
flowData = data;
})
// Subscribe to the error event
oneLayerFlow.onError((error) => {
// Handle the error
})
// Start the flow when needed
oneLayerFlow.start()
// Later in the code update the configuration
oneLayerFlow.updateConfig({
polygon: [
[ -64.816, -18.751 ],
[ -64.816, -28.452 ],
[ -51.672, -28.452 ],
[ -51.672, -18.751 ],
[ -64.816, -18.751 ]
],
aircraftCategory: "C60",
})
// Filter the data
const filteredData = GeoUtils.getOneLayerHexagonsDataSlice({
data: flowData,
filters: {
altitudeFrom: 22,
altitudeTo: 35,
severity: 2,
},
});
// Parse the data for GeoJsonLayer
const layerData =() => {
const hexagons = GeoUtils.prepareOneLayerHexagonsDataForMapHexagons({ data: filteredData });
return GeoUtils.getHexagonsFeatureCollection(Object.values(hexagons));
};
const layer = () =>
new GeoJsonLayer({
...ONELAYER_GEOJSON_LAYER_CONFIG,
data: layerData,
});
// Later in the code terminate the flow when jobs are done
oneLayerFlow.terminate()
Advanced usage
For advanced examples check the React Demo Application.