UNPKG

@sprucelabs/spruce-cli

Version:

Command line interface for building Spruce skills.

270 lines • 13.1 kB
"use strict"; var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) { var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d; if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc); else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r; return c > 3 && r && Object.defineProperty(target, key, r), r; }; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); const mercury_types_1 = require("@sprucelabs/mercury-types"); const spruce_event_utils_1 = require("@sprucelabs/spruce-event-utils"); const spruce_skill_utils_1 = require("@sprucelabs/spruce-skill-utils"); const test_utils_1 = require("@sprucelabs/test-utils"); const test_utils_2 = require("@sprucelabs/test-utils"); const EventStore_1 = __importDefault(require("../../features/event/stores/EventStore")); const AbstractEventTest_1 = __importDefault(require("../../tests/AbstractEventTest")); const constants_1 = require("../../tests/constants"); const test_utility_1 = __importDefault(require("../../tests/utilities/test.utility")); const EVENT_NAME_READABLE = 'my event store amazing event'; const EVENT_NAME = 'my-event-store-amazing-event'; const EVENT_CAMEL = 'myEventStoreAmazingEvent'; class EventStoreTest extends AbstractEventTest_1.default { static createAction; static events; static get version() { return spruce_skill_utils_1.versionUtil.generateVersion(); } static async beforeEach() { await super.beforeEach(); this.createAction = this.Action('event', 'create'); spruce_skill_utils_1.diskUtil.writeFile(this.resolvePath('package.json'), '{}'); await this.people.loginAsDemoPerson(constants_1.DEMO_NUMBER_EVENT_STORE); this.events = this.Store('event'); } static async hasFetchEventContractsMethod() { test_utils_1.assert.isFunction(this.events.fetchEventContracts); } static async fetchesCoreEventContracts() { const results = await this.events.fetchEventContracts({ localNamespace: 'my-skill', }); const { contracts, errors } = results; test_utils_1.assert.isTrue(contracts.length >= 1); for (const contract of contracts) { (0, mercury_types_1.validateEventContract)(contract); } test_utils_1.assert.isEqual(errors.length, 0); } static async registerEventContract() { const organizationFixture = this.getOrganizationFixture(); const org = await organizationFixture.seedDemoOrg({ name: 'my new org', }); const { eventStore: eventStore1, skill: skill1 } = await this.seedSkillAndInstallAtOrg(org, 'skill 1'); const { eventStore: eventStore2 } = await this.seedSkillAndInstallAtOrg(org, 'skill 2'); await eventStore1.registerEventContract({ eventContract: { eventSignatures: { [`my-fantastic-event::${this.version.constValue}`]: { emitPayloadSchema: (0, spruce_event_utils_1.buildEmitTargetAndPayloadSchema)({ eventName: `my-fantastic-event::${this.version.constValue}`, targetSchema: spruce_event_utils_1.eventTargetSchema, }), emitPermissionContract: (0, mercury_types_1.buildPermissionContract)({ id: 'my-fantastic-event-contract', name: 'Fantastic emit perms', permissions: [ { id: 'can-emit-perms', name: 'can emit perm', defaults: { skill: false, }, }, ], }), }, }, }, }); const { contracts } = await eventStore2.fetchEventContracts({ localNamespace: 'my-skill', }); test_utils_1.assert.isTrue(contracts.length > 2); const skillContract = contracts[1]; const sig = spruce_event_utils_1.eventContractUtil.getSignatureByName(skillContract, `${skill1.slug}.my-fantastic-event::${this.version.constValue}`); test_utils_1.assert.isEqual(sig.emitPermissionContract?.id, `${skill1.slug}.my-fantastic-event-contract`); } static async badLocalContractThrowsNiceError() { await this.FeatureFixture().installCachedFeatures('events'); const skill = await this.getSkillFixture().registerCurrentSkill({ name: 'my new skill', }); const results = await this.createAction.execute({ nameReadable: EVENT_NAME_READABLE, nameKebab: EVENT_NAME, nameCamel: EVENT_CAMEL, }); test_utils_1.assert.isFalsy(results.errors); const match = test_utility_1.default.assertFileByNameInGeneratedFiles(`emitPayload.builder.ts`, results.files); spruce_skill_utils_1.diskUtil.writeFile(match, 'export default {}'); const err = await test_utils_1.assert.doesThrowAsync(() => this.events.loadLocalContract(skill.slug), new RegExp(`${skill.slug}.${EVENT_NAME}::${spruce_skill_utils_1.versionUtil.generateVersion().constValue}`)); test_utils_2.errorAssert.assertError(err, 'INVALID_EVENT_CONTRACT'); } static async badLocalSignature() { await this.installEventsSkill(); const skill = await this.getSkillFixture().registerCurrentSkill({ name: 'my new skill', }); const results = await this.createAction.execute({ nameReadable: EVENT_NAME_READABLE, nameKebab: EVENT_NAME, nameCamel: EVENT_CAMEL, }); test_utils_1.assert.isFalsy(results.errors); const match = test_utility_1.default.assertFileByNameInGeneratedFiles(`event.options.ts`, results.files); spruce_skill_utils_1.diskUtil.writeFile(match, 'export default {waka: true}'); const err = await test_utils_1.assert.doesThrowAsync(() => this.events.loadLocalContract(skill.slug), new RegExp(`${skill.slug}.${EVENT_NAME}::${spruce_skill_utils_1.versionUtil.generateVersion().constValue}`)); test_utils_2.errorAssert.assertError(err, 'INVALID_EVENT_CONTRACT'); } static async mixesInLocalContracts() { await this.installEventsSkill(); const skill = await this.getSkillFixture().registerCurrentSkill({ name: 'my new skill', }); await this.createAction.execute({ nameReadable: EVENT_NAME_READABLE, nameKebab: EVENT_NAME, nameCamel: EVENT_CAMEL, }); await this.copyEventBuildersAndPermissions(EVENT_NAME); await this.Action('event', 'sync').execute({}); const { contracts } = await this.events.fetchEventContracts({ localNamespace: skill.slug, namespaces: ['core'], }); test_utils_1.assert.isLength(contracts, 2); const name = spruce_event_utils_1.eventNameUtil.join({ eventName: EVENT_NAME, eventNamespace: skill.slug, version: this.version.constValue, }); let wasFound = false; for (const contract of contracts) { if (contract.eventSignatures[name]?.emitPayloadSchema) { wasFound = true; test_utils_1.assert.isEqual(contract.eventSignatures[name].emitPayloadSchema?.id, EVENT_CAMEL + 'EmitTargetAndPayload'); test_utils_1.assert.isTruthy(contract.eventSignatures[name].emitPayloadSchema?.fields ?.target); test_utils_1.assert.isTruthy(contract.eventSignatures[name].emitPayloadSchema?.fields ?.payload); test_utils_1.assert.isTruthy(contract.eventSignatures[name].responsePayloadSchema); test_utils_1.assert.isTruthy(contract.eventSignatures[name].emitPermissionContract); test_utils_1.assert.isTruthy(contract.eventSignatures[name].listenPermissionContract); (0, mercury_types_1.validateEventContract)(contract); } } test_utils_1.assert.isTrue(wasFound); } static async mixesInLocalContractWithGlobalEventsAndDoesNotReturnContractTwice() { const { skill, fqen } = await this.installAndRegisterOneGlobalEvent(); const { contracts } = await this.events.fetchEventContracts({ localNamespace: skill.slug, }); const totalMatches = contracts.reduce((count, contract) => { if (contract.eventSignatures[fqen]) { count++; } return count; }, 0); test_utils_1.assert.isEqual(totalMatches, 1); } static async doesNotLoadGlobalContractsForSelf() { const { fqen, skill } = await this.installAndRegisterOneGlobalEvent(); const eventsPath = this.resolvePath('src', 'events'); spruce_skill_utils_1.diskUtil.deleteDir(eventsPath); const { contracts } = await this.events.fetchEventContracts({ localNamespace: skill.slug, }); const unified = spruce_event_utils_1.eventContractUtil.unifyContracts(contracts); test_utils_1.assert.isTruthy(unified); test_utils_1.assert.doesThrow(() => spruce_event_utils_1.eventContractUtil.getSignatureByName(unified, fqen)); } static async globbyPatternLooksEverywhere() { const store = this.events; const expected = this.resolvePath('src', '**', 'events', '**/*.(builder|options).ts'); //@ts-ignore test_utils_1.assert.isEqual(store.generateGlobbyForLocalEvents(), expected); } static async passesBackJsErrorsWhenFetchingEventContracts() { const msg = (0, test_utils_1.generateId)(); this.events = this.Store('event', { apiClientFactory: async () => { throw new Error(msg); }, }); await test_utils_1.assert.doesThrowAsync(() => this.events.fetchEventContracts(), msg); } static async installAndRegisterOneGlobalEvent() { await this.installEventsSkill(); const skill = await this.getSkillFixture().registerCurrentSkill({ name: 'event store test skill', }); const results = await this.createAction.execute({ nameReadable: EVENT_NAME_READABLE, nameKebab: EVENT_NAME, nameCamel: EVENT_CAMEL, isGlobal: true, }); const { fqen } = results.meta ?? {}; test_utils_1.assert.isTruthy(fqen); const boot = await this.Action('skill', 'boot').execute({ local: true }); boot.meta?.kill(); EventStore_1.default.clearCache(); return { boot, skill, fqen, createResults: results }; } static async seedSkillAndInstallAtOrg(org, name) { const skill = await this.getSkillFixture().seedDemoSkill({ name, }); await this.getOrganizationFixture().installSkillAtOrganization(skill.id, org.id); const client = await this.connectToApi({ skillId: skill.id, apiKey: skill.apiKey, }); const eventStore = this.Store('event', { apiClientFactory: async () => { return client; }, }); return { eventStore, skill }; } static async installEventsSkill() { await this.FeatureFixture().installCachedFeatures('events'); } } exports.default = EventStoreTest; __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "hasFetchEventContractsMethod", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "fetchesCoreEventContracts", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "registerEventContract", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "badLocalContractThrowsNiceError", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "badLocalSignature", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "mixesInLocalContracts", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "mixesInLocalContractWithGlobalEventsAndDoesNotReturnContractTwice", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "doesNotLoadGlobalContractsForSelf", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "globbyPatternLooksEverywhere", null); __decorate([ (0, test_utils_1.test)() ], EventStoreTest, "passesBackJsErrorsWhenFetchingEventContracts", null); //# sourceMappingURL=EventStore.test.js.map