5 Replies Latest reply on Jun 20, 2004 3:21 AM by aloubyansky

    Foreign Key is also Primary Key

    minimini

      Dear Jboss Experts

      I've a question on cmr. I've read a lot of topics in this forum relating on this, but I haven't found an entry for my specific problem:

      i've an ejb with a composed primary key. one field of the primary key is defined as foreign key column too (and not null). i've configured my container to insert-after-ejb-post-create.

      My problem is, that I don't know, how to set the PK / FK - field of the bean, when I set it during ejbCreate() the following exception occurs:
      A CMR field cannot be set or added to a relationship in ejbCreate; this should be done in the ejbPostCreate method instead [EJB 2.0 Spec. 10.5.2].

      When I set it in ejbPostCreate the following exception is the result:
      A CMP field that is a member of the primary key can only be set in ejbCreate [EJB 2.0 Spec. 10.3.5]

      I can't change the DB constraints because other applications work with this DB too.

      IMHO this should not be such a big problem, but I don't see a solution nor a sound workaround... Every help highly appreciated :-)

        • 1. Re: Foreign Key is also Primary Key
          aloubyansky

          Could you post the ejbCreate implementation, stacktrace and DDs?

          • 2. Re: Foreign Key is also Primary Key
            madadi

            Dear Alexey Loubyansky,

            I too having same problem actually i thought that i solved but it works due to i created another primary key in second table.

            userid is Primary key for One table and Foreign Key for 2nd table.I created the one more Primary key in second table(sem) than i can store info from registration form but when i want to use foreign key of second table to store info it does't work.



            Servlet Code:


            beanRemote = home.create(fname,lname,dob,sex,userid,password,street,city,zipc,phone,email );

            db = home.findByPrimaryKey(userid);


            beanRemotes = homes.create(userid,dept,mno,sem );

            dbs = homes.findByPrimaryKey(sem);





            private boolean checkUSERID ( String userid, InitialContext context )

            throws NamingException {
            Object object = context.lookup("RegistrationEjb");
            RegistrationHome home = ( RegistrationHome )
            PortableRemoteObject
            .narrow ( object, RegistrationHome.class );

            try {
            System.out.println("");
            Registration data = home.findByPrimaryKey( userid );
            if ( data!=null ) {
            if ( data.getUserid().equals( userid ) ) {
            return true;
            }
            } else {
            return false;
            }

            } catch ( Exception exception ) {
            return false;
            }


            return true;
            }


            private boolean checkSEM ( String sem, InitialContext context )

            throws NamingException {
            Object object = context.lookup("RegistrationspecificEjb");
            RegistrationspecificHome home = ( RegistrationspecificHome )
            PortableRemoteObject
            .narrow ( object, RegistrationspecificHome.class );

            try {
            System.out.println("");
            Registrationspecific data = home.findByPrimaryKey( sem );
            if ( data!=null ) {
            if ( data.getSem().equals( sem ) ) {
            return true;
            }
            } else {
            return false;
            }

            } catch ( Exception exception ) {
            return false;
            }


            return true;
            }

            ejb-code:

            public interface RegistrationspecificHome extends EJBHome{

            public static final String COMP_NAME="java:comp/env/ejb/madadi/Registrationspecific";

            public static final String JNDI_NAME="ejb/madadi/RegistrationspecificEjb";

            public Registrationspecific create(String userid,String dept,String mno,String sem) throws RemoteException, CreateException;
            public Registrationspecific findByPrimaryKey(String sem) throws FinderException, RemoteException;
            public Registrationspecific findAll() throws FinderException, RemoteException;





            public interface RegistrationHome extends EJBHome{

            public static final String COMP_NAME="java:comp/env/ejb/madadi/Registration";

            public static final String JNDI_NAME="ejb/madadi/RegistrationEjb";

            public Registration create(String fname, String lname, String dob, String sex, String userid, String password, String street, String city, String zipc, String phone, String email) throws RemoteException, CreateException;
            public Registration findByPrimaryKey(String userid) throws FinderException, RemoteException;
            public Registration findAll() throws FinderException, RemoteException;

            }





            public abstract class RegistrationspecificEjb implements EntityBean {



            public abstract String getUserid();
            public abstract String getDept();
            public abstract String getMno();
            public abstract String getSem();

            public abstract void setUserid(String userid);
            public abstract void setDept(String dept);
            public abstract void setMno(String mno);
            public abstract void setSem(String sem);

            public String ejbCreate(String userid,String dept,String mno,String sem ) throws RemoteException, CreateException
            {


            setUserid(userid);
            setDept(dept);
            setMno(mno);
            setSem(sem);


            return (null);

            }



            public abstract class RegistrationEjb implements EntityBean {

            // Called by container after setEntityContext
            // Use the abstract methods to set parameters


            public abstract String getFname();
            public abstract String getLname();
            public abstract String getUserid();
            public abstract String getPassword();
            public abstract String getDob();
            public abstract String getStreet();
            public abstract String getCity();
            public abstract String getZipc();
            public abstract String getPhone();
            public abstract String getEmail();
            public abstract String getSex();


            public abstract void setFname(String fname);
            public abstract void setLname(String lname);
            public abstract void setUserid(String userid);
            public abstract void setPassword(String password);
            public abstract void setDob(String dob);
            public abstract void setStreet(String street);
            public abstract void setCity(String city);
            public abstract void setZipc(String zipc);
            public abstract void setPhone(String phone);
            public abstract void setEmail(String email);
            public abstract void setSex(String sex);

            public String ejbCreate(String fname, String lname, String dob, String sex, String userid, String password, String street, String city, String zipc, String phone, String email ) throws RemoteException, CreateException
            {
            // Called by container after setEntityContext
            // Use the abstract methods to set parameters

            setFname(fname);
            setLname(lname);
            setUserid(userid);
            setPassword(password);
            setDob(dob);
            setStreet(street);
            setCity(city);
            setZipc(zipc);
            setPhone(phone);
            setEmail(email);
            setSex(sex);


            return (null);

            }


            xml-files:


            <?xml version="1.0" encoding="UTF-8"?>
            <!DOCTYPE ejb-jar PUBLIC "-//Sun Microsystems, Inc.//DTD Enterprise JavaBeans
            2.0//EN" "http://java.sun.com/j2ee/dtds/ejb-jar_2_0.dtd">
            <ejb-jar>

            Registration
            <display-name>Registration</display-name>

            <enterprise-beans>

            <ejb-name>RegistrationEjb</ejb-name>
            <ejb-class>madadi.entity.RegistrationEjb</ejb-class>
            madadi.entity.RegistrationHome
            madadi.entity.Registration
            <persistence-type>Container</persistence-type>
            <prim-key-class>java.lang.String</prim-key-class>
            False
            <primkey-field>userid</primkey-field>
            <abstract-schema-name>Registration</abstract-schema-name>
            <cmp-version>2.x</cmp-version>
            <cmp-field>
            <field-name>fname</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>lname</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>dob</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>sex</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>userid</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>password</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>street</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>city</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>zipc</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>phone</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>email</field-name>
            </cmp-field>


            <query-method>
            <method-name>findAll</method-name>
            <method-params />
            </query-method>
            <return-type-mapping>Local</return-type-mapping>
            <ejb-ql><![CDATA[SELECT OBJECT(pdata) FROM Registration as pdata]]></ejb-ql>


            <query-method>
            <method-name>findByPrimaryKey</method-name>
            <method-params>
            <method-param>java.lang.String</method-param>
            </method-params>
            </query-method>
            <return-type-mapping>Local</return-type-mapping>
            <ejb-ql><![CDATA[SELECT OBJECT(pdata) FROM Registration as pdata]]></ejb-ql>





            <ejb-name>RegistrationspecificEjb</ejb-name>
            <ejb-class>madadi.entity.RegistrationspecificEjb</ejb-class>
            madadi.entity.RegistrationspecificHome
            madadi.entity.Registrationspecific
            <persistence-type>Container</persistence-type>
            <prim-key-class>java.lang.String</prim-key-class>
            False
            <primkey-field>sem</primkey-field>
            <abstract-schema-name>Registrationspecific</abstract-schema-name>
            <cmp-version>2.x</cmp-version>

            <cmp-field>
            <field-name>userid</field-name>
            </cmp-field>

            <cmp-field>
            <field-name>dept</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>mno</field-name>
            </cmp-field>
            <cmp-field>
            <field-name>sem</field-name>
            </cmp-field>

            <query-method>
            <method-name>findAll</method-name>
            <method-params />
            </query-method>
            <return-type-mapping>Local</return-type-mapping>
            <ejb-ql><![CDATA[SELECT OBJECT(sdata) FROM Registration as sdata]]></ejb-ql>


            <query-method>
            <method-name>findByPrimaryKey</method-name>
            <method-params>
            <method-param>java.lang.String</method-param>
            </method-params>
            </query-method>
            <return-type-mapping>Local</return-type-mapping>
            <ejb-ql><![CDATA[SELECT OBJECT(sdata) FROM Registration as sdata]]></ejb-ql>




            </enterprise-beans>

            <assembly-descriptor>
            <container-transaction>

            <ejb-name>RegistrationEjb</ejb-name>
            <method-name>*</method-name>

            <trans-attribute>Supports</trans-attribute>
            </container-transaction>

            <container-transaction>

            <ejb-name>RegistrationspecificEjb</ejb-name>
            <method-name>*</method-name>

            <trans-attribute>Supports</trans-attribute>
            </container-transaction>

            <security-role>
            no description
            <role-name>users</role-name>
            </security-role>



            <ejb-relation>
            <ejb-relation-name>userid in specific_data is a foreign key</ejb-relation-name>
            <ejb-relationship-role>
            <ejb-relationship-role-name>RegistrationEjb</ejb-relationship-role-name>
            One
            <relationship-role-source>
            <ejb-name>RegistrationEjb</ejb-name>
            </relationship-role-source>
            <cmr-field>
            <cmr-field-name>userid</cmr-field-name>
            <cmr-field-type>java.lang.String</cmr-field-type>
            </cmr-field>
            </ejb-relationship-role>
            <ejb-relationship-role>
            <ejb-relationship-role-name>RegistrationspecificEjb</ejb-relationship-role-name>
            one
            <cascade-delete />
            <relationship-role-source>
            <ejb-name>RegistrationspecificEjb</ejb-name>
            </relationship-role-source>
            </ejb-relationship-role>
            </ejb-relation>



            </assembly-descriptor>

            </ejb-jar>


            regards
            madadi

            • 3. Re: Foreign Key is also Primary Key
              aloubyansky

               

               <cmr-field>
              <cmr-field-name>userid</cmr-field-name>
              <cmr-field-type>java.lang.String</cmr-field-type>
              </cmr-field>
              


              This is not going to work. A field can't be both CMP and CMR at the same time. And from ejb-jar_2_0.dtd

              <!--
              The cmr-field-type element specifies the class of a
              collection-valued logical relationship field in the entity bean
              class. The value of the cmr-field-type element must be either:
              java.util.Collection or java.util.Set.
              
              Used in: cmr-field
              -->
              <!ELEMENT cmr-field-type (#PCDATA)>
              


              • 4. Re: Foreign Key is also Primary Key
                madadi

                hai..

                Is it possible that i can use userid as a Primarykey for one table and Foreign key for other table.

                because i have a one registration form which contains personal data and specific data. but both should store in 2 different table.

                in my database i declared user id as a Primarykey for personal_data table and foreign key for specific_data table.

                so what will be the solution ? i want to store data in both tables and retrieve info from both tables.

                regards
                madadi

                • 5. Re: Foreign Key is also Primary Key
                  aloubyansky

                  Yes, you can. First, get familiar with ejb-jar.xml and mapping in jbosscmp-jdbc.xml.