<?xml version="1.0" encoding="UTF-8"?>
<!-- A prototype xsd schema for the pojoserver xml deployer
$Id: bean-deployer_1_0.xsd,v 1.1.2.1 2005/09/16 23:22:16 adrian Exp $
 -->
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema"
   targetNamespace="urn:jboss:bean-deployer"
   xmlns="urn:jboss:bean-deployer"
   elementFormDefault="qualified"
   attributeFormDefault="unqualified"
   version="1.0">

   <xsd:annotation>
      <xsd:documentation>
         <![CDATA[
         The xml deployer schema. The deployment document instance
         root element should reference the schema in the root
         deployment element using something like:

         <deployment
            xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            xsi:schemaLocation="urn:jboss:bean-deployer bean-deployer_1_0.xsd"
            xmlns="urn:jboss:bean-deployer">
         ...
         ]]>
      </xsd:documentation>
   </xsd:annotation>

   <xsd:element name="deployment" type="deploymentType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The root of the xml deployer instance document
           ]]>
         </xsd:documentation>
      </xsd:annotation>
   </xsd:element>

   <xsd:complexType name="deploymentType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The deployment contains a number of beans and bean factories.
           
           e.g.
           <deployment ...>
              <bean .../>          
              <bean .../>    
              <beanfactory .../>
           </deployment>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="bean" type="beanType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="beanfactory" type="beanfactoryType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
   </xsd:complexType>

   <xsd:complexType name="beanType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The bean is an instance of a pojo.
           
           e.g.
           <bean name="MyName" class="com.acme.POJO">
              <constructor .../>
              <property .../>
              <property .../>
              <depends .../>
           </bean>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="annotation" type="annotationType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="constructor" type="constructorType" minOccurs="0"/>
         <xsd:element name="property" type="propertyType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="create" type="lifecycleType" minOccurs="0"/>
         <xsd:element name="start" type="lifecycleType" minOccurs="0"/>
         <xsd:element name="stop" type="lifecycleType" minOccurs="0"/>
         <xsd:element name="destroy" type="lifecycleType" minOccurs="0"/>
         <xsd:element name="depends" type="dependsType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="demand" type="demandType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="supply" type="supplyType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="name" type="xsd:string" use="optional"/>
      <xsd:attribute name="class" type="xsd:token" use="required"/>
      <xsd:attribute name="mode" type="controllerModeType" use="optional"/>
   </xsd:complexType>

   <xsd:complexType name="beanfactoryType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The beanfactory is a org.jboss.beans.metadata.plugins.factory.GenericBeanFactory deployment.
           This gives you a factory such you can invoke create() multiple times with the guarantee
           that the injected objects are "installed".

           e.g.
           <bean name="User" class="com.acme.User">
              <property name="factory"><inject bean="Factory"/></property>
           </bean>
           
           <beanfactory name="Factory" class="com.acme.SomeBean">
              <property name="someProperty"><inject bean="SomeOtherBean"/></property>
           </beanFactory>
           
           package com.acme.User;
           public class User {
              // factory has been configured at this point
              public void setFactory(GenericBeanFactory factory) { 
                 SomeBean bean1 = factory.create();
                 System.out.println(bean1.getSomeProperty()); // "SomeOtherBean"
                 SomeBean bean2 = factory.create();
                 System.out.println(bean2.getSomeProperty()); // "SomeOtherBean"
              }
           }
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="constructor" type="constructorType" minOccurs="0"/>
         <xsd:element name="property" type="propertyType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="name" type="xsd:string" use="optional"/>
      <xsd:attribute name="class" type="xsd:token" use="required"/>
   </xsd:complexType>

   <xsd:complexType name="constructorType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The constructor for this bean(factory) instance.
           
           e.g. simple constructor - new POJO(new String("String value"));
           <bean name="MyBean" class="com.acme.POJO">
              <constructor>
                 <parameter>String value</parameter>
              </constructor>
           </bean>
           
           e.g. static factory - com.acme.Factory.newInstance(new String("String value"));
           <bean name="MyBean" class="com.acme.POJO">
              <constructor factoryClass="com.acme.Factory" factoryMethod="newInstance">
                 <parameter>String value</parameter>
              </constructor>
           </bean>

           e.g. instance factory - "SomeOtherBean".newInstance(new String("String value"));
           <bean name="MyBean" class="com.acme.POJO">
              <constructor factoryMethod="newInstance">
                 <factory bean="SomeOtherBean"/>
                 <parameter>String value</parameter>
              </constructor>
           </bean>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="annotation" type="annotationType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="factory" type="dependencyType" minOccurs="0"/>
         <xsd:element name="parameter" type="parameterType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="factoryClass" type="classNameType" use="optional"/>
      <xsd:attribute name="factoryMethod" type="xsd:token" use="optional"/>
   </xsd:complexType>

   <xsd:complexType name="lifecycleType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The lifecycle lets you override the method parameters passed to the
           create, start, stop, destroy lifecycle callbacks.
           
           e.g.
           <bean>
              <create method="initialize">
                 <parameter>String value</parameter>
              </create>
           </bean>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="annotation" type="annotationType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="parameter" type="parameterType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="method" type="xsd:token" use="optional"/>
   </xsd:complexType>

   <xsd:complexType name="dependencyType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A dependency represents an injection into the bean.
           They can be used anywhere a string value can appear.
           
           e.g. Bean instance - "InjectedIntoMe".setSomeProperty("BeanInjected");
           <bean name="InjectedIntoMe" ...>
              <property name="someProperty"><inject bean="BeanInjected"/>
           </bean>
           <bean name="BeanInjected" .../>
           
           e.g. Bean property - "InjectedIntoMe".setSomeProperty("BeanInjected".getOtherProperty());
           <bean name="InjectedIntoMe" ...>
              <property name="someProperty"><inject bean="BeanInjected" property="otherProperty"/>
           </bean>
           <bean name="BeanInjected" .../>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:attribute name="bean" type="xsd:string" use="required"/>
      <xsd:attribute name="property" type="xsd:string" use="optional"/>
      <xsd:attribute name="state" type="controllerStateType" use="optional"/>
   </xsd:complexType>

   <xsd:complexType name="parameterType" mixed="true">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A parameter is used to define the constructor, factory
           and lifecycle method usage.
           
           e.g. Using number of parameters when this is unique enough
           <bean ...>
              <constructor>
                 <parameter>1st Parameter</parameter>
                 <parameter>2nd Parameter</parameter>
              </constructor>
           </bean>
           
           e.g. Explicitly stating the parameter type to resolve overloading
           <bean ...>
              <constructor>
                 <parameter>1st Parameter</parameter>
                 <parameter class="java.lang.String">2nd Parameter</parameter>
              </constructor>
           </bean>

           e.g. To override the injected type use <value/>
           <bean ...>
              <constructor>
                 <parameter>1st Parameter</parameter>
                 <!-- Parameter is java.lang.Object, but we inject a String -->
                 <parameter class="java.lang.Object">
                    <value class="java.lang.String">2nd Parameter</value>
                 </parameter>
              </constructor>
           </bean>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="annotatedValueType"/>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="propertyType" mixed="true">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A property defines values passed to the setters.
           
           e.g. Using the type from the setter argument
           <bean ...>
              <property name="someProperty">Some value</property>
           </bean>
           
           e.g. Overridding the injected type
           <bean ...>
              <property name="someProperty" class="java.lang.String">Some value</property>
           </bean>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="namedValueType"/>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="annotationType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The annotation type represents an annotation on the particular join point.
           TODO: This is currently unimplemented.
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="attribute" type="annotationAttributeType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="name" type="xsd:string" use="required"/>
   </xsd:complexType>

   <xsd:complexType name="annotationAttributeType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           An attribute attached to a particular annotation.
           TODO: This is currently unimplemented.
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:attribute name="name" type="xsd:string" use="required"/>
      <xsd:attribute name="value" type="xsd:string" use="required"/>
   </xsd:complexType>

   <xsd:simpleType name="classNameType">
      <xsd:annotation>
         <xsd:documentation> The elements that use this type designate the name
            of a Java class or interface. The name is in the form of a "binary
            name", as defined in the JLS and as used in Class.forName().
         </xsd:documentation>
      </xsd:annotation>
      <xsd:restriction base="xsd:string">
         <xsd:whiteSpace value="collapse"/>
      </xsd:restriction>
   </xsd:simpleType>

   <xsd:group name="valueGroup">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           The value group represents the comment elements of the other configurations
           <parameter/>, <property/> or collection components
           e.g.

           <property name="someProperty">
              <list><value class="java.lang.String">Hello</value></list>
           </property>
           
           e.g. This also defines the null value
           <property name="someProperty"><null/></property>
           as opposed to the empty string
           <property name="someProperty"></property>
           or the string "null"
           <property name="someProperty">null</property>

           TODO: "any" is currently unimplemented.
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:choice>
         <xsd:element name="value" type="plainValueType"/>
         <xsd:element name="collection" type="collectionType"/>
         <xsd:element name="list" type="listType"/>
         <xsd:element name="set" type="setType"/>
         <xsd:element name="array" type="arrayType"/>
         <xsd:element name="map" type="mapType"/>
         <xsd:element name="inject" type="dependencyType"/>
         <xsd:element name="null">
            <xsd:complexType/>
         </xsd:element>
         <xsd:any namespace="##other" processContents="strict">
            <xsd:annotation>
               <xsd:documentation>An extension value</xsd:documentation>
            </xsd:annotation>
         </xsd:any>
      </xsd:choice>
   </xsd:group>

   <xsd:complexType name="plainValueType" mixed="true">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A simple value, used in collections and to specify a type for parameters.
           
           e.g.
           <parameter><value class="com.acme.MyClass">xxx</value></parameter>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:attribute name="class" type="classNameType" use="optional"/>
   </xsd:complexType>

   <xsd:complexType name="valueType" mixed="true">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A value that can take other values, i.e. properties and parameters.
           
           e.g.
           <parameter><value class="com.acme.MyClass">xxx</value></parameter>
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="plainValueType">
            <xsd:sequence>
               <xsd:choice minOccurs="0">
                  <xsd:group ref="valueGroup"/>
               </xsd:choice>
            </xsd:sequence>
         </xsd:extension>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="annotatedValueType" mixed="true">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A value that can take annotations.
           TODO: This is currently unimplemented.
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="valueType">
            <xsd:sequence>
               <xsd:element name="annotation" type="annotationType" minOccurs="0" maxOccurs="unbounded"/>
            </xsd:sequence>
         </xsd:extension>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="namedValueType" mixed="true">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A value that has a name, currently only a property.
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="annotatedValueType">
            <xsd:attribute name="name" type="xsd:string" use="required"/>
         </xsd:extension>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="baseCollectionType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            A collection defines a java.util.Collection object.
            It has two class definitions:
            class: The implementation class of the collection
            elementClass: The default implementation class of the elements
            The default "class" is a java.util.ArrayList unless the point of injection
            defines a concrete type, e.g. in the signature of the setter
            
            example:
            <property name="whatever" class="java.util.ArrayList" elementClass="java.net.URL">
               <value>http://localhost</value> <!-- Creates a URL -->
               <value class="java.lang.String">http://localhost</value> <!-- Creates a String -->
            </property>
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:choice minOccurs="0" maxOccurs="unbounded">
         <xsd:group ref="valueGroup"/>
      </xsd:choice>
      <xsd:attribute name="class" type="classNameType" use="optional"/>
      <xsd:attribute name="elementClass" type="classNameType" use="optional"/>      
   </xsd:complexType>

   <xsd:complexType name="collectionType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A collection, see baseCollectionType
           the default collection is a java.util.ArrayList
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="baseCollectionType"/>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="listType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A list, see baseCollectionType
           the default list is a java.util.ArrayList
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="baseCollectionType"/>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="setType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           A set, see baseCollectionType
           the default set is a java.util.HashSet
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="baseCollectionType"/>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="arrayType">
      <xsd:annotation>
         <xsd:documentation>
           <![CDATA[
           An array, see baseCollectionType
           the default array is a java.lang.Object[]
           ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:complexContent>
         <xsd:extension base="baseCollectionType"/>
      </xsd:complexContent>
   </xsd:complexType>

   <xsd:complexType name="mapType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            A map defines a java.util.Map object.
            It has three class definitions:
            class: The implementation class of the class
            keyClass: The default implementation class of the keys
            valueClass: The default implementation class of the values
            The default "class" is a java.util.HashMap unless the point of injection
            defines a concrete type, e.g. in the signature of the setter
            
            e.g.:
            <property name="whatever" class="java.util.HashMap" keyClass="java.lang.String" valueClas="java.net.URL">
               <!-- map.put(new String("default"), new URL("http://localhost"));
               <entry><key>default</key><value>http://localhost</value>
               <!-- map.put(new String("default"), new String("http://localhost"));
               <entry><key>default</key><value class="java.lang.String">http://localhost</value>
            </property>
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="entry" type="entryType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="class" type="classNameType" use="optional"/>
      <xsd:attribute name="keyClass" type="classNameType" use="optional"/>      
      <xsd:attribute name="valueClass" type="classNameType" use="optional"/>      
   </xsd:complexType>

   <xsd:complexType name="entryType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            An entry in map. These are made of key/value pairs
            
            e.g.:
            <entry><key>default</key><value>http://localhost</value>
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:sequence>
         <xsd:element name="key" type="valueType" minOccurs="0" maxOccurs="unbounded"/>
         <xsd:element name="value" type="valueType" minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
   </xsd:complexType>

   <xsd:complexType name="dependsType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            The depends element is used to define that one bean depends upon
            another for the create/start/stop/destroy lifecycle
            
            e.g.:
            <bean name="IGoFirst" .../>
            <bean name="IGoSecond" ...>
               <depends>IGoFirst</depends>
            </bean>
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:simpleContent>
         <xsd:extension base="xsd:string"/>
      </xsd:simpleContent>
   </xsd:complexType>

   <xsd:complexType name="demandType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            The demand is used to specify a dependency on a supply
            and when the demand is should be deplied
            
            e.g.:
            ISupply must be installed before IDemand is constructed

            <bean name="IDemand" ... whenRequired="Instantiated">
               <demand>theSupply</demand>
            </bean>
            <bean name="ISupply" ...>
               <supply>theSupply</supply>
            </bean>
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:simpleContent>
         <xsd:extension base="xsd:string">
            <xsd:attribute name="whenRequired" type="controllerStateType" use="optional"/>
         </xsd:extension>
      </xsd:simpleContent>
   </xsd:complexType>

   <xsd:complexType name="supplyType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            The supply is used to specify that the bean supplies a demanded dependency
            
            e.g.:
            <bean name="IDemand" ...>
               <demand>theSupply</demand>
            </bean>
            <bean name="ISupply" ...>
               <supply>theSupply</supply>
            </bean>
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:simpleContent>
         <xsd:extension base="xsd:string"/>
      </xsd:simpleContent>
   </xsd:complexType>

   <xsd:simpleType name="controllerStateType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            The controller state is used to say when dependencies must be satisfied.
            Valid values include:
            Described
            Instantiated
            Configured
            Create
            Start
            Installed
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:restriction base="xsd:string">
         <xsd:whiteSpace value="collapse"/>
      </xsd:restriction>
   </xsd:simpleType>

   <xsd:simpleType name="controllerModeType">
      <xsd:annotation>
         <xsd:documentation>
            <![CDATA[
            The controller mode, used to control how automatic the bean progresses
            through the controller lifecyle (the states).
            Valid values include:
            Automatic (default) - the controller takes the bean to "Installed"
            Manual - the user must tell the controller the required state
            On Demand - the controller takes the bean to "Installed" when another bean depends on it
            Disabled - the controller or user cannot change the state
            ]]>
         </xsd:documentation>
      </xsd:annotation>
      <xsd:restriction base="xsd:string">
         <xsd:whiteSpace value="collapse"/>
      </xsd:restriction>
   </xsd:simpleType>

   <!-- 
     WARN:
     Do not use this in the bean deployer, it won't work!
     FIXME:
     The correct way to do this is to have two separate
     schemas (one for deployments the other for beans) 
     then use schema imports.
   -->
   <xsd:element name="bean" type="beanType"/>

   <!-- 
     WARN:
     Do not use this in the bean deployer, it won't work!
     FIXME:
     The correct way to do this is to have two separate
     schemas (one for deployments the other for beans) 
     then use schema imports.
   -->
   <xsd:element name="beanfactory" type="beanfactoryType"/>

</xsd:schema>
