11import '@hyper-hyper-space/node-env' ;
22
3- import { Hashing , HashedObject , MutableObject , MutationOp } from 'data/model' ;
3+ import { Hashing , HashReference , HashedObject , MutableObject , MutationOp } from 'data/model' ;
4+
5+ import { Identity } from 'data/identity' ;
6+
7+
8+ import { SpaceEntryPoint } from 'spaces/SpaceEntryPoint' ;
9+
10+ import { Mesh } from 'mesh/service' ;
11+ import { LinkupManager } from 'net/linkup' ;
12+ import { ObjectDiscoveryPeerSource } from 'mesh/agents/peer' ;
13+ import { PeerGroupInfo } from 'mesh/service' ;
14+ import { IdentityPeer } from 'mesh/agents/peer' ;
415
516import { BeaconValueOp } from './BeaconValueOp' ;
617
7- import { Worker , parentPort } from 'worker_threads' ;
18+ import { Worker } from 'worker_threads' ;
819import { Logger , LogLevel } from 'util/logging' ;
920
10- const createVdf = require ( '@subspace/vdf' ) . default ;
11- ( global as any ) . document = { } ; // yikes!
12-
13- class Beacon extends MutableObject {
21+ class Beacon extends MutableObject implements SpaceEntryPoint {
1422
1523 static log = new Logger ( Beacon . name , LogLevel . DEBUG )
1624
@@ -24,26 +32,11 @@ class Beacon extends MutableObject {
2432 _values : string [ ] ;
2533
2634 _computation ?: Worker ;
35+ _computationTermination ?: Promise < Number > ;
2736 _autoCompute : boolean ;
2837
29- static computeVdf ( ) : void {
30-
31- parentPort ?. on ( 'message' , async ( q : { challenge : string , steps : number } ) => {
32-
33- const vdfInstance = await createVdf ( ) ;
34- const result = vdfInstance . generate ( q . steps , Buffer . from ( q . challenge , 'hex' ) , 2048 , true ) ;
35-
36- parentPort ?. postMessage (
37- {
38- challenge : q . challenge ,
39- steps : q . steps ,
40- result : Buffer . from ( result ) . toString ( 'hex' )
41- }
42- ) ;
43- } ) ;
44-
45-
46- }
38+ _mesh ?: Mesh ;
39+ _peerGroup ?: PeerGroupInfo ;
4740
4841 constructor ( seed ?: string , steps ?: number ) {
4942 super ( Beacon . opClasses ) ;
@@ -64,7 +57,7 @@ class Beacon extends MutableObject {
6457
6558 stopCompute ( ) {
6659 this . _autoCompute = false ;
67- this . stopCompute ( ) ;
60+ this . stopRace ( ) ;
6861 }
6962
7063 race ( ) {
@@ -73,35 +66,58 @@ class Beacon extends MutableObject {
7366 Beacon . log . debug ( ( ) => 'Racing for challenge (' + this . steps + ' steps): "' + this . currentChallenge ( ) + '".' ) ;
7467
7568 this . _computation = new Worker ( './dist-examples/examples/randomness-beacon/model/worker.js' ) ;
76-
77- this . _computation . postMessage ( { steps : this . steps , challenge : this . currentChallenge ( ) } ) ;
78-
69+ console . log ( 'is death immediate?' )
70+ this . _computation . on ( 'online' , ( ) => { console . log ( 'worker is online' ) } ) ;
71+ this . _computation . on ( 'error' , ( err : Error ) => { console . log ( 'ERR' ) ; console . log ( err ) } ) ;
72+ this . _computation . on ( 'exit' , ( exitCode : number ) => {
73+ console . log ( 'worker exited with ' + exitCode ) ;
74+ } )
75+ console . log ( 'created worker' )
7976 this . _computation . on ( 'message' , async ( msg : { challenge : string , result : string } ) => {
8077
8178 Beacon . log . debug ( ( ) => 'Solved challenge "' + msg . challenge + '" with: "' + msg . result + '".' ) ;
8279
83- this . stopRace ( ) ;
80+
8481
8582 if ( msg . challenge === this . currentChallenge ( ) ) {
8683 let op = new BeaconValueOp ( this , this . currentSeq ( ) , msg . result ) ;
8784
8885 if ( this . _lastOp !== undefined ) {
8986 op . setPrevOps ( new Set ( [ this . _lastOp . createReference ( ) ] ) . values ( ) ) ;
87+ } else {
88+ op . setPrevOps ( new Set < HashReference < BeaconValueOp > > ( ) . values ( ) ) ;
9089 }
9190
9291 await this . applyNewOp ( op ) ;
93- if ( this . _autoCompute ) {
94- this . race ( ) ;
95- }
92+ await this . getStore ( ) . save ( this ) ;
93+
94+ } else {
95+ console . log ( 'mismatched challenge' ) ;
9696 }
9797 } ) ;
98+ this . _computation . postMessage ( { steps : this . steps , challenge : this . currentChallenge ( ) } ) ;
99+ console . log ( 'posted message to worker' )
100+
101+ } else {
102+ console . log ( 'race was called but a computation is running' ) ;
98103 }
99104 }
100105
101106 stopRace ( ) {
107+ console . log ( 'stopRace()' ) ;
102108 if ( this . _computation !== undefined ) {
103- this . _computation . terminate ( ) ;
104- this . _computation = undefined ;
109+ if ( this . _computationTermination === undefined ) {
110+ console . log ( 'need to stop' )
111+ this . _computationTermination = this . _computation . terminate ( ) . then (
112+ ( ret : number ) => {
113+ console . log ( 'stopped' ) ;
114+ this . _computation = undefined ;
115+ this . _computationTermination = undefined ;
116+ return ret ;
117+ }
118+ ) ;
119+
120+ }
105121 }
106122 }
107123
@@ -131,7 +147,12 @@ class Beacon extends MutableObject {
131147 if ( this . _lastOp === undefined ||
132148 ! this . _lastOp . equals ( op ) ) {
133149
134- if ( op . prevOps ?. size ( ) === 0 ) {
150+ if ( op . prevOps === undefined ) {
151+ throw new Error ( 'BeaconValueOp must have a defined prevOps set (even if it is empty).' ) ;
152+ }
153+
154+
155+ if ( op . prevOps . size ( ) === 0 ) {
135156
136157 if ( this . _lastOp !== undefined ) {
137158 throw new Error ( 'Initial BeaconValueOp received, but there are already other ops in this beacon.' ) ;
@@ -142,7 +163,7 @@ class Beacon extends MutableObject {
142163 throw new Error ( 'Non-initial BeaconValueOp received, but there are no values in this beacon.' ) ;
143164 }
144165
145- if ( ! this . _lastOp . equals ( op . prevOps ? .values ( ) . next ( ) . value ) ) {
166+ if ( ! this . _lastOp . hash ( ) === op . prevOps . values ( ) . next ( ) . value . hash ) {
146167 throw new Error ( 'Received BeaconValueOp does not point to last known beacon value.' ) ;
147168 }
148169 }
@@ -151,10 +172,16 @@ class Beacon extends MutableObject {
151172
152173 this . _values . push ( Hashing . toHex ( op . hash ( ) ) ) ;
153174
154- this . stopRace ( ) ;
155-
156175 if ( this . _autoCompute ) {
157- this . race ( ) ;
176+ if ( this . _computation === undefined ) {
177+ console . log ( 'computation was finished' ) ;
178+ this . race ( ) ;
179+ } else {
180+ console . log ( 'chaining' ) ;
181+ this . stopRace ( ) ;
182+ this . _computationTermination ?. then ( ( ) => { console . log ( 'finished now!' ) ; this . race ( ) ; } ) ;
183+ }
184+
158185 }
159186
160187 }
@@ -178,6 +205,58 @@ class Beacon extends MutableObject {
178205 return this . steps !== undefined && this . getId ( ) !== undefined ;
179206 }
180207
208+ async startSync ( ) : Promise < void > {
209+
210+ let resources = this . getResources ( ) ;
211+
212+ if ( resources === undefined ) {
213+ throw new Error ( 'Cannot start sync: resources not configured.' ) ;
214+ }
215+
216+ this . _mesh = resources . mesh ;
217+
218+ if ( this . _mesh === undefined ) {
219+ throw new Error ( 'Cannot start sync: mesh is missing from configured resources.' ) ;
220+ }
221+
222+ let linkupServers = resources . config . linkupServers === undefined ?
223+ [ LinkupManager . defaultLinkupServer ] : resources . config . linkupServer as string [ ] ;
224+
225+
226+ let localIdentity = resources . config . id as Identity ;
227+
228+ const localPeer = await new IdentityPeer ( linkupServers [ 0 ] as string , localIdentity . hash ( ) , localIdentity ) . asPeer ( ) ;
229+
230+ this . _mesh . startObjectBroadcast ( this , linkupServers , [ localPeer . endpoint ] ) ;
231+
232+ let peerSource = new ObjectDiscoveryPeerSource ( this . _mesh , this , linkupServers , localPeer . endpoint , IdentityPeer . getEndpointParser ( resources . store ) ) ;
233+
234+ this . _peerGroup = {
235+ id : 'sync-for-' + this . hash ( ) ,
236+ localPeer : localPeer ,
237+ peerSource : peerSource
238+ }
239+
240+ this . _mesh . joinPeerGroup ( this . _peerGroup ) ;
241+ this . _mesh . syncObjectWithPeerGroup ( this . _peerGroup . id , this ) ;
242+
243+ this . loadAndWatchForChanges ( ) ;
244+ }
245+
246+ async stopSync ( ) : Promise < void > {
247+
248+ const peerGroupId = this . _peerGroup ?. id as string ;
249+
250+ this . _mesh ?. stopSyncObjectWithPeerGroup ( peerGroupId , this . hash ( ) ) ;
251+ this . _mesh ?. stopObjectBroadcast ( this . hash ( ) ) ;
252+ this . _mesh ?. leavePeerGroup ( peerGroupId ) ;
253+
254+ this . _mesh = undefined ;
255+ this . _peerGroup = undefined ;
256+ }
257+
181258}
182259
260+ HashedObject . registerClass ( Beacon . className , Beacon ) ;
261+
183262export { Beacon } ;
0 commit comments