Passed
Pull Request — master (#348)
by
unknown
02:35
created

ProgramStateMachineTypeClass.SuspendedToReady()   A

Complexity

Conditions 1

Size

Total Lines 21
Code Lines 14

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 14
nop 1
dl 0
loc 21
rs 9.7
c 0
b 0
f 0
1
'''
2
https://reference.opcfoundation.org/v104/Core/docs/Part10/
3
https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.1/
4
5
Basic statemachines described in OPC UA Spec.:
6
StateMachineType
7
FiniteStateMachineType
8
ExclusiveLimitStateMachineType
9
FileTransferStateMachineType
10
ProgramStateMachineType
11
ShelvedStateMachineType
12
13
Relevant information:
14
Overview - https://reference.opcfoundation.org/v104/Core/docs/Part10/5.2.3/#5.2.3.1
15
States - https://reference.opcfoundation.org/v104/Core/docs/Part10/5.2.3/#5.2.3.2
16
Transitions - https://reference.opcfoundation.org/v104/Core/docs/Part10/5.2.3/#5.2.3.3
17
Events - https://reference.opcfoundation.org/v104/Core/docs/Part10/5.2.5/
18
'''
19
import asyncio, logging
20
21
#FIXME 
22
# -change to relativ imports!
23
# -remove unused imports
24
from asyncua import Server, ua, Node
25
from asyncua.common.event_objects import TransitionEvent, ProgramTransitionEvent
26
27
_logger = logging.getLogger(__name__)
28
29
class StateTypeClass(object):
30
    _count = 0
31
    def __init__(self, name, node=None, auto_id=True):
32
        self.name = name
33
        self.node = node
34
        if auto_id:
35
            self._id = type(self)._count + 1 #according to the specs a unique number for each state
36
            type(self)._count = self._id
37
            return
38
        self._id = 0
39
    
40
    def set_id(self, id):
41
        self._id = id
42
43
class TransitionTypeClass(object):
44
    _count = 0
45
    def __init__(self, name, node=None, auto_id=True):
46
        self.name = name
47
        self.node = node
48
        if auto_id:
49
            self._id = type(self)._count + 1  #according to the specs a unique number for each transition
50
            type(self)._count = self._id
51
            return
52
        self._id = 0
53
    
54
    def set_id(self, id):
55
        self._id = id
56
57
class StateMachineTypeClass(object):
58
    '''
59
    Implementation of an StateMachineType (most basic type)
60
    '''
61
    def __init__(self, server=None, parent=None, idx=None, name=None):
62
        if not isinstance(server, Server): 
63
            raise ValueError
64
        if not isinstance(parent, Node): 
65
            raise ValueError
66
        if idx == None:
67
            idx = parent.nodeid.NamespaceIndex
68
        if name == None:
69
            name = "StateMachine"
70
        self.locale = "en-US"
71
        self._server = server
72
        self._parent = parent
73
        self._state_machine_node = None
74
        self._state_machine_type = ua.NodeId(2299, 0) #StateMachineType
75
        self._name = name
76
        self._idx = idx
77
        self._optionals = False
78
        self._current_state_node = None
79
        self._current_state_id_node = None
80
        self._last_transition_node = None
81
        self._last_transition_id_node = None
82
        self._evgen = None
83
        self.evtype = TransitionEvent()
84
85
    async def install(self, optionals=False):
86
        '''
87
        setup adressspace
88
        '''
89
        self._optionals = optionals
90
        self._state_machine_node = await self._parent.add_object(
91
            self._idx, 
92
            self._name, 
93
            objecttype=self._state_machine_type, 
94
            instantiate_optional=optionals
95
            )
96
        await self.init(self._state_machine_node)
97
    
98
    async def init(self, statemachine):
99
        '''
100
        initialize subnodes
101
        '''
102
        #FIXME check for childrens typdefinitions which matches statemachine
103
        self._current_state_node = await statemachine.get_child(["CurrentState"])
104
        self._current_state_id_node = await statemachine.get_child(["CurrentState","Id"])
105
        if self._optionals:
106
            self._last_transition_node = await statemachine.get_child(["LastTransition"])
107
            self._last_transition_id_node = await statemachine.get_child(["LastTransition","Id"])
108
        self._evgen = await self._server.get_event_generator(self.evtype, self._state_machine_node)
109
110
    async def change_state(
111
        self, 
112
        state, 
113
        transition=None, 
114
        event_msg=None,
115
        severity=500
116
        ):
117
        '''
118
        method to change the state of the statemachine
119
        state (type StateTypeClass mandatory)
120
        transition (type TransitionTypeClass optional)
121
        event_msg (type string optional)
122
        severity (type Int optional)
123
        '''
124
        #FIXME check StateType exist
125
        #FIXME check TransitionTypeType exist
126
        await self._write_state(state)
127
        if transition:
128
            await self._write_transition(transition)
129
        if event_msg:
130
            if isinstance(event_msg, (type(""))):
131
                event_msg = ua.LocalizedText(event_msg, self.locale)
132
            self._evgen.event.Message = event_msg
133
            self._evgen.event.Severity = severity
134
            await self._evgen.trigger()
135
136
    async def _write_state(self, state):
137
        await self._current_state_node.write_value(ua.LocalizedText(state.name, self.locale))
138
        if state.node:
139
            await self._current_state_id_node.write_value(state.node.nodeid)
140
141
    async def _write_transition(self, transition):
142
        await self._last_transition_node.write_value(ua.LocalizedText(transition.name, self.locale))
143
        if transition.node:
144
            await self._last_transition_id_node.write_value(transition.node.nodeid)
145
    
146
    async def add_state(self, state, state_type=ua.NodeId(2307, 0), optionals=False):
147
        '''
148
        state: StateTypeClass
149
        InitialStateType: ua.NodeId(2309, 0)
150
        StateType: ua.NodeId(2307, 0)
151
        ChoiceStateType: ua.NodeId(15109,0)
152
        '''
153
        if not isinstance(state, StateTypeClass):
154
            raise ValueError
155
        state.node = await self._state_machine_node.add_object(
156
            self._idx, 
157
            state.name, 
158
            objecttype=state_type, 
159
            instantiate_optional=optionals
160
            )
161
        state_number = await state.node.get_child(["StateNumber"])
162
        await state_number.write_value(state._id, ua.VariantType.UInt32)
163
        return state.node
164
165
    async def add_transition(self, transition, transition_type=ua.NodeId(2310, 0), optionals=False):
166
        '''
167
        transition: TransitionTypeClass
168
        transition_type: ua.NodeId(2310, 0)
169
        '''
170
        if not isinstance(transition, TransitionTypeClass):
171
            raise ValueError
172
        transition.node = await self._state_machine_node.add_object(
173
            self._idx, 
174
            transition.name, 
175
            objecttype=transition_type, 
176
            instantiate_optional=optionals
177
            )
178
        transition_number = await transition.node.get_child(["TransitionNumber"])
179
        await transition_number.write_value(transition._id, ua.VariantType.UInt32)
180
        return transition.node
181
182
    async def remove(self, nodes):
183
        #FIXME
184
        raise NotImplementedError
185
186
class FiniteStateMachineTypeClass(StateMachineTypeClass):
187
    '''
188
    Implementation of an FiniteStateMachineType a little more advanced than the basic one
189
    if you need to know the avalible states and transition from clientside
190
    '''
191
    def __init__(self, server=None, parent=None, idx=None, name=None):
192
        super().__init__(server, parent, idx, name)
193
        if name == None:
194
            name = "FiniteStateMachine"
195
        self._state_machine_type = ua.NodeId(2771, 0)
196
        self._avalible_states_node = None
197
        self._avalible_transitions_node = None
198
199
    async def install(self, optionals=False):
200
        '''
201
        setup adressspace and initialize 
202
        '''
203
        self._optionals = optionals
204
        self._state_machine_node = await self._parent.add_object(
205
            self._idx, 
206
            self._name, 
207
            objecttype=self._state_machine_type, 
208
            instantiate_optional=optionals
209
            )
210
211
    async def init(self, avalible_states, avalible_transitions, ):
212
        #FIXME get children and map children
213
        #await self.find_all_states()
214
        await self.set_avalible_states(avalible_states)
215
        #await self.find_all_transitions()
216
        await self.set_avalible_transitions(avalible_transitions)
217
218
    async def set_avalible_states(self, states):
219
        #check if its list
220
        await self._avalible_states_node.write_value(states, varianttype=ua.VariantType.NodeId)
221
222
    async def set_avalible_transitions(self, transitions):
223
        #check if its list
224
        await self._avalible_transitions_node.write_value(transitions, varianttype=ua.VariantType.NodeId)
225
226
    async def find_all_states(self):
227
        return NotImplementedError
228
    
229
    async def find_all_transitions(self):
230
        return NotImplementedError
231
232
class ExclusiveLimitStateMachineTypeClass(FiniteStateMachineTypeClass):
233
    '''
234
    NOT IMPLEMENTED "ExclusiveLimitStateMachineType"
235
    '''
236
    def __init__(self, server=None, parent=None, idx=None, name=None):
237
        super().__init__(server, parent, idx, name)
238
        if name == None:
239
            name = "ExclusiveLimitStateMachine"
240
        self._state_machine_type = ua.NodeId(9318, 0)
241
        raise NotImplementedError
242
243
class FileTransferStateMachineTypeClass(FiniteStateMachineTypeClass):
244
    '''
245
    NOT IMPLEMENTED "FileTransferStateMachineType"
246
    '''
247
    def __init__(self, server=None, parent=None, idx=None, name=None):
248
        super().__init__(server, parent, idx, name)
249
        if name == None:
250
            name = "FileTransferStateMachine"
251
        self._state_machine_type = ua.NodeId(15803, 0)
252
        raise NotImplementedError
253
254
class ProgramStateMachineTypeClass(FiniteStateMachineTypeClass):
255
    '''
256
    https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.3/
257
    Implementation of an ProgramStateMachine its quite a complex statemachine with the 
258
    optional possibility to make the statchange from clientside via opcua-methods
259
    '''
260
    def __init__(self, server=None, parent=None, idx=None, name=None):
261
        super().__init__(server, parent, idx, name)
262
        if name == None:
263
            name = "ProgramStateMachine"
264
        self._state_machine_type = ua.NodeId(2391, 0)
265
        self.evtype = ProgramTransitionEvent()
266
267
        # 5.2.3.2 ProgramStateMachineType states
268
        self._ready_state_node = None #State node
269
        self._halted_state_node = None #State node
270
        self._running_state_node = None #State node
271
        self._suspended_state_node = None #State node
272
273
        # 5.2.3.3 ProgramStateMachineType transitions
274
        self._halted_to_ready_node = None #Transition node
275
        self._ready_to_running_node = None #Transition node
276
        self._running_to_halted_node = None #Transition node
277
        self._running_to_ready_node = None #Transition node
278
        self._running_to_suspended_node = None #Transition node
279
        self._suspended_to_running_node = None #Transition node
280
        self._suspended_to_halted_node = None #Transition node
281
        self._suspended_to_ready_node = None #Transition node
282
        self._ready_to_halted_node = None #Transition node
283
284
        # 5.2.3.2 ProgramStateMachineType states
285
        self._halted_state_id_node = None #State property (StateNumber value 11)
286
        self._ready_state_id_node = None #State property (StateNumber value 12)
287
        self._running_state_id_node = None #State property (StateNumber value 13)
288
        self._suspended_state_id_node = None #State property (StateNumber value 14)
289
290
        # 5.2.3.3 ProgramStateMachineType transitions
291
        self._halted_to_ready_id_node = None #Transition property (TransitionNumber value 1)
292
        self._ready_to_running_id_node = None #Transition property (TransitionNumber value 2)
293
        self._running_to_halted_id_node = None #Transition property (TransitionNumber value 3)
294
        self._running_to_ready_id_node = None #Transition property (TransitionNumber value 4)
295
        self._running_to_suspended_id_node = None #Transition property (TransitionNumber value 5)
296
        self._suspended_to_running_id_node = None #Transition property (TransitionNumber value 6)
297
        self._suspended_to_halted_id_node = None #Transition property (TransitionNumber value 7)
298
        self._suspended_to_ready_id_node = None #Transition property (TransitionNumber value 8)
299
        self._ready_to_halted_id_node = None #Transition property (TransitionNumber value 9)
300
301
        # 4.2.7 Program Control Methods (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.7/)
302
        self._halt_method_node = None #uamethod node
303
        self._reset_method_node = None #uamethod node
304
        self._resume_method_node = None #uamethod node
305
        self._start_method_node = None #uamethod node
306
        self._suspend_method_node = None #uamethod node
307
308
        #can be overwritten if you want a different language
309
        self.localizedtext_ready = ua.LocalizedText("Ready", "en-US")
310
        self.localizedtext_running = ua.LocalizedText("Running", "en-US")
311
        self.localizedtext_halted = ua.LocalizedText("Halted", "en-US")
312
        self.localizedtext_suspended= ua.LocalizedText("Suspended", "en-US")
313
        self.localizedtext_halted_to_ready = ua.LocalizedText("HaltedToReady", "en-US")
314
        self.localizedtext_ready_to_running = ua.LocalizedText("ReadyToRunning", "en-US")
315
        self.localizedtext_running_to_halted = ua.LocalizedText("RunningToHalted", "en-US")
316
        self.localizedtext_running_to_ready = ua.LocalizedText("RunningToReady", "en-US")
317
        self.localizedtext_running_to_suspended = ua.LocalizedText("RunningToSuspended", "en-US")
318
        self.localizedtext_suspended_to_running = ua.LocalizedText("SuspendedToRunning", "en-US")
319
        self.localizedtext_suspended_to_halted = ua.LocalizedText("SuspendedToHalted", "en-US")
320
        self.localizedtext_suspended_to_ready = ua.LocalizedText("SuspendedToReady", "en-US")
321
        self.localizedtext_ready_to_halted = ua.LocalizedText("ReadyToHalted", "en-US")
322
323
    async def install(self, optionals=False):
324
        '''
325
        setup adressspace and initialize 
326
        '''
327
        self._optionals = optionals
328
        self._state_machine_node = await self._parent.add_object(
329
            self._idx, 
330
            self._name, 
331
            objecttype=self._state_machine_type, 
332
            instantiate_optional=optionals
333
            )
334
        #FIXME get children and map children
335
336
    #Transition
337
    async def HaltedToReady(self):
338
        await self._current_state.write_value(
339
            self.localizedtext_ready,
340
            varianttype=ua.VariantType.LocalizedText
341
            ) 
342
        await self._current_state_id.write_value(
343
            self._ready_state.nodeid, 
344
            varianttype=ua.VariantType.NodeId
345
            )
346
        await self._last_transition.write_value(
347
            self.localizedtext_halted_to_ready,
348
            varianttype=ua.VariantType.LocalizedText
349
            ) 
350
        await self._last_transition_id.write_value(
351
            self._halted_to_ready.nodeid,
352
            varianttype=ua.VariantType.NodeId
353
            )
354
        #FIXME 
355
        # trigger ProgramTransitionEventType and 
356
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
357
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
358
359
    #Transition
360
    async def ReadyToRunning(self):
361
        await self._current_state.write_value(
362
            self.localizedtext_running,
363
            varianttype=ua.VariantType.LocalizedText
364
            ) 
365
        await self._current_state_id.write_value(
366
            self._running_state.nodeid, 
367
            varianttype=ua.VariantType.NodeId
368
            )
369
        await self._last_transition.write_value(
370
            self.localizedtext_ready_to_running,
371
            varianttype=ua.VariantType.LocalizedText
372
            ) 
373
        await self._last_transition_id.write_value(
374
            self._ready_to_running.nodeid, 
375
            varianttype=ua.VariantType.NodeId
376
            )
377
        #FIXME 
378
        # trigger ProgramTransitionEventType and 
379
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
380
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
381
382
    #Transition
383
    async def RunningToHalted(self):
384
        await self._current_state.write_value(
385
            self.localizedtext_halted,
386
            varianttype=ua.VariantType.LocalizedText
387
            ) 
388
        await self._current_state_id.write_value(
389
            self._halted_state.nodeid, 
390
            varianttype=ua.VariantType.NodeId
391
            )
392
        await self._last_transition.write_value(
393
            self.localizedtext_running_to_halted,
394
            varianttype=ua.VariantType.LocalizedText
395
            ) 
396
        await self._last_transition_id.write_value(
397
            self._running_to_halted.nodeid, 
398
            varianttype=ua.VariantType.NodeId
399
            )
400
        #FIXME 
401
        # trigger ProgramTransitionEventType and 
402
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
403
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
404
405
    #Transition
406
    async def RunningToReady(self):
407
        await self._current_state.write_value(
408
            self.localizedtext_ready,
409
            varianttype=ua.VariantType.LocalizedText
410
            ) 
411
        await self._current_state_id.write_value(
412
            self._ready_state.nodeid, 
413
            varianttype=ua.VariantType.NodeId
414
            )
415
        await self._last_transition.write_value(
416
            self.localizedtext_running_to_ready,
417
            varianttype=ua.VariantType.LocalizedText
418
            ) 
419
        await self._last_transition_id.write_value(
420
            self._running_to_ready.nodeid, 
421
            varianttype=ua.VariantType.NodeId
422
            )
423
        #FIXME 
424
        # trigger ProgramTransitionEventType and 
425
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
426
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
427
428
    #Transition
429
    async def RunningToSuspended(self):
430
        await self._current_state.write_value(
431
            self.localizedtext_suspended,
432
            varianttype=ua.VariantType.LocalizedText
433
            ) 
434
        await self._current_state_id.write_value(
435
            self._suspended_state.nodeid, 
436
            varianttype=ua.VariantType.NodeId
437
            )
438
        await self._last_transition.write_value(
439
            self.localizedtext_running_to_suspended,
440
            varianttype=ua.VariantType.LocalizedText
441
            ) 
442
        await self._last_transition_id.write_value(
443
            self._running_to_suspended.nodeid, 
444
            varianttype=ua.VariantType.NodeId
445
            )
446
        #FIXME 
447
        # trigger ProgramTransitionEventType and 
448
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
449
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
450
451
    #Transition 
452
    async def SuspendedToRunning(self):
453
        await self._current_state.write_value(
454
            self.localizedtext_running,
455
            varianttype=ua.VariantType.LocalizedText
456
            ) 
457
        await self._current_state_id.write_value(
458
            self._running_state.nodeid, 
459
            varianttype=ua.VariantType.NodeId
460
            )
461
        await self._last_transition.write_value(
462
            self.localizedtext_suspended_to_running,
463
            varianttype=ua.VariantType.LocalizedText
464
            )
465
        await self._last_transition_id.write_value(
466
            self._suspended_to_running.nodeid, 
467
            varianttype=ua.VariantType.NodeId
468
            )
469
        #FIXME 
470
        # trigger ProgramTransitionEventType and 
471
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
472
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
473
474
    #Transition
475
    async def SuspendedToHalted(self):
476
        await self._current_state.write_value(
477
            self.localizedtext_halted,
478
            varianttype=ua.VariantType.LocalizedText
479
            ) 
480
        await self._current_state_id.write_value(
481
            self._halted_state.nodeid, 
482
            varianttype=ua.VariantType.NodeId
483
            )
484
        await self._last_transition.write_value(
485
            self.localizedtext_suspended_to_halted,
486
            varianttype=ua.VariantType.LocalizedText
487
            ) 
488
        await self._last_transition_id.write_value(
489
            self._suspended_to_halted.nodeid, 
490
            varianttype=ua.VariantType.NodeId
491
            )
492
        #FIXME 
493
        # trigger ProgramTransitionEventType and 
494
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
495
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
496
497
    #Transition
498
    async def SuspendedToReady(self):
499
        await self._current_state.write_value(
500
            self.localizedtext_ready,
501
            varianttype=ua.VariantType.LocalizedText
502
            ) 
503
        await self._current_state_id.write_value(
504
            self._ready_state.nodeid, 
505
            varianttype=ua.VariantType.NodeId
506
            )
507
        await self._last_transition.write_value(
508
            self.localizedtext_suspended_to_ready,
509
            varianttype=ua.VariantType.LocalizedText
510
            ) 
511
        await self._last_transition_id.write_value(
512
            self._suspended_to_ready.nodeid, 
513
            varianttype=ua.VariantType.NodeId
514
            )
515
        #FIXME 
516
        # trigger ProgramTransitionEventType and 
517
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
518
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
519
520
    #Transition 
521
    async def ReadyToHalted(self):
522
        await self._current_state.write_value(
523
            self.localizedtext_halted,
524
            varianttype=ua.VariantType.LocalizedText
525
            ) 
526
        await self._current_state_id.write_value(
527
            self._halted_state.nodeid, 
528
            varianttype=ua.VariantType.NodeId
529
            )
530
        await self._last_transition.write_value(
531
            self.localizedtext_ready_to_halted,
532
            varianttype=ua.VariantType.LocalizedText
533
            ) 
534
        await self._last_transition_id.write_value(
535
            self._ready_to_halted.nodeid, 
536
            varianttype=ua.VariantType.NodeId
537
            )
538
        #FIXME 
539
        # trigger ProgramTransitionEventType and 
540
        # AuditUpdateMethodEvents/AuditProgramTransitionEventType (https://reference.opcfoundation.org/v104/Core/docs/Part10/4.2.2/)
541
        return ua.StatusCode(ua.status_codes.StatusCodes.Good)
542
543
    #method to be linked to uamethod
544
    async def Start(self):
545
        if await self._current_state.read_value() == self.localizedtext_ready:
546
            return await ReadyToRunning()
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable ReadyToRunning does not seem to be defined.
Loading history...
547
        else:
548
            return ua.StatusCode(ua.status_codes.StatusCodes.BadNotExecutable)
549
550
    #method to be linked to uamethod
551
    async def Suspend(self):
552
        if await self._current_state.read_value() == self.localizedtext_running:
553
            return await RunningToSuspended()
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable RunningToSuspended does not seem to be defined.
Loading history...
554
        else:
555
            return ua.StatusCode(ua.status_codes.StatusCodes.BadNotExecutable)
556
557
    #method to be linked to uamethod
558
    async def Resume(self):
559
        if await self._current_state.read_value() == self.localizedtext_suspended:
560
            return await SuspendedToRunning()
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable SuspendedToRunning does not seem to be defined.
Loading history...
561
        else:
562
            return ua.StatusCode(ua.status_codes.StatusCodes.BadNotExecutable)
563
564
    #method to be linked to uamethod
565
    async def Halt(self):
566
        if await self._current_state.read_value() == self.localizedtext_ready:
567
            return await ReadyToHalted()
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable ReadyToHalted does not seem to be defined.
Loading history...
568
        elif await self._current_state.read_value() == self.localizedtext_running:
569
            return await RunningToHalted()
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable RunningToHalted does not seem to be defined.
Loading history...
570
        elif await self._current_state.read_value() == self.localizedtext_suspended:
571
            return await SuspendedToHalted()
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable SuspendedToHalted does not seem to be defined.
Loading history...
572
        else:
573
            return ua.StatusCode(ua.status_codes.StatusCodes.BadNotExecutable)
574
575
    #method to be linked to uamethod
576
    async def Reset(self):
577
        if await self._current_state.read_value() == self.localizedtext_halted:
578
            return await HaltedToReady()
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable HaltedToReady does not seem to be defined.
Loading history...
579
        else:
580
            return ua.StatusCode(ua.status_codes.StatusCodes.BadNotExecutable)
581
582
class ShelvedStateMachineTypeClass(FiniteStateMachineTypeClass):
583
    '''
584
    NOT IMPLEMENTED "ShelvedStateMachineType"
585
    '''
586
    def __init__(self, server=None, parent=None, idx=None, name=None):
587
        super().__init__(server, parent, idx, name)
588
        if name == None:
589
            name = "ShelvedStateMachine"
590
        self._state_machine_type = ua.NodeId(2929, 0)
591
        raise NotImplementedError
592
593
594
595
#FIXME REMOVE BEFOR MERGE
596
#Devtest / Workbench
597
if __name__ == "__main__":
598
    async def main():
599
        logging.basicConfig(level=logging.INFO)
600
        _logger = logging.getLogger('asyncua')
601
602
        server = Server()
603
        await server.init()
604
605
        idx = await server.register_namespace("http://testnamespace.org/UA")
606
607
        mystatemachine = StateMachineTypeClass(server, server.nodes.objects, idx, "StateMachine")
608
        await mystatemachine.install(optionals=True)
609
610
        state1 = StateTypeClass("Idle")
611
        await mystatemachine.add_state(state1)
612
        state2 = StateTypeClass("Loading")
613
        await mystatemachine.add_state(state2)
614
        state3 = StateTypeClass("Initializing")
615
        await mystatemachine.add_state(state3)
616
        state4 = StateTypeClass("Processing")
617
        await mystatemachine.add_state(state4)
618
        state5 = StateTypeClass("Finished")
619
        await mystatemachine.add_state(state5)
620
621
        trans1 = TransitionTypeClass("to Idle")
622
        await mystatemachine.add_transition(trans1)
623
        trans2 = TransitionTypeClass("to Loading")
624
        await mystatemachine.add_transition(trans2)
625
        trans3 = TransitionTypeClass("to Initializing")
626
        await mystatemachine.add_transition(trans3)
627
        trans4 = TransitionTypeClass("to Processing")
628
        await mystatemachine.add_transition(trans4)
629
        trans5 = TransitionTypeClass("to Finished")
630
        await mystatemachine.add_transition(trans5)
631
632
        await mystatemachine.change_state(state1, trans1, f"{mystatemachine._name}: Idle", 300)
633
634
635
        async with server:
636
            while 1:
637
                await asyncio.sleep(2)
638
                await mystatemachine.change_state(state2, trans2, f"{mystatemachine._name}: Loading", 350)
639
                await asyncio.sleep(2)
640
                await mystatemachine.change_state(state3, trans3, f"{mystatemachine._name}: Initializing", 400)
641
                await asyncio.sleep(2)
642
                await mystatemachine.change_state(state4, trans4, f"{mystatemachine._name}: Processing", 600)
643
                await asyncio.sleep(2)
644
                await mystatemachine.change_state(state5, trans5, f"{mystatemachine._name}: Finished", 800)
645
                await asyncio.sleep(2)
646
                await mystatemachine.change_state(state1, trans1, f"{mystatemachine._name}: Idle", 500)
647
648
    asyncio.run(main())
649