use of io.jenkins.plugins.casc.ConfiguratorException in project configuration-as-code-plugin by jenkinsci.
the class ErrorOnConflictMergeStrategy method merge.
@Override
public void merge(Node root, Node node, String source) throws ConfiguratorException {
if (root.getNodeId() != node.getNodeId()) {
// means one of those yaml file doesn't conform to JCasC schema
throw new ConfiguratorException(String.format("Found incompatible configuration elements %s %s", source, node.getStartMark()));
}
switch(root.getNodeId()) {
case sequence:
SequenceNode seq = (SequenceNode) root;
SequenceNode seq2 = (SequenceNode) node;
seq.getValue().addAll(seq2.getValue());
return;
case mapping:
MappingNode map = (MappingNode) root;
MappingNode map2 = (MappingNode) node;
// merge common entries
final Iterator<NodeTuple> it = map2.getValue().iterator();
while (it.hasNext()) {
NodeTuple t2 = it.next();
for (NodeTuple tuple : map.getValue()) {
final Node key = tuple.getKeyNode();
final Node key2 = t2.getKeyNode();
if (key.getNodeId() == NodeId.scalar) {
// We don't support merge for more complex cases (yet)
if (((ScalarNode) key).getValue().equals(((ScalarNode) key2).getValue())) {
merge(tuple.getValueNode(), t2.getValueNode(), source);
it.remove();
}
} else {
throw new ConfiguratorException(String.format("Found non-mergeable configuration keys %s %s)", source, node.getEndMark()));
}
}
}
// .. and add others
map.getValue().addAll(map2.getValue());
return;
default:
new OverrideMergeStrategy().merge(root, node, source);
}
}
use of io.jenkins.plugins.casc.ConfiguratorException in project configuration-as-code-plugin by jenkinsci.
the class DataBoundConfiguratorTest method packageParametersAreNonnullByDefault.
@Test
public void packageParametersAreNonnullByDefault() {
Mapping config = new Mapping();
ConfiguratorRegistry registry = ConfiguratorRegistry.get();
String expectedMessage = "string is required to configure class io.jenkins.plugins.casc.impl.configurators.nonnull.nonnullparampackage.PackageParametersAreNonnullByDefault";
ConfiguratorException exception = assertThrows(ConfiguratorException.class, () -> registry.lookupOrFail(PackageParametersAreNonnullByDefault.class).configure(config, new ConfigurationContext(registry)));
assertThat(exception.getMessage(), is(expectedMessage));
}
use of io.jenkins.plugins.casc.ConfiguratorException in project configuration-as-code-plugin by jenkinsci.
the class DataBoundConfigurator method tryConstructor.
private T tryConstructor(Constructor<T> constructor, Mapping config, ConfigurationContext context) throws ConfiguratorException {
final Parameter[] parameters = constructor.getParameters();
final String[] names = ClassDescriptor.loadParameterNames(constructor);
Object[] args = new Object[names.length];
if (parameters.length > 0) {
for (int i = 0; i < names.length; i++) {
final CNode value = config.get(names[i]);
final Class t = parameters[i].getType();
Class<?> clazz = constructor.getDeclaringClass();
if (value == null && (parameters[i].isAnnotationPresent(Nonnull.class) || constructor.isAnnotationPresent(ParametersAreNonnullByDefault.class) || clazz.isAnnotationPresent(ParametersAreNonnullByDefault.class) || clazz.getPackage().isAnnotationPresent(ParametersAreNonnullByDefault.class) && !parameters[i].isAnnotationPresent(CheckForNull.class))) {
if (Set.class.isAssignableFrom(t)) {
LOGGER.log(Level.FINER, "The parameter to be set is @Nonnull but is not present; " + "setting equal to empty set.");
args[i] = Collections.emptySet();
} else if (List.class.isAssignableFrom(t)) {
LOGGER.log(Level.FINER, "The parameter to be set is @Nonnull but is not present; " + "setting equal to empty list.");
args[i] = Collections.emptyList();
} else {
throw new ConfiguratorException(names[i] + " is required to configure " + target);
}
continue;
}
if (value != null) {
if (Collection.class.isAssignableFrom(t)) {
final Type pt = parameters[i].getParameterizedType();
final Configurator lookup = context.lookupOrFail(pt);
final Collection<Object> collection;
if (Set.class.isAssignableFrom(t)) {
collection = new HashSet<>();
} else {
collection = new ArrayList<>();
}
for (CNode o : value.asSequence()) {
collection.add(lookup.configure(o, context));
}
args[i] = collection;
} else {
final Type pt = parameters[i].getParameterizedType();
final Type k = pt != null ? pt : t;
final Configurator configurator = context.lookupOrFail(k);
args[i] = configurator.configure(value, context);
}
if (LOGGER.isLoggable(Level.FINE)) {
LOGGER.log(Level.FINE, "Setting {0}.{1} = {2}", new Object[] { target, names[i], t == Secret.class || Attribute.calculateIfSecret(target, names[i]) ? "****" : value });
}
} else if (t.isPrimitive()) {
args[i] = defaultPrimitiveValue(t);
}
}
}
final T object;
try {
object = constructor.newInstance(args);
} catch (IllegalArgumentException | InstantiationException | InvocationTargetException | IllegalAccessException ex) {
List<String> argumentTypes = new ArrayList<>(args.length);
for (Object arg : args) {
argumentTypes.add(arg != null ? arg.getClass().getName() : "null");
}
List<String> parameterTypes = new ArrayList<>(parameters.length);
for (Parameter parameter : parameters) {
parameterTypes.add(parameter.getParameterizedType().getTypeName());
}
List<String> expectedParamList = new ArrayList<>(parameters.length);
for (int i = 0; i < parameters.length; i++) {
expectedParamList.add(names[i] + " " + parameterTypes.get(i));
}
throw new ConfiguratorException(this, "Failed to construct instance of " + target + ".\n Constructor: " + constructor + ".\n Arguments: " + argumentTypes + ".\n Expected Parameters: " + String.join(", ", expectedParamList), ex);
}
// constructor was successful, so let's removed configuration elements we have consumed doing so.
for (String name : names) {
config.remove(name);
}
return object;
}
use of io.jenkins.plugins.casc.ConfiguratorException in project configuration-as-code-plugin by jenkinsci.
the class ConfigurableConfigurator method check.
@Override
public T check(CNode config, ConfigurationContext context) throws ConfiguratorException {
try {
final T instance = target.getDeclaredConstructor().newInstance();
instance.check(config);
return instance;
} catch (InstantiationException | IllegalAccessException | NoSuchMethodException | InvocationTargetException e) {
throw new ConfiguratorException("Cannot instantiate Configurable " + target + " with default constructor", e);
}
}
use of io.jenkins.plugins.casc.ConfiguratorException in project configuration-as-code-plugin by jenkinsci.
the class YamlUtils method merge.
public static Node merge(List<YamlSource> sources, ConfigurationContext context) throws ConfiguratorException {
Node root = null;
MergeStrategy mergeStrategy = MergeStrategyFactory.getMergeStrategyOrDefault(context.getMergeStrategy());
for (YamlSource<?> source : sources) {
try (Reader reader = reader(source)) {
final Node node = read(source, reader, context);
if (root == null) {
root = node;
} else {
if (node != null) {
mergeStrategy.merge(root, node, source.toString());
}
}
} catch (IOException io) {
throw new ConfiguratorException("Failed to read " + source, io);
}
}
return root;
}
Aggregations