Best JavaScript code snippet using playwright-internal
subscribe.spec.js
Source:subscribe.spec.js  
...69      });70    });7172    it('should invoke the callback when the specified context has been created with update()', (done) => {73      const contextName = gtf.contexts.getContextName();74      const context = { id: gtf.contexts.getContextName() };7576      glue.contexts77        .subscribe(contextName, (data) => {78          if (data.id === context.id) {79            done();80          }81        })82        .then((unsubscribeFn) => {83          gtf.addWindowHook(unsubscribeFn);84          return glue.contexts.update(contextName, context);85        })86        .catch((err) => done(err));87    });8889    it('should invoke the callback when the specified context has been created with set()', (done) => {90      const contextName = gtf.contexts.getContextName();91      const context = { id: gtf.contexts.getContextName() };9293      glue.contexts94        .subscribe(contextName, (data) => {95          if (data.id === context.id) {96            done();97          }98        })99        .then((unsubscribeFn) => {100          gtf.addWindowHook(unsubscribeFn);101          return glue.contexts.set(contextName, context);102        })103        .catch((err) => done(err));104    });105106    it('should invoke the callback when the specified context has been created with setPath()', (done) => {107      const contextName = gtf.contexts.getContextName();108109      glue.contexts110        .subscribe(contextName, (data) => {111          if (data.prop === 'value') {112            done();113          }114        })115        .then((unsubscribeFn) => {116          gtf.addWindowHook(unsubscribeFn);117          return glue.contexts.setPath(contextName, 'prop', 'value');118        })119        .catch((err) => done(err));120    });121122    it('should invoke the callback when the specified context has been created with setPaths()', (done) => {123      const contextName = gtf.contexts.getContextName();124      const contextPaths = [125        { path: 'prop1', value: 'value1' },126        { path: 'prop2', value: 'value2' },127      ];128129      glue.contexts130        .subscribe(contextName, (data) => {131          if (data.prop1 === 'value1') {132            done();133          }134        })135        .then((unsubscribeFn) => {136          gtf.addWindowHook(unsubscribeFn);137          return glue.contexts.setPaths(contextName, contextPaths);138        })139        .catch((err) => done(err));140    });141142    it('should invoke the callback with an object as first argument when the specified context has been created with update()', (done) => {143      const contextName = gtf.contexts.getContextName();144      const context = {145        id: gtf.contexts.getContextName(),146        complexObj: gtf.contexts.generateComplexObject(10),147      };148149      glue.contexts150        .subscribe(contextName, (updatedObject) => {151          if (updatedObject.id === context.id) {152            try {153              expect(updatedObject).to.be.an('object');154              done();155            } catch (error) {156              done(error);157            }158          }159        })160        .then((unsubscribeFn) => {161          gtf.addWindowHook(unsubscribeFn);162163          return glue.contexts.update(contextName, context);164        })165        .catch((err) => done(err));166    });167168    it('should invoke the callback with an object as first argument when the specified context has been created with set()', (done) => {169      const contextName = gtf.contexts.getContextName();170      const context = {171        id: gtf.contexts.getContextName(),172        complexObj: gtf.contexts.generateComplexObject(10),173      };174175      glue.contexts176        .subscribe(contextName, (updatedObject) => {177          if (updatedObject.id === context.id) {178            try {179              expect(updatedObject).to.be.an('object');180              done();181            } catch (error) {182              done(error);183            }184          }185        })186        .then((unsubscribeFn) => {187          gtf.addWindowHook(unsubscribeFn);188          return glue.contexts.set(contextName, context);189        })190        .catch((err) => done(err));191    });192193    it('should invoke the callback with an object as first argument  when the specified context has been created with setPath()', (done) => {194      const contextName = gtf.contexts.getContextName();195      const context = {196        id: gtf.contexts.getContextName(),197        complexObj: gtf.contexts.generateComplexObject(10),198      };199200      glue.contexts201        .subscribe(contextName, (updatedObject) => {202          if (updatedObject.prop1.id === context.id) {203            try {204              expect(updatedObject).to.be.an('object');205              done();206            } catch (error) {207              done(error);208            }209          }210        })211        .then((unsubscribeFn) => {212          gtf.addWindowHook(unsubscribeFn);213          return glue.contexts.setPath(contextName, 'prop1', context);214        })215        .catch((err) => done(err));216    });217218    it('should invoke the callback with an object as first argument  when the specified context has been created with setPaths()', (done) => {219      const contextName = gtf.contexts.getContextName();220221      glue.contexts222        .subscribe(contextName, (updatedObject) => {223          if (updatedObject.prop1 === 'value1') {224            try {225              expect(updatedObject).to.be.an('object');226              done();227            } catch (error) {228              done(error);229            }230          }231        })232        .then((unsubscribeFn) => {233          gtf.addWindowHook(unsubscribeFn);234          return glue.contexts.setPaths(contextName, [235            { path: 'prop1', value: 'value1' },236            { path: 'prop2', value: 'value2' },237          ]);238        })239240        .catch((err) => done(err));241    });242243    it('should invoke the callback with correct data as first argument when the specified context has been created with update()', (done) => {244      const contextName = gtf.contexts.getContextName();245      const context = {246        id: gtf.contexts.getContextName(),247        complexObj: gtf.contexts.generateComplexObject(10),248      };249250      glue.contexts251        .subscribe(contextName, (updatedObject) => {252          if (updatedObject.id === context.id) {253            try {254              expect(updatedObject).to.eql(context);255              done();256            } catch (error) {257              done(error);258            }259          }260        })261        .then((unsubscribeFn) => {262          gtf.addWindowHook(unsubscribeFn);263          return glue.contexts.update(contextName, context);264        })265        .catch((err) => done(err));266    });267268    it('should invoke the callback with correct data as first argument when the specified context has been created with set()', (done) => {269      const contextName = gtf.contexts.getContextName();270      const context = {271        id: gtf.contexts.getContextName(),272        complexObj: gtf.contexts.generateComplexObject(10),273      };274275      glue.contexts276        .subscribe(contextName, (updatedObject) => {277          if (updatedObject.id === context.id) {278            try {279              expect(updatedObject).to.eql(context);280              done();281            } catch (error) {282              done(error);283            }284          }285        })286        .then((unsubscribeFn) => {287          gtf.addWindowHook(unsubscribeFn);288          return glue.contexts.set(contextName, context);289        })290        .catch((err) => done(err));291    });292293    it('should invoke the callback with correct data as first argument when the specified context has been created with setPath()', (done) => {294      const contextName = gtf.contexts.getContextName();295      const context = {296        id: gtf.contexts.getContextName(),297        complexObj: gtf.contexts.generateComplexObject(10),298      };299300      glue.contexts301        .subscribe(contextName, (updatedObject) => {302          if (updatedObject.prop1.id === context.id) {303            try {304              expect(updatedObject).to.eql({ prop1: context });305              done();306            } catch (error) {307              done(error);308            }309          }310        })311        .then((unsubscribeFn) => {312          gtf.addWindowHook(unsubscribeFn);313          return glue.contexts.setPath(contextName, 'prop1', context);314        })315        .catch((err) => done(err));316    });317318    it('should invoke the callback with correct data as first argument when the specified context has been created with setPaths()', (done) => {319      const contextName = gtf.contexts.getContextName();320      const prop1Context = {321        id: gtf.contexts.getContextName(),322        complexObj: gtf.contexts.generateComplexObject(10),323      };324      const prop2Context = {325        title: 'prop2 context',326        value: 'prop2 value',327      };328329      glue.contexts330        .subscribe(contextName, (updatedObject) => {331          if (updatedObject.prop1.id === prop1Context.id) {332            try {333              expect(updatedObject).to.eql({334                prop1: prop1Context,335                prop2: prop2Context,336              });337              done();338            } catch (error) {339              done(error);340            }341          }342        })343        .then((unsubscribeFn) => {344          gtf.addWindowHook(unsubscribeFn);345          return glue.contexts.setPaths(contextName, [346            { path: 'prop1', value: prop1Context },347            { path: 'prop2', value: prop2Context },348          ]);349        })350351        .catch((err) => done(err));352    });353354    it('should invoke the callback 3 times when a context is updated 3 times with update()', (done) => {355      const ready = gtf.waitFor(3, done);356      const context = {357        id: gtf.contexts.getContextName(),358        name: gtf.contexts.getContextName(),359        complexObj: gtf.contexts.generateComplexObject(10),360      };361362      glue.contexts363        .subscribe(context.name, (data) => {364          if (data.id === context.id) {365            ready();366          }367        })368        .then((unsubscribeFn) => {369          gtf.addWindowHook(unsubscribeFn);370          return glue.contexts.update(context.name, context);371        })372        .then(() => glue.contexts.update(context.name, { date: new Date() }))373        .then(() => glue.contexts.update(context.name, { prop: 'value' }))374        .catch((err) => done(err));375    });376377    it('should invoke the callback 3 times when a context is changed 3 times with set()', (done) => {378      const ready = gtf.waitFor(3, done);379      const contextName = gtf.contexts.getContextName();380      const id = gtf.contexts.getContextName();381      const context = {382        id,383        name: gtf.contexts.getContextName(),384        complexObj: gtf.contexts.generateComplexObject(10),385      };386387      glue.contexts388        .subscribe(contextName, (data) => {389          if (data.id === context.id) {390            ready();391          }392        })393        .then((unsubscribeFn) => {394          gtf.addWindowHook(unsubscribeFn);395396          return glue.contexts.set(contextName, context);397        })398        .then(() => glue.contexts.set(contextName, { id, date: new Date() }))399        .then(() => glue.contexts.set(contextName, { id, prop: 'value' }))400        .catch((err) => done(err));401    });402403    it('should invoke the callback 3 times when a context is changed 3 times with setPath()', (done) => {404      const ready = gtf.waitFor(3, done);405      const context = {406        id: gtf.contexts.getContextName(),407        name: gtf.contexts.getContextName(),408        complexObj: gtf.contexts.generateComplexObject(10),409      };410411      glue.contexts412        .subscribe(context.name, (data) => {413          if (data.prop1.id === context.id) {414            ready();415          }416        })417        .then((unsubscribeFn) => {418          gtf.addWindowHook(unsubscribeFn);419          return glue.contexts.setPath(context.name, 'prop1', context);420        })421        .then(() => glue.contexts.setPath(context.name, 'prop2', { date: new Date() }))422        .then(() => glue.contexts.setPath(context.name, 'prop3', { prop: 'value' }))423        .catch((err) => done(err));424    });425426    it('should invoke the callback 3 times when a context is changed 3 times with setPaths()', (done) => {427      const ready = gtf.waitFor(3, done);428      const context = {429        id: gtf.contexts.getContextName(),430        name: gtf.contexts.getContextName(),431        complexObj: gtf.contexts.generateComplexObject(10),432      };433434      glue.contexts435        .subscribe(context.name, (data) => {436          if (data.prop1.id === context.id) {437            ready();438          }439        })440        .then((unsubscribeFn) => {441          gtf.addWindowHook(unsubscribeFn);442          return glue.contexts.setPaths(context.name, [{ path: 'prop1', value: context }]);443        })444        .then(() => glue.contexts.setPaths(context.name, [{ path: 'prop2', value: { date: new Date() } }]))445        .then(() => glue.contexts.setPaths(context.name, [{ path: 'prop3', value: { prop: 'value' } }]))446        .catch((err) => done(err));447    });448449    it('should invoke the callback with the updated data as first argument when the specified context has been changed with update()', (done) => {450      const context = {451        name: gtf.contexts.getContextName(),452        complexObj: gtf.contexts.generateComplexObject(10),453      };454      const newContext = {455        id: gtf.contexts.getContextName(),456        date: new Date(),457        title: 'new context',458      };459460      glue.contexts461        .update(context.name, context)462        .then(() =>463          glue.contexts.subscribe(context.name, (updatedObject) => {464            if (updatedObject.id === newContext.id) {465              try {466                expect(updatedObject).to.eql(Object.assign({}, context, newContext));467                done();468              } catch (error) {469                done(error);470              }471            }472          })473        )474        .then((unsubscribeFn) => {475          gtf.addWindowHook(unsubscribeFn);476          return glue.contexts.update(context.name, newContext);477        })478        .catch((err) => done(err));479    });480481    it('should invoke the callback with the new data as first argument when the specified context has been changed with set()', (done) => {482      const contextName = gtf.contexts.getContextName();483      const context = gtf.contexts.generateComplexObject(10);484      const newContext = {485        id: gtf.contexts.getContextName(),486        date: new Date(),487        title: 'new context',488      };489490      glue.contexts491        .set(contextName, context)492        .then(() =>493          glue.contexts.subscribe(contextName, (updatedObject) => {494            if (updatedObject.id === newContext.id) {495              try {496                expect(updatedObject).to.eql(newContext);497                done();498              } catch (error) {499                done(error);500              }501            }502          })503        )504        .then((unsubscribeFn) => {505          gtf.addWindowHook(unsubscribeFn);506          return glue.contexts.set(contextName, newContext);507        })508        .catch((err) => done(err));509    });510511    it('should invoke the callback with the new data as first argument when the specified context has been updated with setPath()', (done) => {512      const contextName = gtf.contexts.getContextName();513      const prop1Context = {514        date: new Date(),515        title: 'new context',516      };517      const prop2Context = {518        id: gtf.contexts.getContextName(),519        complexObj: gtf.contexts.generateComplexObject(10),520      };521522      glue.contexts523        .setPath(contextName, 'prop1', prop1Context)524        .then(() =>525          glue.contexts.subscribe(contextName, (updatedObject) => {526            if (updatedObject.prop2.id === prop2Context.id) {527              try {528                expect(updatedObject).to.eql({529                  prop1: prop1Context,530                  prop2: prop2Context,531                });532                done();533              } catch (error) {534                done(error);535              }536            }537          })538        )539        .then((unsubscribeFn) => {540          gtf.addWindowHook(unsubscribeFn);541          return glue.contexts.setPath(contextName, 'prop2', prop2Context);542        })543        .catch((err) => done(err));544    });545546    it('should invoke the callback with the new data as first argument when the specified context has been updated with setPaths()', (done) => {547      const contextName = gtf.contexts.getContextName();548      const prop1Context = {549        date: new Date(),550        title: 'new context',551      };552      const prop2Context = {553        id: gtf.contexts.getContextName(),554        complexObj: gtf.contexts.generateComplexObject(10),555      };556557      glue.contexts558        .setPaths(contextName, [{ path: 'prop1', value: prop1Context }])559        .then(() =>560          glue.contexts.subscribe(contextName, (updatedObject) => {561            if (updatedObject.prop2.id === prop2Context.id) {562              try {563                expect(updatedObject).to.eql({564                  prop1: prop1Context,565                  prop2: prop2Context,566                });567                done();568              } catch (error) {569                done(error);570              }571            }572          })573        )574        .then((unsubscribeFn) => {575          gtf.addWindowHook(unsubscribeFn);576          return glue.contexts.setPaths(contextName, [{ path: 'prop2', value: prop2Context }]);577        })578        .catch((err) => done(err));579    });580581    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been updated with update()', (done) => {582      const contextName = gtf.contexts.getContextName();583      const initContext = {584        id: gtf.contexts.getContextName(),585        complexObj: gtf.contexts.generateComplexObject(10),586      };587      const newContext = gtf.contexts.generateComplexObject(10);588589      glue.contexts590        .update(contextName, initContext)591        .then(() =>592          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {593            if (Object.keys(objectToUpdateWith).length) {594              try {595                expect(objectToUpdateWith).to.eql(newContext);596                done();597              } catch (error) {598                done(error);599              }600            }601          })602        )603        .then((unsubscribeFn) => {604          gtf.addWindowHook(unsubscribeFn);605          return glue.contexts.update(contextName, newContext);606        })607        .catch((err) => done(err));608    });609610    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been changed with set()', (done) => {611      const contextName = gtf.contexts.getContextName();612      const initContext = gtf.contexts.generateComplexObject(10);613      const newContext = {614        id: gtf.contexts.getContextName(),615        complexObj: gtf.contexts.generateComplexObject(10),616      };617618      glue.contexts619        .set(contextName, initContext)620        .then(() =>621          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {622            if (Object.keys(objectToUpdateWith).length) {623              try {624                expect(objectToUpdateWith).to.eql(newContext);625                done();626              } catch (error) {627                done(error);628              }629            }630          })631        )632        .then((unsubscribeFn) => {633          gtf.addWindowHook(unsubscribeFn);634          return glue.contexts.set(contextName, newContext);635        })636        .catch((err) => done(err));637    });638639    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been updated with setPath()', (done) => {640      const contextName = gtf.contexts.getContextName();641      const prop1Context = {642        id: gtf.contexts.getContextName(),643        complexObj: gtf.contexts.generateComplexObject(10),644      };645      const prop2Context = {646        date: new Date(),647        title: 'new context',648      };649650      glue.contexts651        .setPath(contextName, 'prop1', prop1Context)652        .then(() =>653          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {654            if (Object.keys(objectToUpdateWith).length) {655              try {656                expect(objectToUpdateWith).to.eql({ prop2: prop2Context });657                done();658              } catch (error) {659                done(error);660              }661            }662          })663        )664        .then((unsubscribeFn) => {665          gtf.addWindowHook(unsubscribeFn);666          return glue.contexts.setPath(contextName, 'prop2', prop2Context);667        })668        .catch((err) => done(err));669    });670671    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been updated with setPaths()', (done) => {672      const contextName = gtf.contexts.getContextName();673      const prop1Context = {674        date: new Date(),675        title: 'new context',676      };677      const prop2Context = {678        id: gtf.contexts.getContextName(),679        complexObj: gtf.contexts.generateComplexObject(10),680      };681682      glue.contexts683        .setPaths(contextName, [{ path: 'prop1', value: prop1Context }])684        .then(() =>685          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {686            if (Object.keys(objectToUpdateWith).length) {687              try {688                expect(objectToUpdateWith).to.eql({689                  prop2: prop2Context,690                });691                done();692              } catch (error) {693                done(error);694              }695            }696          })697        )698        .then((unsubscribeFn) => {699          gtf.addWindowHook(unsubscribeFn);700          return glue.contexts.setPaths(contextName, [{ path: 'prop2', value: prop2Context }]);701        })702        .catch((err) => done(err));703    });704705    it('should invoke the callback with an array as third argument when context is updated with existing keys set to null with update()', (done) => {706      const contextName = gtf.contexts.getContextName();707      const context = {708        name: gtf.contexts.getContextName(),709        complexObj: gtf.contexts.generateComplexObject(10),710        id: 'unique identifier',711        title: 'title',712        date: new Date(),713      };714715      glue.contexts716        .update(contextName, context)717        .then(() =>718          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith, removedKeys) => {719            if (Object.keys(objectToUpdateWith).length) {720              try {721                expect(removedKeys).to.eql(['title', 'date']);722                done();723              } catch (error) {724                done(error);725              }726            }727          })728        )729        .then((unsubscribeFn) => {730          gtf.addWindowHook(unsubscribeFn);731          return glue.contexts.update(contextName, { title: null, date: null });732        })733        .catch((err) => done(err));734    });735736    it('should invoke the callback with an array of the removed keys as third argument when context is updated with existing keys set to null with setPath()', (done) => {737      const contextName = gtf.contexts.getContextName();738739      glue.contexts740        .setPath(contextName, 'prop1.prop2', 'prop2 value')741        .then(() =>742          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith, removedKeys) => {743            if (Object.keys(objectToUpdateWith).length) {744              try {745                expect(removedKeys).to.be.an('array');746                expect(removedKeys).to.eql(['prop1']);747                done();748              } catch (error) {749                done(error);750              }751            }752          })753        )754        .then((unsubscribeFn) => {755          gtf.addWindowHook(unsubscribeFn);756          return glue.contexts.setPath(contextName, 'prop1', null);757        })758        .catch((err) => done(err));759    });760761    it('should invoke the callback with an array of the removed keys as third argument when context is updated with existing keys set to null with setPaths()', (done) => {762      const contextName = gtf.contexts.getContextName();763764      glue.contexts765        .setPaths(contextName, [{ path: 'prop1.prop2', value: 'prop2 value' }])766        .then(() =>767          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith, removedKeys) => {768            if (Object.keys(objectToUpdateWith).length) {769              try {770                expect(removedKeys).to.be.an('array');771                expect(removedKeys).to.eql(['prop1']);772                done();773              } catch (error) {774                done(error);775              }776            }777          })778        )779        .then((unsubscribeFn) => {780          gtf.addWindowHook(unsubscribeFn);781          return glue.contexts.setPaths(contextName, [{ path: 'prop1', value: null }]);782        })783        .catch((err) => done(err));784    });785786    it('should invoke the callback with an unsubscribe function as a fourth argument and be able to unsubscribe when invoking that function', (done) => {787      const contextName = gtf.contexts.getContextName();788      const context = {789        id: gtf.contexts.getContextName(),790        complexObj: gtf.contexts.generateComplexObject(10),791        date: new Date(),792      };793794      let counter = 0;795796      glue.contexts797        .subscribe(contextName, (updatedObject, objectToUpdateWith, removedKeys, unsubscribeFn) => {798          if (updatedObject.id === context.id) {799            if (updatedObject.unsubscribe === true) {800              unsubscribeFn();801            } else {802              counter++;803            }804          }805        })806        .then((unsubscribeFn) => {807          gtf.addWindowHook(unsubscribeFn);808          return glue.contexts.update(contextName, context);809        })810        .then(() => glue.contexts.update(contextName, { test: 'test' }))811        .then(() => glue.contexts.update(contextName, { tick: 42 }))812        .then(() => glue.contexts.update(contextName, { unsubscribe: true }))813        .then(() => glue.contexts.update(contextName, { glue: 42 }))814        .then(() => glue.contexts.update(contextName, { prop: 'value' }))815        .then(() => {816          expect(counter).to.eql(3);817          done();818        })819        .catch((err) => done(err));820    });821822    it('should return a function', (done) => {823      const contextName = gtf.contexts.getContextName();824825      glue.contexts826        .subscribe(contextName, () => {})827        .then((unsubscribeFn) => {828          gtf.addWindowHook(unsubscribeFn);829          expect(unsubscribeFn).to.be.a('function');830          done();831        })832        .catch((err) => done(err));833    });834835    it('should return an unsubscribe function which unsubscribes from context updates when invoked', (done) => {836      const contextName = gtf.contexts.getContextName();837      const context = {838        id: gtf.contexts.getContextName(),839        complexObj: gtf.contexts.generateComplexObject(10),840      };841842      let un;843      let counter = 0;844845      glue.contexts846        .subscribe(contextName, (data) => {847          if (data.id === context.id) {848            counter++;849          }850        })851        .then((unsubscribeFn) => {852          un = unsubscribeFn;853          gtf.addWindowHook(un);854          return glue.contexts.update(contextName, context);855        })856        .then(() => glue.contexts.update(contextName, { tick: 42 }))857        .then(() => glue.contexts.update(contextName, { glue: 42 }))858        .then(() => un())859        .then(() => glue.contexts.update(contextName, { data: 'new data' }))860        .then(() => glue.contexts.update(contextName, { date: new Date() }))861        .then(() => {862          expect(counter).to.eql(3);863          done();864        })865        .catch((err) => done(err));866    });867868    it('should return snapshot when get() is followed by subscribe()', (done) => {869      const contextName = gtf.contexts.getContextName();870      const context = gtf.contexts.generateComplexObject(10);871      const ready = gtf.waitFor(2, done);872873      glue.contexts874        .subscribe(contextName, async () => {875          try {876            const contextData = await glue.contexts.get(contextName);877            expect(contextData).to.eql(context);878            ready();879          } catch (error) {880            done(error);881          }882883          await glue.contexts.subscribe(contextName, (dataFromSubscribe) => {884            try {885              expect(dataFromSubscribe).to.eql(context);886              ready();887            } catch (error) {888              done(error);889            }890          });891        })892        .then((unFn) => {893          gtf.addWindowHook(unFn);894          return glue.contexts.update(contextName, context);895        })896        .catch((err) => done(err));897    });898  });899900  describe('when manipulated by another app, ', function () {901    let secondApp;902903    beforeEach(async () => {904      secondApp = await gtf.createApp();905    });906907    afterEach(() => secondApp.stop());908909    it('should be invoked when a context is updated and is invoked after the context was created', (done) => {910      const contextName = gtf.contexts.getContextName();911      const sampleContext = { test: 1 };912913      secondApp.contexts914        .update(contextName, sampleContext)915        .then(() => {916          return glue.contexts.subscribe(contextName, () => {917            done();918          });919        })920        .then((unsubscribeFn) => gtf.addWindowHook(unsubscribeFn))921        .then(() => {922          return secondApp.contexts.update(contextName, { test: 2 });923        })924        .catch(done);925    });926927    it('should be invoked when a context is set and is invoked after the context was created', (done) => {928      const contextName = gtf.contexts.getContextName();929      const sampleContext = { test: 1 };930931      secondApp.contexts932        .set(contextName, sampleContext)933        .then(() => {934          return glue.contexts.subscribe(contextName, () => {935            done();936          });937        })938        .then((unsubscribeFn) => gtf.addWindowHook(unsubscribeFn))939        .then(() => {940          return secondApp.contexts.set(contextName, { test: 2 });941        })942        .catch(done);943    });944945    it('should invoke the callback when the specified context has been created with update()', (done) => {946      const contextName = gtf.contexts.getContextName();947      const context = { id: gtf.contexts.getContextName() };948949      glue.contexts950        .subscribe(contextName, (data) => {951          if (data.id === context.id) {952            done();953          }954        })955        .then((unsubscribeFn) => {956          gtf.addWindowHook(unsubscribeFn);957          return secondApp.contexts.update(contextName, context);958        })959        .catch((err) => done(err));960    });961962    it('should invoke the callback when the specified context has been created with set()', (done) => {963      const contextName = gtf.contexts.getContextName();964      const context = { id: gtf.contexts.getContextName() };965966      glue.contexts967        .subscribe(contextName, (data) => {968          if (data.id === context.id) {969            done();970          }971        })972        .then((unsubscribeFn) => {973          gtf.addWindowHook(unsubscribeFn);974          return secondApp.contexts.set(contextName, context);975        })976        .catch((err) => done(err));977    });978979    it('should invoke the callback when the specified context has been created with setPath()', (done) => {980      const contextName = gtf.contexts.getContextName();981982      glue.contexts983        .subscribe(contextName, (data) => {984          if (data.prop === 'value') {985            done();986          }987        })988        .then((unsubscribeFn) => {989          gtf.addWindowHook(unsubscribeFn);990          return secondApp.contexts.setPath(contextName, 'prop', 'value');991        })992        .catch((err) => done(err));993    });994995    it('should invoke the callback when the specified context has been created with setPaths()', (done) => {996      const contextName = gtf.contexts.getContextName();997      const contextPaths = [998        { path: 'prop1', value: 'value1' },999        { path: 'prop2', value: 'value2' },1000      ];10011002      glue.contexts1003        .subscribe(contextName, (data) => {1004          if (data.prop1 === 'value1') {1005            done();1006          }1007        })1008        .then((unsubscribeFn) => {1009          gtf.addWindowHook(unsubscribeFn);1010          return secondApp.contexts.setPaths(contextName, contextPaths);1011        })1012        .catch((err) => done(err));1013    });10141015    it('should invoke the callback with an object as first argument  when the specified context has been created with update()', (done) => {1016      const contextName = gtf.contexts.getContextName();1017      const context = {1018        id: gtf.contexts.getContextName(),1019        complexObj: gtf.contexts.generateComplexObject(10),1020      };10211022      glue.contexts1023        .subscribe(contextName, (updatedObject) => {1024          try {1025            expect(updatedObject).to.be.an('object');1026            done();1027          } catch (error) {1028            done(error);1029          }1030        })1031        .then((unsubscribeFn) => {1032          gtf.addWindowHook(unsubscribeFn);1033          return secondApp.contexts.update(contextName, context);1034        })1035        .catch((err) => done(err));1036    });10371038    it('should invoke the callback with an object as first argument  when the specified context has been created with set()', (done) => {1039      const contextName = gtf.contexts.getContextName();1040      const context = {1041        id: gtf.contexts.getContextName(),1042        complexObj: gtf.contexts.generateComplexObject(10),1043      };10441045      glue.contexts1046        .subscribe(contextName, (updatedObject) => {1047          if (updatedObject.id === context.id) {1048            try {1049              expect(updatedObject).to.be.an('object');1050              done();1051            } catch (error) {1052              done(error);1053            }1054          }1055        })1056        .then((unsubscribeFn) => {1057          gtf.addWindowHook(unsubscribeFn);1058          return secondApp.contexts.set(contextName, context);1059        })1060        .catch((err) => done(err));1061    });10621063    it('should invoke the callback with an object as first argument  when the specified context has been created with setPath()', (done) => {1064      const contextName = gtf.contexts.getContextName();1065      const context = {1066        id: gtf.contexts.getContextName(),1067        complexObj: gtf.contexts.generateComplexObject(10),1068      };10691070      glue.contexts1071        .subscribe(contextName, (updatedObject) => {1072          if (updatedObject.prop1.id === context.id) {1073            try {1074              expect(updatedObject).to.be.an('object');1075              done();1076            } catch (error) {1077              done(error);1078            }1079          }1080        })1081        .then((unsubscribeFn) => {1082          gtf.addWindowHook(unsubscribeFn);1083          return secondApp.contexts.setPath(contextName, 'prop1', context);1084        })1085        .catch((err) => done(err));1086    });10871088    it('should invoke the callback with an object as first argument  when the specified context has been created with setPaths()', (done) => {1089      const contextName = gtf.contexts.getContextName();10901091      glue.contexts1092        .subscribe(contextName, (updatedObject) => {1093          if (updatedObject.prop1 === 'value1') {1094            try {1095              expect(updatedObject).to.be.an('object');1096              done();1097            } catch (error) {1098              done(error);1099            }1100          }1101        })1102        .then((unsubscribeFn) => {1103          gtf.addWindowHook(unsubscribeFn);1104          return secondApp.contexts.setPaths(contextName, [1105            { path: 'prop1', value: 'value1' },1106            { path: 'prop2', value: 'value2' },1107          ]);1108        })11091110        .catch((err) => done(err));1111    });11121113    it('should invoke the callback with correct data as first argument when the specified context has been created with update()', (done) => {1114      const contextName = gtf.contexts.getContextName();1115      const context = {1116        id: gtf.contexts.getContextName(),1117        complexObj: gtf.contexts.generateComplexObject(10),1118      };11191120      glue.contexts1121        .subscribe(contextName, (updatedObject) => {1122          if (updatedObject.id === context.id) {1123            try {1124              expect(updatedObject).to.eql(context);1125              done();1126            } catch (error) {1127              done(error);1128            }1129          }1130        })1131        .then((unsubscribeFn) => {1132          gtf.addWindowHook(unsubscribeFn);1133          return secondApp.contexts.update(contextName, context);1134        })1135        .catch((err) => done(err));1136    });11371138    it('should invoke the callback with correct data as first argument when the specified context has been created with set()', (done) => {1139      const contextName = gtf.contexts.getContextName();1140      const context = {1141        id: gtf.contexts.getContextName(),1142        complexObj: gtf.contexts.generateComplexObject(10),1143      };11441145      glue.contexts1146        .subscribe(contextName, (updatedObject) => {1147          if (updatedObject.id === context.id) {1148            try {1149              expect(updatedObject).to.eql(context);1150              done();1151            } catch (error) {1152              done(error);1153            }1154          }1155        })1156        .then((unsubscribeFn) => {1157          gtf.addWindowHook(unsubscribeFn);1158          return secondApp.contexts.set(contextName, context);1159        })1160        .catch((err) => done(err));1161    });11621163    it('should invoke the callback with correct data as first argument when the specified context has been created with setPath()', (done) => {1164      const contextName = gtf.contexts.getContextName();1165      const context = {1166        id: gtf.contexts.getContextName(),1167        complexObj: gtf.contexts.generateComplexObject(10),1168      };11691170      glue.contexts1171        .subscribe(contextName, (updatedObject) => {1172          if (updatedObject.prop1.id === context.id) {1173            try {1174              expect(updatedObject).to.eql({ prop1: context });1175              done();1176            } catch (error) {1177              done(error);1178            }1179          }1180        })1181        .then((unsubscribeFn) => {1182          gtf.addWindowHook(unsubscribeFn);1183          return secondApp.contexts.setPath(contextName, 'prop1', context);1184        })1185        .catch((err) => done(err));1186    });11871188    it('should invoke the callback with correct data as first argument when the specified context has been created with setPaths()', (done) => {1189      const contextName = gtf.contexts.getContextName();1190      const prop1Context = {1191        id: gtf.contexts.getContextName(),1192        complexObj: gtf.contexts.generateComplexObject(10),1193      };1194      const prop2Context = {1195        title: 'prop2 context',1196        value: 'prop2 value',1197      };11981199      glue.contexts1200        .subscribe(contextName, (updatedObject) => {1201          if (updatedObject.prop1.id === prop1Context.id) {1202            try {1203              expect(updatedObject).to.eql({1204                prop1: prop1Context,1205                prop2: prop2Context,1206              });1207              done();1208            } catch (error) {1209              done(error);1210            }1211          }1212        })1213        .then((unsubscribeFn) => {1214          gtf.addWindowHook(unsubscribeFn);1215          return secondApp.contexts.setPaths(contextName, [1216            { path: 'prop1', value: prop1Context },1217            { path: 'prop2', value: prop2Context },1218          ]);1219        })12201221        .catch((err) => done(err));1222    });12231224    it('should invoke the callback 3 times when a context is updated 3 times with update()', (done) => {1225      const ready = gtf.waitFor(3, done);1226      const context = {1227        id: gtf.contexts.getContextName(),1228        name: gtf.contexts.getContextName(),1229        complexObj: gtf.contexts.generateComplexObject(10),1230      };12311232      glue.contexts1233        .subscribe(context.name, (data) => {1234          if (data.id === context.id) {1235            ready();1236          }1237        })1238        .then((unsubscribeFn) => {1239          gtf.addWindowHook(unsubscribeFn);1240          return secondApp.contexts.update(context.name, context);1241        })1242        .then(() => secondApp.contexts.update(context.name, { date: new Date() }))1243        .then(() => secondApp.contexts.update(context.name, { prop: 'value' }))1244        .catch((err) => done(err));1245    });12461247    it('should invoke the callback 3 times when a context is changed 3 times with set()', (done) => {1248      const ready = gtf.waitFor(3, done);1249      const contextName = gtf.contexts.getContextName();1250      const id = gtf.contexts.getContextName();12511252      const context = {1253        id,1254        name: gtf.contexts.getContextName(),1255        complexObj: gtf.contexts.generateComplexObject(10),1256      };12571258      glue.contexts1259        .subscribe(contextName, (data) => {1260          if (data.id === context.id) {1261            ready();1262          }1263        })1264        .then((unsubscribeFn) => {1265          gtf.addWindowHook(unsubscribeFn);1266          return secondApp.contexts.set(contextName, context);1267        })1268        .then(() => secondApp.contexts.set(contextName, { id, date: new Date() }))1269        .then(() => secondApp.contexts.set(contextName, { id, prop: 'value' }))1270        .catch((err) => done(err));1271    });12721273    it('should invoke the callback 3 times when a context is changed 3 times with setPath()', (done) => {1274      const ready = gtf.waitFor(3, done);1275      const context = {1276        id: gtf.contexts.getContextName(),1277        name: gtf.contexts.getContextName(),1278        complexObj: gtf.contexts.generateComplexObject(10),1279      };12801281      glue.contexts1282        .subscribe(context.name, (data) => {1283          if (data.prop1.id === context.id) {1284            ready();1285          }1286        })1287        .then((unsubscribeFn) => {1288          gtf.addWindowHook(unsubscribeFn);1289          return secondApp.contexts.setPath(context.name, 'prop1', context);1290        })1291        .then(() => secondApp.contexts.setPath(context.name, 'prop2', { date: new Date() }))1292        .then(() => secondApp.contexts.setPath(context.name, 'prop3', { prop: 'value' }))1293        .catch((err) => done(err));1294    });12951296    it('should invoke the callback 3 times when a context is changed 3 times with setPaths()', (done) => {1297      const ready = gtf.waitFor(3, done);1298      const context = {1299        id: gtf.contexts.getContextName(),1300        name: gtf.contexts.getContextName(),1301        complexObj: gtf.contexts.generateComplexObject(10),1302      };13031304      glue.contexts1305        .subscribe(context.name, (data) => {1306          if (data.prop1.id === context.id) {1307            ready();1308          }1309        })1310        .then((unsubscribeFn) => {1311          gtf.addWindowHook(unsubscribeFn);1312          return secondApp.contexts.setPaths(context.name, [{ path: 'prop1', value: context }]);1313        })1314        .then(() => secondApp.contexts.setPaths(context.name, [{ path: 'prop2', value: { date: new Date() } }]))1315        .then(() => secondApp.contexts.setPaths(context.name, [{ path: 'prop3', value: { prop: 'value' } }]))1316        .catch((err) => done(err));1317    });13181319    it('should invoke the callback with the updated data as first argument when the specified context has been changed with update()', (done) => {1320      const context = {1321        name: gtf.contexts.getContextName(),1322        complexObj: gtf.contexts.generateComplexObject(10),1323      };1324      const newContext = {1325        id: gtf.contexts.getContextName(),1326        date: new Date(),1327        title: 'new context',1328      };13291330      glue.contexts1331        .update(context.name, context)1332        .then(() => {1333          return glue.contexts.subscribe(context.name, (updatedObject) => {1334            if (updatedObject.id === newContext.id) {1335              try {1336                expect(updatedObject).to.eql(Object.assign({}, context, newContext));1337                done();1338              } catch (error) {1339                done(error);1340              }1341            }1342          });1343        })1344        .then((unsubscribeFn) => {1345          gtf.addWindowHook(unsubscribeFn);1346          return secondApp.contexts.update(context.name, newContext);1347        })1348        .catch((err) => done(err));1349    });13501351    it('should invoke the callback with the new data as first argument when the specified context has been changed with set()', (done) => {1352      const contextName = gtf.contexts.getContextName();1353      const context = gtf.contexts.generateComplexObject(10);1354      const newContext = {1355        id: gtf.contexts.getContextName(),1356        date: new Date(),1357        title: 'new context',1358      };13591360      glue.contexts1361        .set(contextName, context)1362        .then(() => {1363          return glue.contexts.subscribe(contextName, (updatedObject) => {1364            if (updatedObject.id === newContext.id) {1365              try {1366                expect(updatedObject).to.eql(newContext);1367                done();1368              } catch (error) {1369                done(error);1370              }1371            }1372          });1373        })1374        .then((unsubscribeFn) => {1375          gtf.addWindowHook(unsubscribeFn);1376          return secondApp.contexts.set(contextName, newContext);1377        })1378        .catch((err) => done(err));1379    });13801381    it('should invoke the callback with the new data as first argument when the specified context has been updated with setPath()', (done) => {1382      const contextName = gtf.contexts.getContextName();1383      const prop1Context = {1384        date: new Date(),1385        title: 'new context',1386      };1387      const prop2Context = {1388        id: gtf.contexts.getContextName(),1389        complexObj: gtf.contexts.generateComplexObject(10),1390      };13911392      secondApp.contexts1393        .setPath(contextName, 'prop1', prop1Context)1394        .then(() =>1395          glue.contexts.subscribe(contextName, (updatedObject) => {1396            if (updatedObject.prop2.id === prop2Context.id) {1397              try {1398                expect(updatedObject).to.eql({1399                  prop1: prop1Context,1400                  prop2: prop2Context,1401                });1402                done();1403              } catch (error) {1404                done(error);1405              }1406            }1407          })1408        )1409        .then((unsubscribeFn) => {1410          gtf.addWindowHook(unsubscribeFn);1411          return secondApp.contexts.setPath(contextName, 'prop2', prop2Context);1412        })1413        .catch((err) => done(err));1414    });14151416    it('should invoke the callback with the new data as first argument when the specified context has been updated with setPaths()', (done) => {1417      const contextName = gtf.contexts.getContextName();1418      const prop1Context = {1419        date: new Date(),1420        title: 'new context',1421      };1422      const prop2Context = {1423        id: gtf.contexts.getContextName(),1424        complexObj: gtf.contexts.generateComplexObject(10),1425      };14261427      secondApp.contexts1428        .setPaths(contextName, [{ path: 'prop1', value: prop1Context }])1429        .then(() =>1430          glue.contexts.subscribe(contextName, (updatedObject) => {1431            if (updatedObject.prop2.id === prop2Context.id) {1432              try {1433                expect(updatedObject).to.eql({1434                  prop1: prop1Context,1435                  prop2: prop2Context,1436                });1437                done();1438              } catch (error) {1439                done(error);1440              }1441            }1442          })1443        )1444        .then((unsubscribeFn) => {1445          gtf.addWindowHook(unsubscribeFn);1446          return secondApp.contexts.setPaths(contextName, [{ path: 'prop2', value: prop2Context }]);1447        })1448        .catch((err) => done(err));1449    });14501451    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been updated with update()', (done) => {1452      const contextName = gtf.contexts.getContextName();1453      const initContext = {1454        id: gtf.contexts.getContextName(),1455        complexObj: gtf.contexts.generateComplexObject(10),1456      };1457      const newContext = gtf.contexts.generateComplexObject(10);14581459      glue.contexts1460        .update(contextName, initContext)1461        .then(() => {1462          return glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {1463            if (Object.keys(objectToUpdateWith).length) {1464              try {1465                expect(objectToUpdateWith).to.eql(newContext);1466                done();1467              } catch (error) {1468                done(error);1469              }1470            }1471          });1472        })1473        .then((unsubscribeFn) => {1474          gtf.addWindowHook(unsubscribeFn);1475          return secondApp.contexts.update(contextName, newContext);1476        })1477        .catch((err) => done(err));1478    });14791480    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been changed with set()', (done) => {1481      const contextName = gtf.contexts.getContextName();1482      const initContext = gtf.contexts.generateComplexObject(10);1483      const newContext = {1484        id: gtf.contexts.getContextName(),1485        complexObj: gtf.contexts.generateComplexObject(10),1486      };14871488      glue.contexts1489        .set(contextName, initContext)1490        .then(() => {1491          return glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {1492            if (Object.keys(objectToUpdateWith).length) {1493              try {1494                expect(objectToUpdateWith).to.eql(newContext);1495                done();1496              } catch (error) {1497                done(error);1498              }1499            }1500          });1501        })1502        .then((unsubscribeFn) => {1503          gtf.addWindowHook(unsubscribeFn);1504          return secondApp.contexts.set(contextName, newContext);1505        })1506        .catch((err) => done(err));1507    });15081509    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been updated with setPath()', (done) => {1510      const contextName = gtf.contexts.getContextName();1511      const prop1Context = {1512        id: gtf.contexts.getContextName(),1513        complexObj: gtf.contexts.generateComplexObject(10),1514      };1515      const prop2Context = {1516        date: new Date(),1517        title: 'new context',1518      };15191520      secondApp.contexts1521        .setPath(contextName, 'prop1', prop1Context)1522        .then(() =>1523          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {1524            if (Object.keys(objectToUpdateWith).length) {1525              try {1526                expect(objectToUpdateWith).to.eql({ prop2: prop2Context });1527                done();1528              } catch (error) {1529                done(error);1530              }1531            }1532          })1533        )1534        .then((unsubscribeFn) => {1535          gtf.addWindowHook(unsubscribeFn);1536          return secondApp.contexts.setPath(contextName, 'prop2', prop2Context);1537        })1538        .catch((err) => done(err));1539    });15401541    it('should invoke the callback with the object to update the context with as a second argument when the specified context has been updated with setPaths()', (done) => {1542      const contextName = gtf.contexts.getContextName();1543      const prop1Context = {1544        date: new Date(),1545        title: 'new context',1546      };1547      const prop2Context = {1548        id: gtf.contexts.getContextName(),1549        complexObj: gtf.contexts.generateComplexObject(10),1550      };15511552      secondApp.contexts1553        .setPaths(contextName, [{ path: 'prop1', value: prop1Context }])1554        .then(() =>1555          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith) => {1556            if (Object.keys(objectToUpdateWith).length) {1557              try {1558                expect(objectToUpdateWith).to.eql({1559                  prop2: prop2Context,1560                });1561                done();1562              } catch (error) {1563                done(error);1564              }1565            }1566          })1567        )1568        .then((unsubscribeFn) => {1569          gtf.addWindowHook(unsubscribeFn);1570          return secondApp.contexts.setPaths(contextName, [{ path: 'prop2', value: prop2Context }]);1571        })1572        .catch((err) => done(err));1573    });15741575    it('should invoke the callback with an array as third argument when context is updated with existing keys set to null with update()', (done) => {1576      const contextName = gtf.contexts.getContextName();1577      const context = {1578        name: gtf.contexts.getContextName(),1579        complexObj: gtf.contexts.generateComplexObject(10),1580        id: 'unique identifier',1581        title: 'title',1582        date: new Date(),1583      };15841585      glue.contexts1586        .update(contextName, context)1587        .then(() => {1588          return glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith, removedKeys) => {1589            if (Object.keys(objectToUpdateWith).length) {1590              try {1591                expect(removedKeys).to.eql(['title', 'date']);1592                done();1593              } catch (error) {1594                done(error);1595              }1596            }1597          });1598        })1599        .then((unsubscribeFn) => {1600          gtf.addWindowHook(unsubscribeFn);1601          return secondApp.contexts.update(contextName, { title: null, date: null });1602        })1603        .catch((err) => done(err));1604    });16051606    it('should invoke the callback with an array of the removed keys as third argument when context is updated with existing keys set to null with setPath()', (done) => {1607      const contextName = gtf.contexts.getContextName();16081609      secondApp.contexts1610        .setPath(contextName, 'prop1.prop2', 'prop2 value')1611        .then(() =>1612          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith, removedKeys) => {1613            if (Object.keys(objectToUpdateWith).length) {1614              try {1615                expect(removedKeys).to.be.an('array');1616                expect(removedKeys).to.eql(['prop1']);1617                done();1618              } catch (error) {1619                done(error);1620              }1621            }1622          })1623        )1624        .then((unsubscribeFn) => {1625          gtf.addWindowHook(unsubscribeFn);1626          return secondApp.contexts.setPath(contextName, 'prop1', null);1627        })1628        .catch((err) => done(err));1629    });16301631    it('should invoke the callback with an array of the removed keys as third argument when context is updated with existing keys set to null with setPaths()', (done) => {1632      const contextName = gtf.contexts.getContextName();16331634      secondApp.contexts1635        .setPaths(contextName, [{ path: 'prop1.prop2', value: 'prop2 value' }])1636        .then(() =>1637          glue.contexts.subscribe(contextName, (updatedObject, objectToUpdateWith, removedKeys) => {1638            if (Object.keys(objectToUpdateWith).length) {1639              try {1640                expect(removedKeys).to.be.an('array');1641                expect(removedKeys).to.eql(['prop1']);1642                done();1643              } catch (error) {1644                done(error);1645              }1646            }1647          })1648        )1649        .then((unsubscribeFn) => {1650          gtf.addWindowHook(unsubscribeFn);1651          return secondApp.contexts.setPaths(contextName, [{ path: 'prop1', value: null }]);1652        })1653        .catch((err) => done(err));1654    });16551656    it('should invoke the callback with an unsubscribe function as a fourth argument and be able to unsubscribe when invoking that function', (done) => {1657      const contextName = gtf.contexts.getContextName();1658      const context = {1659        id: gtf.contexts.getContextName(),1660        complexObj: gtf.contexts.generateComplexObject(10),1661        date: new Date(),1662      };16631664      let counter = 0;16651666      glue.contexts1667        .subscribe(contextName, (_u, _o, _r, unsubscribeFn) => {1668          if (_u.id === context.id) {1669            if (_u.unsubscribe === true) {1670              unsubscribeFn();1671            } else {1672              counter++;1673            }1674          }1675        })1676        .then((unsubscribeFn) => {1677          gtf.addWindowHook(unsubscribeFn);1678          return secondApp.contexts.update(contextName, context);1679        })1680        .then(() => secondApp.contexts.update(contextName, { test: 'test' }))1681        .then(() => secondApp.contexts.update(contextName, { tick: 42 }))1682        .then(() => secondApp.contexts.update(contextName, { unsubscribe: true }))1683        .then(() => secondApp.contexts.update(contextName, { glue: 42 }))1684        .then(() => secondApp.contexts.update(contextName, { prop: 'value' }))1685        .then(() => {1686          expect(counter).to.eql(3);1687          done();1688        })1689        .catch((err) => done(err));1690    });16911692    it('should return an unsubscribe function which unsubscribes from context updates when invoked', async () => {1693      const context = {1694        name: gtf.contexts.getContextName(),1695        complexObj: gtf.contexts.generateComplexObject(10),1696      };1697      let counter = 0;16981699      const unsubscribeFn = await glue.contexts.subscribe(context.name, () => {1700        counter++;1701      });1702      gtf.addWindowHook(unsubscribeFn);17031704      await secondApp.contexts.update(context.name, {1705        anotherComplexObj: gtf.contexts.generateComplexObject(10),1706      });1707      await secondApp.contexts.update(context.name, { tick: 42 });1708      await secondApp.contexts.update(context.name, { glue: 42 });17091710      unsubscribeFn();17111712      await secondApp.contexts.update(context.name, { data: 'new data' });1713      await secondApp.contexts.update(context.name, { date: new Date() });17141715      expect(counter).to.eql(3);1716    });17171718    it("should return correct data when another app resolves creating a context and subscribe should also return correct data when there's a subscription for the given context", (done) => {1719      const contextName = gtf.contexts.getContextName();1720      const context = gtf.contexts.generateComplexObject(10);17211722      const ready = gtf.waitFor(2, done);17231724      secondApp.contexts1725        .update(contextName, context)1726        .then(() => {1727          return glue.contexts.subscribe(contextName, (data) => {1728            try {1729              expect(data).to.eql(context);1730              ready();1731            } catch (error) {1732              done(error);1733            }
...update.spec.js
Source:update.spec.js  
...61    });6263    it('should throw when only one argument is passed', (done) => {64      try {65        glue.contexts.update(gtf.contexts.getContextName());66        done('Should throw an error');67      } catch (error) {68        done();69      }70    });7172    it('should not throw when 2 valid arguments are passed', async () => {73      let randomContextName = gtf.contexts.getContextName();74      let complexObject = gtf.contexts.generateComplexObject(10);75      await glue.contexts.update(randomContextName, complexObject);76    });7778    it('should not throw when more than 2 valid arguments are passed', async () => {79      let randomContextName = gtf.contexts.getContextName();80      let complexObject = gtf.contexts.generateComplexObject(10);81      await glue.contexts.update(randomContextName, complexObject, 'Tick42');82    });8384    [undefined, null, false, true, '', 42, [], { tick: 42 }, ['string']].forEach((invalidName) => {85      it(`should throw when an invalid first argument (${JSON.stringify(invalidName)}) is passed`, (done) => {86        const complexObject = gtf.contexts.generateComplexObject(10);8788        try {89          glue.contexts.update(invalidName, complexObject);90          done('Should throw an error');91        } catch (error) {92          done();93        }94      });95    });9697    [undefined, false, true, '', 42].forEach((invalidData) => {98      it(`should throw when an invalid second argument (${JSON.stringify(invalidData)}) is passed`, (done) => {99        try {100          glue.contexts.update(gtf.contexts.getContextName(), invalidData);101          done('Should throw an error');102        } catch (error) {103          done();104        }105      });106    });107108    it.skip('should throw when invoked with null as a second argument', (done) => {109      try {110        glue.contexts.update(gtf.contexts.getContextName(), null);111        done('Should throw an error');112      } catch (error) {113        done();114      }115    });116117    it.skip('should throw when invoked with empty array as a second argument', (done) => {118      try {119        glue.contexts.update(gtf.contexts.getContextName(), []);120        done('Should throw an error');121      } catch (error) {122        done();123      }124    });125126    it.skip('should return undefined', async () => {127      const context = {128        name: gtf.contexts.getContextName(),129        complexObj: gtf.contexts.generateComplexObject(10),130      };131132      const returned = await glue.contexts.update(context.name, context);133      expect(returned).to.eql(undefined);134    });135136    it("should create a new context when there isn't one with the given context name", async () => {137      const contextName = gtf.contexts.getContextName();138      const complexObject = gtf.contexts.generateComplexObject(10);139140      const contextAlreadyExists = glue.contexts.all().includes(contextName);141142      if (!contextAlreadyExists) {143        await glue.contexts.update(contextName, complexObject);144      } else {145        throw new Error('Invalid test - context already exists!');146      }147148      const newContext = await glue.contexts.get(contextName);149      expect(newContext).to.eql(complexObject);150    });151152    it("should create 3 more elements when there aren't any contexts with passed names", async () => {153      const oldLength = glue.contexts.all().length;154      await glue.contexts.update(gtf.contexts.getContextName(), {});155      await glue.contexts.update(gtf.contexts.getContextName(), {});156      await glue.contexts.update(gtf.contexts.getContextName(), {});157      const newLength = glue.contexts.all().length;158159      expect(oldLength + 3).to.eql(newLength);160    });161162    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {163      const randomContextName = gtf.contexts.getContextName();164      const complexObject = gtf.contexts.generateComplexObject(10);165166      const oldLength = glue.contexts.all().length;167      await glue.contexts.update(randomContextName, complexObject);168      const newLength = glue.contexts.all().length;169170      expect(oldLength + 1).to.eql(newLength);171    });172173    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {174      const randomContextName = gtf.contexts.getContextName();175      const complexObject = gtf.contexts.generateComplexObject(10);176177      await glue.contexts.update(randomContextName, complexObject);178      const oldContextsLength = glue.contexts.all().length;179180      await glue.contexts.update(randomContextName, { newProp: 'value' });181      const newContextsLength = glue.contexts.all().length;182183      expect(oldContextsLength).to.eql(newContextsLength);184    });185186    it('should add new context keys to an existing context when invoked with valid name and data', async () => {187      const randomContextName = gtf.contexts.getContextName();188      const complexObject = gtf.contexts.generateComplexObject(10);189190      await glue.contexts.update(randomContextName, complexObject);191      const initialKeysLength = Object.keys(await glue.contexts.get(randomContextName)).length;192193      const newContext = {194        unique: 'unique',195        title: randomContextName,196      };197198      await glue.contexts.update(randomContextName, newContext);199200      const newKeysLength = Object.keys(await glue.contexts.get(randomContextName)).length;201202      expect(initialKeysLength + 2).to.eql(newKeysLength);203      expect([...Object.keys(complexObject), ...Object.keys(newContext)]).to.eql(Object.keys(await glue.contexts.get(randomContextName)));204    });205206    it('should update already existing key values when invoked with valid name and data', async () => {207      const context = {208        id: 'unique identifier',209        name: gtf.contexts.getContextName(),210        complexObject: gtf.contexts.generateComplexObject(10),211      };212      await glue.contexts.update(context.name, context);213      const newId = { id: 'NEW unique identifier' };214      await glue.contexts.update(context.name, newId);215      const updatedContext = await glue.contexts.get(context.name);216217      expect(updatedContext.id).to.eql(newId.id);218    });219220    it('should remove context keys when passed data has already existing keys set to null', async () => {221      const context = {222        id: 'unique identifier',223        name: gtf.contexts.getContextName(),224        complexObject: gtf.contexts.generateComplexObject(10),225      };226227      await glue.contexts.update(context.name, context);228      const initialKeys = Object.keys(await glue.contexts.get(context.name));229      const keyToRemove = { id: null };230      await glue.contexts.update(context.name, keyToRemove);231      const newKeys = Object.keys(await glue.contexts.get(context.name));232233      expect(newKeys.includes('id')).to.be.false;234      expect(initialKeys.length - 1).to.eql(newKeys.length);235    });236237    it('should create a new complex object when invoked with valid name and complex data', async () => {238      const complexContext = {239        name: gtf.contexts.getContextName(),240        complexObject: gtf.contexts.generateComplexObject(200),241      };242      await glue.contexts.update(complexContext.name, complexContext);243244      const newContext = await glue.contexts.get(complexContext.name);245      expect(newContext).to.eql(complexContext);246    });247248    it('should update an existing complex context with another complex object', async () => {249      const contextName = gtf.contexts.getContextName();250      const initComplexContext = {251        complexObject: gtf.contexts.generateComplexObject(200),252      };253      await glue.contexts.update(contextName, initComplexContext);254255      const newComplexContext = {256        newComplexObj: gtf.contexts.generateComplexObject(200),257      };258      await glue.contexts.update(contextName, newComplexContext);259260      const newContext = await glue.contexts.get(contextName);261      expect(newContext).to.eql(Object.assign({}, initComplexContext, newComplexContext));262    });263264    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {265      const contextName = gtf.contexts.getContextName();266267      glue.contexts268        .subscribe(contextName, () => {269          done();270        })271        .then(() => glue.contexts.update(contextName, {}));272    });273274    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {275      const context = {276        name: gtf.contexts.getContextName(),277        complexObj: gtf.contexts.generateComplexObject(10),278      };279280      glue.contexts281        .subscribe(context.name, (updatedObject) => {282       try {283        expect(updatedObject).to.eql(context);284        done();285       } catch (error) {286         done(error);287       }288        })289        .then(() => glue.contexts.update(context.name, context))290        .catch((err) => done(err));291    });292293    it('should invoke the callback registered with subscribe() method 3 times when a context is changed 3 times', async () => {294      let counter = 0;295296      const context = {297        name: gtf.contexts.getContextName(),298        complexObj: gtf.contexts.generateComplexObject(10),299      };300301      await glue.contexts.subscribe(context.name, () => {302        counter++;303      });304305      await glue.contexts.update(context.name, context);306      await glue.contexts.update(context.name, { date: new Date() });307      await glue.contexts.update(context.name, { prop: 'value' });308309      expect(counter).to.eql(3);310    });311  });312313  describe('when manipulated by another app ', function () {314    let secondApp;315316    beforeEach(async () => {317      secondApp = await gtf.createApp();318    });319320    afterEach(() => secondApp.stop());321322    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {323      const randomContextName = gtf.contexts.getContextName();324      const complexObject = gtf.contexts.generateComplexObject(10);325326      const oldLength = glue.contexts.all().length;327      await secondApp.contexts.update(randomContextName, complexObject);328      const newLength = glue.contexts.all().length;329330      expect(oldLength + 1).to.eql(newLength);331    });332333    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {334      const randomContextName = gtf.contexts.getContextName();335      const complexObject = gtf.contexts.generateComplexObject(10);336337      await glue.contexts.update(randomContextName, complexObject);338      const oldContextsLength = glue.contexts.all().length;339340      await secondApp.contexts.update(randomContextName, { newProp: 'value' });341      const newContextsLength = glue.contexts.all().length;342343      expect(oldContextsLength).to.eql(newContextsLength);344    });345346    it('should add new context keys to an existing context created by another app when invoked with valid name and data', async () => {347      const randomContextName = gtf.contexts.getContextName();348      const complexObject = gtf.contexts.generateComplexObject(10);349350      await glue.contexts.update(randomContextName, complexObject);351      const initialKeysLength = Object.keys(await glue.contexts.get(randomContextName)).length;352353      const newContext = {354        unique: 'unique',355        title: randomContextName,356      };357358      await secondApp.contexts.update(randomContextName, newContext);359360      const newKeysLength = Object.keys(await glue.contexts.get(randomContextName)).length;361362      expect(initialKeysLength + 2).to.eql(newKeysLength);363      expect([...Object.keys(complexObject), ...Object.keys(newContext)]).to.eql(Object.keys(await glue.contexts.get(randomContextName)));364    });365366    it('should update already existing key values of a context created by another app when invoked with valid name and data', async () => {367      const context = {368        id: 'unique identifier',369        name: gtf.contexts.getContextName(),370        complexObject: gtf.contexts.generateComplexObject(10),371      };372      await glue.contexts.update(context.name, context);373      const newId = { id: 'NEW unique identifier' };374      await secondApp.contexts.update(context.name, newId);375      const updatedContext = await glue.contexts.get(context.name);376377      expect(updatedContext.id).to.eql(newId.id);378    });379380    it('should remove context keys of a context created by another app when passed data has already existing keys set to null', async () => {381      const context = {382        id: 'unique identifier',383        name: gtf.contexts.getContextName(),384        complexObject: gtf.contexts.generateComplexObject(10),385      };386387      await glue.contexts.update(context.name, context);388      const initialKeys = Object.keys(await glue.contexts.get(context.name));389      const keyToRemove = { id: null };390      await secondApp.contexts.update(context.name, keyToRemove);391      const newKeys = Object.keys(await glue.contexts.get(context.name));392393      expect(newKeys.includes('id')).to.be.false;394      expect(initialKeys.length - 1).to.eql(newKeys.length);395    });396397    it('should create a new complex object when invoked with valid name and complex data', async () => {398      const complexContext = {399        name: gtf.contexts.getContextName(),400        complexObject: gtf.contexts.generateComplexObject(200),401      };402      await secondApp.contexts.update(complexContext.name, complexContext);403404      const newContext = await glue.contexts.get(complexContext.name);405      expect(newContext).to.eql(complexContext);406    });407408    it('should update an existing complex context with another complex object', async () => {409      const contextName = gtf.contexts.getContextName();410      const initComplexContext = {411        complexObject: gtf.contexts.generateComplexObject(200),412      };413      await secondApp.contexts.update(contextName, initComplexContext);414415      const newComplexContext = {416        newComplexObj: gtf.contexts.generateComplexObject(200),417      };418      await secondApp.contexts.update(contextName, newComplexContext);419420      const newContext = await glue.contexts.get(contextName);421      expect(newContext).to.eql(Object.assign({}, initComplexContext, newComplexContext));422    });423424    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {425      const contextName = gtf.contexts.getContextName();426427      glue.contexts428        .subscribe(contextName, () => {429          done();430        })431        .then(() => secondApp.contexts.update(contextName, {}));432    });433434    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {435      const context = {436        name: gtf.contexts.getContextName(),437        complexObj: gtf.contexts.generateComplexObject(10),438      };439440      glue.contexts441        .subscribe(context.name, (updatedObject) => {442          try {443            expect(updatedObject).to.eql(context);444            done();445          } catch (error) {446            done(error);447          }448        })449        .then(() => secondApp.contexts.update(context.name, context))450        .catch((err) => done(err));451    });452453    it('should invoke the callback registered with subscribe() method 3 times when a context is changed 3 times', async () => {454      let counter = 0;455456      const context = {457        name: gtf.contexts.getContextName(),458        complexObj: gtf.contexts.generateComplexObject(10),459      };460461      await glue.contexts.subscribe(context.name, () => {462        counter++;463      });464465      await secondApp.contexts.update(context.name, context);466      await secondApp.contexts.update(context.name, { date: new Date() });467      await secondApp.contexts.update(context.name, { prop: 'value' });468469      expect(counter).to.eql(3);470    });471472    contextsForTesting.forEach((context) => {473      it(`should update the context between 2 applications with ${context.type}`, async () => {474        const contextName = gtf.contexts.getContextName();475        await glue.contexts.update(contextName, context);476477        const contextFromSecondApp = await secondApp.contexts.get(contextName);478479        expect(contextFromSecondApp).to.eql(context);480      });481    });482483    it('should merge the contexts when top level properties are the same', async () => {484      const contextName = gtf.contexts.getContextName();485      const firstContext = {486        a: 1,487        b: 2,488      };489490      const secondContext = {491        b: 0,492        c: 3,493      };494495      await glue.contexts.update(contextName, firstContext);496      await glue.contexts.update(contextName, secondContext);497498      const contextFromSecondApp = await secondApp.contexts.get(contextName);499500      expect(contextFromSecondApp.a).to.eql(firstContext.a);501      expect(contextFromSecondApp.b).to.eql(secondContext.b);502      expect(contextFromSecondApp.c).to.eql(secondContext.c);503    });504505    it.skip('should merge the contexts when inner properties are affected', async () => {506      const contextName = gtf.contexts.getContextName();507      const firstContext = {508        first: {509          a: 1,510          b: 2,511        },512      };513514      const secondContext = {515        first: {516          b: 0,517          c: 3,518        },519      };520521      await glue.contexts.update(contextName, firstContext);522      await glue.contexts.update(contextName, secondContext);523524      const contextFromSecondApp = await secondApp.contexts.get(contextName);525526      expect(contextFromSecondApp.first.a).to.eql(firstContext.first.a);527      expect(contextFromSecondApp.first.b).to.eql(secondContext.first.b);528      expect(contextFromSecondApp.first.c).to.eql(secondContext.first.c);529    });530531    it(`should not replace the old context when the new context is ${context.type} and 2 applications are used`, async () => {532      const contextName = gtf.contexts.getContextName();533      const initialContext = {534        isSaved: true,535      };536537      await glue.contexts.update(contextName, initialContext);538      await glue.contexts.update(contextName, { context: 'context' });539540      const contextFromSecondApp = await secondApp.contexts.get(contextName);541542      expect(contextFromSecondApp.isSaved).to.be.true;543    });544545    it.skip('should merge the contexts when top level array is affected', async () => {546      const contextName = gtf.contexts.getContextName();547      const firstContext = {548        a: [1],549        b: [2],550      };551552      const secondContext = {553        b: [0],554        c: [3],555      };556557      await glue.contexts.update(contextName, firstContext);558      await glue.contexts.update(contextName, secondContext);559560      const contextFromSecondApp = await secondApp.contexts.get(contextName);
...set.spec.js
Source:set.spec.js  
...63    });6465    it('should throw when only one argument is passed', (done) => {66      try {67        glue.contexts.set(gtf.contexts.getContextName());68        done('Should throw an error!');69      } catch (error) {70        done();71      }72    });7374    it('should not throw when 2 valid arguments are passed', async () => {75      let randomContextName = gtf.contexts.getContextName();76      let complexObject = gtf.contexts.generateComplexObject(10);77      await glue.contexts.set(randomContextName, complexObject);78    });7980    it('should not throw when more than 2 valid arguments are passed', async () => {81      let randomContextName = gtf.contexts.getContextName();82      let complexObject = gtf.contexts.generateComplexObject(10);83      await glue.contexts.set(randomContextName, complexObject, 'third argument');84    });8586    [undefined, null, false, true, '', 42, [], { tick: 42 }].forEach((invalidName) => {87      it(`should throw when an invalid first argument (${JSON.stringify(invalidName)}) is passed`, (done) => {88        const complexObject = gtf.contexts.generateComplexObject(10);8990        try {91          glue.contexts.set(invalidName, complexObject);92          done('Should throw an error');93        } catch (error) {94          done();95        }96      });97    });9899    [undefined, false, true, '', 42].forEach((invalidData) => {100      it(`should throw when an invalid second argument (${JSON.stringify(invalidData)}) is passed`, (done) => {101        try {102          glue.contexts.set(gtf.contexts.getContextName(), invalidData);103          done('Should throw an error');104        } catch (error) {105          done();106        }107      });108    });109110    it.skip('should throw when invoked with null as a second argument', (done) => {111      try {112        glue.contexts.set(gtf.contexts.getContextName(), null);113        done('Should throw an error');114      } catch (error) {115        done();116      }117    });118119    it.skip('should throw when invoked with empty array as a second argument', (done) => {120      try {121        glue.contexts.set(gtf.contexts.getContextName(), []);122        done('Should throw an error');123      } catch (error) {124        done();125      }126    });127128    it.skip('should return undefined', async () => {129      const context = {130        name: gtf.contexts.getContextName(),131        complexObj: gtf.contexts.generateComplexObject(10),132      };133134      const returned = await glue.contexts.set(context.name, context);135      expect(returned).to.eql(undefined);136    });137138    it("should create a new context if there isn't one with the given name", async () => {139      const contextName = gtf.contexts.getContextName();140      const complexObject = gtf.contexts.generateComplexObject(10);141142      const contextAlreadyExists = glue.contexts.all().includes(contextName);143144      if (!contextAlreadyExists) {145        await glue.contexts.set(contextName, complexObject);146      } else {147        throw new Error('Invalid test - context already exists!');148      }149150      const newContext = await glue.contexts.get(contextName);151      expect(newContext).to.eql(complexObject);152    });153154    it("should create 3 more elements when there aren't any contexts with passed names", async () => {155      const oldLength = glue.contexts.all().length;156      await glue.contexts.set(gtf.contexts.getContextName(), {});157      await glue.contexts.set(gtf.contexts.getContextName(), {});158      await glue.contexts.set(gtf.contexts.getContextName(), {});159      const newLength = glue.contexts.all().length;160161      expect(oldLength + 3).to.eql(newLength);162    });163164    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {165      const randomContextName = gtf.contexts.getContextName();166      const complexObject = gtf.contexts.generateComplexObject(10);167168      const oldLength = glue.contexts.all().length;169      await glue.contexts.set(randomContextName, complexObject);170      const newLength = glue.contexts.all().length;171172      expect(oldLength + 1).to.eql(newLength);173    });174175    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {176      const randomContextName = gtf.contexts.getContextName();177      const complexObject = gtf.contexts.generateComplexObject(10);178179      await glue.contexts.set(randomContextName, complexObject);180      const oldContextsLength = glue.contexts.all().length;181182      await glue.contexts.set(randomContextName, { newProp: 'value' });183      const newContextsLength = glue.contexts.all().length;184185      expect(oldContextsLength).to.eql(newContextsLength);186    });187188    it('should remove all previous context properties', async () => {189      const contextName = gtf.contexts.getContextName();190      const initContext = {191        id: gtf.contexts.getContextName(),192        name: 'initial Context',193        complexObject: gtf.contexts.generateComplexObject(10),194      };195196      await glue.contexts.set(contextName, initContext);197      const initialKeys = Object.keys(await glue.contexts.get(contextName));198199      const newContext = {200        product: 'GTF',201        company: 'Tick42',202      };203204      await glue.contexts.set(contextName, newContext);205      const newKeys = Object.keys(await glue.contexts.get(contextName));206207      const repetitiveKeys = initialKeys.filter((key) => newKeys.includes(key));208209      expect(repetitiveKeys).to.eql([]);210    });211212    it('should replace the context with the passed object when invoked with valid name and data', async () => {213      const contextName = gtf.contexts.getContextName();214      const initContext = {215        id: 'unique identifier',216        complexObject: gtf.contexts.generateComplexObject(10),217      };218219      await glue.contexts.set(contextName, initContext);220221      const newContext = {222        name: 'new context',223        title: 'test',224      };225226      await glue.contexts.set(contextName, newContext);227228      const currentContext = await glue.contexts.get(contextName);229      expect(currentContext).to.eql(newContext);230    });231232    it('should create a new complex object when invoked with valid name and complex data', async () => {233      const complexContext = {234        name: gtf.contexts.getContextName(),235        complexObject: gtf.contexts.generateComplexObject(200),236      };237238      await glue.contexts.set(complexContext.name, complexContext);239240      const currentContext = await glue.contexts.get(complexContext.name);241      expect(currentContext).to.eql(complexContext);242    });243244    it('should replace an existing complex context with another complex object', async () => {245      const contextName = gtf.contexts.getContextName();246      const initComplexContext = {247        complexObject: gtf.contexts.generateComplexObject(200),248      };249      await glue.contexts.set(contextName, initComplexContext);250251      const newComplexContext = {252        newComplexObj: gtf.contexts.generateComplexObject(200),253      };254      await glue.contexts.set(contextName, newComplexContext);255256      const currentContext = await glue.contexts.get(contextName);257      expect(currentContext).to.eql(newComplexContext);258    });259260    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {261      const contextName = gtf.contexts.getContextName();262263      glue.contexts264        .subscribe(contextName, () => {265          done();266        })267        .then(() => glue.contexts.set(contextName, {}));268    });269270    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {271      const context = {272        name: gtf.contexts.getContextName(),273        complexObj: gtf.contexts.generateComplexObject(10),274      };275276      glue.contexts277        .subscribe(context.name, (updatedObject) => {278          try {279            expect(updatedObject).to.eql(context);280            done();281          } catch (error) {282            done(error)283          }284285        })286        .then(() => glue.contexts.set(context.name, context))287        .catch((err) => done(err));288    });289290    it('should invoke the callback registered with subscribe() method 3 times when a context is changed 3 times', async () => {291      let counter = 0;292293      const context = {294        name: gtf.contexts.getContextName(),295        complexObj: gtf.contexts.generateComplexObject(10),296      };297298      await glue.contexts.subscribe(context.name, () => {299        counter++;300      });301302      await glue.contexts.set(context.name, context);303      await glue.contexts.set(context.name, { date: new Date() });304      await glue.contexts.set(context.name, { prop: 'value' });305306      expect(counter).to.eql(3);307    });308  });309310  describe('when manipulated by another app ', function () {311    let secondApp;312313    beforeEach(async () => {314      secondApp = await gtf.createApp();315    });316317    afterEach(() => secondApp.stop());318319    it("should create a new context if there isn't one with the given name", async () => {320      const contextName = gtf.contexts.getContextName();321      const complexObject = gtf.contexts.generateComplexObject(10);322323      const contextAlreadyExists = glue.contexts.all().includes(contextName);324325      if (!contextAlreadyExists) {326        await secondApp.contexts.set(contextName, complexObject);327      } else {328        throw new Error('Invalid test - context already exists!');329      }330331      const newContext = await glue.contexts.get(contextName);332      expect(newContext).to.eql(complexObject);333    });334335    it("should create 3 more elements when there aren't any contexts with passed names", async () => {336      const oldLength = glue.contexts.all().length;337      await secondApp.contexts.set(gtf.contexts.getContextName(), {});338      await secondApp.contexts.set(gtf.contexts.getContextName(), {});339      await secondApp.contexts.set(gtf.contexts.getContextName(), {});340      const newLength = glue.contexts.all().length;341342      expect(oldLength + 3).to.eql(newLength);343    });344345    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {346      const randomContextName = gtf.contexts.getContextName();347      const complexObject = gtf.contexts.generateComplexObject(10);348349      const oldLength = glue.contexts.all().length;350      await secondApp.contexts.set(randomContextName, complexObject);351      const newLength = glue.contexts.all().length;352353      expect(oldLength + 1).to.eql(newLength);354    });355356    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {357      const randomContextName = gtf.contexts.getContextName();358      const complexObject = gtf.contexts.generateComplexObject(10);359360      await glue.contexts.set(randomContextName, complexObject);361      const oldContextsLength = glue.contexts.all().length;362363      await secondApp.contexts.set(randomContextName, { newProp: 'value' });364      const newContextsLength = glue.contexts.all().length;365366      expect(oldContextsLength).to.eql(newContextsLength);367    });368369    it('should remove all previous context properties', async () => {370      const contextName = gtf.contexts.getContextName();371      const initContext = {372        id: gtf.contexts.getContextName(),373        name: 'initial Context',374        complexObject: gtf.contexts.generateComplexObject(10),375      };376377      await secondApp.contexts.set(contextName, initContext);378      const initialKeys = Object.keys(await glue.contexts.get(contextName));379380      const newContext = {381        product: 'GTF',382        company: 'Tick42',383      };384385      await secondApp.contexts.set(contextName, newContext);386      const newKeys = Object.keys(await glue.contexts.get(contextName));387388      const repetitiveKeys = initialKeys.filter((key) => newKeys.includes(key));389390      expect(repetitiveKeys).to.eql([]);391    });392393    it('should replace the context with the passed object when invoked with valid name and data', async () => {394      const contextName = gtf.contexts.getContextName();395      const initContext = {396        id: 'unique identifier',397        complexObject: gtf.contexts.generateComplexObject(10),398      };399400      await secondApp.contexts.set(contextName, initContext);401402      const newContext = {403        name: 'new context',404        title: 'test',405      };406407      await secondApp.contexts.set(contextName, newContext);408409      const currentContext = await glue.contexts.get(contextName);410      expect(currentContext).to.eql(newContext);411    });412413    it('should create a new complex object when invoked with valid name and complex data', async () => {414      const complexContext = {415        name: gtf.contexts.getContextName(),416        complexObject: gtf.contexts.generateComplexObject(200),417      };418419      await secondApp.contexts.set(complexContext.name, complexContext);420421      const newContext = await glue.contexts.get(complexContext.name);422      expect(newContext).to.eql(complexContext);423    });424425    it('should replace an existing complex context with another complex object', async () => {426      const contextName = gtf.contexts.getContextName();427      const initComplexContext = {428        complexObject: gtf.contexts.generateComplexObject(200),429      };430      await secondApp.contexts.set(contextName, initComplexContext);431432      const newComplexContext = {433        newComplexObj: gtf.contexts.generateComplexObject(200),434      };435      await secondApp.contexts.set(contextName, newComplexContext);436437      const currentContext = await glue.contexts.get(contextName);438      expect(currentContext).to.eql(newComplexContext);439    });440441    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {442      const contextName = gtf.contexts.getContextName();443444      glue.contexts445        .subscribe(contextName, () => {446          done();447        })448        .then(() => secondApp.contexts.set(contextName, {}));449    });450451    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {452      const context = {453        name: gtf.contexts.getContextName(),454        complexObj: gtf.contexts.generateComplexObject(10),455      };456457      glue.contexts458        .subscribe(context.name, (updatedObject) => {459          try {460            expect(updatedObject).to.eql(context);461            done();462          } catch (error) {463            done(error);464          }465        })466        .then(() => secondApp.contexts.set(context.name, context))467        .catch((err) => done(err));468    });469470    it('should invoke the callback registered with subscribe() method 3 times when a context is changed 3 times', async () => {471      let counter = 0;472473      const context = {474        name: gtf.contexts.getContextName(),475        complexObj: gtf.contexts.generateComplexObject(10),476      };477478      await glue.contexts.subscribe(context.name, () => {479        counter++;480      });481482      await glue.contexts.set(context.name, context);483      await glue.contexts.set(context.name, { date: new Date() });484      await glue.contexts.set(context.name, { prop: 'value' });485486      expect(counter).to.eql(3);487    });488489    contextsForTesting.forEach((context) => {490      it(`should set the context between 2 applications with ${context.type}`, async () => {491        const contextName = gtf.contexts.getContextName();492        await glue.contexts.set(contextName, context);493494        const contextFromSecondApp = await secondApp.contexts.get(contextName);495496        expect(contextFromSecondApp).to.eql(context);497      });498499      it(`should replace the old context when the new context is ${context.type} and 2 applications are used`, async () => {500        const contextName = gtf.contexts.getContextName();501        const initialContext = {502          isSaved: true,503        };504505        await glue.contexts.set(contextName, initialContext);506        await glue.contexts.set(contextName, context);507508        const contextFromSecondApp = await secondApp.contexts.get(contextName);509510        expect(contextFromSecondApp.isSaved).to.be.undefined;511      });512    });513514    it('should replace the context when top level properties are the same', async () => {515      const contextName = gtf.contexts.getContextName();516      const firstContext = {517        a: 1,518        b: 2,519      };520521      const secondContext = {522        b: 0,523        c: 3,524      };525526      await glue.contexts.set(contextName, firstContext);527      await glue.contexts.set(contextName, secondContext);528529      const contextFromSecondApp = await secondApp.contexts.get(contextName);530531      expect(contextFromSecondApp).to.eql(secondContext);532    });533534    it('should replace the context when inner properties are affected', async () => {535      const contextName = gtf.contexts.getContextName();536      const firstContext = {537        first: {538          a: 1,539          b: 2,540        },541      };542543      const secondContext = {544        first: {545          b: 0,546          c: 3,547        },548      };549      await glue.contexts.set(contextName, firstContext);550      await glue.contexts.set(contextName, secondContext);551552      const contextFromSecondApp = await secondApp.contexts.get(contextName);553554      expect(contextFromSecondApp).to.eql(secondContext);555    });556557    it('should replace the context when top level array is affected', async () => {558      const contextName = gtf.contexts.getContextName();559      const firstContext = {560        a: [1],561        b: [2],562      };563564      const secondContext = {565        b: [0],566        c: [3],567      };568      await glue.contexts.set(contextName, firstContext);569      await glue.contexts.set(contextName, secondContext);570571      const contextFromSecondApp = await secondApp.contexts.get(contextName);572573      expect(contextFromSecondApp).to.eql(secondContext);574    });575576    it('should replace the context when an inner array is affected', async () => {577      const contextName = gtf.contexts.getContextName();578      const firstContext = {579        first: {580          a: [1],581          b: [2],582        },583      };584585      const secondContext = {586        first: {587          b: [0],588          c: [3],589        },590      };591      await glue.contexts.set(contextName, firstContext);
...setPaths.spec.js
Source:setPaths.spec.js  
...73        done(error);74      }75    });76    it("should create a new context when there isn't one with the given context name", async () => {77      const contextName = gtf.contexts.getContextName();78      await glue.contexts.setPaths(contextName, [{ path: 'prop', value: 'value' }]);79      const newContext = await glue.contexts.get(contextName);80      expect(newContext).to.eql({ prop: 'value' });81    });82    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {83      const contextName = gtf.contexts.getContextName();84      const oldLength = glue.contexts.all().length;85      await glue.contexts.setPaths(contextName, [{ path: 'prop1', value: 'value' }]);86      const newLength = glue.contexts.all().length;87      expect(oldLength + 1).to.eql(newLength);88    });89    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {90      const contextName = gtf.contexts.getContextName();91      const complexObject = gtf.contexts.generateComplexObject(10);92      const anotherComplexObject = gtf.contexts.generateComplexObject(10);93      await glue.contexts.setPaths(contextName, [{ path: 'prop1.prop2', value: complexObject }]);94      const oldLength = glue.contexts.all().length;95      await glue.contexts.setPaths(contextName, [{ path: 'prop1.prop2', value: anotherComplexObject }]);96      const newLength = glue.contexts.all().length;97      expect(oldLength).to.eql(newLength);98    });99    it('should add new nested properties to the passed paths', async () => {100      const contextName = gtf.contexts.getContextName();101      const complexObject = gtf.contexts.generateComplexObject(10);102      const anotherComplexObject = gtf.contexts.generateComplexObject(10);103      await glue.contexts.setPaths(contextName, [104        { path: 'prop1.prop2', value: complexObject },105        { path: 'prop3.prop4', value: anotherComplexObject },106      ]);107      const newContext = await glue.contexts.get(contextName);108      expect(newContext).to.eql({109        prop1: { prop2: complexObject },110        prop3: { prop4: anotherComplexObject },111      });112    });113    it('should not change previous context properties', async () => {114      const contextName = gtf.contexts.getContextName();115      const context = gtf.contexts.generateComplexObject(10);116      const complexObject = gtf.contexts.generateComplexObject(10);117      await glue.contexts.update(contextName, context);118      await glue.contexts.setPaths(contextName, [{ path: 'prop1.prop2', value: complexObject }]);119      const newContext = await glue.contexts.get(contextName);120      expect(newContext).to.eql(121        Object.assign({}, context, {122          prop1: { prop2: complexObject },123        })124      );125    });126    it('should update already existing context key values when invoked with valid data', async () => {127      const contextName = gtf.contexts.getContextName();128      const initContext = gtf.contexts.generateComplexObject(10);129      await glue.contexts.setPaths(contextName, [{ path: 'path1.path2', value: initContext }]);130      const newContext = gtf.contexts.generateComplexObject(10);131      await glue.contexts.setPaths(contextName, [{ path: 'path1.path2', value: newContext }]);132      const currentContext = await glue.contexts.get(contextName);133      expect(currentContext).to.eql({134        path1: { path2: newContext },135      });136    });137    it('should remove context key when passed data has an already existing key set to null', async () => {138      const context = {139        id: 'unique identifier',140        name: gtf.contexts.getContextName(),141        complexObject: gtf.contexts.generateComplexObject(10),142      };143      await glue.contexts.update(context.name, context);144      await glue.contexts.setPaths(context.name, [{ path: 'prop1.prop2', value: 'prop2 value' }]);145      const initialKeys = Object.keys(await glue.contexts.get(context.name));146      await glue.contexts.setPaths(context.name, [{ path: 'prop1', value: null }]);147      const newKeys = Object.keys(await glue.contexts.get(context.name));148      expect(newKeys.includes('prop1')).to.be.false;149      expect(initialKeys.length - 1).to.eql(newKeys.length);150    });151    it('should create a new complex context when invoked with valid arguments', async () => {152      const contextName = gtf.contexts.getContextName();153      const complexObj = gtf.contexts.generateComplexObject(200);154      await glue.contexts.setPaths(contextName, [{ path: 'prop1', value: complexObj }]);155      const newContext = await glue.contexts.get(contextName);156      expect(newContext).to.eql({ prop1: complexObj });157    });158    it('should add new prop with complex data when updating an existing complex context', async () => {159      const contextName = gtf.contexts.getContextName();160      const complexObject = gtf.contexts.generateComplexObject();161      const anotherComplexObject = gtf.contexts.generateComplexObject();162      await glue.contexts.setPaths(contextName, [163        { path: 'prop1', value: complexObject },164        { path: 'prop2', value: anotherComplexObject },165      ]);166      const newContext = await glue.contexts.get(contextName);167      expect(newContext).to.eql({168        prop1: complexObject,169        prop2: anotherComplexObject,170      });171    });172    it('should replace an already existing complex property with another complex object', async () => {173      const contextName = gtf.contexts.getContextName();174      const prop2Context = {175        id: gtf.contexts.getContextName(),176        prop2: 'value',177      };178      const initComplexObj = gtf.contexts.generateComplexObject(200);179      const anotherComplexObj = gtf.contexts.generateComplexObject(200);180      await glue.contexts.setPaths(contextName, [181        { path: 'prop1', value: initComplexObj },182        { path: 'prop2', value: prop2Context },183      ]);184      await glue.contexts.setPaths(contextName, [{ path: 'prop1', value: anotherComplexObj }]);185      const newContext = await glue.contexts.get(contextName);186      expect(newContext).to.eql({ prop1: anotherComplexObj, prop2: prop2Context });187    });188    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {189      const contextName = gtf.contexts.getContextName();190      glue.contexts191        .subscribe(contextName, (updatedCtx) => {192          if (updatedCtx.prop) {193            done();194          }195        })196        .then((unsubscribeFn) => {197          gtf.addWindowHook(unsubscribeFn);198          return glue.contexts.setPaths(contextName, [{ path: 'prop', value: 'value' }]);199        })200        .catch((err) => done(err));201    });202    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {203      const contextName = gtf.contexts.getContextName();204      const prop1Context = {205        id: gtf.contexts.getContextName(),206        complexObj: gtf.contexts.generateComplexObject(10),207      };208      const prop2Context = {209        title: 'prop2 context',210        value: 'prop2 value',211      };212      glue.contexts213        .subscribe(contextName, (updatedObject) => {214          if (Object.keys(updatedObject).length) {215            try {216              expect(updatedObject).to.eql({ prop1: prop1Context, prop2: prop2Context });217              done();218            } catch (err) {219              done(err);220            }221          }222        })223        .then((unsubscribeFn) => {224          gtf.addWindowHook(unsubscribeFn);225          return glue.contexts.setPaths(contextName, [226            { path: 'prop1', value: prop1Context },227            { path: 'prop2', value: prop2Context },228          ]);229        })230        .catch((err) => done(err));231    });232    it('should invoke the callback registered with subscribe() method 3 times when a context is updated 3 times', (done) => {233      const contextName = gtf.contexts.getContextName();234      const prop1Context = {235        id: gtf.contexts.getContextName(),236        complexObj: gtf.contexts.generateComplexObject(10),237      };238      const prop2Context = {239        title: 'prop2 context',240        value: 'prop2 value',241      };242      const ready = gtf.waitFor(3, done);243      glue.contexts244        .subscribe(contextName, (data) => {245          if (data.prop1.id === prop1Context.id) {246            ready();247          }248        })249        .then((unsubscribeFn) => {250          gtf.addWindowHook(unsubscribeFn);251          return glue.contexts.setPaths(contextName, [{ path: 'prop1', value: prop1Context }]);252        })253        .then(() => glue.contexts.setPaths(contextName, [{ path: 'prop2', value: prop2Context }]))254        .then(() => glue.contexts.setPaths(contextName, [{ path: 'prop3', value: 'value3' }]))255        .catch((err) => done(err));256    });257  });258  describe('when manipulated by another app, ', function () {259    let supportApp;260    beforeEach(async () => {261      supportApp = await gtf.createApp();262    });263    afterEach(() => supportApp.stop());264    it("should create a new context when there isn't one with the given context name", async () => {265      const contextName = gtf.contexts.getContextName();266      await supportApp.contexts.setPaths(contextName, [{ path: 'prop', value: 'value' }]);267      const newContext = await glue.contexts.get(contextName);268      expect(newContext).to.eql({ prop: 'value' });269    });270    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {271      const contextName = gtf.contexts.getContextName();272      const oldLength = glue.contexts.all().length;273      await supportApp.contexts.setPaths(contextName, [{ path: 'prop1', value: 'value' }]);274      const newLength = glue.contexts.all().length;275      expect(oldLength + 1).to.eql(newLength);276    });277    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {278      const contextName = gtf.contexts.getContextName();279      const complexObject = gtf.contexts.generateComplexObject(10);280      const anotherComplexObject = gtf.contexts.generateComplexObject(10);281      await supportApp.contexts.setPaths(contextName, [{ path: 'prop1.prop2', value: complexObject }]);282      const oldLength = glue.contexts.all().length;283      await supportApp.contexts.setPaths(contextName, [{ path: 'prop1.prop2', value: anotherComplexObject }]);284      const newLength = glue.contexts.all().length;285      expect(oldLength).to.eql(newLength);286    });287    it('should add new nested properties to the passed paths', async () => {288      const contextName = gtf.contexts.getContextName();289      const complexObject = gtf.contexts.generateComplexObject(10);290      const anotherComplexObject = gtf.contexts.generateComplexObject(10);291      await supportApp.contexts.setPaths(contextName, [292        { path: 'prop1.prop2', value: complexObject },293        { path: 'prop3.prop4', value: anotherComplexObject },294      ]);295      const newContext = await glue.contexts.get(contextName);296      expect(newContext).to.eql({297        prop1: { prop2: complexObject },298        prop3: { prop4: anotherComplexObject },299      });300    });301    it('should not change previous context properties', async () => {302      const contextName = gtf.contexts.getContextName();303      const context = gtf.contexts.generateComplexObject(10);304      const complexObject = gtf.contexts.generateComplexObject(10);305      await glue.contexts.update(contextName, context);306      await supportApp.contexts.setPaths(contextName, [{ path: 'prop1.prop2', value: complexObject }]);307      const newContext = await glue.contexts.get(contextName);308      expect(newContext).to.eql(309        Object.assign({}, context, {310          prop1: { prop2: complexObject },311        })312      );313    });314    it('should update already existing context key values when invoked with valid data', async () => {315      const contextName = gtf.contexts.getContextName();316      const initContext = gtf.contexts.generateComplexObject(10);317      await glue.contexts.setPaths(contextName, [{ path: 'path1.path2', value: initContext }]);318      const newContext = gtf.contexts.generateComplexObject(10);319      await supportApp.contexts.setPaths(contextName, [{ path: 'path1.path2', value: newContext }]);320      const currentContext = await glue.contexts.get(contextName);321      expect(currentContext).to.eql({322        path1: { path2: newContext },323      });324    });325    it('should remove context key when passed data has an already existing key set to null', async () => {326      const context = {327        id: 'unique identifier',328        name: gtf.contexts.getContextName(),329        complexObject: gtf.contexts.generateComplexObject(10),330      };331      await glue.contexts.update(context.name, context);332      await glue.contexts.setPaths(context.name, [{ path: 'prop1.prop2', value: 'prop2 value' }]);333      const initialKeys = Object.keys(await glue.contexts.get(context.name));334      await supportApp.contexts.setPaths(context.name, [{ path: 'prop1', value: null }]);335      const newKeys = Object.keys(await glue.contexts.get(context.name));336      expect(newKeys.includes('prop1')).to.be.false;337      expect(initialKeys.length - 1).to.eql(newKeys.length);338    });339    it('should create a new complex context when invoked with valid arguments', async () => {340      const contextName = gtf.contexts.getContextName();341      const complexObj = gtf.contexts.generateComplexObject(200);342      await supportApp.contexts.setPaths(contextName, [{ path: 'prop1', value: complexObj }]);343      const newContext = await glue.contexts.get(contextName);344      expect(newContext).to.eql({ prop1: complexObj });345    });346    it('should add new prop with complex data when updating an existing complex context', async () => {347      const contextName = gtf.contexts.getContextName();348      const complexObject = gtf.contexts.generateComplexObject();349      const anotherComplexObject = gtf.contexts.generateComplexObject();350      await supportApp.contexts.setPaths(contextName, [351        { path: 'prop1', value: complexObject },352        { path: 'prop2', value: anotherComplexObject },353      ]);354      const newContext = await glue.contexts.get(contextName);355      expect(newContext).to.eql({356        prop1: complexObject,357        prop2: anotherComplexObject,358      });359    });360    it('should replace an already existing complex property with another complex object', async () => {361      const contextName = gtf.contexts.getContextName();362      const prop2Context = {363        id: gtf.contexts.getContextName(),364        prop2: 'value',365      };366      const initComplexObj = gtf.contexts.generateComplexObject(200);367      const anotherComplexObj = gtf.contexts.generateComplexObject(200);368      await glue.contexts.setPaths(contextName, [369        { path: 'prop1', value: initComplexObj },370        { path: 'prop2', value: prop2Context },371      ]);372      await supportApp.contexts.setPaths(contextName, [{ path: 'prop1', value: anotherComplexObj }]);373      const newContext = await glue.contexts.get(contextName);374      expect(newContext).to.eql({ prop1: anotherComplexObj, prop2: prop2Context });375    });376    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {377      const contextName = gtf.contexts.getContextName();378      glue.contexts379        .subscribe(contextName, () => {380          done();381        })382        .then((unsubscribeFn) => {383          gtf.addWindowHook(unsubscribeFn);384          return supportApp.contexts.setPaths(contextName, [{ path: 'prop', value: 'value' }]);385        })386        .catch((err) => done(err));387    });388    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {389      const contextName = gtf.contexts.getContextName();390      const prop1Context = {391        id: gtf.contexts.getContextName(),392        complexObj: gtf.contexts.generateComplexObject(10),393      };394      const prop2Context = {395        title: 'prop2 context',396        value: 'prop2 value',397      };398      glue.contexts399        .subscribe(contextName, (updatedObject) => {400          if (Object.keys(updatedObject).length) {401            try {402              expect(updatedObject).to.eql({ prop1: prop1Context, prop2: prop2Context });403              done();404            } catch (err) {405              done(err);406            }407          }408        })409        .then(() =>410          supportApp.contexts.setPaths(contextName, [411            { path: 'prop1', value: prop1Context },412            { path: 'prop2', value: prop2Context },413          ])414        )415        .catch((err) => done(err));416    });417    it('should invoke the callback registered with subscribe() method 3 times when a context is updated 3 times', (done) => {418      const contextName = gtf.contexts.getContextName();419      const prop1Context = {420        id: gtf.contexts.getContextName(),421        complexObj: gtf.contexts.generateComplexObject(10),422      };423      const prop2Context = {424        title: 'prop2 context',425        value: 'prop2 value',426      };427      const ready = gtf.waitFor(3, done);428      glue.contexts429        .subscribe(contextName, (data) => {430          if (data.prop1.id === prop1Context.id) {431            ready();432          }433        })434        .then((unsubscribeFn) => {...setPath.spec.js
Source:setPath.spec.js  
...73      const returned = await glue.contexts.setPath('contextName', 'prop1.prop2', 'value');74      expect(returned).to.eql(undefined);75    });76    it("should create a new context when there isn't one with the given context name", async () => {77      const contextName = gtf.contexts.getContextName();78      await glue.contexts.setPath(contextName, 'prop', 'value');79      const newContext = await glue.contexts.get(contextName);80      expect(newContext).to.eql({ prop: 'value' });81    });82    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {83      const contextName = gtf.contexts.getContextName();84      const complexObject = gtf.contexts.generateComplexObject(10);85      const oldLength = glue.contexts.all().length;86      await glue.contexts.setPath(contextName, 'prop1.prop2', complexObject);87      const newLength = glue.contexts.all().length;88      expect(oldLength + 1).to.eql(newLength);89    });90    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {91      const contextName = gtf.contexts.getContextName();92      const complexObject = gtf.contexts.generateComplexObject(10);93      const anotherComplexObject = gtf.contexts.generateComplexObject(10);94      await glue.contexts.setPath(contextName, 'prop1.prop2', complexObject);95      const oldLength = glue.contexts.all().length;96      await glue.contexts.setPath(contextName, 'prop3.prop4', anotherComplexObject);97      const newLength = glue.contexts.all().length;98      expect(oldLength).to.eql(newLength);99    });100    it('should add new nested properties to the passed path', async () => {101      const contextName = gtf.contexts.getContextName();102      await glue.contexts.setPath(contextName, 'prop1.prop2.prop3', 'prop3 value');103      const newContext = await glue.contexts.get(contextName);104      expect(newContext).to.eql({105        prop1: { prop2: { prop3: 'prop3 value' } },106      });107    });108    it('should not change previous context properties', async () => {109      const contextName = gtf.contexts.getContextName();110      const context = gtf.contexts.generateComplexObject(10);111      await glue.contexts.update(contextName, context);112      await glue.contexts.setPath(contextName, 'prop1.prop2.prop3', 'prop3 value');113      const newContext = await glue.contexts.get(contextName);114      expect(newContext).to.eql(115        Object.assign({}, context, {116          prop1: { prop2: { prop3: 'prop3 value' } },117        })118      );119    });120    it('should update already existing context key values when invoked with valid data', async () => {121      const contextName = gtf.contexts.getContextName();122      const initContext = gtf.contexts.generateComplexObject(10);123      await glue.contexts.setPath(contextName, 'path1.path2', initContext);124      const newContext = gtf.contexts.generateComplexObject(10);125      await glue.contexts.setPath(contextName, 'path1.path2', newContext);126      expect(await glue.contexts.get(contextName)).to.eql({127        path1: { path2: newContext },128      });129    });130    it("should add properties on top level of context when invoked with an empty string ('') as a second argument", async () => {131      const contextName = gtf.contexts.getContextName();132      const initContext = gtf.contexts.generateComplexObject(10);133      await glue.contexts.setPath(contextName, '', initContext);134      const newContext = await glue.contexts.get(contextName);135      expect(newContext).to.eql(initContext);136    });137    it('should remove context key when passed data has an already existing key set to null', async () => {138      const context = {139        id: 'unique identifier',140        name: gtf.contexts.getContextName(),141        complexObject: gtf.contexts.generateComplexObject(10),142      };143      await glue.contexts.update(context.name, context);144      await glue.contexts.setPath(context.name, 'prop1.prop2', 'prop2 value');145      const initialKeys = Object.keys(await glue.contexts.get(context.name));146      await glue.contexts.setPath(context.name, 'prop1', null);147      const newKeys = Object.keys(await glue.contexts.get(context.name));148      expect(newKeys.includes('prop1')).to.be.false;149      expect(initialKeys.length - 1).to.eql(newKeys.length);150    });151    it('should create a new complex context when invoked with valid arguments', async () => {152      const contextName = gtf.contexts.getContextName();153      const complexObj = gtf.contexts.generateComplexObject(200);154      await glue.contexts.setPath(contextName, 'prop1', complexObj);155      const newContext = await glue.contexts.get(contextName);156      expect(newContext).to.eql({ prop1: complexObj });157    });158    it('should add new prop with complex data when updating an existing complex context', async () => {159      const contextName = gtf.contexts.getContextName();160      const initComplexObj = gtf.contexts.generateComplexObject(200);161      const anotherComplexObj = gtf.contexts.generateComplexObject(200);162      await glue.contexts.setPath(contextName, 'prop1', initComplexObj);163      await glue.contexts.setPath(contextName, 'prop2', anotherComplexObj);164      const newContext = await glue.contexts.get(contextName);165      expect(newContext).to.eql({ prop1: initComplexObj, prop2: anotherComplexObj });166    });167    it('should replace an already existing complex property with another complex object', async () => {168      const contextName = gtf.contexts.getContextName();169      const initComplexObj = gtf.contexts.generateComplexObject(200);170      const anotherComplexObj = gtf.contexts.generateComplexObject(200);171      await glue.contexts.setPath(contextName, 'prop1', initComplexObj);172      await glue.contexts.setPath(contextName, 'prop1', anotherComplexObj);173      const newContext = await glue.contexts.get(contextName);174      expect(newContext).to.eql({ prop1: anotherComplexObj });175    });176    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {177      const contextName = gtf.contexts.getContextName();178      glue.contexts179        .subscribe(contextName, () => {180          done();181        })182        .then((unsubscribeFn) => {183          gtf.addWindowHook(unsubscribeFn);184          return glue.contexts.setPath(contextName, 'prop', 'value');185        })186        .catch((err) => done(err));187    });188    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {189      const contextName = gtf.contexts.getContextName();190      const context = {191        id: gtf.contexts.getContextName(),192        complexObj: gtf.contexts.generateComplexObject(10),193      };194      glue.contexts195        .subscribe(contextName, (updatedObject) => {196          if (Object.keys(updatedObject).length) {197            try {198              expect(updatedObject).to.eql({ prop1: context });199              done();200            } catch (err) {201              done(err);202            }203          }204        })205        .then((unsubscribeFn) => {206          gtf.addWindowHook(unsubscribeFn);207          return glue.contexts.setPath(contextName, 'prop1', context);208        })209        .catch((err) => done(err));210    });211    it('should invoke the callback registered with subscribe() method 3 times when a context is updated 3 times', (done) => {212      const contextName = gtf.contexts.getContextName();213      const context = {214        id: gtf.contexts.getContextName(),215        complexObj: gtf.contexts.generateComplexObject(10),216      };217      const ready = gtf.waitFor(3, done);218      glue.contexts219        .subscribe(contextName, (data) => {220          if (data.prop1.id === context.id) {221            ready();222          }223        })224        .then((unsubscribeFn) => {225          gtf.addWindowHook(unsubscribeFn);226          return glue.contexts.setPath(contextName, 'prop1', context);227        })228        .then(() => glue.contexts.setPath(contextName, 'prop2', { date: new Date() }))229        .then(() => glue.contexts.setPath(contextName, 'prop3', 'value3'))230        .catch((err) => done(err));231    });232  });233  describe('when manipulate by another glue app, ', function () {234    let supportApp;235    beforeEach(async () => {236      supportApp = await gtf.createApp();237    });238    afterEach(() => supportApp.stop());239    it('should return undefined', async () => {240      const returned = await supportApp.contexts.setPath('contextName', 'prop1.prop2', 'value');241      expect(returned).to.eql(undefined);242    });243    it("should create a new context when there isn't one with the given context name", async () => {244      const contextName = gtf.contexts.getContextName();245      await supportApp.contexts.setPath(contextName, 'prop', 'value');246      const newContext = await glue.contexts.get(contextName);247      expect(newContext).to.eql({ prop: 'value' });248    });249    it("should add one more element to the array returned from all() when there isn't a context with passed name", async () => {250      const contextName = gtf.contexts.getContextName();251      const complexObject = gtf.contexts.generateComplexObject(10);252      const oldLength = glue.contexts.all().length;253      await supportApp.contexts.setPath(contextName, 'prop1.prop2', complexObject);254      const newLength = glue.contexts.all().length;255      expect(oldLength + 1).to.eql(newLength);256    });257    it('should not add one more element to the array returned from all() when there is a context with passed name', async () => {258      const contextName = gtf.contexts.getContextName();259      const complexObject = gtf.contexts.generateComplexObject(10);260      const anotherComplexObject = gtf.contexts.generateComplexObject(10);261      await supportApp.contexts.setPath(contextName, 'prop1.prop2', complexObject);262      const oldLength = glue.contexts.all().length;263      await supportApp.contexts.setPath(contextName, 'prop3.prop4', anotherComplexObject);264      const newLength = glue.contexts.all().length;265      expect(oldLength).to.eql(newLength);266    });267    it('should add new nested properties to the passed path', async () => {268      const contextName = gtf.contexts.getContextName();269      await supportApp.contexts.setPath(contextName, 'prop1.prop2.prop3', 'prop3 value');270      const newContext = await glue.contexts.get(contextName);271      expect(newContext).to.eql({272        prop1: { prop2: { prop3: 'prop3 value' } },273      });274    });275    it('should not change previous context properties', async () => {276      const contextName = gtf.contexts.getContextName();277      const context = gtf.contexts.generateComplexObject(10);278      await supportApp.contexts.update(contextName, context);279      await supportApp.contexts.setPath(contextName, 'prop1.prop2.prop3', 'prop3 value');280      const newContext = await glue.contexts.get(contextName);281      expect(newContext).to.eql(282        Object.assign({}, context, {283          prop1: { prop2: { prop3: 'prop3 value' } },284        })285      );286    });287    it('should update already existing context key values when invoked with valid data', async () => {288      const contextName = gtf.contexts.getContextName();289      const initContext = gtf.contexts.generateComplexObject(10);290      await supportApp.contexts.setPath(contextName, 'path1.path2', initContext);291      const newContext = gtf.contexts.generateComplexObject(10);292      await supportApp.contexts.setPath(contextName, 'path1.path2', newContext);293      expect(await glue.contexts.get(contextName)).to.eql({294        path1: { path2: newContext },295      });296    });297    it("should add properties on top level of context when invoked with an empty string ('') as a second argument", async () => {298      const contextName = gtf.contexts.getContextName();299      const initContext = gtf.contexts.generateComplexObject(10);300      await supportApp.contexts.setPath(contextName, '', initContext);301      const newContext = await glue.contexts.get(contextName);302      expect(newContext).to.eql(initContext);303    });304    it('should remove context key when passed data has an already existing key set to null', async () => {305      const context = {306        id: 'unique identifier',307        name: gtf.contexts.getContextName(),308        complexObject: gtf.contexts.generateComplexObject(10),309      };310      await glue.contexts.update(context.name, context);311      await supportApp.contexts.setPath(context.name, 'prop1.prop2', 'prop2 value');312      const initialKeys = Object.keys(await glue.contexts.get(context.name));313      await supportApp.contexts.setPath(context.name, 'prop1', null);314      const newKeys = Object.keys(await glue.contexts.get(context.name));315      expect(newKeys.includes('prop1')).to.be.false;316      expect(initialKeys.length - 1).to.eql(newKeys.length);317    });318    it('should create a new complex context when invoked with valid arguments', async () => {319      const contextName = gtf.contexts.getContextName();320      const complexObj = gtf.contexts.generateComplexObject(200);321      await supportApp.contexts.setPath(contextName, 'prop1', complexObj);322      const newContext = await glue.contexts.get(contextName);323      expect(newContext).to.eql({ prop1: complexObj });324    });325    it('should add new prop with complex data when updating an existing complex context', async () => {326      const contextName = gtf.contexts.getContextName();327      const initComplexObj = gtf.contexts.generateComplexObject(200);328      const anotherComplexObj = gtf.contexts.generateComplexObject(200);329      await supportApp.contexts.setPath(contextName, 'prop1', initComplexObj);330      await supportApp.contexts.setPath(contextName, 'prop2', anotherComplexObj);331      const newContext = await glue.contexts.get(contextName);332      expect(newContext).to.eql({ prop1: initComplexObj, prop2: anotherComplexObj });333    });334    it('should replace an already existing complex property with another complex object', async () => {335      const contextName = gtf.contexts.getContextName();336      const initComplexObj = gtf.contexts.generateComplexObject(200);337      const anotherComplexObj = gtf.contexts.generateComplexObject(200);338      await supportApp.contexts.setPath(contextName, 'prop1', initComplexObj);339      await supportApp.contexts.setPath(contextName, 'prop1', anotherComplexObj);340      const newContext = await glue.contexts.get(contextName);341      expect(newContext).to.eql({ prop1: anotherComplexObj });342    });343    it("should invoke the callback registered with subscribe() method when there's a subscription for the context", (done) => {344      const contextName = gtf.contexts.getContextName();345      glue.contexts346        .subscribe(contextName, () => {347          done();348        })349        .then((unsubscribeFn) => {350          gtf.addWindowHook(unsubscribeFn);351          return supportApp.contexts.setPath(contextName, 'prop', 'value');352        })353        .catch((err) => done(err));354    });355    it("should invoke the callback registered with subscribe() method with the correct data as first argument when there's a subscription for the context", (done) => {356      const contextName = gtf.contexts.getContextName();357      const context = {358        id: gtf.contexts.getContextName(),359        complexObj: gtf.contexts.generateComplexObject(10),360      };361      glue.contexts362        .subscribe(contextName, (updatedObject) => {363          if (Object.keys(updatedObject)) {364            try {365              expect(updatedObject).to.eql({ prop1: context });366              done();367            } catch (err) {368              done(err);369            }370          }371        })372        .then((unsubscribeFn) => {373          gtf.addWindowHook(unsubscribeFn);374          return supportApp.contexts.setPath(contextName, 'prop1', context);375        })376        .catch((err) => done(err));377    });378    it('should invoke the callback registered with subscribe() method 3 times when a context is updated 3 times', (done) => {379      const contextName = gtf.contexts.getContextName();380      const context = {381        id: gtf.contexts.getContextName(),382        complexObj: gtf.contexts.generateComplexObject(10),383      };384      const ready = gtf.waitFor(3, done);385      glue.contexts386        .subscribe(contextName, (data) => {387          if (data.prop1.id === context.id) {388            ready();389          }390        })391        .then((unsubscribeFn) => {392          gtf.addWindowHook(unsubscribeFn);393          return supportApp.contexts.setPath(contextName, 'prop1', context);394        })395        .then(() => supportApp.contexts.setPath(contextName, 'prop2', { date: new Date() }))...get.spec.js
Source:get.spec.js  
...82    });8384    it('should return an object', async () => {85      const context = {86        name: gtf.contexts.getContextName(),87        complexObj: gtf.contexts.generateComplexObject(10),88      };89      await glue.contexts.update(context.name, context);9091      const currentContext = await glue.contexts.get(context.name);92      expect(currentContext).to.be.an('object');93    });9495    it('should return an empty object when invoked with a non-existent context name', async () => {96      const nonExistentContext = await glue.contexts.get('randomContextName');97      expect(nonExistentContext).to.eql({});98    });99100    it('should return the same data as the one created with update()', async () => {101      const context = {102        name: gtf.contexts.getContextName(),103        complexObj: gtf.contexts.generateComplexObject(10),104      };105      await glue.contexts.update(context.name, context);106107      const currentContext = await glue.contexts.get(context.name);108      expect(currentContext).to.eql(context);109    });110111    it('should return the same data as the one created with set()', async () => {112      const context = {113        name: gtf.contexts.getContextName(),114        complexObj: gtf.contexts.generateComplexObject(10),115      };116      await glue.contexts.set(context.name, context);117118      const currentContext = await glue.contexts.get(context.name);119      expect(currentContext).to.eql(context);120    });121122    it('should return correct data after updating it 3 times with update()', async () => {123      let contextName = gtf.contexts.getContextName();124      const initContext = {125        companyName: 'Tick42',126        location: 'Sofia',127      };128      await glue.contexts.update(contextName, initContext);129130      const secondContextToUpdate = {131        products: [132          {133            name: 'Glue42 Enterprise',134            description: 'Desktop application integration platform',135          },136          {137            name: 'Glue42 Core',138            description: 'Web application integration platform',139          },140        ],141      };142143      await glue.contexts.update(contextName, secondContextToUpdate);144145      const thirdContextToUpdate = {146        coreValues: ['keep learning', "don't be a mushroom", 'give a shit'],147      };148149      await glue.contexts.update(contextName, thirdContextToUpdate);150151      const currentContext = await glue.contexts.get(contextName);152      expect(currentContext).to.eql(Object.assign({}, initContext, secondContextToUpdate, thirdContextToUpdate));153    });154155    it('should return correct data after replacing an existing context data with set()', async () => {156      const contextName = gtf.contexts.getContextName();157      const context = {158        complexObj: gtf.contexts.generateComplexObject(10),159      };160161      await glue.contexts.set(contextName, context);162163      const newContext = {164        id: 'unique identifier',165        date: new Date(),166        title: 'new context',167      };168      await glue.contexts.set(contextName, newContext);169170      const currentContext = await glue.contexts.get(contextName);171      expect(currentContext).to.eql(newContext);172    });173174    it('should return correct data when creating a complex object with update()', async () => {175      const context = {176        name: gtf.contexts.getContextName(),177        complexObj: gtf.contexts.generateComplexObject(200),178      };179      await glue.contexts.update(context.name, context);180181      const currentContext = await glue.contexts.get(context.name);182      expect(currentContext).to.eql(context);183    });184185   186    it('should return correct data when updating an existing complex context with another complex object', async () => {187      const contextName = gtf.contexts.getContextName();188      const context = {189        complexObj: gtf.contexts.generateComplexObject(200),190      };191      await glue.contexts.update(contextName, context);192193      const newContext = {194        newComplexObj: gtf.contexts.generateComplexObject(200),195      };196197      await glue.contexts.update(contextName, newContext);198199      const currentContext = await glue.contexts.get(contextName);200      expect(currentContext).to.eql(Object.assign({}, context, newContext));201    });202203    it('should return correct data when creating a complex object with set()', async () => {204      const context = {205        name: gtf.contexts.getContextName(),206        complexObj: gtf.contexts.generateComplexObject(200),207      };208      await glue.contexts.set(context.name, context);209210      const currentContext = await glue.contexts.get(context.name);211      expect(currentContext).to.eql(context);212    });213214    it('should return correct data after replacing an existing complex context with another complex object', async () => {215      const contextName = gtf.contexts.getContextName();216      const context = {217        complexObj: gtf.contexts.generateComplexObject(200),218      };219      await glue.contexts.set(contextName, context);220221      const newContext = {222        newComplexObj: gtf.contexts.generateComplexObject(200),223      };224225      await glue.contexts.set(contextName, newContext);226227      const currentContext = await glue.contexts.get(contextName);228      expect(currentContext).to.eql(newContext);229    });230231    it('should return correct data as soon as data becomes available', (done) => {232      const context = {233        name: gtf.contexts.getContextName(),234        complexObj: gtf.contexts.generateComplexObject(10),235      };236237      const ready = gtf.waitFor(2, done);238239      glue.contexts240        .update(context.name, context)241        .then(() => glue.contexts.get(context.name))242        .then((ctxData) => {243          expect(ctxData).to.eql(context);244          ready();245        })246        .then(() => glue.contexts.get(context.name))247        .then((ctxData2) => {248          expect(ctxData2).to.eql(context);249          ready();250        })251        .catch((err) => done(err));252    });253254    it('double get should return snapshot', (done) => {255      const contextName = gtf.contexts.getContextName();256      const context = gtf.contexts.generateComplexObject(10);257258      glue.contexts259        .subscribe(contextName, async (updatedCtx) => {260          try {261            const contexts = await Promise.all([glue.contexts.get(contextName), glue.contexts.get(contextName)]);262            expect(contexts[0]).to.eql(context);263            expect(contexts[1]).to.eql(context);264            expect(updatedCtx).to.eql(context);265            done();266          } catch (err) {267            done(err);268          }269        })270        .then((unFn) => {271          gtf.addWindowHook(unFn);272          return glue.contexts.update(contextName, context);273        })274        .catch((err) => done(err));275    });276277    it('should return snapshot when get() is followed by subscribe()', (done) => {278      const contextName = gtf.contexts.getContextName();279      const context = {280        id: gtf.contexts.getContextName(),281        complexObj: gtf.contexts.generateComplexObject(10),282      };283      const ready = gtf.waitFor(2, done);284285      glue.contexts286        .subscribe(contextName, async (updatedCtx) => {287          if (updatedCtx.id === context.id) {288            try {289              const contextData = await glue.contexts.get(contextName);290              expect(contextData).to.eql(context);291              expect(updatedCtx).to.eql(context);292              ready();293            } catch (err) {294              done(err);295            }296          }297298          await glue.contexts.subscribe(contextName, (dataFromSubscribe) => {299            if (dataFromSubscribe.id === context.id) {300              try {301                expect(dataFromSubscribe).to.eql(context);302                ready();303              } catch (err) {304                done(err);305              }306            }307          });308        })309        .then((unFn) => gtf.addWindowHook(unFn))310        .then(() => glue.contexts.update(contextName, context))311        .catch((err) => done(err));312    });313  });314315  describe('when manipulated by another app, ', function () {316    let secondApp;317318    beforeEach(async () => {319      secondApp = await gtf.createApp();320    });321322    afterEach(() => secondApp.stop());323324    it('should return the same data as the one created with update()', async () => {325      const contextName = gtf.contexts.getContextName();326      const context = {327        complexObj: gtf.contexts.generateComplexObject(10),328      };329330      await secondApp.contexts.update(contextName, context);331332      const currentContext = await glue.contexts.get(contextName);333      expect(currentContext).to.eql(context);334    });335336    it('should return the same data as the one created with set()', async () => {337      const contextName = gtf.contexts.getContextName();338      const context = {339        complexObj: gtf.contexts.generateComplexObject(10),340      };341      await secondApp.contexts.set(contextName, context);342343      const currentContext = await glue.contexts.get(contextName);344      expect(currentContext).to.eql(context);345    });346347    it('should return correct data after updating it 3 times with update()', async () => {348      const contextName = gtf.contexts.getContextName();349      const initialContext = {350        complexObj: gtf.contexts.generateComplexObject(10),351      };352353      await secondApp.contexts.update(contextName, initialContext);354355      const secondContextToUpdate = {356        date: new Date(),357        title: 'second context',358      };359360      await secondApp.contexts.update(contextName, secondContextToUpdate);361362      const thirdContextToUpdate = {363        id: 'unique identifier',364        name: contextName,365      };366367      await secondApp.contexts.update(contextName, thirdContextToUpdate);368369      const currentContext = await glue.contexts.get(contextName);370      expect(currentContext).to.eql(Object.assign({}, initialContext, secondContextToUpdate, thirdContextToUpdate));371    });372373    it('should return correct data when replacing an existing context data with set()', async () => {374      const contextName = gtf.contexts.getContextName();375      const initContext = {376        complexObj: gtf.contexts.generateComplexObject(10),377        title: 'initial context',378      };379380      await secondApp.contexts.set(contextName, initContext);381382      const newContext = {383        name: gtf.contexts.getContextName(),384        date: new Date(),385      };386387      await secondApp.contexts.set(contextName, newContext);388389      const currentContext = await glue.contexts.get(contextName);390      expect(currentContext).to.eql(newContext);391    });392393    it('should return correct data when creating a complex object with update()', async () => {394      const context = {395        name: gtf.contexts.getContextName(),396        complexObj: gtf.contexts.generateComplexObject(200),397      };398      await secondApp.contexts.update(context.name, context);399400      const currentContext = await glue.contexts.get(context.name);401      expect(currentContext).to.eql(context);402    });403404    it('should return correct data when updating an existing complex context with another complex object', async () => {405      const contextName = gtf.contexts.getContextName();406      const context = {407        complexObj: gtf.contexts.generateComplexObject(200),408      };409      await secondApp.contexts.update(contextName, context);410411      const newContext = {412        newComplexObj: gtf.contexts.generateComplexObject(200),413      };414415      await secondApp.contexts.update(contextName, newContext);416417      const currentContext = await glue.contexts.get(contextName);418      expect(currentContext).to.eql(Object.assign({}, context, newContext));419    });420421    it('should return correct data when creating a complex object with set()', async () => {422      const context = {423        name: gtf.contexts.getContextName(),424        complexObj: gtf.contexts.generateComplexObject(200),425      };426      await secondApp.contexts.set(context.name, context);427428      const currentContext = await glue.contexts.get(context.name);429      expect(currentContext).to.eql(context);430    });431432    it('should return correct data when replacing an existing complex context with another complex object', async () => {433      const contextName = gtf.contexts.getContextName();434      const context = {435        complexObj: gtf.contexts.generateComplexObject(200),436      };437      await secondApp.contexts.set(contextName, context);438439      const newContext = {440        newComplexObj: gtf.contexts.generateComplexObject(200),441      };442443      await secondApp.contexts.set(contextName, newContext);444445      const currentContext = await glue.contexts.get(contextName);446      expect(currentContext).to.eql(newContext);447    });448449    it('should return correct data as soon as data becomes available', (done) => {450      const context = {451        name: gtf.contexts.getContextName(),452        complexObj: gtf.contexts.generateComplexObject(10),453      };454455      const ready = gtf.waitFor(2, done);456457      secondApp.contexts458        .update(context.name, context)459        .then(() => glue.contexts.get(context.name))460        .then((ctxData) => {461          expect(ctxData).to.eql(context);462          ready();463        })464        .then(() => glue.contexts.get(context.name))465        .then((ctxData2) => {466          expect(ctxData2).to.eql(context);467          ready();468        })469        .catch((err) => done(err));470    });471472    it("should return correct data when another app resolves creating a context and subscribe should also return correct data when there's a subscription for the given context", (done) => {473      const contextName = gtf.contexts.getContextName();474      const context = gtf.contexts.generateComplexObject(10);475      const ready = gtf.waitFor(2, done);476477      secondApp.contexts478        .update(contextName, context)479        .then(() =>480          glue.contexts.subscribe(contextName, (data) => {481            try {482              expect(data).to.eql(context);483              ready();484            } catch (error) {485              done(error);486            }487          })488        )489        .then((unsubscribeFn) => {490          gtf.addWindowHook(unsubscribeFn);491          return glue.contexts.get(contextName);492        })493        .then((ctxData) => {494          expect(ctxData).to.eql(context);495          ready();496        })497        .catch((err) => done(err));498    });499500    contextsForTesting.forEach((context) => {501      it(`should get the old context when the new context is ${context.type} and 2 applications are used`, async () => {502        const contextName = gtf.contexts.getContextName();503        const initialContext = {504          isSaved: true,505        };506507        await secondApp.contexts.set(contextName, initialContext);508        await secondApp.contexts.set(contextName, context);509510        const myContext = await glue.contexts.get(contextName);511512        expect(myContext.isSaved).to.be.undefined;513      });514515      it(`should get a merged context when the new context is ${context.type} and 2 applications are used`, async () => {516        const contextName = gtf.contexts.getContextName();517        const initialContext = {518          isSaved: true,519        };520521        await secondApp.contexts.update(contextName, initialContext);522        await secondApp.contexts.update(contextName, context);523524        const myContext = await glue.contexts.get(contextName);525526        expect(myContext.isSaved).to.be.true;527      });528    });529  });530});
all.spec.js
Source:all.spec.js  
...45      });46    });4748    it('should return an array', async () => {49      await glue.contexts.update(gtf.contexts.getContextName(), {});50      expect(glue.contexts.all()).to.be.an('array');51    });5253    it('should return an array of strings', async () => {54      await glue.contexts.update(gtf.contexts.getContextName(), {});55      await glue.contexts.update(gtf.contexts.getContextName(), {});56      await glue.contexts.update(gtf.contexts.getContextName(), {});5758      glue.contexts.all().forEach((contextName) => {59        expect(contextName).to.be.a('string');60      });61    });6263    it('should return one more element when a valid context is created with update()', async () => {64      const oldLength = glue.contexts.all().length;65      await glue.contexts.update(gtf.contexts.getContextName(), {});66      const newLength = glue.contexts.all().length;6768      expect(oldLength + 1).to.eql(newLength);69    });7071    it('should return 3 more elements when 3 valid contexts are created with update()', async () => {72      const oldLength = glue.contexts.all().length;73      await glue.contexts.update(gtf.contexts.getContextName(), {});74      await glue.contexts.update(gtf.contexts.getContextName(), {});75      await glue.contexts.update(gtf.contexts.getContextName(), {});76      const newLength = glue.contexts.all().length;7778      expect(oldLength + 3).to.eql(newLength);79    });8081    it('should not return one more element when an invalid context is created with update()', (done) => {82      const oldLength = glue.contexts.all().length;8384      try {85        glue.contexts.update(gtf.contexts.getContextName(), 'invalidContext');86        done('update() method should throw an error');87      } catch (error) {88        const newLength = glue.contexts.all().length;89        expect(oldLength).to.eql(newLength);90        done();91      }92    });9394    it('should contain the new context after a new context is updated', async () => {95      const contextName = gtf.contexts.getContextName();96      await glue.contexts.update(contextName, { test: 42 });9798      const allContexts = glue.contexts.all();99100      const containsContext = allContexts.indexOf(contextName) >= 0;101102      expect(containsContext).to.be.true;103    });104105    it('should contain the new context after a new context is set', async () => {106      const contextName = gtf.contexts.getContextName();107      await glue.contexts.set(contextName, { test: 42 });108109      const allContexts = glue.contexts.all();110111      const containsContext = allContexts.indexOf(contextName) >= 0;112113      expect(containsContext).to.be.true;114    });115116    it('should not change when updating an already existing context with update()', async () => {117      const randomContextName = gtf.contexts.getContextName();118119      await glue.contexts.update(randomContextName, {});120      const oldLength = glue.contexts.all().length;121122      await glue.contexts.update(randomContextName, { tick: 42 });123      const newLength = glue.contexts.all().length;124125      expect(oldLength).to.eql(newLength);126    });127128    it('should return one more element when a valid context is created with set()', async () => {129      const oldLength = glue.contexts.all().length;130      await glue.contexts.set(gtf.contexts.getContextName(), {});131      const newLength = glue.contexts.all().length;132133      expect(oldLength + 1).to.eql(newLength);134    });135136    it('should return 3 more elements when 3 valid contexts are created with set()', async () => {137      const oldLength = glue.contexts.all().length;138      await glue.contexts.set(gtf.contexts.getContextName(), {});139      await glue.contexts.set(gtf.contexts.getContextName(), {});140      await glue.contexts.set(gtf.contexts.getContextName(), {});141      const newLength = glue.contexts.all().length;142143      expect(oldLength + 3).to.eql(newLength);144    });145146    it('should not return one more element when an invalid context is created with set()', (done) => {147      const oldLength = glue.contexts.all().length;148149      try {150        glue.contexts.set(gtf.contexts.getContextName(), 'invalidContext');151        done('set() method should throw an error');152      } catch (error) {153        const newLength = glue.contexts.all().length;154        expect(oldLength).to.eql(newLength);155        done();156      }157    });158159    it('should not change when updating an already existing context with set()', async () => {160      const randomContextName = gtf.contexts.getContextName();161162      await glue.contexts.set(randomContextName, { tick: 42 });163      const oldLength = glue.contexts.all().length;164165      await glue.contexts.set(randomContextName, { glue: 42 });166      const newLength = glue.contexts.all().length;167168      expect(oldLength).to.eql(newLength);169    });170171    it('should return one more element when a valid context is created with setPath()', async () => {172      const oldLength = glue.contexts.all().length;173      await glue.contexts.setPath(gtf.contexts.getContextName(), 'prop', {});174      const newLength = glue.contexts.all().length;175176      expect(oldLength + 1).to.eql(newLength);177    });178179    it('should return 3 more elements when 3 valid contexts are created with setPath()', async () => {180      const oldLength = glue.contexts.all().length;181      await glue.contexts.setPath(gtf.contexts.getContextName(), 'prop', {});182      await glue.contexts.setPath(gtf.contexts.getContextName(), 'prop', {});183      await glue.contexts.setPath(gtf.contexts.getContextName(), 'prop', {});184      const newLength = glue.contexts.all().length;185186      expect(oldLength + 3).to.eql(newLength);187    });188189    it('should not return one more element when an invalid context is created with setPath() - invoked with invalid first argument', (done) => {190      const oldLength = glue.contexts.all().length;191192      try {193        glue.contexts.setPath(undefined, 'prop1', 'invalidContext');194        done('setPath() method should throw an error');195      } catch (error) {196        const newLength = glue.contexts.all().length;197        expect(oldLength).to.eql(newLength);198        done();199      }200    });201202    it('should not return one more element when an invalid context is created with setPath() - invoked with invalid second argument', (done) => {203      const oldLength = glue.contexts.all().length;204205      try {206        glue.contexts.setPath(gtf.contexts.getContextName(), undefined, 'invalidContext');207        done('setPath() method should throw an error');208      } catch (error) {209        const newLength = glue.contexts.all().length;210        expect(oldLength).to.eql(newLength);211        done();212      }213    });214215    it('should not change when updating an already existing context with setPath()', async () => {216      const randomContextName = gtf.contexts.getContextName();217218      await glue.contexts.setPath(randomContextName, 'prop1', {});219      const oldLength = glue.contexts.all().length;220221      await glue.contexts.setPath(randomContextName, 'prop2', { tick: 42 });222      const newLength = glue.contexts.all().length;223224      expect(oldLength).to.eql(newLength);225    });226227    it('should return one more element when a valid context is created with setPaths()', async () => {228      const oldLength = glue.contexts.all().length;229      await glue.contexts.setPaths(gtf.contexts.getContextName(), [{ path: 'prop', value: 'value' }]);230      const newLength = glue.contexts.all().length;231232      expect(oldLength + 1).to.eql(newLength);233    });234235    it('should return 3 more elements when 3 valid contexts are created with setPaths()', async () => {236      const oldLength = glue.contexts.all().length;237238      await glue.contexts.setPaths(gtf.contexts.getContextName(), [{ path: 'prop', value: 'value' }]);239      await glue.contexts.setPaths(gtf.contexts.getContextName(), [{ path: 'prop', value: 'value' }]);240      await glue.contexts.setPaths(gtf.contexts.getContextName(), [{ path: 'prop', value: 'value' }]);241242      const newLength = glue.contexts.all().length;243      expect(oldLength + 3).to.eql(newLength);244    });245246    it('should not return one more element when an invalid context is created with setPaths() - invoked with invalid first argument', (done) => {247      const oldLength = glue.contexts.all().length;248249      try {250        glue.contexts.setPaths(undefined, [{ path: 'prop1', value: 'value' }]);251        done('setPaths() method should throw an error when invoked with invalid first argument');252      } catch (error) {253        const newLength = glue.contexts.all().length;254        expect(oldLength).to.eql(newLength);255        done();256      }257    });258259    it('should not return one more element when an invalid context is created with setPaths() - invoked with invalid second argument', (done) => {260      const oldLength = glue.contexts.all().length;261262      try {263        glue.contexts.setPaths('contextName', undefined);264        done('setPath() method should throw an error');265      } catch (error) {266        const newLength = glue.contexts.all().length;267        expect(oldLength).to.eql(newLength);268        done();269      }270    });271272    it('should not change when updating an already existing context with setPaths()', async () => {273      const randomContextName = gtf.contexts.getContextName();274275      await glue.contexts.setPaths(randomContextName, [276        { path: 'prop1', value: 'value1' },277        { path: 'prop2', value: 'value2' },278      ]);279      const oldLength = glue.contexts.all().length;280281      await glue.contexts.setPaths(randomContextName, [282        { path: 'prop3', value: 'value3' },283        { path: 'prop4', value: 'value4' },284      ]);285      const newLength = glue.contexts.all().length;286287      expect(oldLength).to.eql(newLength);288    });289290    it('should return an array with decreased length when a valid context is destroyed', async () => {291      const randomContextName = gtf.contexts.getContextName();292      const randomContextNameTwo = gtf.contexts.getContextName();293294      await glue.contexts.update(randomContextName, {});295      await glue.contexts.update(randomContextNameTwo, {});296      const oldLength = glue.contexts.all().length;297      await glue.contexts.destroy(randomContextNameTwo);298      const newLength = glue.contexts.all().length;299300      expect(oldLength - 1).to.eql(newLength);301    });302  });303304  describe('when manipulated by another app, ', function () {305    let secondApp;306307    beforeEach(async () => {308      secondApp = await gtf.createApp();309    });310311    afterEach(() => secondApp.stop());312313    it('should contain the new context after a new context is updated', async () => {314      const contextName = gtf.contexts.getContextName();315      await secondApp.contexts.update(contextName, { test: 42 });316317      const allContexts = glue.contexts.all();318319      const containsContext = allContexts.indexOf(contextName) >= 0;320321      expect(containsContext).to.be.true;322    });323324    it('should contain the new context after a new context is set', async () => {325      const contextName = gtf.contexts.getContextName();326      await secondApp.contexts.set(contextName, { test: 42 });327328      const allContexts = glue.contexts.all();329330      const containsContext = allContexts.indexOf(contextName) >= 0;331332      expect(containsContext).to.be.true;333    });334335    it('should return one more element when a valid context is created with update()', async () => {336      const oldLength = glue.contexts.all().length;337      await secondApp.contexts.update(gtf.contexts.getContextName(), {});338      const newLength = glue.contexts.all().length;339340      expect(oldLength + 1).to.eql(newLength);341    });342343    it('should return 3 more elements when 3 valid contexts are created with update()', async () => {344      const oldLength = glue.contexts.all().length;345346      await secondApp.contexts.update(gtf.contexts.getContextName(), {});347      await secondApp.contexts.update(gtf.contexts.getContextName(), {});348      await secondApp.contexts.update(gtf.contexts.getContextName(), {});349350      const newLength = glue.contexts.all().length;351      expect(oldLength + 3).to.eql(newLength);352    });353354    it('should not return one more element when an invalid context is created with update()', (done) => {355      const oldLength = glue.contexts.all().length;356357      secondApp.contexts358        .update('', {})359        .then(() => {360          done('update() method should throw an error');361        })362        .catch((err) => {363          const newLength = glue.contexts.all().length;364          expect(oldLength).to.eql(newLength);365          done();366        });367    });368369    it('should not change when updating an already existing context with update()', async () => {370      const randomContextName = gtf.contexts.getContextName();371372      await glue.contexts.update(randomContextName, {});373      const oldLength = glue.contexts.all().length;374375      await secondApp.contexts.update(randomContextName, { tick: 42 });376      const newLength = glue.contexts.all().length;377378      expect(oldLength).to.eql(newLength);379    });380381    it('should return one more element when a valid context is created with set()', async () => {382      const oldLength = glue.contexts.all().length;383      await secondApp.contexts.set(gtf.contexts.getContextName(), {});384      const newLength = glue.contexts.all().length;385386      expect(oldLength + 1).to.eql(newLength);387    });388389    it('should return 3 more elements when 3 valid contexts are created with set()', async () => {390      const oldLength = glue.contexts.all().length;391392      await secondApp.contexts.set(gtf.contexts.getContextName(), {});393      await secondApp.contexts.set(gtf.contexts.getContextName(), {});394      await secondApp.contexts.set(gtf.contexts.getContextName(), {});395396      const newLength = glue.contexts.all().length;397      expect(oldLength + 3).to.eql(newLength);398    });399400    it('should not return one more element when an invalid context is created with set()', (done) => {401      const oldLength = glue.contexts.all().length;402403      secondApp.contexts404        .set('', {})405        .then(() => {406          done('set() method should throw an error');407        })408        .catch((err) => {409          const newLength = glue.contexts.all().length;410          expect(oldLength).to.eql(newLength);411          done();412        });413    });414415    it('should not change when updating an already existing context with set()', async () => {416      const randomContextName = gtf.contexts.getContextName();417418      await glue.contexts.set(randomContextName, { tick: 42 });419      const oldLength = glue.contexts.all().length;420421      await secondApp.contexts.set(randomContextName, { glue: 42 });422      const newLength = glue.contexts.all().length;423424      expect(oldLength).to.eql(newLength);425    });426427    it('should return an array with decreased length when a valid context is destroyed', async () => {428      const randomContextName = gtf.contexts.getContextName();429      const randomContextNameTwo = gtf.contexts.getContextName();430431      await glue.contexts.update(randomContextName, {});432      await glue.contexts.update(randomContextNameTwo, {});433      const oldLength = glue.contexts.all().length;434      await secondApp.contexts.destroy(randomContextNameTwo);435      const newLength = glue.contexts.all().length;436437      expect(oldLength - 1).to.eql(newLength);438    });439  });
...getComponentName.js
Source:getComponentName.js  
1  function getWrappedName(outerType, innerType, wrapperName) {2    var functionName = innerType.displayName || innerType.name || '';3    return outerType.displayName || (functionName !== '' ? wrapperName + "(" + functionName + ")" : wrapperName);4  }5  function getContextName(type) {6    return type.displayName || 'Context';7  }8  function getComponentName(type) {9    if (type == null) {10      // Host root, text node or just invalid type.11      return null;12    }13    {14      if (typeof type.tag === 'number') {15        error('Received an unexpected object in getComponentName(). ' + 'This is likely a bug in React. Please file an issue.');16      }17    }18    if (typeof type === 'function') {19      return type.displayName || type.name || null;20    }21    if (typeof type === 'string') {22      return type;23    }24    switch (type) {25      case REACT_FRAGMENT_TYPE:26        return 'Fragment';27      case REACT_PORTAL_TYPE:28        return 'Portal';29      case REACT_PROFILER_TYPE:30        return 'Profiler';31      case REACT_STRICT_MODE_TYPE:32        return 'StrictMode';33      case REACT_SUSPENSE_TYPE:34        return 'Suspense';35      case REACT_SUSPENSE_LIST_TYPE:36        return 'SuspenseList';37    }38    if (typeof type === 'object') {39      switch (type.$$typeof) {40        case REACT_CONTEXT_TYPE:41          var context = type;42          return getContextName(context) + '.Consumer';43        case REACT_PROVIDER_TYPE:44          var provider = type;45          return getContextName(provider._context) + '.Provider';46        case REACT_FORWARD_REF_TYPE:47          return getWrappedName(type, type.render, 'ForwardRef');48        case REACT_MEMO_TYPE:49          return getComponentName(type.type);50        case REACT_BLOCK_TYPE:51          return getComponentName(type._render);52        case REACT_LAZY_TYPE:53          {54            var lazyComponent = type;55            var payload = lazyComponent._payload;56            var init = lazyComponent._init;57            try {58              return getComponentName(init(payload));59            } catch (x) {...Using AI Code Generation
1const { getContextName } = require('playwright/lib/server/browserContext');2const context = await page.context();3const contextName = await getContextName(context);4const { getBrowserName } = require('playwright/lib/server/browser');5const browserName = await getBrowserName(browser);61. [Playwright Internal API](Using AI Code Generation
1const context = await browser.newContext();2const contextName = await context._browserContext._options.name;3console.log("contextName: ", contextName);4await context.close();5await browser.close();6const context = await browser.newContext({ name: 'my-context' });7const contextName = await context.name();8console.log("contextName: ", contextName);9await context.close();10await browser.close();11const context = await browser.newContext();12const browserName = await context._browserContext._browser._options.name;13console.log("browserName: ", browserName);14await context.close();15await browser.close();LambdaTest’s Playwright tutorial will give you a broader idea about the Playwright automation framework, its unique features, and use cases with examples to exceed your understanding of Playwright testing. This tutorial will give A to Z guidance, from installing the Playwright framework to some best practices and advanced concepts.
Get 100 minutes of automation test minutes FREE!!
