Exemplo n.º 1
0
    def start(self, dmd, reactor):
        """Start the servers.

        @param dmd {dmd} The dmd reference
        @param reactor {IReactor} Twisted reactor instance
        """
        # Finish initialization
        modeling_paused = ModelingPaused(dmd, self.__modeling_pause_timeout)
        self.__worklist = ZenHubWorklist(modeling_paused=modeling_paused)

        # configure Metrology for the worklists
        register_metrics_on_worklist(self.__worklist)

        self.__workers = WorkerPool()
        self.__stats = StatsMonitor()
        self.__workerdispatcher = WorkerPoolDispatcher(
            reactor, self.__worklist, self.__workers, self.__stats,
        )
        events = EventDispatcher(dmd.ZenEventManager)
        executor = DispatchingExecutor(
            [events], default=self.__workerdispatcher,
        )
        service_factory = WorkerInterceptorFactory(executor)
        self.__services = HubServiceRegistry(dmd, service_factory)

        # Start the Perspective Broker server
        avatar = HubAvatar(self.__services, self.__workers)
        realm = HubRealm(avatar)
        checkers = getCredentialCheckers(self.__passwdfile)
        hubportal = portal.Portal(realm, checkers)
        hubserver_factory = ZenPBServerFactory(hubportal)
        tcp_version = "tcp6" if ipv6_available() else "tcp"
        pb_descriptor = "%s:port=%s" % (tcp_version, self.__pbport)
        pb_server = serverFromString(reactor, pb_descriptor)

        dfr = pb_server.listen(hubserver_factory)
        dfr.addCallback(self.__setKeepAlive)

        # Initialize and start the XMLRPC server
        self.__xmlrpc_site = AuthXmlRpcService.makeSite(dmd, checkers)
        xmlrpc_descriptor = "%s:port=%s" % (tcp_version, self.__xmlrpcport)
        xmlrpc_server = serverFromString(reactor, xmlrpc_descriptor)
        xmlrpc_server.listen(self.__xmlrpc_site)
Exemplo n.º 2
0
    def __init__(self, dmd, instance):
        from Products.ZenHub import ZENHUB_ZENRENDER
        if instance == ZENHUB_ZENRENDER:
            self.dmd = dmd
            self.instance = instance
        else:
            NullConfigService.__init__(self, dmd, instance)

        global htmlResource
        try:
            if not htmlResource:
                htmlResource = Render()
                log.info("Starting graph retrieval listener on port 8090")
                interface = '::' if ipv6_available() else ''
                reactor.listenTCP(8090, server.Site(htmlResource), interface=interface)
            htmlResource.addRenderer(self)
        except CannotListenError, e:
            # Probably in a hub worker; no big deal
            log.debug("Not starting render listener because the port is "
                      "already in use.")
Exemplo n.º 3
0
    def postStartup(self):
        """
        Listen for HTTP requests for RRD data or graphs.
        """
        self._daemon = zope.component.getUtility(ICollector)

        # Start listening for HTTP requests
        httpPort = self. _daemon.options.httpport
        collector = self._daemon.options.monitor
        log.info("Starting %s zenrender webserver on port %s",
                      collector, httpPort)
        renderer = HttpRender(collector)
        interface = '::' if ipv6_available() else ''
        reactor.listenTCP(httpPort, server.Site(renderer), interface=interface)

        # Add remote_ methods from renderer directly to the daemon
        for name in dir(renderer):
            if name.startswith('remote_'):
                func = getattr(renderer, name)
                setattr(self._daemon, name, func)
Exemplo n.º 4
0
    def postStartup(self):
        """
        Listen for HTTP requests for RRD data or graphs.
        """
        self._daemon = zope.component.getUtility(ICollector)

        # Start listening for HTTP requests
        httpPort = self._daemon.options.httpport
        collector = self._daemon.options.monitor
        log.info("Starting %s zenrender webserver on port %s", collector,
                 httpPort)
        renderer = HttpRender(collector)
        interface = '::' if ipv6_available() else ''
        reactor.listenTCP(httpPort, server.Site(renderer), interface=interface)

        # Add remote_ methods from renderer directly to the daemon
        for name in dir(renderer):
            if name.startswith('remote_'):
                func = getattr(renderer, name)
                setattr(self._daemon, name, func)
Exemplo n.º 5
0
    def __init__(self, dmd, instance):
        from Products.ZenHub import ZENHUB_ZENRENDER
        if instance == ZENHUB_ZENRENDER:
            self.dmd = dmd
            self.instance = instance
        else:
            NullConfigService.__init__(self, dmd, instance)

        global htmlResource
        try:
            if not htmlResource:
                htmlResource = Render()
                log.info("Starting graph retrieval listener on port 8090")
                interface = '::' if ipv6_available() else ''
                reactor.listenTCP(8090,
                                  server.Site(htmlResource),
                                  interface=interface)
            htmlResource.addRenderer(self)
        except CannotListenError, e:
            # Probably in a hub worker; no big deal
            log.debug("Not starting render listener because the port is "
                      "already in use.")
Exemplo n.º 6
0
    def __init__(self):
        """
        Hook ourselves up to the Zeo database and wait for collectors
        to connect.
        """
        # list of remote worker references
        self.workers = []
        self.workTracker = {}
        # zenhub execution stats:
        # [count, idle_total, running_total, last_called_time]
        self.executionTimer = collections.defaultdict(lambda: [0, 0.0, 0.0, 0])
        self.workList = _ZenHubWorklist()
        # set of worker processes
        self.worker_processes = set()
        # map of worker pids -> worker processes
        self.workerprocessmap = {}
        self.shutdown = False
        self.counters = collections.Counter()
        self._invalidations_paused = False

        wl = self.workList
        metricNames = {x[0] for x in registry}

        class EventWorkList(Gauge):
            @property
            def value(self):
                return len(wl.eventworklist)

        if 'zenhub.eventWorkList' not in metricNames:
            Metrology.gauge('zenhub.eventWorkList', EventWorkList())

        class ADMWorkList(Gauge):
            @property
            def value(self):
                return len(wl.applyworklist)

        if 'zenhub.admWorkList' not in metricNames:
            Metrology.gauge('zenhub.admWorkList', ADMWorkList())

        class OtherWorkList(Gauge):
            @property
            def value(self):
                return len(wl.otherworklist)

        if 'zenhub.otherWorkList' not in metricNames:
            Metrology.gauge('zenhub.otherWorkList', OtherWorkList())

        class WorkListTotal(Gauge):
            @property
            def value(self):
                return len(wl)

        if 'zenhub.workList' not in metricNames:
            Metrology.gauge('zenhub.workList', WorkListTotal())

        ZCmdBase.__init__(self)
        import Products.ZenHub
        load_config("hub.zcml", Products.ZenHub)
        notify(HubWillBeCreatedEvent(self))

        if self.options.profiling:
            self.profiler = ContinuousProfiler('zenhub', log=self.log)
            self.profiler.start()

        # Worker selection handler
        self.workerselector = WorkerSelector(self.options)
        self.workList.log = self.log

        # make sure we don't reserve more than n-1 workers for events
        maxReservedEventsWorkers = 0
        if self.options.workers:
            maxReservedEventsWorkers = self.options.workers - 1
        if self.options.workersReservedForEvents > maxReservedEventsWorkers:
            self.options.workersReservedForEvents = maxReservedEventsWorkers
            self.log.info(
                "reduced number of workers reserved for sending events to %d",
                self.options.workersReservedForEvents)

        self.zem = self.dmd.ZenEventManager
        loadPlugins(self.dmd)
        self.services = {}

        er = HubRealm(self)
        checker = self.loadChecker()
        pt = portal.Portal(er, [checker])
        interface = '::' if ipv6_available() else ''
        pbport = reactor.listenTCP(self.options.pbport,
                                   pb.PBServerFactory(pt),
                                   interface=interface)
        self.setKeepAlive(pbport.socket)

        xmlsvc = AuthXmlRpcService(self.dmd, checker)
        reactor.listenTCP(self.options.xmlrpcport,
                          server.Site(xmlsvc),
                          interface=interface)

        # responsible for sending messages to the queues
        import Products.ZenMessaging.queuemessaging
        load_config_override('twistedpublisher.zcml',
                             Products.ZenMessaging.queuemessaging)
        notify(HubCreatedEvent(self))
        self.sendEvent(eventClass=App_Start,
                       summary="%s started" % self.name,
                       severity=0)

        self._initialize_invalidation_filters()
        reactor.callLater(self.options.invalidation_poll_interval,
                          self.processQueue)

        self._metric_writer = metricWriter()
        self.rrdStats = self.getRRDStats()

        if self.options.workers:
            self.workerconfig = zenPath(
                'var', 'zenhub', '{}_worker.conf'.format(self._getConf().id))
            self._createWorkerConf()
            for i in range(self.options.workers):
                self.createWorker(i)

            # start cyclic call to giveWorkToWorkers
            reactor.callLater(2, self.giveWorkToWorkers, True)

        # set up SIGUSR2 handling
        try:
            signal.signal(signal.SIGUSR2, self.sighandler_USR2)
        except ValueError:
            # If we get called multiple times, this will generate an exception:
            # ValueError: signal only works in main thread
            # Ignore it as we've already set up the signal handler.
            pass
        # ZEN-26671 Wait at least this duration in secs
        # before signaling a worker process
        self.SIGUSR_TIMEOUT = 5
Exemplo n.º 7
0
 def version(self):
     if self.__version is None:
         self.__version = "tcp6" if ipv6_available() else "tcp"
     return self.__version