@@ -6,6 +6,7 @@ const Factory = require('./modelFactory');
66const mongo = require ( '../mongo' ) ;
77const Event = require ( '../models/event' ) ;
88const { ObjectID } = require ( 'mongodb' ) ;
9+ const { composeFullRepetitionEvent } = require ( '../utils/merge' ) ;
910
1011/**
1112 * @typedef {Object } RecentEventSchema
@@ -393,21 +394,43 @@ class EventsFactory extends Factory {
393394 *
394395 * @param {string|ObjectID } eventId - Event's id
395396 * @param {Number } limit - count limitations
396- * @param {Number } skip - selection offset
397+ * @param {Number } cursor - cursor for pagination
397398 *
398399 * @return {EventRepetitionSchema[] }
399400 *
400401 * @todo move to Repetitions(?) model
401402 */
402- async getEventRepetitions ( eventId , limit = 10 , skip = 0 ) {
403+ async getEventRepetitions ( repetitionId , limit = 10 , cursor = undefined ) {
403404 limit = this . validateLimit ( limit ) ;
404- skip = this . validateSkip ( skip ) ;
405+ cursor = cursor ? new ObjectID ( cursor ) : undefined ;
406+
407+ const result = {
408+ repetitions : [ ] ,
409+ cursor : undefined ,
410+ } ;
405411
406412 /**
407413 * Get original event
408414 * @type {EventSchema }
409415 */
410- const eventOriginal = await this . findById ( eventId ) ;
416+ let eventOriginal = await this . findById ( repetitionId ) ;
417+
418+ /**
419+ * If original event is not found, it can mean that client is trying to get repetitions of original event
420+ */
421+ if ( ! eventOriginal ) {
422+ const repetition = await this . getEventRepetition ( repetitionId ) ;
423+
424+ if ( ! repetition ) {
425+ return result ;
426+ }
427+
428+ eventOriginal = await this . findById ( repetition . eventId ) ;
429+ }
430+
431+ if ( ! eventOriginal ) {
432+ return result ;
433+ }
411434
412435 /**
413436 * Collect repetitions
@@ -416,13 +439,27 @@ class EventsFactory extends Factory {
416439 const repetitions = await this . getCollection ( this . TYPES . REPETITIONS )
417440 . find ( {
418441 groupHash : eventOriginal . groupHash ,
442+ _id : cursor ? { $lte : cursor } : { } ,
419443 } )
420444 . sort ( { _id : - 1 } )
421- . limit ( limit )
422- . skip ( skip )
445+ . limit ( limit + 1 )
423446 . toArray ( ) ;
424447
425- const isLastPortion = repetitions . length < limit && skip === 0 ;
448+ if ( repetitions . length === limit + 1 ) {
449+ result . cursor = repetitions . pop ( ) . _id ;
450+ }
451+
452+ for ( const repetition of repetitions ) {
453+ result . repetitions . push ( {
454+ ...eventOriginal ,
455+ _id : repetition . _id ,
456+ payload : composeFullRepetitionEvent ( eventOriginal , repetition ) . payload ,
457+ timestamp : repetition . timestamp ,
458+ firstAppearanceTimestamp : eventOriginal . timestamp ,
459+ } ) ;
460+ }
461+
462+ const isLastPortion = repetitions . length < limit ;
426463
427464 /**
428465 * For last portion:
@@ -434,16 +471,14 @@ class EventsFactory extends Factory {
434471 * @type {EventRepetitionSchema }
435472 */
436473 const firstRepetition = {
437- _id : eventOriginal . _id ,
438- payload : eventOriginal . payload ,
439- groupHash : eventOriginal . groupHash ,
440- timestamp : eventOriginal . timestamp ,
474+ ...eventOriginal ,
475+ firstAppearanceTimestamp : eventOriginal . timestamp ,
441476 } ;
442477
443- repetitions . push ( firstRepetition ) ;
478+ result . repetitions . push ( firstRepetition ) ;
444479 }
445480
446- return repetitions ;
481+ return result ;
447482 }
448483
449484 /**
@@ -455,10 +490,40 @@ class EventsFactory extends Factory {
455490 * @todo move to Repetitions(?) model
456491 */
457492 async getEventRepetition ( repetitionId ) {
458- return this . getCollection ( this . TYPES . REPETITIONS )
493+ const repetition = await this . getCollection ( this . TYPES . REPETITIONS )
459494 . findOne ( {
460495 _id : ObjectID ( repetitionId ) ,
461496 } ) ;
497+
498+ if ( ! repetition ) {
499+ /**
500+ * If repetition is not found, it can mean that client is trying to get original event
501+ */
502+ const event = await this . findById ( repetitionId ) ;
503+
504+ if ( ! event ) {
505+ return null ;
506+ }
507+
508+ return {
509+ ...event ,
510+ firstAppearanceTimestamp : event . timestamp ,
511+ } ;
512+ }
513+
514+ const originalEvent = await this . findById ( repetition . eventId ) ;
515+
516+ if ( ! originalEvent ) {
517+ return null ;
518+ }
519+
520+ return {
521+ ...originalEvent ,
522+ _id : repetition . _id ,
523+ payload : composeFullRepetitionEvent ( originalEvent , repetition ) . payload ,
524+ timestamp : repetition . timestamp ,
525+ firstAppearanceTimestamp : originalEvent . timestamp ,
526+ } ;
462527 }
463528
464529 /**
@@ -501,7 +566,15 @@ class EventsFactory extends Factory {
501566 *
502567 * @return {Promise<void> }
503568 */
504- async visitEvent ( eventId , userId ) {
569+ async visitEvent ( repetitionId , userId ) {
570+ const repetition = await this . getCollection ( this . TYPES . REPETITIONS )
571+ . findOne ( { _id : new ObjectID ( repetitionId ) } ) ;
572+
573+ /**
574+ * If repetition is not found, it can mean that client is trying to work with original event
575+ */
576+ const eventId = repetition ? repetition . eventId : repetitionId ;
577+
505578 return this . getCollection ( this . TYPES . EVENTS )
506579 . updateOne (
507580 { _id : new ObjectID ( eventId ) } ,
@@ -517,7 +590,15 @@ class EventsFactory extends Factory {
517590 *
518591 * @return {Promise<void> }
519592 */
520- async toggleEventMark ( eventId , mark ) {
593+ async toggleEventMark ( repetitionId , mark ) {
594+ const repetition = await this . getCollection ( this . TYPES . REPETITIONS )
595+ . findOne ( { _id : new ObjectID ( repetitionId ) } ) ;
596+
597+ /**
598+ * If repetition is not found, it can mean that client is trying to work with original event
599+ */
600+ const eventId = repetition ? repetition . eventId : repetitionId ;
601+
521602 const collection = this . getCollection ( this . TYPES . EVENTS ) ;
522603 const query = { _id : new ObjectID ( eventId ) } ;
523604
0 commit comments