Browse files

Merge pull request #526 from excilys/272_Otto_integration

Otto integration. Fixes #272
  • Loading branch information...
2 parents bd8cd24 + 26199a5 commit 2aa295eed7c89b20d8d6a61d7ee5d6cdc378215e @pyricau pyricau committed Mar 5, 2013
View
14 ...s/androidannotations/src/main/java/org/androidannotations/AndroidAnnotationProcessor.java
@@ -16,6 +16,8 @@
package org.androidannotations;
import static org.androidannotations.helper.AndroidManifestFinder.ANDROID_MANIFEST_FILE_OPTION;
+import static org.androidannotations.helper.CanonicalNameConstants.PRODUCE;
+import static org.androidannotations.helper.CanonicalNameConstants.SUBSCRIBE;
import static org.androidannotations.helper.ModelConstants.TRACE_OPTION;
import java.io.IOException;
@@ -164,6 +166,7 @@
import org.androidannotations.processing.OptionsMenuProcessor;
import org.androidannotations.processing.OrmLiteDaoProcessor;
import org.androidannotations.processing.PrefProcessor;
+import org.androidannotations.processing.ProduceProcessor;
import org.androidannotations.processing.ResProcessor;
import org.androidannotations.processing.RestServiceProcessor;
import org.androidannotations.processing.RoboGuiceProcessor;
@@ -172,6 +175,7 @@
import org.androidannotations.processing.SeekBarTouchStartProcessor;
import org.androidannotations.processing.SeekBarTouchStopProcessor;
import org.androidannotations.processing.SharedPrefProcessor;
+import org.androidannotations.processing.SubscribeProcessor;
import org.androidannotations.processing.SystemServiceProcessor;
import org.androidannotations.processing.TextChangeProcessor;
import org.androidannotations.processing.TouchProcessor;
@@ -229,6 +233,7 @@
import org.androidannotations.validation.OptionsMenuValidator;
import org.androidannotations.validation.OrmLiteDaoValidator;
import org.androidannotations.validation.PrefValidator;
+import org.androidannotations.validation.ProduceValidator;
import org.androidannotations.validation.ResValidator;
import org.androidannotations.validation.RestServiceValidator;
import org.androidannotations.validation.RoboGuiceValidator;
@@ -238,6 +243,7 @@
import org.androidannotations.validation.SeekBarTouchStartValidator;
import org.androidannotations.validation.SeekBarTouchStopValidator;
import org.androidannotations.validation.SharedPrefValidator;
+import org.androidannotations.validation.SubscribeValidator;
import org.androidannotations.validation.SystemServiceValidator;
import org.androidannotations.validation.TextChangeValidator;
import org.androidannotations.validation.TouchValidator;
@@ -429,13 +435,16 @@ private ModelValidator buildModelValidator(IRClass rClass, AndroidSystemServices
*/
modelValidator.register(new AfterViewsValidator(processingEnv));
modelValidator.register(new TraceValidator(processingEnv));
+ modelValidator.register(new SubscribeValidator(processingEnv));
+ modelValidator.register(new ProduceValidator(processingEnv));
modelValidator.register(new RunnableValidator(UiThread.class.getName(), processingEnv));
modelValidator.register(new RunnableValidator(Background.class.getName(), processingEnv));
modelValidator.register(new InstanceStateValidator(processingEnv));
modelValidator.register(new OrmLiteDaoValidator(processingEnv, rClass));
modelValidator.register(new HttpsClientValidator(processingEnv, rClass));
modelValidator.register(new OnActivityResultValidator(processingEnv, rClass));
modelValidator.register(new HierarchyViewerSupportValidator(processingEnv, androidManifest));
+
return modelValidator;
}
@@ -521,6 +530,8 @@ private ModelProcessor buildModelProcessor(IRClass rClass, AndroidSystemServices
if (traceActivated()) {
modelProcessor.register(new TraceProcessor());
}
+ modelProcessor.register(new SubscribeProcessor());
+ modelProcessor.register(new ProduceProcessor());
modelProcessor.register(new UiThreadProcessor());
modelProcessor.register(new BackgroundProcessor());
modelProcessor.register(new AfterInjectProcessor());
@@ -652,6 +663,9 @@ private String stackTraceToString(Throwable e) {
set.add(annotationClass.getName());
}
+ set.add(SUBSCRIBE);
+ set.add(PRODUCE);
+
supportedAnnotationNames = Collections.unmodifiableSet(set);
}
return supportedAnnotationNames;
View
25 ...ions/androidannotations/src/main/java/org/androidannotations/helper/AnnotationHelper.java
@@ -15,6 +15,9 @@
*/
package org.androidannotations.helper;
+import static org.androidannotations.helper.ModelConstants.GENERATION_SUFFIX;
+import static org.androidannotations.helper.ModelConstants.VALID_ENHANCED_COMPONENT_ANNOTATIONS;
+
import java.lang.annotation.Annotation;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
@@ -372,4 +375,26 @@ public DeclaredType extractAnnotationClassParameter(Element element, String anno
return extractAnnotationClassParameter(element, annotationName, "value");
}
+ public boolean enclosingElementIsGenerated(Element element) {
+ /*
+ * TODO This isn't really safe, can we find a better way?
+ */
+ Element enclosingElement = element.getEnclosingElement();
+ return enclosingElement.getSimpleName().toString().endsWith(GENERATION_SUFFIX);
+ }
+
+ public boolean enclosingElementHasEnhancedComponentAnnotation(Element element) {
+ Element enclosingElement = element.getEnclosingElement();
+ return hasOneOfClassAnnotations(enclosingElement, VALID_ENHANCED_COMPONENT_ANNOTATIONS);
+ }
+
+ public boolean hasOneOfClassAnnotations(Element element, List<Class<? extends Annotation>> validAnnotations) {
+ for (Class<? extends Annotation> validAnnotation : validAnnotations) {
+ if (element.getAnnotation(validAnnotation) != null) {
+ return true;
+ }
+ }
+ return false;
+ }
+
}
View
6 ...ndroidannotations/src/main/java/org/androidannotations/helper/CanonicalNameConstants.java
@@ -162,6 +162,12 @@
public static final String SCHEME_REGISTRY = "org.apache.http.conn.scheme.SchemeRegistry";
public static final String SINGLE_CLIENT_CONN_MANAGER = "org.apache.http.impl.conn.SingleClientConnManager";
+ /*
+ * Otto
+ */
+ public static final String SUBSCRIBE = "com.squareup.otto.Subscribe";
+ public static final String PRODUCE = "com.squareup.otto.Produce";
+
private CanonicalNameConstants() {
}
View
21 ...ations/androidannotations/src/main/java/org/androidannotations/helper/ModelConstants.java
@@ -15,12 +15,33 @@
*/
package org.androidannotations.helper;
+import static java.util.Arrays.asList;
+
+import java.lang.annotation.Annotation;
+import java.util.List;
+
+import org.androidannotations.annotations.EActivity;
+import org.androidannotations.annotations.EApplication;
+import org.androidannotations.annotations.EBean;
+import org.androidannotations.annotations.EFragment;
+import org.androidannotations.annotations.EProvider;
+import org.androidannotations.annotations.EReceiver;
+import org.androidannotations.annotations.EService;
+import org.androidannotations.annotations.EView;
+import org.androidannotations.annotations.EViewGroup;
+
public abstract class ModelConstants {
public static final String GENERATION_SUFFIX = "_";
public static final String TRACE_OPTION = "trace";
+ @SuppressWarnings("unchecked")
+ public static final List<Class<? extends Annotation>> VALID_ENHANCED_VIEW_SUPPORT_ANNOTATIONS = asList(EActivity.class, EViewGroup.class, EView.class, EBean.class, EFragment.class);
+
+ @SuppressWarnings("unchecked")
+ public static final List<Class<? extends Annotation>> VALID_ENHANCED_COMPONENT_ANNOTATIONS = asList(EApplication.class, EActivity.class, EViewGroup.class, EView.class, EBean.class, EService.class, EReceiver.class, EProvider.class, EFragment.class);
+
private ModelConstants() {
}
View
38 ...tions/androidannotations/src/main/java/org/androidannotations/helper/ValidatorHelper.java
@@ -25,6 +25,8 @@
import static org.androidannotations.helper.CanonicalNameConstants.HTTP_MESSAGE_CONVERTER;
import static org.androidannotations.helper.CanonicalNameConstants.INTERNET_PERMISSION;
import static org.androidannotations.helper.ModelConstants.GENERATION_SUFFIX;
+import static org.androidannotations.helper.ModelConstants.VALID_ENHANCED_COMPONENT_ANNOTATIONS;
+import static org.androidannotations.helper.ModelConstants.VALID_ENHANCED_VIEW_SUPPORT_ANNOTATIONS;
import java.lang.annotation.Annotation;
import java.util.ArrayList;
@@ -49,14 +51,8 @@
import javax.lang.model.util.Elements;
import org.androidannotations.annotations.EActivity;
-import org.androidannotations.annotations.EApplication;
import org.androidannotations.annotations.EBean;
import org.androidannotations.annotations.EFragment;
-import org.androidannotations.annotations.EProvider;
-import org.androidannotations.annotations.EReceiver;
-import org.androidannotations.annotations.EService;
-import org.androidannotations.annotations.EView;
-import org.androidannotations.annotations.EViewGroup;
import org.androidannotations.annotations.Trace;
import org.androidannotations.annotations.ViewById;
import org.androidannotations.annotations.rest.Delete;
@@ -91,12 +87,6 @@
private static final Collection<Integer> VALID_LOG_LEVELS = Arrays.asList(LOG_VERBOSE, LOG_DEBUG, LOG_INFO, LOG_WARN, LOG_ERROR);
- @SuppressWarnings("unchecked")
- private static final List<Class<? extends Annotation>> VALID_ENHANCED_VIEW_SUPPORT_ANNOTATIONS = asList(EActivity.class, EViewGroup.class, EView.class, EBean.class, EFragment.class);
-
- @SuppressWarnings("unchecked")
- private static final List<Class<? extends Annotation>> VALID_ENHANCED_COMPONENT_ANNOTATIONS = asList(EApplication.class, EActivity.class, EViewGroup.class, EView.class, EBean.class, EService.class, EReceiver.class, EProvider.class, EFragment.class);
-
protected final TargetAnnotationHelper annotationHelper;
public ValidatorHelper(TargetAnnotationHelper targetAnnotationHelper) {
@@ -159,6 +149,13 @@ public void isNotPrivate(Element element, IsValid valid) {
}
}
+ public void isPublic(Element element, IsValid valid) {
+ if (!annotationHelper.isPublic(element)) {
+ valid.invalidate();
+ annotationHelper.printAnnotationError(element, "%s cannot be used on a non public element");
+ }
+ }
+
public void enclosingElementHasEBeanAnnotation(Element element, AnnotationElements validatedElements, IsValid valid) {
Element enclosingElement = element.getEnclosingElement();
hasClassAnnotation(element, enclosingElement, validatedElements, EBean.class, valid);
@@ -467,6 +464,15 @@ public void returnTypeIsVoid(ExecutableElement executableElement, IsValid valid)
}
}
+ public void returnTypeIsNotVoid(ExecutableElement executableElement, IsValid valid) {
+ TypeMirror returnType = executableElement.getReturnType();
+
+ if (returnType.getKind() == TypeKind.VOID) {
+ valid.invalidate();
+ annotationHelper.printAnnotationError(executableElement, "%s can only be used on a method with a return type non void");
+ }
+ }
+
public void zeroOrOneParameter(ExecutableElement executableElement, IsValid valid) {
List<? extends VariableElement> parameters = executableElement.getParameters();
@@ -682,6 +688,14 @@ public void extendsType(Element element, String typeQualifiedName, IsValid valid
}
}
+ public void hasExactlyOneParameter(ExecutableElement executableElement, IsValid valid) {
+ List<? extends VariableElement> parameters = executableElement.getParameters();
+ if (parameters.size() != 1) {
+ valid.invalidate();
+ annotationHelper.printAnnotationError(executableElement, "%s can only be used on a method with exactly one parameter, instead of " + parameters.size());
+ }
+ }
+
public void hasOneOrTwoParametersAndFirstIsBoolean(ExecutableElement executableElement, IsValid valid) {
List<? extends VariableElement> parameters = executableElement.getParameters();
View
48 .../androidannotations/src/main/java/org/androidannotations/processing/ProduceProcessor.java
@@ -0,0 +1,48 @@
+/**
+ * Copyright (C) 2010-2013 eBusiness Information, Excilys Group
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed To in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.androidannotations.processing;
+
+import static org.androidannotations.helper.CanonicalNameConstants.PRODUCE;
+
+import javax.lang.model.element.Element;
+import javax.lang.model.element.ExecutableElement;
+
+import org.androidannotations.helper.APTCodeModelHelper;
+
+import com.sun.codemodel.JClassAlreadyExistsException;
+import com.sun.codemodel.JCodeModel;
+import com.sun.codemodel.JMethod;
+
+public class ProduceProcessor implements DecoratingElementProcessor {
+
+ private final APTCodeModelHelper helper = new APTCodeModelHelper();
+
+ @Override
+ public String getTarget() {
+ return PRODUCE;
+ }
+
+ @Override
+ public void process(Element element, JCodeModel codeModel, EBeanHolder holder) throws JClassAlreadyExistsException {
+
+ ExecutableElement executableElement = (ExecutableElement) element;
+
+ JMethod delegatingMethod = helper.overrideAnnotatedMethod(executableElement, holder);
+
+ delegatingMethod.annotate(holder.refClass(PRODUCE));
+ }
+
+}
View
48 ...ndroidannotations/src/main/java/org/androidannotations/processing/SubscribeProcessor.java
@@ -0,0 +1,48 @@
+/**
+ * Copyright (C) 2010-2013 eBusiness Information, Excilys Group
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed To in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.androidannotations.processing;
+
+import static org.androidannotations.helper.CanonicalNameConstants.SUBSCRIBE;
+
+import javax.lang.model.element.Element;
+import javax.lang.model.element.ExecutableElement;
+
+import org.androidannotations.helper.APTCodeModelHelper;
+
+import com.sun.codemodel.JClassAlreadyExistsException;
+import com.sun.codemodel.JCodeModel;
+import com.sun.codemodel.JMethod;
+
+public class SubscribeProcessor implements DecoratingElementProcessor {
+
+ private final APTCodeModelHelper helper = new APTCodeModelHelper();
+
+ @Override
+ public String getTarget() {
+ return SUBSCRIBE;
+ }
+
+ @Override
+ public void process(Element element, JCodeModel codeModel, EBeanHolder holder) throws JClassAlreadyExistsException {
+
+ ExecutableElement executableElement = (ExecutableElement) element;
+
+ JMethod delegatingMethod = helper.overrideAnnotatedMethod(executableElement, holder);
+
+ delegatingMethod.annotate(holder.refClass(SUBSCRIBE));
+ }
+
+}
View
72 .../androidannotations/src/main/java/org/androidannotations/validation/ProduceValidator.java
@@ -0,0 +1,72 @@
+/**
+ * Copyright (C) 2010-2013 eBusiness Information, Excilys Group
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed To in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.androidannotations.validation;
+
+import static org.androidannotations.helper.CanonicalNameConstants.PRODUCE;
+
+import javax.annotation.processing.ProcessingEnvironment;
+import javax.lang.model.element.Element;
+import javax.lang.model.element.ExecutableElement;
+
+import org.androidannotations.helper.TargetAnnotationHelper;
+import org.androidannotations.helper.ValidatorHelper;
+import org.androidannotations.model.AnnotationElements;
+
+public class ProduceValidator implements ElementValidator {
+
+ private final ValidatorHelper validatorHelper;
+ private final TargetAnnotationHelper annotationHelper;
+
+ public ProduceValidator(ProcessingEnvironment processingEnv) {
+ annotationHelper = new TargetAnnotationHelper(processingEnv, getTarget());
+ validatorHelper = new ValidatorHelper(annotationHelper);
+ }
+
+ @Override
+ public String getTarget() {
+ return PRODUCE;
+ }
+
+ @Override
+ public boolean validate(Element element, AnnotationElements validatedElements) {
+
+ if (!annotationHelper.enclosingElementHasEnhancedComponentAnnotation(element)) {
+ return false;
+ }
+
+ IsValid valid = new IsValid();
+
+ ExecutableElement executableElement = (ExecutableElement) element;
+
+ /*
+ * We check that twice to skip invalid annotated elements
+ */
+ validatorHelper.enclosingElementHasEnhancedComponentAnnotation(executableElement, validatedElements, valid);
+
+ validatorHelper.returnTypeIsNotVoid(executableElement, valid);
+
+ validatorHelper.isPublic(element, valid);
+
+ validatorHelper.doesntThrowException(executableElement, valid);
+
+ validatorHelper.isNotFinal(element, valid);
+
+ validatorHelper.zeroParameter(executableElement, valid);
+
+ return valid.isValid();
+ }
+
+}
View
72 ...ndroidannotations/src/main/java/org/androidannotations/validation/SubscribeValidator.java
@@ -0,0 +1,72 @@
+/**
+ * Copyright (C) 2010-2013 eBusiness Information, Excilys Group
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed To in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.androidannotations.validation;
+
+import static org.androidannotations.helper.CanonicalNameConstants.SUBSCRIBE;
+
+import javax.annotation.processing.ProcessingEnvironment;
+import javax.lang.model.element.Element;
+import javax.lang.model.element.ExecutableElement;
+
+import org.androidannotations.helper.TargetAnnotationHelper;
+import org.androidannotations.helper.ValidatorHelper;
+import org.androidannotations.model.AnnotationElements;
+
+public class SubscribeValidator implements ElementValidator {
+
+ private final ValidatorHelper validatorHelper;
+ private final TargetAnnotationHelper annotationHelper;
+
+ public SubscribeValidator(ProcessingEnvironment processingEnv) {
+ annotationHelper = new TargetAnnotationHelper(processingEnv, getTarget());
+ validatorHelper = new ValidatorHelper(annotationHelper);
+ }
+
+ @Override
+ public String getTarget() {
+ return SUBSCRIBE;
+ }
+
+ @Override
+ public boolean validate(Element element, AnnotationElements validatedElements) {
+
+ if (!annotationHelper.enclosingElementHasEnhancedComponentAnnotation(element)) {
+ return false;
+ }
+
+ IsValid valid = new IsValid();
+
+ ExecutableElement executableElement = (ExecutableElement) element;
+
+ /*
+ * We check that twice to skip invalid annotated elements
+ */
+ validatorHelper.enclosingElementHasEnhancedComponentAnnotation(executableElement, validatedElements, valid);
+
+ validatorHelper.returnTypeIsVoid(executableElement, valid);
+
+ validatorHelper.isPublic(element, valid);
+
+ validatorHelper.doesntThrowException(executableElement, valid);
+
+ validatorHelper.isNotFinal(element, valid);
+
+ validatorHelper.hasExactlyOneParameter(executableElement, valid);
+
+ return valid.isValid();
+ }
+
+}
View
12 AndroidAnnotations/functional-test-1-5/src/main/java/com/squareup/otto/Produce.java
@@ -0,0 +1,12 @@
+package com.squareup.otto;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.METHOD)
+public @interface Produce {
+
+}
View
12 AndroidAnnotations/functional-test-1-5/src/main/java/com/squareup/otto/Subscribe.java
@@ -0,0 +1,12 @@
+package com.squareup.otto;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.METHOD)
+public @interface Subscribe {
+
+}
View
5 ...notations/functional-test-1-5/src/main/java/org/androidannotations/test15/otto/Event.java
@@ -0,0 +1,5 @@
+package org.androidannotations.test15.otto;
+
+public class Event {
+
+}
View
25 ...ations/functional-test-1-5/src/main/java/org/androidannotations/test15/otto/OttoBean.java
@@ -0,0 +1,25 @@
+package org.androidannotations.test15.otto;
+
+import org.androidannotations.annotations.Background;
+import org.androidannotations.annotations.EBean;
+import org.androidannotations.annotations.Trace;
+
+import com.squareup.otto.Produce;
+import com.squareup.otto.Subscribe;
+
+@EBean
+public class OttoBean {
+
+ @Trace
+ @Background
+ @Subscribe
+ public void onEvent(Event event) {
+
+ }
+
+ @Produce
+ public Event produceEvent() {
+ return new Event();
+ }
+
+}

0 comments on commit 2aa295e

Please sign in to comment.