Skip to content

Commit 1202533

Browse files
feat(overmind-angular): replace angular connect with service
BREAKING CHANGE: connect is replaced with service
1 parent edb4181 commit 1202533

File tree

1 file changed

+74
-130
lines changed
  • packages/node_modules/overmind-angular/src

1 file changed

+74
-130
lines changed
Lines changed: 74 additions & 130 deletions
Original file line numberDiff line numberDiff line change
@@ -1,146 +1,90 @@
1-
import { EventType, Overmind, TApp, Configuration } from 'overmind'
1+
// import { Injectable } from "@angular/core"
2+
import { Overmind, EventType } from 'overmind'
3+
import { BehaviorSubject, Observable } from 'rxjs'
4+
import { map } from 'rxjs/operators'
25

3-
// @ts-ignore
4-
import { NgZone } from '@angular/core'
5-
import { IMutation } from 'proxy-state-tree'
6-
7-
export interface IConnect<Config extends Configuration> {
8-
state: TApp<Config>['state']
9-
actions: TApp<Config>['actions']
10-
effects: TApp<Config>['effects']
11-
addMutationListener: (cb: (mutation: IMutation) => void) => () => void
12-
}
6+
const IS_PRODUCTION = process.env.NODE_ENV === 'production'
137

148
let nextComponentId = 0
159

16-
export const createConnect = <A extends Overmind<any>>(overmind: A) => (
17-
propsCallback?: (
18-
overmind: {
19-
state: A['state']
20-
actions: A['actions']
21-
effects: A['effects']
22-
}
23-
) => object
24-
) => {
10+
export const Track = (Component) => {
11+
if (IS_PRODUCTION) {
12+
return
13+
}
14+
2515
const componentId = nextComponentId++
2616
let componentInstanceId = 0
2717

28-
return function(target: any) {
29-
const targetNgOnInit = target.prototype.ngOnInit
30-
const targetNgDoCheck = target.prototype.ngDoCheck
31-
const targetNgAfterContentInit = target.prototype.ngAfterContentInit
32-
const targetNgAfterViewInit = target.prototype.ngAfterViewInit
33-
const targetNgAfterViewChecked = target.prototype.ngAfterViewChecked
34-
35-
target.prototype.ngOnInit = function() {
36-
const ngZ = new NgZone({ enableLongStackTrace: false })
37-
38-
this.__tree = (overmind as any).proxyStateTree.getTrackStateTree()
39-
this.__currentFlushId = 0
40-
this.overmind = {
41-
state: this.__tree.state,
42-
actions: overmind.actions,
43-
effects: overmind.effects,
44-
addMutationListener: overmind.addMutationListener,
45-
}
46-
if (propsCallback) {
47-
Object.assign(
48-
this,
49-
propsCallback({
50-
state: this.__tree.state,
51-
actions: overmind.actions,
52-
effects: overmind.effects,
53-
})
54-
)
55-
}
56-
this.__shouldUpdatePaths = false
57-
this.__componentInstanceId = componentInstanceId++
58-
this.__onUpdate = (mutations, paths, flushId) => {
59-
this.__currentFlushId = flushId
60-
61-
if (this.cdr) {
62-
this.cdr.markForCheck()
63-
}
64-
ngZ.run(() => {})
65-
}
66-
67-
if (targetNgOnInit) {
68-
targetNgOnInit.call(this)
69-
}
70-
71-
if (
72-
!this.cdr &&
73-
(!target['__annotations__'][0] ||
74-
target['__annotations__'][0].changeDetection === 0)
75-
) {
76-
throw new Error(
77-
'overmind-angular ERROR: You have to inject the ChangeDetectionRef as "cdr" on the component. In the constructor, add argument: "private cdr: ChangeDetectorRef" '
78-
)
79-
}
80-
}
18+
function findService(target) {
19+
return Object.keys(target).find((key) => target[key] instanceof Service)
20+
}
8121

82-
target.prototype.ngAfterContentInit = function() {
83-
this.__tree.track(this.__onUpdate)
22+
const targetNgOnInit = Component.prototype.ngOnInit
23+
Component.prototype.ngOnInit = function() {
24+
const service = this[findService(this)]
25+
service.addComponent({
26+
componentId,
27+
componentInstanceId: componentInstanceId++,
28+
name: Component.name,
29+
})
8430

85-
if (targetNgAfterContentInit) {
86-
targetNgAfterContentInit.call(this)
87-
}
88-
}
31+
targetNgOnInit && targetNgOnInit.call(this)
32+
}
33+
}
8934

90-
target.prototype.ngAfterViewInit = function() {
91-
overmind.eventHub.emitAsync(EventType.COMPONENT_ADD, {
92-
componentId,
93-
componentInstanceId: this.__componentInstanceId,
94-
name: this.constructor.name || '',
95-
paths: Array.from(this.__tree.pathDependencies) as any,
35+
export class Service<App extends Overmind<any>> {
36+
private tree: any
37+
private state$: Observable<any>
38+
private subject: BehaviorSubject<any>
39+
private overmind: App
40+
private componentDetails: any
41+
actions: App['actions']
42+
effects: App['effects']
43+
addMutationListener: App['addMutationListener']
44+
constructor(overmind: App) {
45+
this.tree = (overmind as any).proxyStateTree.getTrackStateTreeWithProxifier()
46+
this.subject = new BehaviorSubject(this.tree.state)
47+
this.state$ = this.subject.asObservable()
48+
this.overmind = overmind
49+
50+
this.actions = this.overmind.actions
51+
this.addMutationListener = this.overmind.addMutationListener
52+
53+
this.tree.track(this.onUpdate)
54+
}
55+
private addComponent(componentDetails) {
56+
this.componentDetails = componentDetails
57+
this.overmind.eventHub.emitAsync(EventType.COMPONENT_ADD, {
58+
componentId: componentDetails.componentId,
59+
componentInstanceId: componentDetails.componentInstanceId,
60+
name: componentDetails.name,
61+
paths: Array.from(this.tree.pathDependencies) as any,
62+
})
63+
}
64+
private onUpdate = (mutations, paths, flushId) => {
65+
this.tree.track(this.onUpdate)
66+
this.subject.next(this.tree.state)
67+
if (this.componentDetails) {
68+
this.overmind.eventHub.emitAsync(EventType.COMPONENT_UPDATE, {
69+
componentId: this.componentDetails.componentId,
70+
componentInstanceId: this.componentDetails.componentInstanceId,
71+
name: this.componentDetails.name,
72+
paths: Array.from(this.tree.pathDependencies) as any,
73+
flushId,
9674
})
97-
98-
if (targetNgAfterViewInit) {
99-
targetNgAfterViewInit.call(this)
100-
}
101-
}
102-
103-
target.prototype.ngDoCheck = function() {
104-
if (this.__shouldUpdatePaths) {
105-
this.__tree.track(this.__onUpdate)
106-
}
107-
if (targetNgDoCheck) {
108-
targetNgDoCheck.call(this)
109-
}
110-
}
111-
112-
target.prototype.ngAfterViewChecked = function() {
113-
if (this.__shouldUpdatePaths) {
114-
this.__shouldUpdatePaths = false
115-
overmind.eventHub.emitAsync(EventType.COMPONENT_UPDATE, {
116-
componentId,
117-
componentInstanceId: this.__componentInstanceId,
118-
name: this.constructor.name || '',
119-
paths: Array.from(this.__tree.pathDependencies) as any,
120-
flushId: this.__currentFlushId,
121-
})
122-
}
123-
if (targetNgAfterViewChecked) {
124-
targetNgAfterViewChecked.call(this)
125-
}
12675
}
127-
128-
let targetNgOnDestroy = target.prototype.ngOnDestroy
129-
130-
target.prototype.ngOnDestroy = function() {
131-
overmind.eventHub.emitAsync(EventType.COMPONENT_REMOVE, {
132-
componentId,
133-
componentInstanceId: this.__componentInstanceId,
134-
name: this.constructor.name || '',
76+
}
77+
private ngOnDestroy() {
78+
;(this.overmind as any).proxyStateTree.disposeTree(this.tree)
79+
if (this.componentDetails) {
80+
this.overmind.eventHub.emitAsync(EventType.COMPONENT_REMOVE, {
81+
componentId: this.componentDetails.componentId,
82+
componentInstanceId: this.componentDetails.componentInstanceId,
83+
name: this.componentDetails.name,
13584
})
136-
const anyOvermind = overmind as any
137-
anyOvermind.proxyStateTree.disposeTree(this.__tree)
138-
139-
if (targetNgOnDestroy) {
140-
targetNgOnDestroy.call(this)
141-
}
14285
}
143-
144-
return target
86+
}
87+
select(expr: any) {
88+
return this.state$.pipe(map((value) => expr(value)))
14589
}
14690
}

0 commit comments

Comments
 (0)