1 2 3 Previous Next 31 Replies Latest reply on Mar 7, 2008 5:49 PM by adrian.brock Go to original post
      • 15. Re: enums, generics and other animals
        alesj

         

        "scott.stark@jboss.org" wrote:
        You can write an XmlAdapter to handle this:
        https://svn.jboss.org/repos/jbossas/projects/metadata/trunk/src/main/java/org/jboss/metadata/javaee/spec/TransactionAttributeTypeAdapter.java

        Something like this could be made more generic.
        Some sort of camel name matching (+ excluding '_') while iterating over the enums.

        • 16. Re: enums, generics and other animals
          alesj

           

          "adrian@jboss.org" wrote:

          RTFM :-)

          Which FM?

          "adrian@jboss.org" wrote:

          You can actually do some pretty weird stuff, so don't overuse it ;-)

          @XmlEnum(Integer.class)
          public enum OldEnglishMoney
          {
           @XmlEnumValue("D")
           PENNY(1),
           @XmlEnumValue("S")
           SHILLING(12)
           @XmlEnumValue("L")
           POUND(240)
          }
          

          What's so weird here?
          Or where is the overuse?

          If you know underlying value is a string, almost matching enum name, I guess you can do what I proposed. :-)

          And what I could actually do, in a safe manner, is to rename the enums to match the underlying string, and thank IDE for making this possible.
          But I'll stick to getInstance. ;-)

          • 17. Re: enums, generics and other animals

             

            "alesj" wrote:

            But I'll stick to getInstance. ;-)


            You don't need to code this yourself. Just add @XmlEnumValues to the enum class.
            JBoss/AXB already knows how to parse enums. It's things like ControllerState
            that it doesn't know how to do.

            You'd just be reinventing this:
            http://viewvc.jboss.org/cgi-bin/viewvc.cgi/common/jbossxb/trunk/src/main/java/org/jboss/xb/builder/runtime/EnumValueAdapter.java?revision=2545&view=markup

            • 18. Re: enums, generics and other animals
              alesj

               

              "adrian@jboss.org" wrote:

              You don't need to code this yourself. Just add @XmlEnumValues to the enum class.
              JBoss/AXB already knows how to parse enums.

              Does this include the old JBossXB handlers?
              e.g.
              public class InjectionHandler extends DefaultElementHandler
              {
               ...
              
               public void attributes(Object o, QName elementName, ElementBinding element, Attributes attrs, NamespaceContext nsCtx)
               {
               AbstractInjectionValueMetaData injection = (AbstractInjectionValueMetaData) o;
               for (int i = 0; i < attrs.getLength(); ++i)
               {
               String localName = attrs.getLocalName(i);
               ...
               else if ("type".equals(localName))
               injection.setInjectionType(AutowireType.getInstance(attrs.getValue(i)));
               else if ("option".equals(localName))
               injection.setInjectionOption(InjectOption.getInstance(attrs.getValue(i)));
               else if ("fromContext".equals(localName))
               injection.setFromContext(FromContext.getInstance(attrs.getValue(i)));
               }
               }
              }
              


              • 19. Re: enums, generics and other animals

                 

                "alesj" wrote:
                "adrian@jboss.org" wrote:

                You don't need to code this yourself. Just add @XmlEnumValues to the enum class.
                JBoss/AXB already knows how to parse enums.

                Does this include the old JBossXB handlers?


                Obviously not. Although you could get JBossXB to do this work for you
                from the annotations, if you change the type to use that EnumValueAdapter
                (I'm assuming you have such a type in the schema? :-).

                TypeBInding type = schemaBinding.getTypeBinding(qNameFromSchema);
                type.setValueAdapter(new EnumValueAdapter(...));
                


                • 20. Re: enums, generics and other animals
                  alesj

                   

                  "adrian@jboss.org" wrote:
                  I'm assuming you have such a type in the schema? :-).

                  Sure.
                   <xsd:attribute name="mode" type="controllerModeType" use="optional"/>
                   <xsd:attribute name="autowire-type" type="autowireTypeType" use="optional"/>
                   <xsd:attribute name="option" type="optionType" use="optional" default="Strict"/>
                   <xsd:attribute name="fromContext" type="contextType" use="optional"/>
                  


                  "adrian@jboss.org" wrote:

                  TypeBInding type = schemaBinding.getTypeBinding(qNameFromSchema);
                  type.setValueAdapter(new EnumValueAdapter(...));
                  

                  How do you use this with attributes?
                  Since currently we're only handling attributes in the way my last post showed - iterating over string values, matching localName and using the string value from Attributes.getValue(index).


                  • 21. Re: enums, generics and other animals

                     

                    "alesj" wrote:

                    How do you use this with attributes?


                    JBossXB will do it automatically.

                    1) attribute qName="urn:jboss:deployer-beans:2.0:option"
                    2) type qName="urn:jboss:deployer-beans:2.0:optionType"
                    3) convert to an object according to the config on that TypeBinding i.e. the ValueAdapter

                    But looking again, the problem is that we aren't using the AttributeBinding callback for
                    these, we're looking at the attributes directly which are just strings. :-(

                    See DefaultElementHandler

                    
                     // Don't override this
                     public void attributes(Object o, QName elementName, ElementBinding element, Attributes attrs, NamespaceContext nsCtx)
                     {
                     if(attrsHandler != null)
                     {
                     attrsHandler.attributes(o, elementName, element.getType(), attrs, nsCtx);
                     }
                     }
                    
                     // Set an attribute handler on the constructor
                     public DefaultElementHandler(AttributesHandler attrsHandler)
                     {
                     this.attrsHandler = attrsHandler;
                     }
                    


                    i.e.
                    
                    public class MyAttributeHandler extends AttributeHander
                    {
                     public void attribute(QName elemName,
                     QName attrName,
                     AttributeBinding binding,
                     Object owner,
                     Object value)
                     {
                     AbstractInjectionValueMetaData injection = (AbstractInjectionValueMetaData) owner;
                    
                     String localName = attrName.getLocalPart();
                     ...
                     else if ("type".equals(localName))
                     injection.setInjectionType((AutowireType) value)
                     }
                    }
                    


                    But I'm not sure it is worth doing all this work, since these classes are going away soon.

                    • 22. Re: enums, generics and other animals
                      alesj

                       

                      "adrian@jboss.org" wrote:

                      
                      public class MyAttributeHandler extends AttributeHander
                      {
                       public void attribute(QName elemName,
                       QName attrName,
                       AttributeBinding binding,
                       Object owner,
                       Object value)
                       {
                       AbstractInjectionValueMetaData injection = (AbstractInjectionValueMetaData) owner;
                      
                       String localName = attrName.getLocalPart();
                       ...
                       else if ("type".equals(localName))
                       injection.setInjectionType((AutowireType) value)
                       }
                      }
                      


                      Yup, thought this was missing.

                      "adrian@jboss.org" wrote:

                      But I'm not sure it is worth doing all this work, since these classes are going away soon.

                      OK, I'll leave the crappy getInstance until we move 100% to jaxb.
                      I'll put a TODO on removing this. And comment on it at the jaxb JIRA issue.

                      • 23. Re: enums, generics and other animals

                        Why have you created a package called "enums"?

                        That's just stupid. Packages should be based on what they provide
                        not what their contents are.
                        Would you create a package called "classes"? :-)

                        e.g. The metatype project has
                        org.jboss.metatype.api
                        - annotations
                        - types
                        - values

                        I think a package called "annotations" is stupid as well, but it seems to be a convention. :-)

                        Either put the enums in the annotations package or create a package called
                        model or something. This package would also contain callback interfaces referenced
                        (like the ScopeFactory in the metadata repository) so calling it "enums" is plain wrong.

                        A couple of related issues now that I look at the annotations:

                        1) Why do you have class names as strings in the annotations?
                        To be able to read the annotations at all the classloader must exist
                        so there's no problem with letting the users specify classes.

                        2) How can the Factory(Method) annotations work?

                        These are used at object construction. You don't know the type until
                        the object is constructed so how can read the annotations? :-)

                        I could understand it if this was somehow used to annotation a package
                        with what beans need constructing and how to do it.
                        e.g.

                        @Beans
                        ({
                         @Bean(name="blah", class=MyBean.class),
                         @Bean(name="blah2", factory=MyFactory.class, method="create")
                        })
                        package com.acme;
                        



                        • 24. Re: enums, generics and other animals

                           

                          "adrian@jboss.org" wrote:

                          2) How can the Factory(Method) annotations work?

                          These are used at object construction. You don't know the type until
                          the object is constructed so how can read the annotations? :-)


                          At least you didn't create an @ClassLoader annotation :-)

                          • 25. Re: enums, generics and other animals
                            alesj

                             

                            "adrian@jboss.org" wrote:
                            At least you didn't create an @ClassLoader annotation :-)

                            This one is always my favorite to mention, check the IoC slides. ;-)

                            • 26. Re: enums, generics and other animals
                              anil.saldhana

                              Adrian, are you currently at Hyde Park in London (or the particular park) where you can complain/bitch about things without worrying about being arrested?

                              • 27. Re: enums, generics and other animals
                                alesj

                                 

                                "adrian@jboss.org" wrote:
                                Why have you created a package called "enums"?

                                Now you complain. :-)
                                I proposed the name in the first few posts.
                                Just following the silence rule. ;-)

                                "adrian@jboss.org" wrote:

                                Would you create a package called "classes"? :-)

                                Why are then plenty of interfaces packages (not in MC, but 'around')?
                                And the annotations, like you figured out your self.
                                And I didn't start with those. ;-)

                                "adrian@jboss.org" wrote:

                                Either put the enums in the annotations package or create a package called model or something. This package would also contain callback interfaces referenced (like the ScopeFactory in the metadata repository) so calling it "enums" is plain wrong.

                                OK, model it is.

                                "adrian@jboss.org" wrote:

                                1) Why do you have class names as strings in the annotations?
                                To be able to read the annotations at all the classloader must exist
                                so there's no problem with letting the users specify classes.

                                Bug. :-)
                                That's why I called the commit initial.

                                "adrian@jboss.org" wrote:

                                2) How can the Factory(Method) annotations work?

                                These are used at object construction. You don't know the type until
                                the object is constructed so how can read the annotations? :-)

                                Why should the object be constructed?
                                Isn't class enough, to read off the annotations?

                                @Factory does what our constructor xml factory does as well.
                                It just happens to be on the class rather than on the constructor.
                                If the factoryClass is not specified, the class on which it is defined is used.

                                @FactoryMethod is probably an extension, but functionally similar to @Factory with class and method specified.
                                You scan the static methods which are annotated to be factory methods.

                                • 28. Re: enums, generics and other animals

                                   

                                  "anil.saldhana@jboss.com" wrote:
                                  Adrian, are you currently at Hyde Park in London (or the particular park) where you can complain/bitch about things without worrying about being arrested?


                                  It's called "Freedom of Speech". In England you don't have to be at Hyde Park,
                                  as long as you don't "Incite Violence" (recently extended to include
                                  "Promoting terroism"), "Disturb the Peace" or "Blaspheme".

                                  Although by strange co-incidence it looks like the latter is no longer the law
                                  as of this week. ;-)
                                  http://news.bbc.co.uk/2/hi/entertainment/7279182.stm

                                  • 29. Re: enums, generics and other animals

                                     

                                    "alesj" wrote:
                                    "adrian@jboss.org" wrote:
                                    Why have you created a package called "enums"?

                                    Now you complain. :-)
                                    I proposed the name in the first few posts.
                                    Just following the silence rule. ;-)


                                    This thread is pages long (you expect me to spot a package name
                                    called enums in discussion about enums ;-)


                                    @Factory does what our constructor xml factory does as well.
                                    It just happens to be on the class rather than on the constructor.
                                    If the factoryClass is not specified, the class on which it is defined is used.

                                    @FactoryMethod is probably an extension, but functionally similar to @Factory with class and method specified.
                                    You scan the static methods which are annotated to be factory methods.


                                    Ok, makes sense now, it just looked stupid at first glance. I should RTFM
                                    and remember to engage my brain before opening my mouth :-)
                                    /**
                                     * Mark static method as factory method.
                                     *
                                     * @author <a href="mailto:ales.justin@jboss.com">Ales Justin</a>
                                     */
                                    public @interface FactoryMethod