atriusmaps-node-sdk 3.3.31 → 3.3.225

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.
Files changed (122) hide show
  1. package/README.md +19 -1
  2. package/dist/cjs/_virtual/_empty_module_placeholder.js +2 -2
  3. package/dist/cjs/deploy/prepareSDKConfig.js +152 -2
  4. package/dist/cjs/nodesdk/nodeEntry.js +109 -0
  5. package/dist/cjs/package.json.js +190 -7
  6. package/dist/cjs/plugins/clientAPI/src/clientAPI.js +11 -2
  7. package/dist/cjs/plugins/dynamicPois/src/dynamicPois.js +218 -21
  8. package/dist/cjs/plugins/poiDataManager/src/poiDataManager.js +292 -21
  9. package/dist/cjs/plugins/sdkServer/src/sdkHeadless.js +99 -20
  10. package/dist/cjs/plugins/sdkServer/src/sdkServer.js +219 -2
  11. package/dist/cjs/plugins/sdkServer/src/util.js +16 -3
  12. package/dist/cjs/plugins/searchService/src/poiSearch.js +57 -19
  13. package/dist/cjs/plugins/searchService/src/searchService.js +246 -21
  14. package/dist/cjs/plugins/searchService/src/searchTypeahead.js +60 -3
  15. package/dist/cjs/plugins/searchService/src/utils.js +23 -4
  16. package/dist/cjs/plugins/venueDataLoader/src/venueDataLoader.js +472 -23
  17. package/dist/cjs/plugins/venueDataLoader/src/venueLoadingUtils.js +191 -23
  18. package/dist/cjs/plugins/wayfinder/src/findRoute.js +147 -19
  19. package/dist/cjs/plugins/wayfinder/src/minPriorityQueue.js +88 -2
  20. package/dist/cjs/plugins/wayfinder/src/navGraph.js +393 -5
  21. package/dist/cjs/plugins/wayfinder/src/navGraphDebug.js +110 -20
  22. package/dist/cjs/plugins/wayfinder/src/segmentBadges.js +28 -2
  23. package/dist/cjs/plugins/wayfinder/src/segmentBuilder.js +257 -19
  24. package/dist/cjs/plugins/wayfinder/src/segmentCategories.js +29 -2
  25. package/dist/cjs/plugins/wayfinder/src/stepBuilder.js +238 -3
  26. package/dist/cjs/plugins/wayfinder/src/wayfinder.js +597 -22
  27. package/dist/cjs/src/app.js +191 -25
  28. package/dist/cjs/src/configs/postproc-mol-url-parms.js +58 -2
  29. package/dist/cjs/src/configs/postproc-stateTracking.js +53 -19
  30. package/dist/cjs/src/controller.js +43 -4
  31. package/dist/cjs/src/debugTools.js +128 -23
  32. package/dist/cjs/src/env.js +17 -2
  33. package/dist/cjs/src/extModules/bustle.js +128 -4
  34. package/dist/cjs/src/extModules/flexapi/src/help.js +23 -4
  35. package/dist/cjs/src/extModules/flexapi/src/index.js +65 -4
  36. package/dist/cjs/src/extModules/flexapi/src/validate.js +133 -5
  37. package/dist/cjs/src/extModules/geohasher.js +90 -3
  38. package/dist/cjs/src/extModules/log.js +69 -2
  39. package/dist/cjs/src/historyManager.js +29 -2
  40. package/dist/cjs/src/utils/bounds.js +22 -4
  41. package/dist/cjs/src/utils/buildStructureLookup.js +31 -19
  42. package/dist/cjs/src/utils/configUtils.js +71 -3
  43. package/dist/cjs/src/utils/dom.js +48 -5
  44. package/dist/cjs/src/utils/funcs.js +30 -7
  45. package/dist/cjs/src/utils/geodesy.js +35 -3
  46. package/dist/cjs/src/utils/geom.js +212 -25
  47. package/dist/cjs/src/utils/i18n.js +69 -5
  48. package/dist/cjs/src/utils/observable.js +73 -2
  49. package/dist/cjs/src/utils/rand.js +82 -3
  50. package/dist/nodesdk/nodeEntry.js +1 -0
  51. package/dist/package.json.js +1 -0
  52. package/dist/plugins/dynamicPois/src/dynamicPois.js +1 -0
  53. package/dist/plugins/sdkServer/src/sdkHeadless.js +1 -0
  54. package/{lib → dist}/plugins/sdkServer/src/sdkServer.js +1 -1
  55. package/dist/plugins/searchService/src/poiSearch.js +1 -0
  56. package/dist/plugins/searchService/src/searchService.js +1 -0
  57. package/dist/plugins/venueDataLoader/src/venueDataLoader.js +1 -0
  58. package/dist/plugins/venueDataLoader/src/venueLoadingUtils.js +1 -0
  59. package/dist/plugins/wayfinder/src/navGraph.js +1 -0
  60. package/{lib → dist}/plugins/wayfinder/src/segmentBuilder.js +1 -1
  61. package/dist/plugins/wayfinder/src/stepBuilder.js +1 -0
  62. package/dist/plugins/wayfinder/src/wayfinder.js +1 -0
  63. package/dist/src/app.js +1 -0
  64. package/dist/src/configs/postproc-mol-url-parms.js +1 -0
  65. package/{lib → dist}/src/configs/sdkHeadless.json.js +1 -1
  66. package/dist/src/extModules/bustle.js +1 -0
  67. package/dist/src/extModules/log.js +1 -0
  68. package/dist/src/utils/funcs.js +1 -0
  69. package/dist/src/utils/geom.js +1 -0
  70. package/dist/src/utils/i18n.js +1 -0
  71. package/package.json +17 -9
  72. package/config/rollup.config.cjs.js +0 -31
  73. package/dist/cjs/deploy/nodeEntry.js +0 -15
  74. package/dist/cjs/src/auth/Auth.js +0 -23
  75. package/lib/deploy/nodeEntry.js +0 -1
  76. package/lib/package.json.js +0 -1
  77. package/lib/plugins/dynamicPois/src/dynamicPois.js +0 -1
  78. package/lib/plugins/sdkServer/src/sdkHeadless.js +0 -1
  79. package/lib/plugins/searchService/src/poiSearch.js +0 -1
  80. package/lib/plugins/searchService/src/searchService.js +0 -1
  81. package/lib/plugins/venueDataLoader/src/venueDataLoader.js +0 -1
  82. package/lib/plugins/venueDataLoader/src/venueLoadingUtils.js +0 -1
  83. package/lib/plugins/wayfinder/src/navGraph.js +0 -1
  84. package/lib/plugins/wayfinder/src/stepBuilder.js +0 -1
  85. package/lib/plugins/wayfinder/src/wayfinder.js +0 -1
  86. package/lib/src/app.js +0 -1
  87. package/lib/src/auth/Auth.js +0 -1
  88. package/lib/src/configs/postproc-mol-url-parms.js +0 -1
  89. package/lib/src/configs/sdkHeadless.json +0 -28
  90. package/lib/src/extModules/bustle.js +0 -1
  91. package/lib/src/extModules/log.js +0 -1
  92. package/lib/src/utils/funcs.js +0 -1
  93. package/lib/src/utils/geom.js +0 -1
  94. package/lib/src/utils/i18n.js +0 -1
  95. /package/{lib → dist}/_virtual/_empty_module_placeholder.js +0 -0
  96. /package/{lib → dist}/deploy/prepareSDKConfig.js +0 -0
  97. /package/{lib → dist}/plugins/clientAPI/src/clientAPI.js +0 -0
  98. /package/{lib → dist}/plugins/poiDataManager/src/poiDataManager.js +0 -0
  99. /package/{lib → dist}/plugins/sdkServer/src/util.js +0 -0
  100. /package/{lib → dist}/plugins/searchService/src/searchTypeahead.js +0 -0
  101. /package/{lib → dist}/plugins/searchService/src/utils.js +0 -0
  102. /package/{lib → dist}/plugins/wayfinder/src/findRoute.js +0 -0
  103. /package/{lib → dist}/plugins/wayfinder/src/minPriorityQueue.js +0 -0
  104. /package/{lib → dist}/plugins/wayfinder/src/navGraphDebug.js +0 -0
  105. /package/{lib → dist}/plugins/wayfinder/src/segmentBadges.js +0 -0
  106. /package/{lib → dist}/plugins/wayfinder/src/segmentCategories.js +0 -0
  107. /package/{lib → dist}/src/configs/postproc-stateTracking.js +0 -0
  108. /package/{lib → dist}/src/controller.js +0 -0
  109. /package/{lib → dist}/src/debugTools.js +0 -0
  110. /package/{lib → dist}/src/env.js +0 -0
  111. /package/{lib → dist}/src/extModules/flexapi/src/help.js +0 -0
  112. /package/{lib → dist}/src/extModules/flexapi/src/index.js +0 -0
  113. /package/{lib → dist}/src/extModules/flexapi/src/validate.js +0 -0
  114. /package/{lib → dist}/src/extModules/geohasher.js +0 -0
  115. /package/{lib → dist}/src/historyManager.js +0 -0
  116. /package/{lib → dist}/src/utils/bounds.js +0 -0
  117. /package/{lib → dist}/src/utils/buildStructureLookup.js +0 -0
  118. /package/{lib → dist}/src/utils/configUtils.js +0 -0
  119. /package/{lib → dist}/src/utils/dom.js +0 -0
  120. /package/{lib → dist}/src/utils/geodesy.js +0 -0
  121. /package/{lib → dist}/src/utils/observable.js +0 -0
  122. /package/{lib → dist}/src/utils/rand.js +0 -0
@@ -2,34 +2,202 @@
2
2
 
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
- var e = require('ramda');
5
+ var R = require('ramda');
6
6
  var bounds = require('../../../src/utils/bounds.js');
7
7
  var configUtils = require('../../../src/utils/configUtils.js');
8
8
 
9
9
  function _interopNamespace(e) {
10
- if (e && e.__esModule) return e;
11
- var n = Object.create(null);
12
- if (e) {
13
- Object.keys(e).forEach(function (k) {
14
- if (k !== 'default') {
15
- var d = Object.getOwnPropertyDescriptor(e, k);
16
- Object.defineProperty(n, k, d.get ? d : {
17
- enumerable: true,
18
- get: function () { return e[k]; }
19
- });
20
- }
21
- });
22
- }
23
- n["default"] = e;
24
- return Object.freeze(n);
10
+ if (e && e.__esModule) return e;
11
+ var n = Object.create(null);
12
+ if (e) {
13
+ Object.keys(e).forEach(function (k) {
14
+ if (k !== 'default') {
15
+ var d = Object.getOwnPropertyDescriptor(e, k);
16
+ Object.defineProperty(n, k, d.get ? d : {
17
+ enumerable: true,
18
+ get: function () { return e[k]; }
19
+ });
20
+ }
21
+ });
22
+ }
23
+ n["default"] = e;
24
+ return Object.freeze(n);
25
25
  }
26
26
 
27
- var e__namespace = /*#__PURE__*/_interopNamespace(e);
27
+ var R__namespace = /*#__PURE__*/_interopNamespace(R);
28
28
 
29
- const n=async(t,e)=>t?fetch(e,{headers:{Authorization:t}}):fetch(e),s=t=>e=>n(t,e).then((t=>t.json())),o=t=>e=>n(t,e).then((t=>t.text())),l=t=>`https://api.content.locuslabs.com/${t}`,r=(e,a,n,s,o)=>e__namespace.mapObjIndexed(((t,a)=>((t,e,a,n,s,o)=>"theme"===o||"style"===o?`${l(a)}/${e}/${o}/${s}/${n}/${o}.json`:t.replace(/https:\/\/content.locuslabs.com/gi,l(a)))(t,e,n,s,o,a)),a),i=async(t,e)=>{const n={alpha:"alpha-a.locuslabs.com",beta:"beta-a.locuslabs.com",gamma:"gamma-a.locuslabs.com",prod:"a.locuslabs.com"},{assetStage:s,venueId:o,accountId:l,formatVersion:i}=t,c=`https://${n[s]||n.prod}/accounts/${l}`,u=i||"v5",d=t.dataFetch&&configUtils.global[t.dataFetch]&&configUtils.global[t.dataFetch].getFiles?await configUtils.global[t.dataFetch].getFiles(t):await e(`${c}/${u}.json`);if(!d[o])throw Error(`Attempt to access venue ${o} which is not within venue list: ${Object.keys(d)}`);const g=d[o].files,h=(t.dataFetch&&configUtils.global[t.dataFetch]&&configUtils.global[t.dataFetch].getVenueData?await configUtils.global[t.dataFetch].getVenueData(t):await e(g.venueData))[o];h.tileServerAuthInfo&&function(t){const e={defaultOrdinal:0,defaultStructureId:"singleBuilding",formatVersion:"v5",structures:{singleBuilding:{name:"singleBuilding",boundsPolygon:[],defaultLevelId:"singleLevel",id:"singleBuilding",levels:{singleLevel:{boundsPolygon:[],clfloor:0,details:"",id:"singleLevel",name:"singleLevel",ordinal:0}}}},structureOrder:["singleBuilding"]};for(const a in e)t[a]=e[a];}(h),h.venueList=d;const m=(t=>{const e=t.deepLinkProps?t.deepLinkProps.contentStage:null;return "alpha"===e||"beta"===e||"prod"===e?e:null})(t);return h.files=m?r(h.category,g,m,l,o):g,h},c=t=>{const{structureOrder:a,structures:n}=t;return a.map((t=>{const a=n[t],s=bounds.findBoundsOfCoordinates(a.boundsPolygon);return {...a,bounds:s}}))};const u=([t,e,...a])=>[e,t,...a],d=(t,e)=>{return !t||!Array.isArray(t)||t.length<1?t:(a=t[0][0],n=e.ne.lng,s=e.sw.lng,(a>n?a<=s:t=>s)?t:t.map(u));var a,n,s;};
29
+ const fetchURL = async (token, url) => {
30
+ if (token) {
31
+ return fetch(url, {
32
+ headers: {
33
+ Authorization: token
34
+ }
35
+ })
36
+ } else
37
+ return fetch(url)
38
+ };
30
39
 
31
- exports.buildStructures = c;
32
- exports.createFetchJson = s;
33
- exports.createFetchText = o;
34
- exports.getVenueDataFromUrls = i;
35
- exports.normalizeCoords = d;
40
+ const createFetchJson = (token) => url => fetchURL(token, url).then(response => response.json());
41
+ const createFetchText = (token) => url => fetchURL(token, url).then(response => response.text());
42
+
43
+ const baseContentUrl = (contentStage) => `https://api.content.locuslabs.com/${contentStage}`;
44
+
45
+ const remapContentUrl = (url, category, contentStage, accountId, venueId, key) => {
46
+ if (key === 'theme' || key === 'style') {
47
+ return `${baseContentUrl(contentStage)}/${category}/${key}/${venueId}/${accountId}/${key}.json`
48
+ }
49
+ return url.replace(/https:\/\/content.locuslabs.com/gi, baseContentUrl(contentStage))
50
+ };
51
+
52
+ const remapEachURLForContentStage = (category, files, contentStage, accountId, venueId) =>
53
+ R__namespace.mapObjIndexed((file, key) => remapContentUrl(file, category, contentStage, accountId, venueId, key), files);
54
+
55
+ const getContentStage = (vconfig) => {
56
+ const stage = vconfig.deepLinkProps ? vconfig.deepLinkProps.contentStage : null;
57
+ return stage === 'alpha' || stage === 'beta' || stage === 'prod' ? stage : null
58
+ };
59
+
60
+ const getVenueDataFromUrls = async (vconfig, fetchJson, languagesToTry) => {
61
+ const stages = {
62
+ alpha: 'alpha-a.locuslabs.com',
63
+ beta: 'beta-a.locuslabs.com',
64
+ gamma: 'gamma-a.locuslabs.com',
65
+ prod: 'a.locuslabs.com'
66
+ };
67
+
68
+ const { assetStage, accountId, formatVersion } = vconfig;
69
+ let { venueId } = vconfig;
70
+ const stageUrl = stages[assetStage] || stages.prod;
71
+ const accountUrl = `https://${stageUrl}/accounts/${accountId}`;
72
+ const assetFormat = formatVersion || 'v5';
73
+
74
+ // Load the v5.json resource
75
+ const venueList = (vconfig.dataFetch && configUtils.global[vconfig.dataFetch] && configUtils.global[vconfig.dataFetch].getFiles)
76
+ ? await configUtils.global[vconfig.dataFetch].getFiles(vconfig)
77
+ : await fetchJson(`${accountUrl}/${assetFormat}.json`);
78
+
79
+ // Reassign venue id to venueId+langauge preference if that venue in that language is avaialbe to us in the v5 json
80
+ if (languagesToTry.length > 0) {
81
+ const convertedLangsToTry = languagesToTry.map(lang => lang.slice(0, 2)); // Browser langs can look like this [fr', 'fr-FR', 'ar', 'en-US', 'en'] so we need to process them so they match our lang codes which are just 2 digits
82
+ for (let i = 0; i < convertedLangsToTry.length; i += 1) {
83
+ if (venueList[`${venueId}${convertedLangsToTry[i]}`]) {
84
+ venueId = `${venueId}${convertedLangsToTry[i]}`;
85
+ vconfig.venueId = `${venueId}`;
86
+ break
87
+ }
88
+ }
89
+ }
90
+
91
+ if (!venueList[venueId])
92
+ throw Error(`Attempt to access venue ${venueId} which is not within venue list: ${Object.keys(venueList)}`)
93
+ const files = venueList[venueId].files; // mapping of asset "types" (spritesheet, style, badges, etc) to their URL
94
+ const fetchedData = (vconfig.dataFetch && configUtils.global[vconfig.dataFetch] && configUtils.global[vconfig.dataFetch].getVenueData)
95
+ ? await configUtils.global[vconfig.dataFetch].getVenueData(vconfig)
96
+ : await fetchJson(files.venueData);
97
+
98
+ const venueData = fetchedData[venueId];
99
+
100
+ // For tilemaps, we need to embellish the venue data with structure
101
+ if (venueData.tileServerAuthInfo)
102
+ embellishTilemapVenueData(venueData);
103
+
104
+ venueData.venueList = venueList;
105
+ const contentStage = getContentStage(vconfig);
106
+ venueData.files = contentStage // if a contentStage is defined, remap content URLs (see docs/Content-And-Asset-Loading/contentStaging.md)
107
+ ? remapEachURLForContentStage(venueData.category, files, contentStage, accountId, venueId)
108
+ : files;
109
+
110
+ return venueData
111
+ };
112
+
113
+ const buildStructures = (venueData) => {
114
+ const { structureOrder, structures } = venueData;
115
+ return structureOrder.map(structureId => {
116
+ const structure = structures[structureId];
117
+ // Was going to use this for selecting floors - but it seems floor bounds are incorrect? (was testing LAX/lax-msc-2 for example)
118
+ // Object.values(structure.levels).forEach(level => (level.bounds = findBoundsOfCoordinates(level.boundsPolygon)))
119
+ const bounds$1 = bounds.findBoundsOfCoordinates(structure.boundsPolygon);
120
+ return { ...structure, bounds: bounds$1 }
121
+ })
122
+ };
123
+
124
+ function embellishTilemapVenueData (venueData) {
125
+ const additionalFields = {
126
+ defaultOrdinal: 0, // this and below override the venue data
127
+ defaultStructureId: 'singleBuilding',
128
+ formatVersion: 'v5',
129
+ // Note: this structures object does not represent the "buildingsAndLevels" as
130
+ // managed within this app. This is a mock structure for the purposes of rendering
131
+ // a tiled map. It is always a single building, single floor. If user switches
132
+ // buildings or floors, it unmounts this map and remounts a new map with that building/floor
133
+ structures: {
134
+ singleBuilding: {
135
+ name: 'singleBuilding',
136
+ boundsPolygon: [],
137
+ defaultLevelId: 'singleLevel',
138
+ id: 'singleBuilding',
139
+ levels: {
140
+ singleLevel: {
141
+ boundsPolygon: [],
142
+ clfloor: 0,
143
+ details: '',
144
+ id: 'singleLevel',
145
+ name: 'singleLevel',
146
+ ordinal: 0
147
+ }
148
+ }
149
+ }
150
+ },
151
+ structureOrder: [
152
+ 'singleBuilding'
153
+ ]
154
+ };
155
+
156
+ for (const key in additionalFields)
157
+ venueData[key] = additionalFields[key];
158
+ }
159
+
160
+ const between = (val, lim1, lim2) => val > lim1 ? val <= lim2 : val => lim2;
161
+
162
+ // exchanges the first and second items in an array, preserving the rest of the array untouched
163
+ // i.e. [1,2,3,4,5] => [2,1,3,4,5]
164
+ const swapFirstTwoItems = ([c1, c2, ...c3]) => [c2, c1, ...c3];
165
+
166
+ /**
167
+ * Since coordinates are often expressed as [lat, lng] but required by GeoJSON to be [lng, lat],
168
+ * this function will take a list of coordinate pairs and ensure they are in the required format
169
+ * by comparing to the venue bounds.
170
+ *
171
+ * @param {array.array.float} coords list of coordinate pairs, such as [[36.3,-115.85], [36.5, -115.34]]
172
+ * @param {object} venueBounds contains props {ne, sw} which each are objects containing {lat,lng} properties
173
+ * @returns {array.array.float} with [lng,lat,...] for each item
174
+ */
175
+ const normalizeCoords = (coords, venueBounds) => {
176
+ if (!coords || !Array.isArray(coords) || coords.length < 1)
177
+ return coords
178
+
179
+ if (between(coords[0][0], venueBounds.ne.lng, venueBounds.sw.lng)) // looks like a lat - so already in proper order
180
+ return coords
181
+
182
+ // wrong order, so swtich em
183
+ return coords.map(swapFirstTwoItems)
184
+ };
185
+
186
+ // If config.useDynamicUrlParams is true, allow changing even security-related parameters in
187
+ // the URL - else, only allow the changing of "end-user-changable" parameters, such as vid
188
+ // export function updateConfigWithUrlParams (config) {
189
+ // const dlp = config.deepLinkProps
190
+ // if (dlp) {
191
+ // const venueId = dlp.vid ? dlp.vid : config.venueId
192
+ // const assetStage = config.useDynamicUrlParams && dlp.stage ? dlp.stage : config.assetStage
193
+ // const accountId = assetStage === 'alpha' ? 'A1VPTJKREFJWX5' : config.accountId
194
+ // return { ...config, venueId, assetStage, accountId }
195
+ // }
196
+ // return config
197
+ // }
198
+
199
+ exports.buildStructures = buildStructures;
200
+ exports.createFetchJson = createFetchJson;
201
+ exports.createFetchText = createFetchText;
202
+ exports.getVenueDataFromUrls = getVenueDataFromUrls;
203
+ exports.normalizeCoords = normalizeCoords;
@@ -2,29 +2,157 @@
2
2
 
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
- var e = require('ramda');
5
+ var R = require('ramda');
6
6
  var wayfinder = require('./wayfinder.js');
7
7
 
8
8
  function _interopNamespace(e) {
9
- if (e && e.__esModule) return e;
10
- var n = Object.create(null);
11
- if (e) {
12
- Object.keys(e).forEach(function (k) {
13
- if (k !== 'default') {
14
- var d = Object.getOwnPropertyDescriptor(e, k);
15
- Object.defineProperty(n, k, d.get ? d : {
16
- enumerable: true,
17
- get: function () { return e[k]; }
18
- });
19
- }
20
- });
21
- }
22
- n["default"] = e;
23
- return Object.freeze(n);
9
+ if (e && e.__esModule) return e;
10
+ var n = Object.create(null);
11
+ if (e) {
12
+ Object.keys(e).forEach(function (k) {
13
+ if (k !== 'default') {
14
+ var d = Object.getOwnPropertyDescriptor(e, k);
15
+ Object.defineProperty(n, k, d.get ? d : {
16
+ enumerable: true,
17
+ get: function () { return e[k]; }
18
+ });
19
+ }
20
+ });
21
+ }
22
+ n["default"] = e;
23
+ return Object.freeze(n);
24
24
  }
25
25
 
26
- var e__namespace = /*#__PURE__*/_interopNamespace(e);
26
+ var R__namespace = /*#__PURE__*/_interopNamespace(R);
27
27
 
28
- const i=t=>i=>e__namespace.find((e=>e.dst===t),i.edges),r=(r,s,a,n={})=>{const o=[],u=[];let c=!1,l=!1;const d=((e,t,i,r)=>{if(!t||!i)throw Error("bad calculate Route request!");return e.findShortestPath(t,i,r)})(r,s,a,n);if(null===d)return null;let y=null;for(let r=0;r<d.length;r++){const s={distance:0,eta:0};if(y){const e=i(d[r].id)(y);null!=e&&(s.distance=e.distance,s.eta=e.transitTime,"Ground"!==e.type&&(s.portalType=e.type,s.isPortal=!0),e.o&&(s.poiId=e.o),e.path&&(s.curvedPathForward=e.path),e.securityWaitTimes&&(s.securityWaitTimes=e.securityWaitTimes,s.eta=s.securityWaitTimes.queueTime),e.securityLane&&(s.securityLane=e.securityLane,s.isSecurityCheckpoint=!0,e.securityLane.type===wayfinder.SecurityLaneType.SECURITY&&(c=!0),e.securityLane.type===wayfinder.SecurityLaneType.IMMIGRATION&&(l=!0),e.o&&u.push(e.o)));}s.levelDifference=y?d[r].ordinal-y.ordinal:0,s.position=e__namespace.omit(["edges","id"],{...d[r]}),o.push(s),y=d[r];}return e__namespace.last(o).isDestination=!0,{waypoints:o,queues:u,hasSecurity:c,hasImmigration:l}};
28
+ const getEdgeTo = dst => node => R__namespace.find(e => e.dst === dst, node.edges);
29
29
 
30
- exports.findRoute = r;
30
+ /**
31
+ * Returns the shortest route (or path) from start to end.
32
+ * @param {Object} start must include {floorId, lat, lng}
33
+ * @param {Object} end must include {floorId, lat, lng}
34
+ * @param {Object} options optional settings for choosing route
35
+ * @param {boolean} options.requiresAccessibility if true, only accessible routes are returned (no stairs or escalators)
36
+ * @returns {[nodes]} array of NavGraph nodes OR null if no route exists
37
+ * @throws if start or end is not defined
38
+ */
39
+ const calculateRoute = (graph, start, end, options) => {
40
+ if (!start || !end)
41
+ throw Error('bad calculate Route request!')
42
+ return graph.findShortestPath(start, end, options)
43
+ };
44
+
45
+ /**
46
+ * @typedef Waypoint
47
+ * @property {FullPosition} position
48
+ * @property {number} distance
49
+ * @property {number} eta
50
+ * @property {boolean} isSecurityCheckpoint
51
+ * @property {boolean} isPortal
52
+ * @property {string} portalType
53
+ * @property {number} levelDifference
54
+ * @property {boolean} isDestination
55
+ * @property {SecurityWaitTime|null} securityWaitTimes
56
+ * @property {SecurityLane|null} securityLane
57
+ * @property {CurvedPath|null} curvedPathForward
58
+ *
59
+ * @typedef SecurityLane
60
+ * @property {string} id
61
+ * @property {string} type
62
+ *
63
+ * @typedef FullPosition
64
+ * @property {string} floorId
65
+ * @property {string} lat
66
+ * @property {number} lng
67
+ * @property {number} ordinal
68
+ * @property {string} structureId
69
+ *
70
+ * @typedef {Array.<CurvedPoint>} CurvedPath
71
+ *
72
+ * @typedef CurvedPoint
73
+ * @property {ObjCoordinate} end
74
+ * @property {ObjCoordinate} in
75
+ * @property {ObjCoordinate} out
76
+ * @property {ObjCoordinate} start
77
+ *
78
+ * @typedef {{lng: number, lat: number}} ObjCoordinate
79
+ *
80
+ * Returns the shortest route (or path) from start to end.
81
+ * @param graph
82
+ * @param {Endpoint} start
83
+ * @param {Endpoint} destination
84
+ * @param {RouteOptions} options
85
+ * @return {{waypoints: Array.<Waypoint>}|null}
86
+ */
87
+ // todo refactor
88
+ const findRoute = (graph, start, destination, options = {}) => {
89
+ const waypoints = [];
90
+ const queues = [];
91
+
92
+ let hasSecurity = false;
93
+ let hasImmigration = false;
94
+
95
+ const routeNodes = calculateRoute(graph, start, destination, options);
96
+
97
+ if (routeNodes === null)
98
+ return null
99
+
100
+ let previousRouteNode = null;
101
+ for (let i = 0; i < routeNodes.length; i++) {
102
+ const waypoint = {
103
+ distance: 0,
104
+ eta: 0
105
+ };
106
+
107
+ if (previousRouteNode) {
108
+ const edgeUsed = getEdgeTo(routeNodes[i].id)(previousRouteNode);
109
+ if (edgeUsed != null) {
110
+ waypoint.distance = edgeUsed.distance;
111
+ waypoint.eta = edgeUsed.transitTime;
112
+
113
+ if (edgeUsed.type !== 'Ground') {
114
+ waypoint.portalType = edgeUsed.type;
115
+ waypoint.isPortal = true;
116
+ }
117
+
118
+ if (edgeUsed.o)
119
+ waypoint.poiId = edgeUsed.o;
120
+
121
+ if (edgeUsed.path)
122
+ waypoint.curvedPathForward = edgeUsed.path;
123
+ if (edgeUsed.securityWaitTimes) {
124
+ waypoint.securityWaitTimes = edgeUsed.securityWaitTimes;
125
+ waypoint.eta = waypoint.securityWaitTimes.queueTime;
126
+ }
127
+
128
+ if (edgeUsed.securityLane) {
129
+ waypoint.securityLane = edgeUsed.securityLane;
130
+ waypoint.isSecurityCheckpoint = true;
131
+ if (edgeUsed.securityLane.type === wayfinder.SecurityLaneType.SECURITY)
132
+ hasSecurity = true;
133
+ if (edgeUsed.securityLane.type === wayfinder.SecurityLaneType.IMMIGRATION)
134
+ hasImmigration = true;
135
+ if (edgeUsed.o)
136
+ queues.push(edgeUsed.o);
137
+ }
138
+ }
139
+ }
140
+
141
+ waypoint.levelDifference = previousRouteNode ? routeNodes[i].ordinal - previousRouteNode.ordinal : 0;
142
+ waypoint.position = R__namespace.omit(['edges', 'id'], { ...routeNodes[i] });
143
+
144
+ waypoints.push(waypoint);
145
+
146
+ previousRouteNode = routeNodes[i];
147
+ }
148
+ R__namespace.last(waypoints).isDestination = true;
149
+
150
+ return {
151
+ waypoints,
152
+ queues,
153
+ hasSecurity,
154
+ hasImmigration
155
+ }
156
+ };
157
+
158
+ exports.findRoute = findRoute;
@@ -1,5 +1,91 @@
1
1
  'use strict';
2
2
 
3
- class h{constructor(){this.heap=[null],this.heapMap={};}offerWithPriority(h,i){const t=this.heap.push([h,i])-1;this.heapMap[h]=t,this.bubble(t);}raisePriority(h,i){const t=this.heapMap[h];this.heap[t][1]=i,this.bubble(t);}poll(){if(1===this.heap.length)return null;if(2===this.heap.length){const h=this.heap.pop()[0];return delete this.heapMap[h],h}const h=this.heap[1][0];return delete this.heapMap[h],this.heap[1]=this.heap.pop(),this.heapMap[this.heap[1][0]]=1,this.sink(1),h}isEmpty(){return 1===this.heap.length}bubble(h){for(;h>1;){const i=h>>1;if(!this.isHigherPriority(h,i))break;this.swap(h,i),h=i;}}sink(h){for(;2*h<this.heap.length;){const i=void 0!==this.heap[2*h+1]&&this.isHigherPriority(2*h+1,2*h)?2*h+1:2*h;if(this.isHigherPriority(h,i))break;this.swap(h,i),h=i;}}swap(h,i){this.heapMap[this.heap[h][0]]=i,this.heapMap[this.heap[i][0]]=h;const t=this.heap[h];this.heap[h]=this.heap[i],this.heap[i]=t;}isHigherPriority(h,i){return this.heap[h][1]<this.heap[i][1]}}
3
+ class MinPriorityQueue {
4
+ constructor () {
5
+ this.heap = [null]; // array representation of binary heap
6
+ this.heapMap = {};
7
+ }
4
8
 
5
- module.exports = h;
9
+ offerWithPriority (node, priority) {
10
+ const index = this.heap.push([node, priority]) - 1;
11
+
12
+ this.heapMap[node] = index;
13
+ this.bubble(index);
14
+ }
15
+
16
+ raisePriority (node, priority) {
17
+ const index = this.heapMap[node];
18
+ this.heap[index][1] = priority;
19
+
20
+ this.bubble(index);
21
+ }
22
+
23
+ poll () {
24
+ if (this.heap.length === 1) {
25
+ return null
26
+ }
27
+ if (this.heap.length === 2) {
28
+ const value = this.heap.pop()[0];
29
+ delete this.heapMap[value];
30
+ return value
31
+ }
32
+
33
+ const value = this.heap[1][0];
34
+ delete this.heapMap[value];
35
+
36
+ this.heap[1] = this.heap.pop();
37
+ this.heapMap[this.heap[1][0]] = 1;
38
+
39
+ this.sink(1);
40
+
41
+ return value
42
+ }
43
+
44
+ isEmpty () {
45
+ return this.heap.length === 1
46
+ }
47
+
48
+ bubble (i) {
49
+ while (i > 1) {
50
+ const parentIndex = i >> 1; // floor(i/2)
51
+
52
+ if (!this.isHigherPriority(i, parentIndex)) {
53
+ break
54
+ }
55
+
56
+ this.swap(i, parentIndex);
57
+ i = parentIndex;
58
+ }
59
+ }
60
+
61
+ sink (i) {
62
+ while (i * 2 < this.heap.length) {
63
+ const isRightChildHigherPriority = (this.heap[i * 2 + 1] === undefined)
64
+ ? false
65
+ : this.isHigherPriority(i * 2 + 1, i * 2); // i*2 +1 might be null
66
+ const childIndex = isRightChildHigherPriority ? i * 2 + 1 : i * 2;
67
+
68
+ if (this.isHigherPriority(i, childIndex)) {
69
+ break
70
+ }
71
+
72
+ this.swap(i, childIndex);
73
+ i = childIndex;
74
+ }
75
+ }
76
+
77
+ swap (i, j) {
78
+ this.heapMap[this.heap[i][0]] = j;
79
+ this.heapMap[this.heap[j][0]] = i;
80
+
81
+ const temp = this.heap[i];
82
+ this.heap[i] = this.heap[j];
83
+ this.heap[j] = temp;
84
+ }
85
+
86
+ isHigherPriority (i, j) {
87
+ return this.heap[i][1] < this.heap[j][1] // lower score -> higher priority
88
+ }
89
+ }
90
+
91
+ module.exports = MinPriorityQueue;