@@ -9,6 +9,9 @@ import knex from 'chaire-lib-backend/lib/config/shared/db.config';
99
1010import dbQueries from '../transitNodeTransferable.db.queries' ;
1111import nodesDbQueries from '../transitNodes.db.queries' ;
12+ import pathDbQueries from '../transitPaths.db.queries' ;
13+ import linesDbQueries from '../transitLines.db.queries' ;
14+ import agencyDbQueries from '../transitAgencies.db.queries'
1215
1316const objectName = 'transferable node' ;
1417
@@ -42,6 +45,7 @@ beforeAll(async () => {
4245
4346afterAll ( async ( ) => {
4447 await dbQueries . truncate ( ) ;
48+ await agencyDbQueries . truncate ( ) ;
4549 await nodesDbQueries . truncate ( ) ;
4650 await knex . destroy ( ) ;
4751} ) ;
@@ -187,4 +191,177 @@ describe(`${objectName}`, () => {
187191 expect ( transferableNodes ) . toEqual ( [ ] ) ;
188192 } ) ;
189193
194+ } ) ;
195+
196+ describe ( 'getTransferableNodePairs' , ( ) => {
197+ // Make another line of nodes
198+ const otherNodeAttributes = [ 0 , 1 , 2 , 3 , 4 , 5 ] . map ( idx => ( {
199+ id : uuidV4 ( ) ,
200+ code : `000${ idx + 10 } ` ,
201+ name : `NewNode ${ idx + 10 } ` ,
202+ internal_id : `Test${ idx + 10 } ` ,
203+ integer_id : idx + 10 ,
204+ geography : {
205+ type : "Point" as const ,
206+ coordinates : [ - 72.995 - 0.001 * idx , 45 + 0.001 * idx ]
207+ } ,
208+ color : '#ffff00' ,
209+ is_enabled : true ,
210+ is_frozen : false ,
211+ description : `New node description ${ idx } ` ,
212+ default_dwell_time_seconds : 25 ,
213+ routing_radius_meters : 50 ,
214+ data : {
215+ foo : 'bar'
216+ }
217+ } ) ) ;
218+ const agencyId = uuidV4 ( ) ;
219+ const lineIds = [ uuidV4 ( ) , uuidV4 ( ) ] ;
220+ const pathIds = [ uuidV4 ( ) , uuidV4 ( ) , uuidV4 ( ) , uuidV4 ( ) ] ;
221+ const pathNodes = [
222+ // Path stops at each node
223+ nodeAttributes . map ( node => node . id ) ,
224+ // Path stops at nodes with even indexes
225+ nodeAttributes . filter ( ( node , idx ) => idx % 2 === 0 ) . map ( node => node . id ) ,
226+ // Path stops at each other node node
227+ otherNodeAttributes . map ( node => node . id ) ,
228+ // Path stops at other nodes with even indexes
229+ otherNodeAttributes . filter ( ( node , idx ) => idx % 2 === 0 ) . map ( node => node . id )
230+ ]
231+ beforeAll ( async ( ) => {
232+ await dbQueries . truncate ( ) ;
233+ // This should delete also lines and paths
234+ await agencyDbQueries . truncate ( ) ;
235+ await nodesDbQueries . truncate ( ) ;
236+ await nodesDbQueries . createMultiple ( [ ...nodeAttributes , ...otherNodeAttributes ] ) ;
237+ // Create an agency, 2 lines and 4 paths
238+ await agencyDbQueries . create ( {
239+ id : agencyId ,
240+ name : 'test' ,
241+ acronym : 'test'
242+ } as any ) ;
243+ await linesDbQueries . createMultiple ( [ {
244+ id : lineIds [ 0 ] ,
245+ shortname : 'test1' ,
246+ agency_id : agencyId ,
247+ color : '#ffffff' ,
248+ } , {
249+ id : lineIds [ 1 ] ,
250+ shortname : 'test2' ,
251+ agency_id : agencyId ,
252+ color : '#ffffff' ,
253+ } ] as any ) ;
254+ await pathDbQueries . createMultiple ( [ {
255+ id : pathIds [ 0 ] , // Path stops at each other node node
256+ line_id : lineIds [ 0 ] ,
257+ nodes : pathNodes [ 0 ] ,
258+ } , {
259+ id : pathIds [ 1 ] ,
260+ line_id : lineIds [ 0 ] ,
261+ nodes : pathNodes [ 1 ] ,
262+ } , {
263+ id : pathIds [ 2 ] ,
264+ line_id : lineIds [ 1 ] ,
265+ nodes : pathNodes [ 2 ] ,
266+ } , {
267+ id : pathIds [ 3 ] ,
268+ line_id : lineIds [ 1 ] ,
269+ nodes : pathNodes [ 3 ] ,
270+ } ] as any ) ;
271+
272+ // For each node in nodeAttributes and otherNodeAttributes, fake some
273+ // transferable nodes data, the real number does not matter,
274+ // even-indexed nodes from the 2 series are not tranferrable
275+ for ( let i = 0 ; i < nodeAttributes . length ; i ++ ) {
276+ const node = nodeAttributes [ i ] ;
277+ // Ignore the node itself from the array, and add transfers from the other series, ignoring even if the current index is even
278+ const transferableNodeIds = [ ...nodeAttributes . filter ( ( n , idx ) => idx !== i ) . map ( n => n . id ) , ...otherNodeAttributes . filter ( ( n , idx ) => i % 2 !== 0 || idx % 2 !== 0 ) . map ( n => n . id ) ] ;
279+ await dbQueries . saveForNode ( node . id , {
280+ nodesIds : transferableNodeIds ,
281+ walkingTravelTimesSeconds : transferableNodeIds . map ( ( id , idx ) => ( 100 + i ) * idx ) ,
282+ walkingDistancesMeters : transferableNodeIds . map ( ( id , idx ) => ( 150 + i ) * idx ) ,
283+ } ) ;
284+ }
285+ for ( let i = 0 ; i < otherNodeAttributes . length ; i ++ ) {
286+ const node = otherNodeAttributes [ i ] ;
287+ // Ignore the node itself from the array, and add transfers from the other series, ignoring even if the current index is even
288+ const transferableNodeIds = [ ...otherNodeAttributes . filter ( ( n , idx ) => idx !== i ) . map ( n => n . id ) , ...nodeAttributes . filter ( ( n , idx ) => i % 2 !== 0 || idx % 2 !== 0 ) . map ( n => n . id ) ] ;
289+ await dbQueries . saveForNode ( node . id , {
290+ nodesIds : transferableNodeIds ,
291+ walkingTravelTimesSeconds : transferableNodeIds . map ( ( id , idx ) => ( 120 + i ) * idx ) ,
292+ walkingDistancesMeters : transferableNodeIds . map ( ( id , idx ) => ( 180 + i ) * idx ) ,
293+ } ) ;
294+ }
295+ } ) ;
296+
297+ afterAll ( async ( ) => {
298+ await dbQueries . truncate ( ) ;
299+ // This should delete also lines and paths
300+ await agencyDbQueries . truncate ( ) ;
301+ await nodesDbQueries . truncate ( ) ;
302+ } ) ;
303+
304+ test ( 'From/to paths no in database' , async ( ) => {
305+ expect ( await dbQueries . getTransferableNodePairs ( {
306+ pathsFrom : [ uuidV4 ( ) , uuidV4 ( ) ] ,
307+ pathsTo : [ uuidV4 ( ) ]
308+ } ) ) . toEqual ( [ ] ) ;
309+ } ) ;
310+
311+ test ( 'No transferable nodes between paths' , async ( ) => {
312+ expect ( await dbQueries . getTransferableNodePairs ( {
313+ pathsFrom : [ pathIds [ 1 ] ] ,
314+ pathsTo : [ pathIds [ 3 ] ]
315+ } ) ) . toEqual ( [ ] ) ;
316+ } ) ;
317+
318+ test ( 'Transferable nodes between paths' , async ( ) => {
319+ const transferrableNodes = await dbQueries . getTransferableNodePairs ( {
320+ pathsFrom : [ pathIds [ 0 ] ] ,
321+ pathsTo : [ pathIds [ 2 ] ]
322+ } ) ;
323+ // There should be one transferable node per node of the path
324+ expect ( transferrableNodes . length ) . toEqual ( pathNodes [ 0 ] . length ) ;
325+
326+ // Make sure there are no duplicate entries for 2 paths and a node
327+ const noDuplicates1 = new Set ( transferrableNodes . map ( pair => `${ pair . from . pathId } -${ pair . from . nodeId } -${ pair . to . pathId } ` ) ) ;
328+ expect ( noDuplicates1 . size ) . toBe ( transferrableNodes . length ) ;
329+
330+ // pathIds[1] has less node, so there should be less transferable nodes
331+ const transferrableNodesLess = await dbQueries . getTransferableNodePairs ( {
332+ pathsFrom : [ pathIds [ 1 ] ] ,
333+ pathsTo : [ pathIds [ 2 ] ]
334+ } )
335+ expect ( transferrableNodesLess . length ) . toEqual ( pathNodes [ 1 ] . length ) ;
336+
337+ const noDuplicates2 = new Set ( transferrableNodes . map ( pair => `${ pair . from . pathId } -${ pair . from . nodeId } -${ pair . to . pathId } ` ) ) ;
338+ expect ( noDuplicates2 . size ) . toBe ( transferrableNodes . length ) ;
339+ } ) ;
340+
341+ test ( 'Transferable nodes between multiple paths' , async ( ) => {
342+ const transferrableNodes = await dbQueries . getTransferableNodePairs ( {
343+ pathsFrom : [ pathIds [ 0 ] , pathIds [ 1 ] ] ,
344+ pathsTo : [ pathIds [ 2 ] , pathIds [ 3 ] ]
345+ } ) ;
346+ // pathIds[1] and pathIds[3] have no transferable nodes, and some nodes of pathIds[0] don't transfer with some nodes of pathIds[3]
347+ expect ( transferrableNodes . length ) . toEqual ( pathNodes [ 0 ] . length + pathNodes [ 1 ] . length + pathNodes [ 3 ] . length ) ;
348+
349+ // Make sure there are no duplicate entries for 2 paths and a node
350+ const noDuplicates1 = new Set ( transferrableNodes . map ( pair => `${ pair . from . pathId } -${ pair . from . nodeId } -${ pair . to . pathId } ` ) ) ;
351+ expect ( noDuplicates1 . size ) . toBe ( transferrableNodes . length ) ;
352+ } ) ;
353+
354+ test ( 'Invalid path ids' , async ( ) => {
355+ await expect ( dbQueries . getTransferableNodePairs ( {
356+ pathsFrom : [ 'not a uuid' ] ,
357+ pathsTo : [ 'not a uuid again' ]
358+ } ) ) . rejects . toThrow ( expect . anything ( ) ) ;
359+ } ) ;
360+
361+ test ( 'empty path ids' , async ( ) => {
362+ await expect ( dbQueries . getTransferableNodePairs ( {
363+ pathsFrom : [ ] ,
364+ pathsTo : [ ]
365+ } ) ) . rejects . toThrow ( expect . anything ( ) ) ;
366+ } ) ;
190367} ) ;
0 commit comments