Skip to content

Instantly share code, notes, and snippets.

@kdgerona
Last active November 10, 2020 17:18
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kdgerona/2472f41fd58a273a6757746c1e7fffbe to your computer and use it in GitHub Desktop.
Save kdgerona/2472f41fd58a273a6757746c1e7fffbe to your computer and use it in GitHub Desktop.
Generated by XState Viz: https://xstate.js.org/viz
// GenerateWorkers
const worker_data = [
{worker_id: 0},
{worker_id: 1},
{worker_id: 2},
]
const workers_config = worker_data.reduce((acc, curr) => {
const { worker_id } = curr
return {
...acc,
[`worker${worker_id}`]: {
id: `worker${worker_id}`,
initial: 'initialization',
states: {
initialization: {
on: {
[`CONNECT_TO_TRACKER${worker_id}`]: 'ready',
[`CONNECT_FAILED${worker_id}`]: 'reconnect',
}
},
ready: {
entry: `workerReady${worker_id}`,
on: {
[`USER_REQUEST_WORKER${worker_id}`]: {
// actions: `processTask${worker_id}`,
actions: () => console.log('im there'),
target: 'processing'
}
}
},
processing: {
entry: `acknowledgement${worker_id}`,
on: {
[`SUM_DIGITS${worker_id}`]: {
actions: [`sumDigits${worker_id}`]
}
}
// initial: 'checkingUser',
// onDone: 'ready',
// states: {
// checkingUser: {
// after: {
// 3000: 'validating'
// },
// actions: 'checkingUser'
// },
// validating: {
// after: {
// 3000: 'done'
// },
// actions: 'validating'
// },
// done: {
// type: 'final'
// }
// }
},
reconnect: {
after: {
3000: 'initialization'
}
}
}
},
}
},{})
const workerImplementations = worker_data.reduce((acc, curr) => {
const { services, actions, delays, guards, activities} = acc
const { worker_id } = curr
return {
services: {...services},
actions: {
...actions,
[`workerReady${worker_id}`]: send({
type: 'WORKER_READY',
payload: {
worker_data: curr
}
}),
[`acknowledgement${worker_id}`]: send('TASK_ACKNOWLEDGED'),
[`processTask${worker_id}`]: send((_,event) => ({
type: `SUM_DIGITS${worker_id}`,
payload: event.payload
}
)),
[`sumDigits${worker_id}`]: (context, event) => console.log('Task', event)
},
delays: {...delays},
guards: {...guards},
activities: {...activities},
}
},{})
// END
const machineContext = {
fibonacci: 10,
first: 0,
second: 1,
task_queue: [],
enqueue: 0,
dequeue: 0,
worker_list: [],
}
// ** Fibonacci **
const fibonacciConfig = {
initial: 'idle',
states: {
idle: {
on: {
START: {
target: 'processing',
// actions: ['startScheduler']
}
}
},
processing: {
invoke: {
src: 'fibonacciCalculation'
},
on: {
UPDATE_FIBONACCI: {
target: 'fibonacciChecker',
actions: ['updateFibonacci', 'startScheduler']
}
}
},
fibonacciChecker: {
on: {
"": [
{
target: 'idle',
cond: 'fibonacciHasReachedMax',
actions: ['resetFibonacci']
},
{
target: 'processing',
}
]
}
},
}
}
const fibonacciImplementation = {
actions: {
updateFibonacci: assign((context, { payload }) => {
return {
fibonacci: payload.fibonacci,
first: payload.first,
second: payload.second,
task_queue: [...context.task_queue, [payload.first,payload.second]],
enqueue: context.enqueue + 1,
}
}
),
resetFibonacci: assign({
fibonacci: 10,
first: 0,
second: 1,
}),
startScheduler: send('START_TASK_SCHEDULING'),
},
guards: {
fibonacciHasReachedMax: (context) => context.fibonacci <= 0
},
services: {
fibonacciCalculation: (context) => (send) => {
const { fibonacci, first, second } = context
const [newFirst, newSecond] = [second, first + second]
console.log('** hi',context)
send({
type: 'UPDATE_FIBONACCI',
payload: {
fibonacci: fibonacci - 1,
first: newFirst,
second: newSecond,
}
})
}
},
activities: {},
delays: {}
}
// ** Scheduler **
const schedulerConfig = {
initial: 'idle',
states: {
idle: {
on: {
'START_TASK_SCHEDULING': 'check'
}
},
check: {
on: {
"": [
{
target: 'distribute',
cond: 'hasEnqueueAndWorkers'
},
{
target: 'idle'
}
]
}
},
distribute: {
invoke: {
src: 'workerTaskDistribution'
},
on: {
TASK_DISTRIBUTED: {
target: 'check',
actions: ['dequeueTask']
}
}
}
}
}
const schedulerImplementation = {
actions: {
dequeueTask: assign({
dequeue: (context) => context.dequeue + 1
})
},
guards: {
hasEnqueueAndWorkers: (context) => context.enqueue > context.dequeue && context.worker_list.length,
},
services: {
workerTaskDistribution: (context) => (send) => {
const { dequeue, task_queue, worker_list } = context
console.log('distributing....')
const worker = worker_list.shift()
console.log(`USER_REQUEST_WORKER${worker.worker_id}`)
// send({
// type: `USER_REQUEST_WORKER${worker.worker_id}`,
// payload: {
// task: task_queue[dequeue]
// }
// })
send(`USER_REQUEST_WORKER0`)
send('TASK_DISTRIBUTED')
}
},
activities: {},
delays: {}
}
// ** Tracker **
const trackerConfig = {
initial: 'listeningForWorkers',
states: {
listeningForWorkers: {
on: {
WORKER_READY: {
actions: ['assignToWorkerList']
}
}
}
}
}
const trackerImplementations = {
actions: {
assignToWorkerList: assign({
worker_list: (context, { payload }) => [...context.worker_list, payload.worker_data]
})
},
guards: {},
services: {},
activities: {},
delays: {},
}
// ** Machine **
const machineConfig = {
id: 'machine',
context: machineContext,
type: 'parallel',
states: {
fibonacci: {
...fibonacciConfig
},
scheduler: {
...schedulerConfig
},
tracker: {
...trackerConfig
},
workers: {
id: 'workers',
type: 'parallel',
states: {
...workers_config
}
}
},
on: {
'START_MACHINE': {
actions: ['startMachine']
},
'START_FIBONACCI': {
actions: ['startFibonacci']
}
}
}
const machineImplementation = {
actions: {
...fibonacciImplementation.actions,
...schedulerImplementation.actions,
...trackerImplementations.actions,
...workerImplementations.actions,
startMachine: send('START_TASK_SCHEDULING'),
startFibonacci: send('START')
},
guards: {
...fibonacciImplementation.guards,
...schedulerImplementation.guards,
...trackerImplementations.guards,
...workerImplementations.guards,
},
services: {
...fibonacciImplementation.services,
...schedulerImplementation.services,
...trackerImplementations.services,
...workerImplementations.services,
},
activities: {
...fibonacciImplementation.activities,
...schedulerImplementation.activities,
...trackerImplementations.activities,
...workerImplementations.activities,
},
delays: {
...fibonacciImplementation.delays,
...schedulerImplementation.delays,
...trackerImplementations.delays,
...workerImplementations.delays,
}
}
const machine = Machine(machineConfig, machineImplementation)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment