Add explicit CM dependencies
[ta/config-manager.git] / cmframework / src / cmframework / server / cmserver.py
1 #! /usr/bin/python2
2
3 # Copyright 2019 Nokia
4
5 # Licensed under the Apache License, Version 2.0 (the "License");
6 # you may not use this file except in compliance with the License.
7 # You may obtain a copy of the License at
8 #
9 #     http://www.apache.org/licenses/LICENSE-2.0
10 #
11 # Unless required by applicable law or agreed to in writing, software
12 # distributed under the License is distributed on an "AS IS" BASIS,
13 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 # See the License for the specific language governing permissions and
15 # limitations under the License.
16
17 import eventlet  # noqa
18 from eventlet import wsgi  # noqa
19 eventlet.monkey_patch()  # noqa
20 import os
21 import json
22 import sys
23 import logging
24 import traceback
25
26 import ConfigParser
27 from cmframework.utils import cmbackendpluginclient
28 from cmframework.utils import cmlogger
29 from cmframework.utils import cmbackendhandler
30 from cmframework.utils import cmactivationstatehandler
31 from cmframework.utils import cmalarmhandler
32 from cmframework.utils import cmsnapshothandler
33 from cmframework.server import cmargs
34 from cmframework.server import cmprocessor
35 from cmframework.server import cmrestapifactory
36 from cmframework.server import cmwsgihandler
37 from cmframework.server import cmvalidator
38 from cmframework.server import cmactivator
39 from cmframework.server import cmactivateserverhandler
40 from cmframework.server import cmchangemonitor
41 from cmframework.utils.cmansibleinventory import AnsibleInventory
42
43
44 def main():
45     try:
46         # parse the arguments
47         parser = cmargs.CMArgsParser('cmserver')
48         parser.parse(sys.argv[1:])
49
50         # Read configuration names which should be masked in logging
51         mask_names = _read_maskable_names()
52
53         # initialize the logger
54         _ = cmlogger.CMLogger(parser.get_log_dest(),
55                               parser.get_verbose(),
56                               parser.get_log_level(),
57                               mask_names)
58
59         logging.info('CM server is starting up')
60
61         # initialize the change monitor object
62         changemonitor = cmchangemonitor.CMChangeMonitor()
63
64         # load backend plugin
65         logging.info('Initializing backend handler')
66         backend_args = {}
67         backend_args['uri'] = parser.get_backend_uri()
68         backend = cmbackendhandler.CMBackendHandler(parser.get_backend_api(), **backend_args)
69
70         # construct the plugin client library
71         logging.info('Initialize plugin client library')
72         plugin_client = cmbackendpluginclient.CMBackendPluginClient(parser.get_backend_api(),
73                                                                     **backend_args)
74
75         # load activation state handler
76         logging.info('Initializing activation state handler')
77         activationstatehandler_args = {}
78         activationstatehandler_args['uri'] = parser.get_activationstate_handler_uri()
79         activationstate_handler = cmactivationstatehandler.CMActivationStateHandler(
80             parser.get_activationstate_handler_api(), **activationstatehandler_args)
81
82         # initialize validator
83         logging.info('Initializing validator')
84         validator = cmvalidator.CMValidator(parser.get_validators(), plugin_client)
85
86         # initializing activation handling process
87         logging.info('Initializing activator')
88         activator = cmactivator.CMActivator(parser.get_activator_workers())
89
90         # initialize activator rmq handler
91         if not parser.get_disable_remote_activation():
92             from cmframework.server import cmactivatermqhandler
93             logging.info('Initializing activator rmq handler')
94             activatermqhandler = cmactivatermqhandler.CMActivateRMQHandler(parser.get_rmq_ip(),
95                                                                            parser.get_rmq_port())
96             activator.add_handler(activatermqhandler)
97
98         # initialize activator server handler
99         logging.info('Initializing activator server handler')
100         activateserverhandler = cmactivateserverhandler.CMActivateServerHandler(
101             parser.get_activators(), plugin_client, changemonitor, activationstate_handler)
102         activator.add_handler(activateserverhandler)
103
104         # starting activator
105         logging.info('Starting activation handling process')
106         activator.start()
107
108         # start alarm handler
109         logging.info('Starting alarm handler process')
110         alarmhandler = cmalarmhandler.AlarmHandler()
111         alarmhandler.set_library_impl(parser.get_alarmhandler_api())
112         alarmhandler.start()
113
114         # load snapshot handler
115         logging.info('Initializing snapshot handler')
116         snapshothandler_args = {}
117         snapshothandler_args['uri'] = parser.get_snapshot_handler_uri()
118         snapshot_handler = cmsnapshothandler.CMSnapshotHandler(
119             parser.get_snapshot_handler_api(), **snapshothandler_args)
120
121         # initialize processor
122         logging.info('Initializing CM processor')
123         processor = cmprocessor.CMProcessor(backend,
124                                             validator,
125                                             activator,
126                                             changemonitor,
127                                             activationstate_handler,
128                                             snapshot_handler)
129
130         if not parser.is_install_phase():
131             # generate inventory file
132             logging.info('Generate inventory file')
133             properties = backend.get_properties('.*')
134             inventory = AnsibleInventory(properties, parser.get_inventory_handlers())
135             inventory_data = inventory.generate_inventory()
136             with open(parser.get_inventory_data(), 'w') as inventory_file:
137                 inventory_file.write(json.dumps(inventory_data, indent=4, sort_keys=True))
138
139             # publish full activate request to on-line activators
140             logging.info('Ask on-line activators to full translate')
141             processor.activate(startup_activation=True)
142
143             # remove inventory file
144             logging.info('Remove inventory file')
145             try:
146                 os.remove(parser.get_inventory_data())
147             except OSError:
148                 pass
149
150         # initialize rest api factory
151         logging.info('Initializing REST API factory')
152         base_url = 'http://' + parser.get_ip() + ':' + \
153                    str(parser.get_port()) + '/cm/'
154         rest_api_factory = cmrestapifactory.CMRestAPIFactory(processor, base_url)
155
156         # initialize wsgi handler
157         logging.info('Initializing the WSGI handler')
158         wsgihandler = cmwsgihandler.CMWSGIHandler(rest_api_factory)
159
160         # start the http server
161         logging.info('Start listening to http requests')
162         wsgi.server(eventlet.listen((parser.get_ip(), parser.get_port())), wsgihandler)
163     except KeyboardInterrupt as exp:
164         logging.info('CM server shutting down')
165         return 0
166     except Exception as exp:  # pylint: disable=broad-except
167         logging.error('Got exception %s', str(exp))
168         traceback.print_exc()
169         return 1
170
171
172 def _read_maskable_names():
173     MASK_DIR = '/etc/cmframework/masks.d/'
174     all_names = []
175     filenames = [MASK_DIR + f for f in os.listdir(MASK_DIR)]
176     for filename in filenames:
177         config = ConfigParser.SafeConfigParser()
178         config.read(filename)
179         names = json.loads(config.get('Passwords', 'names'))
180         all_names.extend(names)
181     return all_names
182
183
184 if __name__ == "__main__":
185     sys.exit(main())