Search in sources :

Example 1 with EventChannel

use of org.omg.CosNotifyChannelAdmin.EventChannel in project ACS by ACS-Community.

the class EventModel method discoverChannels.

/**
	 * Checks the naming service for NC instances and stores / updates them under the matching service from {@link #notifyServices}.
	 * It does not query the NCs for consumers etc. though.
	 * <p>
	 * This method is broken out from {@link #discoverNotifyServicesAndChannels(boolean)} to make it more readable. 
	 * It should be called only from there, to keep services and NCs aligned.
	 * 
	 * @param bindingMap Name service bindings in the form key = bindingName, value = bindingKind
	 */
private synchronized void discoverChannels(Map<String, String> bindingMap) {
    // known NC names, used to detect NCs that have disappeared. 
    Set<String> oldNcNames = new HashSet<String>();
    for (NotifyServiceData nsData : notifyServices.values()) {
        for (ChannelData channelData : nsData.getChannels()) {
            oldNcNames.add(channelData.getQualifiedName());
        }
    }
    // with the NC ref coming either from the naming service or perhaps from the notify service directly if we can match ncIDs with the MC data.
    for (String bindingName : bindingMap.keySet()) {
        String bindingKind = bindingMap.get(bindingName);
        if (bindingKind.equals(alma.acscommon.NC_KIND.value)) {
            try {
                String channelName = Helper.extractChannelName(bindingName);
                String domainName = Helper.extractDomainName(bindingName);
                // Check if we already know this NC. 
                ChannelData channelData = getNotifyServicesRoot().findChannel(channelName);
                if (channelData != null) {
                    oldNcNames.remove(channelData.getQualifiedName());
                    channelData.setIsNewNc(false);
                } else {
                    m_logger.fine("New NC '" + channelName + "'.");
                    // A new NC. This will happen at startup, and later as NCs get added.
                    // The NC-to-service mapping is based on conventions and CDB data, implemented in the Helper class from jcontnc.
                    Helper notifyHelper = new Helper(channelName, domainName, cs, nctx);
                    String serviceId = notifyHelper.getNotificationFactoryNameForChannel();
                    NotifyServiceData service = notifyServices.get(serviceId);
                    if (service == null) {
                        // This should never happen because since ACS 12.1 we always auto-discover services as part of refreshing NCs.
                        // We read the service and NC bindings only once from the naming service, which avoids timing issues with NCs visible now
                        // even though their notify service would not have been registered before. 
                        // Just in case we leave this code here, but log it as a warning.
                        discoverNotifyServices(bindingMap);
                        service = notifyServices.get(serviceId);
                        String msg = "Unknown notify service '" + simplifyNotifyServiceName(serviceId) + "' required for NC '" + channelName + "'. ";
                        if (service != null) {
                            m_logger.warning(msg + "Added the new service.");
                        } else {
                            m_logger.warning(msg + "Failed to add the new service.");
                        }
                    }
                    if (service != null) {
                        EventChannel nc = resolveNotificationChannel(bindingName);
                        ChannelData cdata = new ChannelData(nc, channelName, service);
                        cdata.setIsNewNc(true);
                        // The system NCs for logging and monitor point archiving use custom event formats and cannot be subscribed to using the normal NCSubscriber.
                        if (domainName.equals(ACS_NC_DOMAIN_LOGGING.value) || domainName.equals(ACS_NC_DOMAIN_ARCHIVING.value)) {
                            cdata.markUnsubscribable();
                        }
                        service.addChannel(channelName, cdata);
                    }
                }
            } catch (Exception ex) {
                m_logger.log(Level.WARNING, "Failed to map NC '" + bindingName + "' to its notify service.", ex);
            }
        }
    }
    // just in case there are non-standard NCs created by someone without proper naming service bindings. 
    for (NotifyServiceData service : notifyServices.values()) {
        if (!service.isReachable()) {
            // we skip services that were unreachable already before
            continue;
        }
        // First set the missing ncId on new ChannelData objects
        if (!service.getNewChannels().isEmpty()) {
            // check first if we can avoid the get_all_channels() remote call
            int[] ncIds = service.getEventChannelFactory().get_all_channels();
            for (int ncId : ncIds) {
                if (service.getChannelById(ncId) == null) {
                    // our ncId is new... try to find matching known new NC
                    EventChannel newNc = null;
                    try {
                        newNc = service.getEventChannelFactory().get_event_channel(ncId);
                    } catch (ChannelNotFound ex) {
                        // should never happen since we just got this Id from the service
                        ex.printStackTrace();
                    }
                    ChannelData matchedNc = service.getChannelByCorbaRef(newNc);
                    if (matchedNc != null) {
                        if (matchedNc.isNewNc()) {
                            matchedNc.setNcId(ncId);
                            m_logger.fine("Service " + service.getName() + ": Matched ncId=" + ncId + " to new NC '" + matchedNc.getName() + "'.");
                        } else {
                            m_logger.warning("Service " + service.getName() + ": Matched ncId=" + ncId + " to NC '" + matchedNc.getName() + "', but expect this NC to be new, which it isn't.");
                        }
                    } else {
                    // ncId is the Id of a new NC that was not registered in the naming service (unless the corberef-based match failed).
                    // We don't create a ChannelData object yet, because we may get its real name below from the MC.
                    }
                }
            }
        }
        // Then check the service's MC object for new (hopefully named) NCs.
        MCProxy mcProxy = new MCProxy(service, m_logger);
        List<String> ncNamesFromMc = mcProxy.listChannels();
        for (String ncNameFromMc : ncNamesFromMc) {
            if (service.getChannelByName(ncNameFromMc) == null) {
                //     and therefore we get only its integer ID from the MC API. 
                try {
                    // Try if we have an ID instead of a name 
                    // see NumberFormatException catch below
                    int ncId = Integer.parseInt(ncNameFromMc);
                    // see ChannelNotFound catch below
                    service.getEventChannelFactory().get_event_channel(ncId);
                    // The NC was created without TAO extension name. 
                    // Check if we know this NC already from the naming service or from a previous round here.
                    ChannelData channelData = service.getChannelById(ncId);
                    if (channelData == null) {
                        // First time we see this NC. It is not in the naming service and there is nowhere we can get a decent name for it.
                        // We simply use the Id as its name.
                        // If this is a problem, then this NC should be created with TAO extension name, or should be registered in the NS.
                        m_logger.info("Service " + service.getName() + ": Found unnamed NC with ID='" + ncId + "' that is not registered in the naming service.");
                        String newNcName = Integer.toString(ncId);
                        EventChannel unnamedNcCorbaRef = null;
                        try {
                            unnamedNcCorbaRef = service.getEventChannelFactory().get_event_channel(ncId);
                        } catch (ChannelNotFound ex) {
                            // should not happen since we just got the ncId from the service
                            ex.printStackTrace();
                        }
                        ChannelData newNcData = new ChannelData(unnamedNcCorbaRef, Integer.toString(ncId), service);
                        newNcData.markUnsubscribable();
                        newNcData.setIsNewNc(true);
                        newNcData.setNcId(ncId);
                        service.addChannel(newNcName, newNcData);
                    }
                } catch (NumberFormatException ex) {
                    // The name was not an integer, and therefore also for sure not an ID.
                    // This means the NC was created using the TAO extensions, and yet it was not registered in the naming service.
                    m_logger.info("Service " + service.getName() + ": Found NC with name='" + ncNameFromMc + "' that is not registered in the naming service. This case was thought to not exist in practice and is therefore not supported yet by the eventGUI. Please inform ACS.");
                } catch (ChannelNotFound ex) {
                    m_logger.warning("Strange NC '" + service.getName() + "/" + ncNameFromMc + "' reported by MC is not listed in the naming service and has an integer name that is not a channel ID.");
                }
            } else if (!bindingMap.containsKey(ncNameFromMc)) {
                // The NC is not in the naming service, but was added based on MC data in a previous round.
                ChannelData nc = service.getChannelByName(ncNameFromMc);
                nc.setIsNewNc(false);
                oldNcNames.remove(nc.getQualifiedName());
            }
        }
    //			for (String statName : nsData.getMc().get_statistic_names()) {
    //				System.out.println(statName);
    //			}
    }
    if (!oldNcNames.isEmpty()) {
        // TODO: Change this when the eventGUI or other tools offers manual NC destruction
        // Actually it could also be that an additional NotifyService with unused NCs was stopped, but in practice this does not happen.
        m_logger.warning("Lost " + oldNcNames.size() + " NCs, which should not happen as we never destroy an NC even if it no longer gets used: " + StringUtils.join(oldNcNames, ' '));
        for (String oldNcQualifiedName : oldNcNames) {
            String oldNcName = oldNcQualifiedName.substring(oldNcQualifiedName.indexOf('#') + 1);
            NotifyServiceData oldNcService = getNotifyServicesRoot().findHostingService(oldNcName);
            ChannelData oldNcData = oldNcService.getChannelByName(oldNcName);
            closeSelectedConsumer(oldNcData);
            oldNcService.removeChannel(oldNcName);
        }
    }
}
Also used : AcsJException(alma.acs.exceptions.AcsJException) NamingContextHelper(org.omg.CosNaming.NamingContextHelper) Helper(alma.acs.nc.Helper) EventChannelHelper(org.omg.CosNotifyChannelAdmin.EventChannelHelper) DynAnyFactoryHelper(org.omg.DynamicAny.DynAnyFactoryHelper) NotificationServiceMonitorControlHelper(gov.sandia.CosNotification.NotificationServiceMonitorControlHelper) EventChannelFactoryHelper(org.omg.CosNotifyChannelAdmin.EventChannelFactoryHelper) EventChannel(org.omg.CosNotifyChannelAdmin.EventChannel) ChannelNotFound(org.omg.CosNotifyChannelAdmin.ChannelNotFound) HashSet(java.util.HashSet)

Example 2 with EventChannel

use of org.omg.CosNotifyChannelAdmin.EventChannel in project ACS by ACS-Community.

the class EventModel method getChannelStatistics.

/**
	 * Called by NotifyServiceUpdateJob (single/periodic refresh of service summary / channel tree).
	 */
public synchronized boolean getChannelStatistics() {
    if (false == discoverNotifyServicesAndChannels()) {
        return false;
    }
    for (NotifyServiceData nsData : notifyServices.values()) {
        if (!nsData.isReachable()) {
            // we skip services that were unreachable already in the above discoverNotifyServicesAndChannels call
            continue;
        }
        // especially if we don't want to display the admin objects as tree nodes to show consumer allocation to the shared admins.
        for (ChannelData channelData : nsData.getChannels()) {
            String channelName = channelData.getQualifiedName();
            EventChannel ec = channelData.getCorbaRef();
            // initial or previous count of consumers / suppliers
            int[] consAndSupp = { 0, 0 };
            if (channelData.isNewNc()) {
                lastConsumerAndSupplierCount.put(channelName, consAndSupp);
            } else if (lastConsumerAndSupplierCount.containsKey(channelName)) {
                consAndSupp = lastConsumerAndSupplierCount.get(channelName);
            }
            // for consumers we must count the proxies, cannot just deduce their number from the consumer admins
            int consumerCount = 0;
            for (int consumerAdminId : ec.get_all_consumeradmins()) {
                try {
                    ConsumerAdmin consumerAdmin = ec.get_consumeradmin(consumerAdminId);
                    int[] push_suppliers_ids = consumerAdmin.push_suppliers();
                    for (int proxyID : push_suppliers_ids) {
                        try {
                            ProxySupplier proxy = consumerAdmin.get_proxy_supplier(proxyID);
                            if (!NCSubscriber.AdminReuseCompatibilityHack.isDummyProxy(proxy)) {
                                consumerCount++;
                            }
                        } catch (ProxyNotFound ex) {
                            m_logger.log(AcsLogLevel.NOTICE, "Proxy with ID='" + proxyID + "' not found for consumer admin with ID='" + consumerAdminId + "', " + "even though this Id got listed a moment ago.", ex);
                        }
                    }
                } catch (AdminNotFound ex) {
                    ex.printStackTrace();
                }
            }
            final String[] roleNames = { "consumer", "supplier" };
            int[] proxyCounts = new int[2];
            int[] proxyDeltas = new int[2];
            proxyCounts[0] = consumerCount;
            // currently for suppliers we have 1 admin object per supplier
            proxyCounts[1] = ec.get_all_supplieradmins().length;
            // same code for consumer and supplier
            for (int i = 0; i < proxyCounts.length; i++) {
                String cstr = channelName;
                int cdiff = proxyCounts[i] - consAndSupp[i];
                if (cdiff != 0) {
                    if (cdiff > 0) {
                        cstr += " has added " + cdiff + " " + roleNames[i];
                    } else if (cdiff < 0) {
                        cstr += " has removed " + (-cdiff) + " " + roleNames[i];
                    }
                    cstr += (Math.abs(cdiff) != 1 ? "s." : ".");
                    m_logger.info(cstr);
                }
                proxyDeltas[i] = cdiff;
            }
            lastConsumerAndSupplierCount.put(channelName, proxyCounts);
            //m_logger.info("Channel: " + channelName + " has " + adminCounts[0] + " consumers and " + adminCounts[1] + " suppliers.");
            channelData.setNumberConsumers(proxyCounts[0]);
            channelData.setNumberSuppliers(proxyCounts[1]);
            channelData.setDeltaConsumers(proxyDeltas[0]);
            channelData.setDeltaSuppliers(proxyDeltas[1]);
        }
    }
    return true;
}
Also used : EventChannel(org.omg.CosNotifyChannelAdmin.EventChannel) ProxyNotFound(org.omg.CosNotifyChannelAdmin.ProxyNotFound) ConsumerAdmin(org.omg.CosNotifyChannelAdmin.ConsumerAdmin) ProxySupplier(org.omg.CosNotifyChannelAdmin.ProxySupplier) AdminNotFound(org.omg.CosNotifyChannelAdmin.AdminNotFound)

Example 3 with EventChannel

use of org.omg.CosNotifyChannelAdmin.EventChannel in project ACS by ACS-Community.

the class EventModel method resolveNotificationChannel.

/**
	 * Resolves a notification channel in the naming service.
	 * 
	 * @return Reference to the event channel specified by channelName.
	 * @param bindingName
	 *           Name of the event channel and trailing domain name, as the NC is registered with the CORBA Naming Service
	 * @throws AcsJException
	 *            Standard ACS Java exception.
	 */
protected EventChannel resolveNotificationChannel(String bindingName) throws AcsJException {
    EventChannel retValue = null;
    String nameServiceKind = alma.acscommon.NC_KIND.value;
    //m_logger.info("Will call 'nctx.resolve' for binding='" + bindingName + "', kind='" + nameServiceKind + "'.");
    try {
        NameComponent[] t_NameSequence = { new NameComponent(bindingName, nameServiceKind) };
        retValue = EventChannelHelper.narrow(nctx.resolve(t_NameSequence));
    } catch (OBJECT_NOT_EXIST ex) {
        m_logger.severe("The NC '" + bindingName + "' no longer exists, probably because its notify service was restarted. The naming service still lists this NC.");
        throw new AcsJUnexpectedExceptionEx(ex);
    } catch (org.omg.CosNaming.NamingContextPackage.NotFound e) {
        // No other suppliers have created the channel yet
        m_logger.info("The '" + bindingName + "' channel has not been created yet.");
        throw new AcsJUnexpectedExceptionEx(e);
    } catch (org.omg.CosNaming.NamingContextPackage.CannotProceed e) {
        // Think there is virtually no chance of this every happening but...
        throw new AcsJUnexpectedExceptionEx(e);
    } catch (org.omg.CosNaming.NamingContextPackage.InvalidName e) {
        // Think there is virtually no chance of this every happening but...
        throw new AcsJUnexpectedExceptionEx(e);
    }
    return retValue;
}
Also used : EventChannel(org.omg.CosNotifyChannelAdmin.EventChannel) NameComponent(org.omg.CosNaming.NameComponent) OBJECT_NOT_EXIST(org.omg.CORBA.OBJECT_NOT_EXIST) NotFound(org.omg.CosNaming.NamingContextPackage.NotFound) AcsJUnexpectedExceptionEx(alma.ACSErrTypeCommon.wrappers.AcsJUnexpectedExceptionEx) CannotProceed(org.omg.CosNaming.NamingContextPackage.CannotProceed)

Aggregations

EventChannel (org.omg.CosNotifyChannelAdmin.EventChannel)3 AcsJUnexpectedExceptionEx (alma.ACSErrTypeCommon.wrappers.AcsJUnexpectedExceptionEx)1 AcsJException (alma.acs.exceptions.AcsJException)1 Helper (alma.acs.nc.Helper)1 NotificationServiceMonitorControlHelper (gov.sandia.CosNotification.NotificationServiceMonitorControlHelper)1 HashSet (java.util.HashSet)1 OBJECT_NOT_EXIST (org.omg.CORBA.OBJECT_NOT_EXIST)1 NameComponent (org.omg.CosNaming.NameComponent)1 NamingContextHelper (org.omg.CosNaming.NamingContextHelper)1 CannotProceed (org.omg.CosNaming.NamingContextPackage.CannotProceed)1 NotFound (org.omg.CosNaming.NamingContextPackage.NotFound)1 AdminNotFound (org.omg.CosNotifyChannelAdmin.AdminNotFound)1 ChannelNotFound (org.omg.CosNotifyChannelAdmin.ChannelNotFound)1 ConsumerAdmin (org.omg.CosNotifyChannelAdmin.ConsumerAdmin)1 EventChannelFactoryHelper (org.omg.CosNotifyChannelAdmin.EventChannelFactoryHelper)1 EventChannelHelper (org.omg.CosNotifyChannelAdmin.EventChannelHelper)1 ProxyNotFound (org.omg.CosNotifyChannelAdmin.ProxyNotFound)1 ProxySupplier (org.omg.CosNotifyChannelAdmin.ProxySupplier)1 DynAnyFactoryHelper (org.omg.DynamicAny.DynAnyFactoryHelper)1