-
Notifications
You must be signed in to change notification settings - Fork 77
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
initial Build Compatible Extension API proposal
Signed-off-by: Ladislav Thon <lthon@redhat.com>
- Loading branch information
Showing
54 changed files
with
2,247 additions
and
9 deletions.
There are no files selected for viewing
23 changes: 23 additions & 0 deletions
23
api/src/main/java/jakarta/enterprise/inject/build/compatible/spi/AnnotationConfig.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
package jakarta.enterprise.inject.build.compatible.spi; | ||
|
||
import jakarta.enterprise.lang.model.AnnotationAttribute; | ||
import jakarta.enterprise.lang.model.AnnotationInfo; | ||
import jakarta.enterprise.lang.model.declarations.ClassInfo; | ||
import java.lang.annotation.Annotation; | ||
import java.util.function.Predicate; | ||
|
||
// TODO better name? | ||
// TODO devise a builder-style API instead (see also Annotations) | ||
public interface AnnotationConfig { | ||
void addAnnotation(Class<? extends Annotation> annotationType, AnnotationAttribute... attributes); | ||
|
||
void addAnnotation(ClassInfo<?> annotationType, AnnotationAttribute... attributes); | ||
|
||
void addAnnotation(AnnotationInfo annotation); | ||
|
||
void addAnnotation(Annotation annotation); | ||
|
||
void removeAnnotation(Predicate<AnnotationInfo> predicate); | ||
|
||
void removeAllAnnotations(); | ||
} |
84 changes: 84 additions & 0 deletions
84
api/src/main/java/jakarta/enterprise/inject/build/compatible/spi/Annotations.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,84 @@ | ||
package jakarta.enterprise.inject.build.compatible.spi; | ||
|
||
import jakarta.enterprise.lang.model.AnnotationAttribute; | ||
import jakarta.enterprise.lang.model.AnnotationAttributeValue; | ||
import jakarta.enterprise.lang.model.AnnotationInfo; | ||
import jakarta.enterprise.lang.model.declarations.ClassInfo; | ||
import java.lang.annotation.Annotation; | ||
import java.util.List; | ||
|
||
// TODO devise a builder-style API instead (see also AnnotationConfig) | ||
public interface Annotations { | ||
AnnotationAttributeValue value(boolean value); | ||
|
||
AnnotationAttributeValue value(byte value); | ||
|
||
AnnotationAttributeValue value(short value); | ||
|
||
AnnotationAttributeValue value(int value); | ||
|
||
AnnotationAttributeValue value(long value); | ||
|
||
AnnotationAttributeValue value(float value); | ||
|
||
AnnotationAttributeValue value(double value); | ||
|
||
AnnotationAttributeValue value(char value); | ||
|
||
AnnotationAttributeValue value(String value); | ||
|
||
AnnotationAttributeValue value(Enum<?> enumValue); | ||
|
||
AnnotationAttributeValue value(Class<? extends Enum<?>> enumType, String enumValue); | ||
|
||
AnnotationAttributeValue value(ClassInfo<?> enumType, String enumValue); | ||
|
||
AnnotationAttributeValue value(Class<?> value); | ||
|
||
AnnotationAttributeValue annotationValue(Class<? extends Annotation> annotationType, AnnotationAttribute... attributes); | ||
|
||
AnnotationAttributeValue annotationValue(ClassInfo<?> annotationType, AnnotationAttribute... attributes); | ||
|
||
AnnotationAttributeValue annotationValue(AnnotationInfo annotation); | ||
|
||
AnnotationAttributeValue annotationValue(Annotation annotation); | ||
|
||
AnnotationAttribute attribute(String name, boolean value); | ||
|
||
AnnotationAttribute attribute(String name, byte value); | ||
|
||
AnnotationAttribute attribute(String name, short value); | ||
|
||
AnnotationAttribute attribute(String name, int value); | ||
|
||
AnnotationAttribute attribute(String name, long value); | ||
|
||
AnnotationAttribute attribute(String name, float value); | ||
|
||
AnnotationAttribute attribute(String name, double value); | ||
|
||
AnnotationAttribute attribute(String name, char value); | ||
|
||
AnnotationAttribute attribute(String name, String value); | ||
|
||
AnnotationAttribute attribute(String name, Enum<?> enumValue); | ||
|
||
AnnotationAttribute attribute(String name, Class<? extends Enum<?>> enumType, String enumValue); | ||
|
||
AnnotationAttribute attribute(String name, ClassInfo<?> enumType, String enumValue); | ||
|
||
AnnotationAttribute attribute(String name, Class<?> value); | ||
|
||
AnnotationAttribute arrayAttribute(String name, AnnotationAttributeValue... values); | ||
|
||
AnnotationAttribute arrayAttribute(String name, List<AnnotationAttributeValue> values); | ||
|
||
AnnotationAttribute annotationAttribute(String name, Class<? extends Annotation> annotationType, | ||
AnnotationAttribute... attributes); | ||
|
||
AnnotationAttribute annotationAttribute(String name, ClassInfo<?> annotationType, AnnotationAttribute... attributes); | ||
|
||
AnnotationAttribute annotationAttribute(String name, AnnotationInfo annotation); | ||
|
||
AnnotationAttribute annotationAttribute(String name, Annotation annotation); | ||
} |
166 changes: 166 additions & 0 deletions
166
api/src/main/java/jakarta/enterprise/inject/build/compatible/spi/AppArchive.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,166 @@ | ||
package jakarta.enterprise.inject.build.compatible.spi; | ||
|
||
import jakarta.enterprise.lang.model.declarations.ClassInfo; | ||
import jakarta.enterprise.lang.model.declarations.FieldInfo; | ||
import jakarta.enterprise.lang.model.declarations.MethodInfo; | ||
import jakarta.enterprise.lang.model.types.Type; | ||
import java.lang.annotation.Annotation; | ||
import java.util.function.Consumer; | ||
|
||
// TODO remove entirely? | ||
public interface AppArchive { | ||
ClassQuery classes(); | ||
|
||
MethodQuery constructors(); // no static initializers | ||
|
||
MethodQuery methods(); // no constructors nor static initializers | ||
|
||
FieldQuery fields(); | ||
|
||
/** | ||
* The {@code exactly} and {@code subtypeOf} methods are additive. | ||
* When called multiple times, they form a union of requested classes (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.classes() | ||
* .exactly(Foo.class) | ||
* .subtypeOf(Bar.class) | ||
* .forEach(...) | ||
* }</pre> | ||
* runs given code for the {@code Foo} class and all subtypes of the {@code Bar} class. | ||
* <p> | ||
* The {@code annotatedWith} methods are additive. | ||
* When called multiple times, they form a union of requested annotations (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.classes() | ||
* .annotatedWith(Foo.class) | ||
* .annotatedWith(Bar.class) | ||
* .forEach(...) | ||
* }</pre> | ||
* runs given code for all classes annotated either with {@code @Foo} or with {@code @Bar} (or both). | ||
*/ | ||
interface ClassQuery { | ||
ClassQuery exactly(Class<?> clazz); | ||
|
||
ClassQuery subtypeOf(Class<?> clazz); | ||
|
||
ClassQuery annotatedWith(Class<? extends Annotation> annotationType); | ||
|
||
void forEach(Consumer<ClassInfo<?>> consumer); | ||
} | ||
|
||
/** | ||
* The {@code declaredOn} method is additive. | ||
* When called multiple times, it forms a union of requested classes (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.methods() | ||
* .declaredOn(appArchive.classes().exactly(Foo.class)) | ||
* .declaredOn(appArchive.classes().subtypeOf(Bar.class)) | ||
* .forEach(...) | ||
* }</pre> | ||
* runs given code for all methods declared on the {@code Foo} class and on all subtypes of the {@code Bar} class. | ||
* Note that this example can be rewritten as | ||
* <pre>{@code | ||
* appArchive.methods() | ||
* .declaredOn(appArchive.classes().exactly(Foo.class).subtypeOf(Bar.class)) | ||
* .forEach(...) | ||
* }</pre> | ||
* which is probably easier to understand. | ||
* <p> | ||
* The {@code withReturnType} methods are additive. | ||
* When called multiple times, they form a union of requested return types (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.methods() | ||
* .withReturnType(Foo.class) | ||
* .withReturnType(Bar.class) | ||
* .forEach(...) | ||
* }</pre> | ||
* runs given code for all methods that return either {@code Foo} or {@code Bar}. | ||
* <p> | ||
* The {@code annotatedWith} methods are additive. | ||
* When called multiple times, they form a union of requested annotations (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.methods() | ||
* .annotatedWith(Foo.class) | ||
* .annotatedWith(Bar.class) | ||
* .forEach(...) | ||
* }</pre> | ||
* runs given code for all methods annotated either with {@code @Foo} or with {@code @Bar} (or both). | ||
*/ | ||
interface MethodQuery { | ||
MethodQuery declaredOn(ClassQuery classes); | ||
|
||
/** | ||
* Equivalent to {@code withReturnType(types.of(type))}, where {@code types} is {@link Types}. | ||
*/ | ||
MethodQuery withReturnType(Class<?> type); | ||
|
||
MethodQuery withReturnType(Type type); | ||
|
||
// TODO parameters? | ||
|
||
MethodQuery annotatedWith(Class<? extends Annotation> annotationType); | ||
|
||
void forEach(Consumer<MethodInfo<?>> consumer); | ||
} | ||
|
||
/** | ||
* The {@code declaredOn} method is additive. | ||
* When called multiple times, it forms a union of requested classes (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.fields() | ||
* .declaredOn(appArchive.classes().exactly(Foo.class)) | ||
* .declaredOn(appArchive.classes().subtypeOf(Bar.class)) | ||
* .forEach(...) | ||
* }</pre> | ||
* runs given code for all fields declared on the {@code Foo} class and on all subtypes of the {@code Bar} class. | ||
* Note that this example can be rewritten as | ||
* <pre>{@code | ||
* appArchive.fields() | ||
* .declaredOn(appArchive.classes().exactly(Foo.class).subtypeOf(Bar.class)) | ||
* .forEach() | ||
* }</pre> | ||
* which is probably easier to understand. | ||
* <p> | ||
* The {@code ofType} methods are additive. | ||
* When called multiple times, they form a union of requested field types (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.fields() | ||
* .ofType(Foo.class) | ||
* .ofType(Bar.class) | ||
* .forEach() | ||
* }</pre> | ||
* runs given code for all fields that are of type either {@code Foo} or {@code Bar}. | ||
* <p> | ||
* The {@code annotatedWith} methods are additive. | ||
* When called multiple times, they form a union of requested annotations (not an intersection). | ||
* For example, | ||
* <pre>{@code | ||
* appArchive.fields() | ||
* .annotatedWith(Foo.class) | ||
* .annotatedWith(Bar.class) | ||
* .forEach(...) | ||
* }</pre> | ||
* runs given code for all fields annotated either with {@code @Foo} or with {@code @Bar} (or both). | ||
*/ | ||
interface FieldQuery { | ||
FieldQuery declaredOn(ClassQuery classes); | ||
|
||
/** | ||
* Equivalent to {@code ofType(types.of(type))}, where {@code types} is {@link Types}. | ||
*/ | ||
FieldQuery ofType(Class<?> type); | ||
|
||
FieldQuery ofType(Type type); | ||
|
||
FieldQuery annotatedWith(Class<? extends Annotation> annotationType); | ||
|
||
void forEach(Consumer<FieldInfo<?>> consumer); | ||
} | ||
} |
10 changes: 10 additions & 0 deletions
10
api/src/main/java/jakarta/enterprise/inject/build/compatible/spi/AppArchiveBuilder.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
package jakarta.enterprise.inject.build.compatible.spi; | ||
|
||
// TODO better name | ||
public interface AppArchiveBuilder { | ||
void add(String fullyQualifiedClassName); | ||
|
||
// TODO adds the type itself or not? (in theory yes, as subtyping is reflexive) | ||
// TODO looks like it can't be implemented on top of Portable Extensions, so maybe remove? | ||
void addSubtypesOf(String fullyQualifiedClassName); | ||
} |
66 changes: 66 additions & 0 deletions
66
api/src/main/java/jakarta/enterprise/inject/build/compatible/spi/AppArchiveConfig.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,66 @@ | ||
package jakarta.enterprise.inject.build.compatible.spi; | ||
|
||
import jakarta.enterprise.lang.model.types.Type; | ||
import java.lang.annotation.Annotation; | ||
import java.util.function.Consumer; | ||
|
||
// TODO remove entirely, if we remove AppArchive/AppDeployment | ||
// TODO maybe AppArchiveConfig shouldn't extend AppArchive, and *ConfigQuery shouldn't extend *Query | ||
public interface AppArchiveConfig extends AppArchive { | ||
@Override | ||
ClassConfigQuery classes(); | ||
|
||
@Override | ||
MethodConfigQuery constructors(); // no static initializers | ||
|
||
@Override | ||
MethodConfigQuery methods(); // no constructors nor static initializers | ||
|
||
@Override | ||
FieldConfigQuery fields(); | ||
|
||
interface ClassConfigQuery extends ClassQuery { | ||
@Override | ||
ClassConfigQuery exactly(Class<?> clazz); | ||
|
||
@Override | ||
ClassConfigQuery subtypeOf(Class<?> clazz); | ||
|
||
@Override | ||
ClassConfigQuery annotatedWith(Class<? extends Annotation> annotationType); | ||
|
||
void configure(Consumer<ClassConfig<?>> consumer); | ||
} | ||
|
||
interface MethodConfigQuery extends MethodQuery { | ||
@Override | ||
MethodConfigQuery declaredOn(ClassQuery classes); | ||
|
||
@Override | ||
MethodConfigQuery withReturnType(Class<?> type); | ||
|
||
@Override | ||
MethodConfigQuery withReturnType(Type type); | ||
|
||
@Override | ||
MethodConfigQuery annotatedWith(Class<? extends Annotation> annotationType); | ||
|
||
void configure(Consumer<MethodConfig<?>> consumer); | ||
} | ||
|
||
interface FieldConfigQuery extends FieldQuery { | ||
@Override | ||
FieldConfigQuery declaredOn(ClassQuery classes); | ||
|
||
@Override | ||
FieldConfigQuery ofType(Class<?> type); | ||
|
||
@Override | ||
FieldConfigQuery ofType(Type type); | ||
|
||
@Override | ||
FieldConfigQuery annotatedWith(Class<? extends Annotation> annotationType); | ||
|
||
void configure(Consumer<FieldConfig<?>> consumer); | ||
} | ||
} |
Oops, something went wrong.