Merge from OSM SO master
[osm/SO.git] / rwprojectmano / plugins / rwprojectmano / rift / tasklets / rwprojectmano / tasklet.py
1 #
2 # Copyright 2017 RIFT.IO Inc
3 #
4 # Licensed under the Apache License, Version 2.0 (the "License");
5 # you may not use this file except in compliance with the License.
6 # You may obtain a copy of the License at
7 #
8 # http://www.apache.org/licenses/LICENSE-2.0
9 #
10 # Unless required by applicable law or agreed to in writing, software
11 # distributed under the License is distributed on an "AS IS" BASIS,
12 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 # See the License for the specific language governing permissions and
14 # limitations under the License.
15 #
16
17 """
18 Mano Project Manager tasklet is responsible for managing the Projects
19 configurations required for Role Based Access Control feature.
20 """
21
22 import asyncio
23
24 import gi
25 gi.require_version('RwDts', '1.0')
26 gi.require_version('RwLog', '1.0')
27 gi.require_version('RwProjectYang', '1.0')
28 gi.require_version('RwProjectManoYang', '1.0')
29 from gi.repository import (
30 RwDts as rwdts,
31 RwLog as rwlog,
32 RwProjectYang,
33 RwProjectManoYang,
34 )
35
36 import rift.tasklets
37
38 from rift.mano.utils.project import (
39 ManoProject,
40 )
41
42 from .projectmano import (
43 ProjectHandler,
44 ProjectStateRolePublisher,
45 )
46
47 from .rolesmano import (
48 RoleConfigPublisher,
49 ProjectConfigSubscriber,
50 )
51
52
53 class ProjectMgrManoProject(ManoProject):
54
55 def __init__(self, name, tasklet):
56 super(ProjectMgrManoProject, self).__init__(tasklet.log, name)
57 self.update(tasklet)
58
59 self.project_sub = ProjectConfigSubscriber(self)
60
61 @asyncio.coroutine
62 def register (self):
63 self._log.info("Initializing the ProjectMgrMano for %s", self.name)
64 yield from self.project_sub.register()
65 self.tasklet.project_state_role_pub.publish_roles(self.name)
66
67 def deregister(self):
68 self._log.debug("De-register project %s", self.name)
69 self.tasklet.project_state_role_pub.unpublish_roles(self.name)
70 self.project_sub.deregister()
71
72
73 class ProjectMgrManoTasklet(rift.tasklets.Tasklet):
74 """Tasklet that manages the Project config
75 """
76 def __init__(self, *args, **kwargs):
77 """Constructs a ProjectManager tasklet"""
78 try:
79 super().__init__(*args, **kwargs)
80 self.rwlog.set_category("rw-mano-log")
81
82 self.projects = {}
83
84 except Exception as e:
85 self.log.exception(e)
86
87
88 def start(self):
89 """Callback that gets invoked when a Tasklet is started"""
90 super().start()
91 self.log.info("Starting Mano Project Manager Tasklet")
92
93 self.log.debug("Registering with dts")
94 self.dts = rift.tasklets.DTS(
95 self.tasklet_info,
96 RwProjectManoYang.get_schema(),
97 self.loop,
98 self.on_dts_state_change
99 )
100
101 self.log.debug("Created DTS Api Object: %s", self.dts)
102
103 def stop(self):
104 """Callback that gets invoked when Tasklet is stopped"""
105 try:
106 self.dts.deinit()
107 except Exception as e:
108 self.log.exception(e)
109
110 @asyncio.coroutine
111 def init(self):
112 """DTS Init state handler"""
113 try:
114 self.log.info("Registering for Project Config")
115 self.project_handler = ProjectHandler(self, ProjectMgrManoProject)
116 self.project_handler.register()
117
118 self.project_state_role_pub = ProjectStateRolePublisher(self)
119 yield from self.project_state_role_pub.register()
120
121 except Exception as e:
122 self.log.exception("Registering for project failed: {}".format(e))
123
124 @asyncio.coroutine
125 def run(self):
126 """DTS run state handler"""
127 pass
128
129 @asyncio.coroutine
130 def on_dts_state_change(self, state):
131 """Handle DTS state change
132
133 Take action according to current DTS state to transition application
134 into the corresponding application state
135
136 Arguments
137 state - current dts state
138
139 """
140 switch = {
141 rwdts.State.INIT: rwdts.State.REGN_COMPLETE,
142 rwdts.State.CONFIG: rwdts.State.RUN,
143 }
144
145 handlers = {
146 rwdts.State.INIT: self.init,
147 rwdts.State.RUN: self.run,
148 }
149
150 # Transition application to next state
151 handler = handlers.get(state, None)
152 if handler is not None:
153 yield from handler()
154
155 # Transition dts to next state
156 next_state = switch.get(state, None)
157 if next_state is not None:
158 self.dts.handle.set_state(next_state)
159
160 def config_ready(self):
161 """Subscription is complete and ready to start publishing."""
162 self.log.debug("Configuration Ready")
163
164
165 # vim: ts=4 sw=4 et