use of org.apache.nifi.components.PropertyDescriptor in project nifi by apache.
the class StandardStateManagerProvider method createStateProvider.
private static StateProvider createStateProvider(final File configFile, final Scope scope, final NiFiProperties properties, final VariableRegistry variableRegistry) throws ConfigParseException, IOException {
final String providerId;
final String providerIdPropertyName;
final String providerDescription;
final String providerXmlElementName;
final String oppositeScopeXmlElementName;
switch(scope) {
case CLUSTER:
providerId = properties.getClusterStateProviderId();
providerIdPropertyName = NiFiProperties.STATE_MANAGEMENT_CLUSTER_PROVIDER_ID;
providerDescription = "Cluster State Provider";
providerXmlElementName = "cluster-provider";
oppositeScopeXmlElementName = "local-provider";
break;
case LOCAL:
providerId = properties.getLocalStateProviderId();
providerIdPropertyName = NiFiProperties.STATE_MANAGEMENT_LOCAL_PROVIDER_ID;
providerDescription = "Local State Provider";
providerXmlElementName = "local-provider";
oppositeScopeXmlElementName = "cluster-provider";
break;
default:
throw new AssertionError("Attempted to create State Provider for unknown Scope: " + scope);
}
if (!configFile.exists()) {
throw new IllegalStateException("Cannot create " + providerDescription + " because the State Management Configuration File " + configFile + " does not exist");
}
if (!configFile.canRead()) {
throw new IllegalStateException("Cannot create " + providerDescription + " because the State Management Configuration File " + configFile + " cannot be read");
}
if (providerId == null) {
if (scope == Scope.CLUSTER) {
throw new IllegalStateException("Cannot create Cluster State Provider because the '" + providerIdPropertyName + "' property is missing from the NiFi Properties file. In order to run NiFi in a cluster, the " + providerIdPropertyName + " property must be configured in nifi.properties");
}
throw new IllegalStateException("Cannot create " + providerDescription + " because the '" + providerIdPropertyName + "' property is missing from the NiFi Properties file");
}
if (providerId.trim().isEmpty()) {
throw new IllegalStateException("Cannot create " + providerDescription + " because the '" + providerIdPropertyName + "' property in the NiFi Properties file has no value set. This is a required property and must reference the identifier of one of the " + providerXmlElementName + " elements in the State Management Configuration File (" + configFile + ")");
}
final StateManagerConfiguration config = StateManagerConfiguration.parse(configFile);
final StateProviderConfiguration providerConfig = config.getStateProviderConfiguration(providerId);
if (providerConfig == null) {
throw new IllegalStateException("Cannot create " + providerDescription + " because the '" + providerIdPropertyName + "' property in the NiFi Properties file is set to '" + providerId + "', but there is no " + providerXmlElementName + " entry in the State Management Configuration File (" + configFile + ") with this id");
}
if (providerConfig.getScope() != scope) {
throw new IllegalStateException("Cannot create " + providerDescription + " because the '" + providerIdPropertyName + "' property in the NiFi Properties file is set to '" + providerId + "', but this id is assigned to a " + oppositeScopeXmlElementName + " entry in the State Management Configuration File (" + configFile + "), rather than a " + providerXmlElementName + " entry");
}
final String providerClassName = providerConfig.getClassName();
final StateProvider provider;
try {
provider = instantiateStateProvider(providerClassName);
} catch (final Exception e) {
throw new RuntimeException("Cannot create " + providerDescription + " of type " + providerClassName, e);
}
if (!ArrayUtils.contains(provider.getSupportedScopes(), scope)) {
throw new RuntimeException("Cannot use " + providerDescription + " (" + providerClassName + ") as it only supports scope(s) " + ArrayUtils.toString(provider.getSupportedScopes()) + " but " + "instance" + " is configured to use scope " + scope);
}
// create variable registry
final Map<PropertyDescriptor, PropertyValue> propertyMap = new HashMap<>();
final Map<PropertyDescriptor, String> propertyStringMap = new HashMap<>();
for (final PropertyDescriptor descriptor : provider.getPropertyDescriptors()) {
propertyMap.put(descriptor, new StandardPropertyValue(descriptor.getDefaultValue(), null, variableRegistry));
propertyStringMap.put(descriptor, descriptor.getDefaultValue());
}
for (final Map.Entry<String, String> entry : providerConfig.getProperties().entrySet()) {
final PropertyDescriptor descriptor = provider.getPropertyDescriptor(entry.getKey());
propertyStringMap.put(descriptor, entry.getValue());
propertyMap.put(descriptor, new StandardPropertyValue(entry.getValue(), null, variableRegistry));
}
final SSLContext sslContext = SslContextFactory.createSslContext(properties, false);
final ComponentLog logger = new SimpleProcessLogger(providerId, provider);
final StateProviderInitializationContext initContext = new StandardStateProviderInitializationContext(providerId, propertyMap, sslContext, logger);
synchronized (provider) {
provider.initialize(initContext);
}
final ValidationContext validationContext = new StandardValidationContext(null, propertyStringMap, null, null, null, variableRegistry);
final Collection<ValidationResult> results = provider.validate(validationContext);
final StringBuilder validationFailures = new StringBuilder();
int invalidCount = 0;
for (final ValidationResult result : results) {
if (!result.isValid()) {
validationFailures.append(result.toString()).append("\n");
invalidCount++;
}
}
if (invalidCount > 0) {
throw new IllegalStateException("Could not initialize State Providers because the " + providerDescription + " is not valid. The following " + invalidCount + " Validation Errors occurred:\n" + validationFailures.toString() + "\nPlease check the configuration of the " + providerDescription + " with ID [" + providerId.trim() + "] in the file " + configFile.getAbsolutePath());
}
return provider;
}
use of org.apache.nifi.components.PropertyDescriptor in project nifi by apache.
the class AbstractConfiguredComponent method removeProperty.
/**
* Removes the property and value for the given property name if a
* descriptor and value exists for the given name. If the property is
* optional its value might be reset to default or will be removed entirely
* if was a dynamic property.
*
* @param name the property to remove
* @param allowRemovalOfRequiredProperties whether or not the property should be removed if it's required
* @return true if removed; false otherwise
* @throws java.lang.IllegalArgumentException if the name is null
*/
private boolean removeProperty(final String name, final boolean allowRemovalOfRequiredProperties) {
if (null == name) {
throw new IllegalArgumentException("Name can not be null");
}
final PropertyDescriptor descriptor = getComponent().getPropertyDescriptor(name);
String value = null;
final boolean allowRemoval = allowRemovalOfRequiredProperties || !descriptor.isRequired();
if (allowRemoval && (value = properties.remove(descriptor)) != null) {
if (descriptor.getControllerServiceDefinition() != null) {
if (value != null) {
final ControllerServiceNode oldNode = serviceProvider.getControllerServiceNode(value);
if (oldNode != null) {
oldNode.removeReference(this);
}
}
}
try {
onPropertyModified(descriptor, value, null);
} catch (final Exception e) {
getLogger().error(e.getMessage(), e);
}
return true;
}
return false;
}
use of org.apache.nifi.components.PropertyDescriptor in project nifi by apache.
the class FlowController method removeRootControllerService.
public void removeRootControllerService(final ControllerServiceNode service) {
final ControllerServiceNode existing = rootControllerServices.get(requireNonNull(service).getIdentifier());
if (existing == null) {
throw new IllegalStateException(service + " is not a member of this Process Group");
}
service.verifyCanDelete();
try (final NarCloseable x = NarCloseable.withComponentNarLoader(service.getControllerServiceImplementation().getClass(), service.getIdentifier())) {
final ConfigurationContext configurationContext = new StandardConfigurationContext(service, controllerServiceProvider, null, variableRegistry);
ReflectionUtils.quietlyInvokeMethodsWithAnnotation(OnRemoved.class, service.getControllerServiceImplementation(), configurationContext);
}
for (final Map.Entry<PropertyDescriptor, String> entry : service.getProperties().entrySet()) {
final PropertyDescriptor descriptor = entry.getKey();
if (descriptor.getControllerServiceDefinition() != null) {
final String value = entry.getValue() == null ? descriptor.getDefaultValue() : entry.getValue();
if (value != null) {
final ControllerServiceNode referencedNode = getRootControllerService(value);
if (referencedNode != null) {
referencedNode.removeReference(service);
}
}
}
}
rootControllerServices.remove(service.getIdentifier());
getStateManagerProvider().onComponentRemoved(service.getIdentifier());
ExtensionManager.removeInstanceClassLoader(service.getIdentifier());
LOG.info("{} removed from Flow Controller", service, this);
}
use of org.apache.nifi.components.PropertyDescriptor in project nifi-minifi by apache.
the class ExtensionManager method checkControllerServiceReferenceEligibility.
private static boolean checkControllerServiceReferenceEligibility(final ConfigurableComponent component, final ClassLoader classLoader) {
// if the extension does not require instance classloading, its eligible
final boolean requiresInstanceClassLoading = component.getClass().isAnnotationPresent(RequiresInstanceClassLoading.class);
final Set<Class> cobundledApis = new HashSet<>();
try (final NarCloseable closeable = NarCloseable.withComponentNarLoader(component.getClass().getClassLoader())) {
final List<PropertyDescriptor> descriptors = component.getPropertyDescriptors();
if (descriptors != null && !descriptors.isEmpty()) {
for (final PropertyDescriptor descriptor : descriptors) {
final Class<? extends ControllerService> serviceApi = descriptor.getControllerServiceDefinition();
if (serviceApi != null && classLoader.equals(serviceApi.getClassLoader())) {
cobundledApis.add(serviceApi);
}
}
}
}
if (!cobundledApis.isEmpty()) {
logger.warn(String.format("Component %s is bundled with its referenced Controller Service APIs %s. The service APIs should not be bundled with component implementations that reference it.", component.getClass().getName(), StringUtils.join(cobundledApis.stream().map(cls -> cls.getName()).collect(Collectors.toSet()), ", ")));
}
// the component is eligible when it does not require instance classloading or when the supporting APIs are bundled in a parent NAR
return requiresInstanceClassLoading == false || cobundledApis.isEmpty();
}
use of org.apache.nifi.components.PropertyDescriptor in project nifi-minifi by apache.
the class ExtensionManager method findReachableApiBundles.
/**
* Find the bundle coordinates for any service APIs that are referenced by this component and not part of the same bundle.
*
* @param component the component being instantiated
*/
protected static Set<BundleCoordinate> findReachableApiBundles(final ConfigurableComponent component) {
final Set<BundleCoordinate> reachableApiBundles = new HashSet<>();
try (final NarCloseable closeable = NarCloseable.withComponentNarLoader(component.getClass().getClassLoader())) {
final List<PropertyDescriptor> descriptors = component.getPropertyDescriptors();
if (descriptors != null && !descriptors.isEmpty()) {
for (final PropertyDescriptor descriptor : descriptors) {
final Class<? extends ControllerService> serviceApi = descriptor.getControllerServiceDefinition();
if (serviceApi != null && !component.getClass().getClassLoader().equals(serviceApi.getClassLoader())) {
final Bundle apiBundle = classLoaderBundleLookup.get(serviceApi.getClassLoader());
reachableApiBundles.add(apiBundle.getBundleDetails().getCoordinate());
}
}
}
}
return reachableApiBundles;
}
Aggregations