diff --git a/modules/effects/spec/effects_metadata.spec.ts b/modules/effects/spec/effects_metadata.spec.ts index a77f3617fd..223927a19f 100644 --- a/modules/effects/spec/effects_metadata.spec.ts +++ b/modules/effects/spec/effects_metadata.spec.ts @@ -23,26 +23,6 @@ describe('Effect Metadata', () => { ]); }); - it('should get the effects metadata for a downleveled class instance', () => { - class Fixture { - static get propDecorators() { - return { - a: [{ type: Effect, args: [{ dispatch: false }] }], - b: [{ type: Effect, args: [] }], - c: [{ type: Effect }], - }; - } - } - - const mock = new Fixture(); - - expect(getSourceMetadata(mock)).toEqual([ - { propertyName: 'a', dispatch: false }, - { propertyName: 'b', dispatch: true }, - { propertyName: 'c', dispatch: true }, - ]); - }); - it('should return an empty array if the class has not been decorated', () => { class Fixture { a: any; diff --git a/modules/effects/src/effects_metadata.ts b/modules/effects/src/effects_metadata.ts index 260f079fa4..02d6c5779b 100644 --- a/modules/effects/src/effects_metadata.ts +++ b/modules/effects/src/effects_metadata.ts @@ -3,7 +3,7 @@ import { ignoreElements } from 'rxjs/operator/ignoreElements'; import { Observable } from 'rxjs/Observable'; import { compose } from '@ngrx/store'; -const METADATA_KEY = '@ngrx/effects'; +const METADATA_KEY = '__@ngrx/effects__'; const r: any = Reflect; export interface EffectMetadata { @@ -11,55 +11,24 @@ export interface EffectMetadata { dispatch: boolean; } -function hasStaticMetadata(sourceType: any): boolean { - return !!(sourceType as any).propDecorators; -} - -function getStaticMetadata(sourceType: any): EffectMetadata[] { - const propDecorators = sourceType.propDecorators; - return Object.keys(propDecorators).reduce( - (all, key) => all.concat(getStaticMetadataEntry(propDecorators[key], key)), - [] - ); -} - -function getStaticMetadataEntry(metadataEntry: any, propertyName: string) { - return metadataEntry - .filter((entry: any) => entry.type === Effect) - .map((entry: any) => { - let dispatch = true; - if (entry.args && entry.args.length) { - dispatch = !!entry.args[0].dispatch; - } - return { propertyName, dispatch }; - }); -} - function getEffectMetadataEntries(sourceProto: any): EffectMetadata[] { - if (hasStaticMetadata(sourceProto.constructor)) { - return getStaticMetadata(sourceProto.constructor); - } - - if (r.hasOwnMetadata(METADATA_KEY, sourceProto)) { - return r.getOwnMetadata(METADATA_KEY, sourceProto); - } - - return []; + return sourceProto.constructor[METADATA_KEY] || []; } function setEffectMetadataEntries(sourceProto: any, entries: EffectMetadata[]) { - r.defineMetadata(METADATA_KEY, entries, sourceProto); + const constructor = sourceProto.constructor; + const meta: EffectMetadata[] = constructor.hasOwnProperty(METADATA_KEY) + ? (constructor as any)[METADATA_KEY] + : Object.defineProperty(constructor, METADATA_KEY, { value: [] })[ + METADATA_KEY + ]; + Array.prototype.push.apply(meta, entries); } -/** - * @Annotation - */ export function Effect({ dispatch } = { dispatch: true }): PropertyDecorator { return function(target: any, propertyName: string) { - const effects: EffectMetadata[] = getEffectMetadataEntries(target); const metadata: EffectMetadata = { propertyName, dispatch }; - - setEffectMetadataEntries(target, [...effects, metadata]); + setEffectMetadataEntries(target, [metadata]); }; }