@any-routing/osrm-data-provider 1.0.0-rc.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +31 -0
- package/eslint.config.mjs +22 -0
- package/package.json +14 -0
- package/project.json +21 -0
- package/src/index.ts +2 -0
- package/src/lib/osrm-data-provider.spec.ts +7 -0
- package/src/lib/osrm-data-provider.ts +120 -0
- package/src/lib/osrm-provider.types.ts +95 -0
- package/src/lib/osrm.executor.ts +156 -0
- package/src/lib/osrm.worker.ts +6 -0
- package/tsconfig.json +23 -0
- package/tsconfig.lib.json +23 -0
- package/tsconfig.spec.json +22 -0
- package/vite.config.mts +59 -0
package/README.md
ADDED
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
# osrm-data-provider
|
|
2
|
+
|
|
3
|
+
`AnyRoutingDataProvider` implementation backed by an [OSRM](https://project-osrm.org/) HTTP server (`route` service, see the [OSRM HTTP API docs](https://project-osrm.org/docs/v5.24.0/api/#requests)).
|
|
4
|
+
|
|
5
|
+
## Usage
|
|
6
|
+
|
|
7
|
+
```ts
|
|
8
|
+
import { AnyRouting } from '@any-routing/core';
|
|
9
|
+
import { OsrmProvider } from '@any-routing/osrm-data-provider';
|
|
10
|
+
|
|
11
|
+
const dataProvider = new OsrmProvider({
|
|
12
|
+
baseUrl: 'https://router.project-osrm.org/route/v1/driving',
|
|
13
|
+
alternatives: 2,
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
const routing = new AnyRouting({
|
|
17
|
+
dataProvider,
|
|
18
|
+
waypointsSyncStrategy: 'none',
|
|
19
|
+
});
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
By default requests run inside a Web Worker (`worker: true`), mirroring `@any-routing/here-data-provider`. Set `worker: false` to run the executor on the main thread instead.
|
|
23
|
+
|
|
24
|
+
## Building
|
|
25
|
+
|
|
26
|
+
Run `nx build osrm-data-provider` to build the library.
|
|
27
|
+
|
|
28
|
+
## Running unit tests
|
|
29
|
+
|
|
30
|
+
Run `nx test osrm-data-provider` to execute the unit tests via [Vitest](https://vitest.dev/).
|
|
31
|
+
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import baseConfig from '../../eslint.config.mjs';
|
|
2
|
+
|
|
3
|
+
export default [
|
|
4
|
+
...baseConfig,
|
|
5
|
+
{
|
|
6
|
+
files: ['**/*.json'],
|
|
7
|
+
rules: {
|
|
8
|
+
'@nx/dependency-checks': [
|
|
9
|
+
'error',
|
|
10
|
+
{
|
|
11
|
+
ignoredFiles: [
|
|
12
|
+
'{projectRoot}/eslint.config.{js,cjs,mjs,ts,cts,mts}',
|
|
13
|
+
'{projectRoot}/vite.config.{js,ts,mjs,mts}',
|
|
14
|
+
],
|
|
15
|
+
},
|
|
16
|
+
],
|
|
17
|
+
},
|
|
18
|
+
languageOptions: {
|
|
19
|
+
parser: await import('jsonc-eslint-parser'),
|
|
20
|
+
},
|
|
21
|
+
},
|
|
22
|
+
];
|
package/package.json
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@any-routing/osrm-data-provider",
|
|
3
|
+
"version": "1.0.0-rc.1",
|
|
4
|
+
"type": "module",
|
|
5
|
+
"main": "./index.js",
|
|
6
|
+
"types": "./index.d.ts",
|
|
7
|
+
"dependencies": {
|
|
8
|
+
"@any-routing/core": "1.0.0-rc.1",
|
|
9
|
+
"comlink": "4.4.2",
|
|
10
|
+
"@turf/bbox": "7.4.0",
|
|
11
|
+
"@turf/helpers": "7.4.0",
|
|
12
|
+
"@types/geojson": "7946.0.16"
|
|
13
|
+
}
|
|
14
|
+
}
|
package/project.json
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "osrm-data-provider",
|
|
3
|
+
"$schema": "../../node_modules/nx/schemas/project-schema.json",
|
|
4
|
+
"sourceRoot": "libs/osrm-data-provider/src",
|
|
5
|
+
"projectType": "library",
|
|
6
|
+
"release": {
|
|
7
|
+
"version": {
|
|
8
|
+
"manifestRootsToUpdate": ["dist/{projectRoot}"],
|
|
9
|
+
"currentVersionResolver": "git-tag",
|
|
10
|
+
"fallbackCurrentVersionResolver": "disk"
|
|
11
|
+
}
|
|
12
|
+
},
|
|
13
|
+
"tags": [],
|
|
14
|
+
"targets": {
|
|
15
|
+
"nx-release-publish": {
|
|
16
|
+
"options": {
|
|
17
|
+
"packageRoot": "dist/{projectRoot}"
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
}
|
package/src/index.ts
ADDED
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
import { wrap, Remote } from 'comlink';
|
|
2
|
+
|
|
3
|
+
import { ExecutorRequestOptions, OsrmExecutor } from './osrm.executor';
|
|
4
|
+
import type {
|
|
5
|
+
AnyRoutingDataProvider,
|
|
6
|
+
RequestOptions,
|
|
7
|
+
Waypoint,
|
|
8
|
+
WaypointPosition,
|
|
9
|
+
} from '@any-routing/core';
|
|
10
|
+
import { OsrmRoutingData, Options } from './osrm-provider.types';
|
|
11
|
+
|
|
12
|
+
const defaultOptions: Partial<Options> = {
|
|
13
|
+
baseUrl: 'https://router.project-osrm.org/route/v1/driving',
|
|
14
|
+
worker: true,
|
|
15
|
+
alternatives: 0,
|
|
16
|
+
steps: true,
|
|
17
|
+
geometries: 'geojson',
|
|
18
|
+
overview: 'full',
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
export class OsrmProvider implements AnyRoutingDataProvider {
|
|
22
|
+
private worker?: Worker;
|
|
23
|
+
// Comlink's `wrap` returns a `Remote<T>` proxy whose methods always
|
|
24
|
+
// resolve to promises, even for originally-synchronous ones — typing
|
|
25
|
+
// this union up front avoids the `@ts-ignore` a plain assignment would
|
|
26
|
+
// otherwise need.
|
|
27
|
+
private executorAPI: OsrmExecutor | Remote<OsrmExecutor>;
|
|
28
|
+
private _options: Options;
|
|
29
|
+
|
|
30
|
+
public get options(): Options {
|
|
31
|
+
return this._options;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
constructor(options: Options = {}) {
|
|
35
|
+
this._options = { ...defaultOptions, ...options };
|
|
36
|
+
|
|
37
|
+
if (this.options.worker === true) {
|
|
38
|
+
this.worker = new Worker(new URL('./osrm.worker', import.meta.url), {
|
|
39
|
+
type: 'module',
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
this.executorAPI = wrap<OsrmExecutor>(this.worker);
|
|
43
|
+
} else {
|
|
44
|
+
this.executorAPI = new OsrmExecutor();
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
public destroy(): void {
|
|
49
|
+
if (this.worker) {
|
|
50
|
+
this.worker.terminate();
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
public request(waypoints: Waypoint[], opts: RequestOptions): Promise<OsrmRoutingData> {
|
|
55
|
+
const url = this.buildUrl(waypoints, { ...this.options, ...opts });
|
|
56
|
+
|
|
57
|
+
// `buildUrl` is a function and must never be forwarded into
|
|
58
|
+
// `requestParams` below — when running with `worker: true`,
|
|
59
|
+
// `executorAPI` is a Comlink `Remote<OsrmExecutor>` and the call goes
|
|
60
|
+
// through `postMessage`'s structured clone algorithm, which cannot
|
|
61
|
+
// clone functions and throws `DataCloneError` at runtime.
|
|
62
|
+
const requestOptions = { ...this.options, ...opts, url };
|
|
63
|
+
delete requestOptions.buildUrl;
|
|
64
|
+
const requestParams: ExecutorRequestOptions = requestOptions;
|
|
65
|
+
|
|
66
|
+
return this.executorAPI.request(requestParams);
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
public async abortAllRequests(): Promise<void> {
|
|
70
|
+
await this.executorAPI.abortAllRequests();
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
public setOption<T extends keyof Options>(optionKey: T, value: Options[T]): void {
|
|
74
|
+
this.options[optionKey] = value;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
public async hasPendingRequests(): Promise<boolean> {
|
|
78
|
+
return await this.executorAPI.hasPendingRequests();
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
private buildUrl(waypoints: Waypoint[], opts: Options & RequestOptions): string {
|
|
82
|
+
if (!waypoints[0] || !waypoints[waypoints.length - 1]) {
|
|
83
|
+
throw new Error('At least two waypoints are required');
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
const coordinates = waypoints.map((w) => this.formatWp(w.position)).join(';');
|
|
87
|
+
|
|
88
|
+
const queryParamsObj: Record<string, string | number | boolean | undefined | null> = {
|
|
89
|
+
alternatives: opts.mode === 'default' ? opts.alternatives ?? 0 : 0,
|
|
90
|
+
steps: opts.steps,
|
|
91
|
+
geometries: opts.geometries || 'geojson',
|
|
92
|
+
overview: opts.overview || 'full',
|
|
93
|
+
continue_straight: opts.continueStraight,
|
|
94
|
+
annotations: opts.annotations,
|
|
95
|
+
...opts.queryParams,
|
|
96
|
+
};
|
|
97
|
+
|
|
98
|
+
// Only truthy/explicitly-set values are sent, matching OSRM's own
|
|
99
|
+
// defaults for anything omitted (mirrors here-data-provider's filter).
|
|
100
|
+
const queryParams: Record<string, string> = Object.entries(queryParamsObj).reduce(
|
|
101
|
+
(acc, [key, value]) => {
|
|
102
|
+
if (value !== undefined && value !== null && value !== '') {
|
|
103
|
+
acc[key] = String(value);
|
|
104
|
+
}
|
|
105
|
+
return acc;
|
|
106
|
+
},
|
|
107
|
+
{} as Record<string, string>,
|
|
108
|
+
);
|
|
109
|
+
|
|
110
|
+
const qp = new URLSearchParams(queryParams).toString();
|
|
111
|
+
|
|
112
|
+
const url = `${this.options.baseUrl}/${coordinates}${qp ? `?${qp}` : ''}`;
|
|
113
|
+
|
|
114
|
+
return this.options.buildUrl ? this.options.buildUrl({ waypoints, options: opts }, url) : url;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
private formatWp({ lat, lng }: WaypointPosition): string {
|
|
118
|
+
return `${lng},${lat}`;
|
|
119
|
+
}
|
|
120
|
+
}
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
import type { AnyRoutingDataResponse, RequestOptions, RouteSummary, Waypoint } from '@any-routing/core';
|
|
2
|
+
import type { ExecutorRequestOptions } from './osrm.executor';
|
|
3
|
+
|
|
4
|
+
export type OsrmGeometry = 'polyline' | 'polyline6' | 'geojson';
|
|
5
|
+
export type OsrmOverview = 'simplified' | 'full' | 'false';
|
|
6
|
+
|
|
7
|
+
export interface OsrmRouteSummary extends RouteSummary {
|
|
8
|
+
rawRoute: OsrmRawRoute;
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
export interface OsrmRoutingData extends AnyRoutingDataResponse {
|
|
12
|
+
routes: OsrmRouteSummary[];
|
|
13
|
+
requestOptions: ExecutorRequestOptions;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export type Options = {
|
|
17
|
+
/**
|
|
18
|
+
* Base URL of the OSRM HTTP server up to and including the profile, e.g.
|
|
19
|
+
* `https://router.project-osrm.org/route/v1/driving`. `{coordinates}` and
|
|
20
|
+
* query options are appended by this provider.
|
|
21
|
+
*/
|
|
22
|
+
baseUrl?: string;
|
|
23
|
+
worker?: boolean;
|
|
24
|
+
alternatives?: number;
|
|
25
|
+
steps?: boolean;
|
|
26
|
+
annotations?: boolean | 'nodes' | 'distance' | 'duration' | 'datasources' | 'weight' | 'speed';
|
|
27
|
+
geometries?: OsrmGeometry;
|
|
28
|
+
overview?: OsrmOverview;
|
|
29
|
+
continueStraight?: 'default' | boolean;
|
|
30
|
+
queryParams?: Record<string, unknown>;
|
|
31
|
+
requestParams?: RequestInit;
|
|
32
|
+
buildUrl?: (ctx: { waypoints: Waypoint[]; options: Options & RequestOptions }, url: string) => string;
|
|
33
|
+
};
|
|
34
|
+
|
|
35
|
+
// ---------------------------------------------------------------------------
|
|
36
|
+
// OSRM `route` service raw response types (the subset the executor reads).
|
|
37
|
+
// Modeled after https://project-osrm.org/docs/v5.24.0/api/#route-service and
|
|
38
|
+
// the OSRM HTTP API docs. `geometries=geojson` is always requested by this
|
|
39
|
+
// provider so `geometry` is always a GeoJSON `LineString`.
|
|
40
|
+
// ---------------------------------------------------------------------------
|
|
41
|
+
|
|
42
|
+
export interface OsrmRawLineStringGeometry {
|
|
43
|
+
type: 'LineString';
|
|
44
|
+
coordinates: [number, number][];
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
export interface OsrmRawStepManeuver {
|
|
48
|
+
location: [number, number];
|
|
49
|
+
bearing_before: number;
|
|
50
|
+
bearing_after: number;
|
|
51
|
+
type: string;
|
|
52
|
+
modifier?: string;
|
|
53
|
+
exit?: number;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
export interface OsrmRawStep {
|
|
57
|
+
distance: number;
|
|
58
|
+
duration: number;
|
|
59
|
+
weight?: number;
|
|
60
|
+
name: string;
|
|
61
|
+
ref?: string;
|
|
62
|
+
geometry: OsrmRawLineStringGeometry;
|
|
63
|
+
maneuver: OsrmRawStepManeuver;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
export interface OsrmRawLeg {
|
|
67
|
+
distance: number;
|
|
68
|
+
duration: number;
|
|
69
|
+
weight?: number;
|
|
70
|
+
summary?: string;
|
|
71
|
+
steps: OsrmRawStep[];
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
export interface OsrmRawRoute {
|
|
75
|
+
distance: number;
|
|
76
|
+
duration: number;
|
|
77
|
+
weight?: number;
|
|
78
|
+
weight_name?: string;
|
|
79
|
+
geometry: OsrmRawLineStringGeometry;
|
|
80
|
+
legs: OsrmRawLeg[];
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
export interface OsrmRawWaypoint {
|
|
84
|
+
hint?: string;
|
|
85
|
+
distance: number;
|
|
86
|
+
name: string;
|
|
87
|
+
location: [number, number];
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
export interface OsrmApiResponse {
|
|
91
|
+
code: string;
|
|
92
|
+
message?: string;
|
|
93
|
+
waypoints?: OsrmRawWaypoint[];
|
|
94
|
+
routes?: OsrmRawRoute[];
|
|
95
|
+
}
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
import bbox from '@turf/bbox';
|
|
2
|
+
import { featureCollection, lineString } from '@turf/helpers';
|
|
3
|
+
import type { BBox, Feature, LineString } from 'geojson';
|
|
4
|
+
|
|
5
|
+
import { type Mode, Requester, type WaypointPosition } from '@any-routing/core';
|
|
6
|
+
|
|
7
|
+
import type {
|
|
8
|
+
Options,
|
|
9
|
+
OsrmApiResponse,
|
|
10
|
+
OsrmRawLeg,
|
|
11
|
+
OsrmRawRoute,
|
|
12
|
+
OsrmRouteSummary,
|
|
13
|
+
OsrmRoutingData,
|
|
14
|
+
} from './osrm-provider.types';
|
|
15
|
+
|
|
16
|
+
export type ExecutorRequestOptions = { url: string; mode: Mode } & Options;
|
|
17
|
+
|
|
18
|
+
/** Properties attached to each rendered segment of a route's shape. */
|
|
19
|
+
type ShapeFeatureProperties = {
|
|
20
|
+
waypoint: number;
|
|
21
|
+
routeId: number;
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
export class OsrmExecutor {
|
|
25
|
+
private readonly requester = new Requester();
|
|
26
|
+
|
|
27
|
+
async request(opts: ExecutorRequestOptions): Promise<OsrmRoutingData> {
|
|
28
|
+
const data = (await this.requester.request(opts.url, {
|
|
29
|
+
method: 'GET',
|
|
30
|
+
headers: {
|
|
31
|
+
Accept: 'application/json',
|
|
32
|
+
},
|
|
33
|
+
...opts.requestParams,
|
|
34
|
+
})) as OsrmApiResponse;
|
|
35
|
+
|
|
36
|
+
if (data.code !== 'Ok' || !data.routes?.length) {
|
|
37
|
+
throw new Error(data.message || `OSRM request failed with code "${data.code}"`);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
const routeSummaries = data.routes.map((route, routeId) =>
|
|
41
|
+
summarizeRoute(route, routeId),
|
|
42
|
+
);
|
|
43
|
+
|
|
44
|
+
const features = routeSummaries.flatMap((routeSummary, fid) =>
|
|
45
|
+
routeSummary.shape.features.map((feature) => ({
|
|
46
|
+
id: fid,
|
|
47
|
+
...feature,
|
|
48
|
+
properties: {
|
|
49
|
+
...feature.properties,
|
|
50
|
+
id: fid,
|
|
51
|
+
routeId: routeSummary.id,
|
|
52
|
+
},
|
|
53
|
+
})),
|
|
54
|
+
);
|
|
55
|
+
|
|
56
|
+
const routesShapeGeojson = featureCollection(features);
|
|
57
|
+
|
|
58
|
+
return {
|
|
59
|
+
routesShapeBounds: bbox(routesShapeGeojson) as BBox,
|
|
60
|
+
rawResponse: data,
|
|
61
|
+
routes: routeSummaries,
|
|
62
|
+
selectedRouteId: routeSummaries.length ? 0 : null,
|
|
63
|
+
routesShapeGeojson,
|
|
64
|
+
version: performance.now(),
|
|
65
|
+
latest: !this.requester.hasPendingRequests,
|
|
66
|
+
mode: opts.mode,
|
|
67
|
+
requestOptions: opts,
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
hasPendingRequests() {
|
|
72
|
+
return this.requester.hasPendingRequests;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
abortAllRequests() {
|
|
76
|
+
this.requester.abortAllRequests();
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
/**
|
|
81
|
+
* Waypoints introduced by a leg: OSRM legs don't carry per-leg
|
|
82
|
+
* departure/arrival coordinates directly, so waypoints are instead derived
|
|
83
|
+
* from the route's own `geometry` boundaries via the accumulated leg
|
|
84
|
+
* distances — simpler and sufficient here: every leg boundary is a waypoint,
|
|
85
|
+
* taken from the first/last coordinate of the leg's own geometry (built up
|
|
86
|
+
* from its steps).
|
|
87
|
+
*/
|
|
88
|
+
function extractLegWaypoints(leg: OsrmRawLeg): WaypointPosition[] {
|
|
89
|
+
const firstStep = leg.steps[0];
|
|
90
|
+
const lastStep = leg.steps[leg.steps.length - 1];
|
|
91
|
+
|
|
92
|
+
if (!firstStep || !lastStep) {
|
|
93
|
+
return [];
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
const [lng, lat] = firstStep.maneuver.location;
|
|
97
|
+
|
|
98
|
+
return [{ lat, lng }];
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
function buildLegShape(
|
|
102
|
+
leg: OsrmRawLeg,
|
|
103
|
+
routeId: number,
|
|
104
|
+
waypointIndex: number,
|
|
105
|
+
): Feature<LineString, ShapeFeatureProperties>[] {
|
|
106
|
+
const legPath = leg.steps.flatMap((step) => step.geometry.coordinates);
|
|
107
|
+
|
|
108
|
+
if (!legPath.length) {
|
|
109
|
+
return [];
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
return [
|
|
113
|
+
lineString(legPath, { waypoint: waypointIndex, routeId }) as Feature<
|
|
114
|
+
LineString,
|
|
115
|
+
ShapeFeatureProperties
|
|
116
|
+
>,
|
|
117
|
+
];
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
const summarizeRoute = (route: OsrmRawRoute, routeId: number): OsrmRouteSummary => {
|
|
121
|
+
const now = new Date();
|
|
122
|
+
|
|
123
|
+
let waypoints: WaypointPosition[] = [];
|
|
124
|
+
let shapeFeatures: Feature<LineString, ShapeFeatureProperties>[] = [];
|
|
125
|
+
let waypointIndex = 0;
|
|
126
|
+
|
|
127
|
+
route.legs.forEach((leg, index) => {
|
|
128
|
+
waypoints = [...waypoints, ...extractLegWaypoints(leg)];
|
|
129
|
+
shapeFeatures = [...shapeFeatures, ...buildLegShape(leg, routeId, waypointIndex)];
|
|
130
|
+
|
|
131
|
+
const isLastLeg = index === route.legs.length - 1;
|
|
132
|
+
if (isLastLeg) {
|
|
133
|
+
const lastStep = leg.steps[leg.steps.length - 1];
|
|
134
|
+
if (lastStep) {
|
|
135
|
+
const [lng, lat] = lastStep.maneuver.location;
|
|
136
|
+
waypoints = [...waypoints, { lat, lng }];
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
waypointIndex += 1;
|
|
141
|
+
});
|
|
142
|
+
|
|
143
|
+
const path = route.geometry.coordinates.map(([lng, lat]) => [lat, lng]);
|
|
144
|
+
|
|
145
|
+
return {
|
|
146
|
+
id: routeId,
|
|
147
|
+
durationTime: route.duration,
|
|
148
|
+
distance: route.distance,
|
|
149
|
+
path,
|
|
150
|
+
arriveTime: new Date(now.getTime() + route.duration * 1000),
|
|
151
|
+
departureTime: now,
|
|
152
|
+
waypoints,
|
|
153
|
+
shape: featureCollection(shapeFeatures),
|
|
154
|
+
rawRoute: route,
|
|
155
|
+
};
|
|
156
|
+
};
|
package/tsconfig.json
ADDED
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "../../tsconfig.base.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"module": "es2022",
|
|
5
|
+
"forceConsistentCasingInFileNames": true,
|
|
6
|
+
"strict": true,
|
|
7
|
+
"importHelpers": true,
|
|
8
|
+
"noImplicitOverride": true,
|
|
9
|
+
"noImplicitReturns": true,
|
|
10
|
+
"noFallthroughCasesInSwitch": true,
|
|
11
|
+
"noPropertyAccessFromIndexSignature": true
|
|
12
|
+
},
|
|
13
|
+
"files": [],
|
|
14
|
+
"include": [],
|
|
15
|
+
"references": [
|
|
16
|
+
{
|
|
17
|
+
"path": "./tsconfig.lib.json"
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
"path": "./tsconfig.spec.json"
|
|
21
|
+
}
|
|
22
|
+
]
|
|
23
|
+
}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "./tsconfig.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"outDir": "../../dist/out-tsc",
|
|
5
|
+
"declaration": true,
|
|
6
|
+
"types": ["node", "vite/client"]
|
|
7
|
+
},
|
|
8
|
+
"include": ["src/**/*.ts"],
|
|
9
|
+
"exclude": [
|
|
10
|
+
"vite.config.ts",
|
|
11
|
+
"vite.config.mts",
|
|
12
|
+
"vitest.config.ts",
|
|
13
|
+
"vitest.config.mts",
|
|
14
|
+
"src/**/*.test.ts",
|
|
15
|
+
"src/**/*.spec.ts",
|
|
16
|
+
"src/**/*.test.tsx",
|
|
17
|
+
"src/**/*.spec.tsx",
|
|
18
|
+
"src/**/*.test.js",
|
|
19
|
+
"src/**/*.spec.js",
|
|
20
|
+
"src/**/*.test.jsx",
|
|
21
|
+
"src/**/*.spec.jsx"
|
|
22
|
+
]
|
|
23
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "./tsconfig.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"outDir": "../../dist/out-tsc",
|
|
5
|
+
"types": ["vitest/globals", "vitest/importMeta", "vite/client", "node", "vitest"]
|
|
6
|
+
},
|
|
7
|
+
"include": [
|
|
8
|
+
"vite.config.ts",
|
|
9
|
+
"vite.config.mts",
|
|
10
|
+
"vitest.config.ts",
|
|
11
|
+
"vitest.config.mts",
|
|
12
|
+
"src/**/*.test.ts",
|
|
13
|
+
"src/**/*.spec.ts",
|
|
14
|
+
"src/**/*.test.tsx",
|
|
15
|
+
"src/**/*.spec.tsx",
|
|
16
|
+
"src/**/*.test.js",
|
|
17
|
+
"src/**/*.spec.js",
|
|
18
|
+
"src/**/*.test.jsx",
|
|
19
|
+
"src/**/*.spec.jsx",
|
|
20
|
+
"src/**/*.d.ts"
|
|
21
|
+
]
|
|
22
|
+
}
|
package/vite.config.mts
ADDED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
/// <reference types='vitest' />
|
|
2
|
+
import { defineConfig } from 'vite';
|
|
3
|
+
import dts from 'vite-plugin-dts';
|
|
4
|
+
import * as path from 'path';
|
|
5
|
+
import { nxViteTsPaths } from '@nx/vite/plugins/nx-tsconfig-paths.plugin';
|
|
6
|
+
import { nxCopyAssetsPlugin } from '@nx/vite/plugins/nx-copy-assets.plugin';
|
|
7
|
+
|
|
8
|
+
export default defineConfig(() => ({
|
|
9
|
+
root: import.meta.dirname,
|
|
10
|
+
cacheDir: '../../node_modules/.vite/libs/osrm-data-provider',
|
|
11
|
+
plugins: [
|
|
12
|
+
nxViteTsPaths(),
|
|
13
|
+
nxCopyAssetsPlugin(['*.md']),
|
|
14
|
+
dts({
|
|
15
|
+
entryRoot: 'src',
|
|
16
|
+
tsconfigPath: path.join(import.meta.dirname, 'tsconfig.lib.json'),
|
|
17
|
+
pathsToAliases: false,
|
|
18
|
+
}),
|
|
19
|
+
],
|
|
20
|
+
// Uncomment this if you are using workers.
|
|
21
|
+
// worker: {
|
|
22
|
+
// plugins: () => [ nxViteTsPaths() ],
|
|
23
|
+
// },
|
|
24
|
+
// Configuration for building your library.
|
|
25
|
+
// See: https://vite.dev/guide/build.html#library-mode
|
|
26
|
+
build: {
|
|
27
|
+
outDir: '../../dist/libs/osrm-data-provider',
|
|
28
|
+
emptyOutDir: true,
|
|
29
|
+
reportCompressedSize: true,
|
|
30
|
+
commonjsOptions: {
|
|
31
|
+
transformMixedEsModules: true,
|
|
32
|
+
},
|
|
33
|
+
lib: {
|
|
34
|
+
// Could also be a dictionary or array of multiple entry points.
|
|
35
|
+
entry: 'src/index.ts',
|
|
36
|
+
name: 'osrm-data-provider',
|
|
37
|
+
fileName: 'index',
|
|
38
|
+
// Change this to the formats you want to support.
|
|
39
|
+
// Don't forget to update your package.json as well.
|
|
40
|
+
formats: ['es' as const],
|
|
41
|
+
},
|
|
42
|
+
rolldownOptions: {
|
|
43
|
+
// External packages that should not be bundled into your library.
|
|
44
|
+
external: [],
|
|
45
|
+
},
|
|
46
|
+
},
|
|
47
|
+
test: {
|
|
48
|
+
name: 'osrm-data-provider',
|
|
49
|
+
watch: false,
|
|
50
|
+
globals: true,
|
|
51
|
+
environment: 'node',
|
|
52
|
+
include: ['{src,tests}/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'],
|
|
53
|
+
reporters: ['default'],
|
|
54
|
+
coverage: {
|
|
55
|
+
reportsDirectory: '../../coverage/libs/osrm-data-provider',
|
|
56
|
+
provider: 'v8' as const,
|
|
57
|
+
},
|
|
58
|
+
},
|
|
59
|
+
}));
|