protected void checkKnownProperty(BuilderASTTransformation transform, AnnotationNode anno, String name, List<PropertyInfo> properties) { for (PropertyInfo prop: properties) { if (name.equals(prop.getName())) { return; } } transform.addError("Error during " + MY_TYPE_NAME + " processing: tried to include unknown property '" + name + "'", anno); }
protected void checkKnownField(BuilderASTTransformation transform, AnnotationNode anno, String name, List<FieldNode> fields) { for (FieldNode field: fields) { if (name.equals(field.getName())) { return; } } transform.addError("Error during " + MY_TYPE_NAME + " processing: tried to include unknown property '" + name + "'", anno); }
private BuilderStrategy createBuilderStrategy(AnnotationNode anno, GroovyClassLoader loader) { ClassNode strategyClass = getMemberClassValue(anno, "builderStrategy", ClassHelper.make(DefaultStrategy.class)); if (strategyClass == null) { addError("Couldn't determine builderStrategy class", anno); return null; } String className = strategyClass.getName(); try { Object instance = loader.loadClass(className).newInstance(); if (instance == null) { addError("Can't load builderStrategy '" + className + "'", anno); return null; } if (!BuilderStrategy.class.isAssignableFrom(instance.getClass())) { addError("The builderStrategy class '" + strategyClass.getName() + "' on " + MY_TYPE_NAME + " is not a builderStrategy", anno); return null; } return (BuilderStrategy) instance; } catch (Exception e) { addError("Can't load builderStrategy '" + className + "' " + e, anno); return null; } }
protected boolean unsupportedAttribute(BuilderASTTransformation transform, AnnotationNode anno, String memberName, String extraMessage) { Object memberValue = transform.getMemberValue(anno, memberName); if (memberValue instanceof String && isUndefined((String) memberValue)) return false; if (memberValue == null) { memberValue = transform.getMemberClassValue(anno, memberName); if (memberValue != null && isUndefined((ClassNode) memberValue)) { memberValue = null; } } if (memberValue != null) { String message = extraMessage.length() == 0 ? "" : " " + extraMessage; transform.addError("Error during " + MY_TYPE_NAME + " processing: Annotation attribute '" + memberName + "' not supported by " + getClass().getName() + message, anno); return true; } return false; }
private boolean checkStatic(MethodNode mNode, String annotationName) { if (!mNode.isStatic() && !mNode.isStaticConstructor() && !(mNode instanceof ConstructorNode)) { addError("Error processing method '" + mNode.getName() + "'. " + annotationName + " not allowed for instance methods.", mNode); return false; } return true; }
private void createBuilderForAnnotatedClass(BuilderASTTransformation transform, ClassNode buildee, AnnotationNode anno, boolean useSetters, boolean allNames, boolean force) { List<String> excludes = new ArrayList<String>(); List<String> includes = new ArrayList<String>(); includes.add(Undefined.STRING); if (!getIncludeExclude(transform, anno, buildee, excludes, includes)) return; if (includes.size() == 1 && Undefined.isUndefined(includes.get(0))) includes = null; List<FieldNode> fields = getFields(transform, anno, buildee); List<FieldNode> filteredFields = filterFields(fields, includes, excludes, allNames); if (filteredFields.isEmpty()) { transform.addError("Error during " + BuilderASTTransformation.MY_TYPE_NAME + " processing: at least one property is required for this strategy", anno); } ClassNode builder = createInnerHelperClass(buildee, getBuilderClassName(buildee, anno), filteredFields.size()); addFields(buildee, filteredFields, builder); buildCommon(buildee, anno, filteredFields, builder); boolean needsConstructor = !AnnotatedNodeUtils.hasAnnotation(buildee, TUPLECONS_TYPE) || force; createBuildeeConstructors(transform, buildee, builder, filteredFields, needsConstructor, useSetters); }
public void build(BuilderASTTransformation transform, AnnotatedNode annotatedNode, AnnotationNode anno) { if (!(annotatedNode instanceof ClassNode)) { transform.addError("Error during " + BuilderASTTransformation.MY_TYPE_NAME + " processing: building for " + annotatedNode.getClass().getSimpleName() + " not supported by " + getClass().getSimpleName(), annotatedNode); return; ClassNode buildee = transform.getMemberClassValue(anno, "forClass"); if (buildee == null) { transform.addError("Error during " + MY_TYPE_NAME + " processing: 'forClass' must be specified for " + getClass().getName(), anno); return;
private void createBuilderForAnnotatedMethod(BuilderASTTransformation transform, MethodNode mNode, AnnotationNode anno, boolean useSetters) { if (transform.getMemberValue(anno, "includes") != null || transform.getMemberValue(anno, "excludes") != null) { transform.addError("Error during " + BuilderASTTransformation.MY_TYPE_NAME + " processing: includes/excludes only allowed on classes", anno); } if (mNode instanceof ConstructorNode) { mNode.setModifiers(ACC_PRIVATE | ACC_SYNTHETIC); } else { if ((mNode.getModifiers() & ACC_STATIC) == 0) { transform.addError("Error during " + BuilderASTTransformation.MY_TYPE_NAME + " processing: method builders only allowed on static methods", anno); } mNode.setModifiers(ACC_PRIVATE | ACC_SYNTHETIC | ACC_STATIC); } ClassNode buildee = mNode.getDeclaringClass(); Parameter[] parameters = mNode.getParameters(); if (parameters.length == 0) { transform.addError("Error during " + BuilderASTTransformation.MY_TYPE_NAME + " processing: at least one parameter is required for this strategy", anno); } ClassNode builder = createInnerHelperClass(buildee, getBuilderClassName(buildee, anno), parameters.length); List<FieldNode> convertedFields = convertParamsToFields(builder, parameters); buildCommon(buildee, anno, convertedFields, builder); if (mNode instanceof ConstructorNode) { createBuildeeConstructors(transform, buildee, builder, convertedFields, false, useSetters); } else { createBuildeeMethods(buildee, mNode, builder, convertedFields); } }
public void build(BuilderASTTransformation transform, AnnotatedNode annotatedNode, AnnotationNode anno) { if (!(annotatedNode instanceof ClassNode)) { transform.addError("Error during " + BuilderASTTransformation.MY_TYPE_NAME + " processing: building for " + annotatedNode.getClass().getSimpleName() + " not supported by " + getClass().getSimpleName(), annotatedNode); return;
public void buildMethod(BuilderASTTransformation transform, MethodNode mNode, AnnotationNode anno) { if (transform.getMemberValue(anno, "includes") != null || transform.getMemberValue(anno, "excludes") != null) { transform.addError("Error during " + BuilderASTTransformation.MY_TYPE_NAME + " processing: includes/excludes only allowed on classes", anno); } ClassNode buildee = mNode.getDeclaringClass(); ClassNode builder = createBuilder(anno, buildee); createBuilderFactoryMethod(anno, buildee, builder); for (Parameter parameter : mNode.getParameters()) { builder.addField(createFieldCopy(buildee, parameter)); builder.addMethod(createBuilderMethodForProp(builder, new PropertyInfo(parameter.getName(), parameter.getType()), getPrefix(anno))); } builder.addMethod(createBuildMethodForMethod(anno, buildee, mNode, mNode.getParameters())); }