9 Replies Latest reply on Sep 18, 2006 11:03 AM by Scott Stark

    ENC Deployment

    Adrian Brock Master

      Since this came up last week, this is an explanation
      of how I see it working.

      It based on the MetaData so read that first:
      http://www.jboss.com/index.html?module=bb&op=viewtopic&t=90873

      The runtime component is just a piece of metadata
      that will be available from the stack.

      e.g. possible ENC jndi implementation

      protected Object lookup(String Name) throws NamingException
      {
       MetaData metaData = repository.peek();
       ENC enc = metadata.getMetaData(ENC.class);
       return enc.getBinding(name); // This will likely just go to the real jndi binding
      }
      


        • 1. Re: ENC Deployment
          Adrian Brock Master

          The major work is how in the ENC is constructed.
          Obviously there will be an ENC deployer.

          This needs to collect all the metadata to populate the ENC structure:
          1) From the spec defined xml
          2) From override xml
          3) From annotations on the class(es)
          4) From the metadata itself (e.g. instance overrides)

          In my opinion, it is best that the ENC Deployer just does step 4.
          Steps 1-3 should be done by the earlier parsers that know
          what to look at, e.g. the ejb, web and client deployers

          If these populate the MetaData hierarchy (converting xml into
          annotations) the ENC deployer just needs to know the ScopeKey
          and collect all the annotations.

          • 2. Re: ENC Deployment
            Adrian Brock Master

            The next step is what the ENC deployer does about the
            dependencies.

            e.g. If I want a DataSource, the DataSource should be deployed
            before I start.

            The way this should work is that the object that wants an ENC
            should be deployed through the Controller, either as a POJO
            or JMX with the relevant dependency:

            <bean name="MyEJB">
             <property name="enc">
             <inject bean="MyEJB,ENCFactory" property="enc"/>
             </property>
             etc.
            


            The ENC deployer creates the ENCFactory using the metadata
            from the scope it was provided with.

            • 3. Re: ENC Deployment
              Adrian Brock Master

              Which leaves the final piece of the puzzle.

              When the ENCFactory is constructed it could have dependencies like:

              <bean name="ENCFactory.MyEJB">
               <property name="beans">
               <map>
               <key>jdbc/DataSource</key>
               <value><inject bean="SomeDataSource"/></value>
              etc.
              


              The SomeDataSource will come from the annotations.

              But what if it is just a jndi binding?

              <bean name="ENCFactory.MyEJB">
               <property name="bindngs">
               <map>
               <key>jdbc/DataSource</key>
               <value>java:/MyDataSource</value>
              


              The way to solve this is to remove the jndi binding from the services
              themselves, so we can create a "registry" of bindings.
              (This also means services don't need to know the jndi population
              mechanism as well).

              Using a use case configuration:
              <bean name="SomeDataSource">
               <property name="JNDIBinding">
               <jndibinding xmlns="urn:jboss:naming:1.0" binding="java:/MyDataSource" bean="SomeDataSoure"/>
              etc.
              


              The jndibinding creates a bean that has a contract like:
              public interface JNDIBinding
              {
               public void setObject(Object object);
              }
              


              When setObject is invoked with a value, the binding
              is added to jndi when it is null it is removed.

              It also gives a bean to depend upon for the "bindings" above.
              e.g. the use case config would really be something like:
              <bean name="java:/MyDataSource" whenRequired="constructed">
               <factory><inject bean="JNDIBindingFactory"/></factory>
               <depends>SomeDataSource</depends>
              </bean>
              


              i.e. The binding is injected into once it is constructed,
              but it doesn't "start" (bind into jndi) until the bean itself is installed.
              What it binds is determined by the setObject().

              Obviously there are additional complications/configuration options
              for when:
              1) The object is not serializable/referencable
              2) The "bindings" above reference an external jndi and so
              cannot form a real dependency
              etc.

              • 4. Re: ENC Deployment
                Adrian Brock Master

                 

                "adrian@jboss.org" wrote:

                Using a use case configuration:
                <bean name="SomeDataSource">
                 <property name="JNDIBinding">
                 <jndibinding xmlns="urn:jboss:naming:1.0" binding="java:/MyDataSource" bean="SomeDataSource"/>
                etc.
                



                We probably need to make this error prone so we can remove
                the bean="SomeDataSoure" and allow it depend on the parent.

                Something like:
                <bean name="java:/MyDataSource" whenRequired="constructed">
                 <factory><inject bean="JNDIBindingFactory"/></factory>
                 <depends><parent/></depends>
                </bean>
                



                • 5. Re: ENC Deployment
                  Bill Burke Master

                   

                  "adrian@jboss.org" wrote:
                  The major work is how in the ENC is constructed.
                  Obviously there will be an ENC deployer.

                  This needs to collect all the metadata to populate the ENC structure:
                  1) From the spec defined xml
                  2) From override xml
                  3) From annotations on the class(es)
                  4) From the metadata itself (e.g. instance overrides)

                  In my opinion, it is best that the ENC Deployer just does step 4.
                  Steps 1-3 should be done by the earlier parsers that know
                  what to look at, e.g. the ejb, web and client deployers

                  If these populate the MetaData hierarchy (converting xml into
                  annotations) the ENC deployer just needs to know the ScopeKey
                  and collect all the annotations.


                  I think we talked about this before...

                  These need to be the steps:

                  1) A registration phase for all deployments
                  2) Analyzation of XMLs, annotations and metadata to determine dependencies.

                  This step is partially complex as bindings can be determined by both the classtype of the component and position in the deployment (is the referenced component in the EJB-JAR? No? The EAR? No? Globally?)

                  3) Register dependencies with controller
                  4) Start and populate ENC and do any injections.

                  I do this in the current J2EE injection/XML processing. Within this phase I create two different objects. One object is an ENCInjector object. This object gets registered with Container and executed at component startup. If there are any injections to be done, these are registered with the container using a different object, an Injector. Injectors inject into object instances and are keyed based on classtype.

                  For EJB Containers there can be multiple class types that have injectors. The BeanClass itself, and any interceptor classes.

                  For Web Containers, you have servlet classes, filter classes, context listener classes, and I believe, taglib classes. The Web tier has the additional problem of JSP classes which are not available at deployment time or may be changed on the fly.

                  I have created an abstraction so that the ENC/Injection Handlers are shared between the EJB and Web tiers



                  • 6. Re: ENC Deployment
                    Bill Burke Master

                     

                    "adrian@jboss.org" wrote:
                    The next step is what the ENC deployer does about the
                    dependencies.

                    e.g. If I want a DataSource, the DataSource should be deployed
                    before I start.

                    The way this should work is that the object that wants an ENC
                    should be deployed through the Controller, either as a POJO
                    or JMX with the relevant dependency:

                    <bean name="MyEJB">
                     <property name="enc">
                     <inject bean="MyEJB,ENCFactory" property="enc"/>
                     </property>
                     etc.
                    


                    The ENC deployer creates the ENCFactory using the metadata
                    from the scope it was provided with.


                    That's nice for basic beans, but as I showed before, it is just not so simple for Java EE land where the ENC -> Global JNDI binding cannot be determine by the available metadata. To put it in other terms, the available metadata may not be enough to construct a Kernel identity or exact JNDI binding. The referenced component will need to be searched for based on the position of the component in the deployment and based on the little of metadata that was made available by the application developer.

                    • 7. Re: ENC Deployment
                      Adrian Brock Master

                       

                      "bill.burke@jboss.com" wrote:

                      I have created an abstraction so that the ENC/Injection Handlers are shared between the EJB and Web tiers


                      So this needs moving into the new deployment layer.

                      • 8. Re: ENC Deployment
                        Adrian Brock Master

                         

                        "bill.burke@jboss.com" wrote:

                        That's nice for basic beans, but as I showed before, it is just not so simple for Java EE land where the ENC -> Global JNDI binding cannot be determine by the available metadata. To put it in other terms, the available metadata may not be enough to construct a Kernel identity or exact JNDI binding. The referenced component will need to be searched for based on the position of the component in the deployment and based on the little of metadata that was made available by the application developer.


                        Whatever mechanism is used needs to be validatable via a "dry run"
                        through the deployers.
                        i.e. It should be possible to create a profile (list of deployments)
                        and then say "does it make sense?", "what is missing/unresolved?", etc.

                        If that is not possible then the modal is broken.

                        Implicit rules like "position in the file" are supportable but
                        inherently prone to error/breakage when the file is changed.
                        e.g. a conflicting definition is interpolated
                        or the order is changed by some user/tool/ide that doesn't understand
                        the importance.

                        But that's not my problem. :-)
                        I've always hated such "scripting" as being brittle.

                        • 9. Re: ENC Deployment
                          Scott Stark Master

                           

                          "bill.burke@jboss.com" wrote:

                          That's nice for basic beans, but as I showed before, it is just not so simple for Java EE land where the ENC -> Global JNDI binding cannot be determine by the available metadata. To put it in other terms, the available metadata may not be enough to construct a Kernel identity or exact JNDI binding. The referenced component will need to be searched for based on the position of the component in the deployment and based on the little of metadata that was made available by the application developer.


                          The rules for completing the metadata need to be a pluggable aspect of the deployment layer so that when deployment processing is complete, the enc deployer and runtime aspect have nothing to do but create the context and install the correct one. A merge of the org.jboss.ejb.EjbUtil link resolution and whatever new rules have been added should be the starting point.