weblogic 6.1 + Jbuilder 9----->ejb

本文介绍在WebLogic 6.1和JBuilder 9环境下,用EJB方式操作tmp_emp表的详细步骤,包括环境设定、数据库和工具设置、EJB模块创建、实体和会话Bean设计、EmployeeModel类建立,还提及EJB调试方法及常见问题解答。

环境设定为:weblogic 6.1 + Jbuilder 9;
数据表为tmp_emp,要求用EJB的方式对这个表进行操作。字段为:
SQL> desc tmp_emp;
Name     Type         Nullable Default Comments                            
-------- ------------ -------- ------- ------------------------------------
ID       VARCHAR2(10)                  职员ID                              
NAME     VARCHAR2(20) Y                职员名称                            
JOB      VARCHAR2(20) Y                职员的工作名称                      
HIREDATE DATE         Y                职员入职时间                        
SAL      NUMBER(7,2)  Y                职员薪水                            
COMM     VARCHAR2(20) Y                备注                                
DEPTID   VARCHAR2(10) Y                职员所属部门ID;和tmp_dept表的ID关联


预备:编码基本pattern:
包名全部用小写字母,如ejbsample.session
类名用大小写结合的方法,且首字母大写,如EmployeeAction
变量名用大小写结合的方法,且首字母小写,如strName
模块级变量前面加上下划线,如_strName
数据库的设置:
安装好Oracle的客户端,保证与数据库服务器正确建立了连接。

JBuilder9的设置:
可以参考以前的文章。要点:oracle的库文件设定好;"Enterprise setup"设定好

WebLogic的设置:

启动Weblogic

打开控制台: http://localhost:7001/console

从JDBC的connection pools里面,"Configure a new JDBC connection pool",参数可以参考下面:

**Name:
ejbDemo
(说明:这个可以任意取)
**URL:
jdbc:oracle:thin:@172.16.3.100:1521:dev3
(说明:这个URL就是JDBC连接时的URL,格式可以参考JDBC的文档;dev3是数据库服务器172.16.3.100上的SID)
**Driver classname:
oracle.jdbc.driver.OracleDriver
**Properties:
user=pm
password=pm
dll=ocijdbc8
protocol=thin
(说明:用户名和密码换成自己的)
**Initial capacity
3
**Maximum capacity
10
(说明:最后别忘了将"Targets"里面"Available" apply到"Chosen"里面去)配置一个"Tx Data Sources":

**Name:
ejbDS
**JNDI Name:
ejbDS
(说明:这就是在EJB设计的时候,要指定的数据源名称)
**Pool Name:
ejbDemo
(说明:这就是前面建立的connection pool的名称)在JBuilder中建立"EJB module":
建议将.jar文件的保存位置可以放到weblogic的applications目录下:C:/bea/wlserver6.1/config/mydomain/applications
建好一个空的module之后,首先配置它的"DataSources"。右击"DataSources",选择"Import Schema from Database"。

首先选择"Driver"为"oracle.jdbc.driver.OracleDriver",然后URL填入"jdbc:oracle:thin:@172.16.3.100:1521:dev3","Username"和"Password"填入正确的(我这里分别填入"pm"、"pm"),"JNDI name"填入前面设定的"ejbDS".
ok之后,JBuilder就自动开始从数据库里面"Importing Schema"。如果没有出现这样的动作,就说明以前数据库的配置没有正确,再检查一遍。
在JBuilder的ejb设计器中设计实体bean:
从JBuilder自动得到的数据表中,找到我们要操作的tmp_emp表。右击它,选择"Creat CMP 2.0 Entity Bean",JBuilder就会自动根据表的结构生成实体bean。如果对JBuilder自动生成的参数不满意,可以自己修改。我改动如下:

**Bean name:
EbnEmployee
(说明:改动Bean name之后,Abstract schema name会自动改成一样的名字)
**Interfaces:
local
**Classes and packages:
ejbsample.employee.entity
(说明:a)包名全部用小写 b)在JBuilder的Classes and packages定义页面,只需要输入default package为ejbsample.employee.entity,
其它的项JBuilder会自动填好)
**增加3个方法(当然,你如果需要添加方法,可以随时到JBuilder的EJB设计器里面来添加):
  void setModel ( EmployeeModel model ) 方法(interface:local)
  EmployeeModel getModel () 方法 (interface :local )
  ejbCreate( EmployeeModel model ) 方法 (interface :local home )
(说明:EmployeeModel类后面马上建立)
在JBuilder的ejb设计器中设计session bean:
在JBuilder的EJB设计容器中右击,选择新建session bean。修改参数如下:
**Bean name: SbnEmployee
**Session type: stateless
**interfaces: remote
**class--default package: ejbsample.employee.session
**增加如下方法(当然,你如果需要添加方法,可以随时到JBuilder的EJB设计器里面来添加):
  EmployeeModel insert ( EmployeeModel model ) 方法 (interfaces: remote )
  EmployeeModel update ( EmployeeModel model ) 方法 (interfaces: remote )
  boolean del ( String pk ) 方法 ( interfaces: remote )
  EmployeeModel findByPk ( String pk ) 方法 ( interfaces: remote )
  boolean delBatch ( String[] sid ) 方法 ( interfaces:remote )
  java.util.ArrayList queryBySql ( String strSql ) 方法 ( interfaces:remote )
  (说明:我们可以看到EmployeeModel类的使用是无处不在的。事实上,EmployeeModel里面包装了所有的页面显示元素,
  在与jsp页面打交道的时候,它要发挥重要作用。)
下面就开始建立EmployeeModel类:
新建一个class,命名为EmployeeModel,package定义为ejbsample.employee,基类选择为java.io.Serializable.内容如下:

package ejbsample.employee;

import java.io.Serializable;

/**
 * Title: (no title)
 * Description: 一般来说,xxModel类可以看作对jsp页面所有显示元素的包装。它将是主要与jsp页面打交道的类
 * Copyright: Copyright (c) 2003
 * Company: Ebuilds
 * @author Alex
 * @version 1.0
 */

public class EmployeeModel implements Serializable {

    private String    _strID;          //职员ID
    private String    _strName;        //职员名称
    private String    _strJob;         //职员的工作名称
    private java.sql.Date          _dtHireDate;     //职员入职时间
    private double    _dSal;           //职员薪水
    private String    _strComm;        //备注
    private String    _strDeptID;      //职员所属部门ID;和tmp_dept表的ID关联

    //设定属性、读取属性 开始
    public String getID () {
        return _strID;
    }
    public void setID ( String in ) {
        _strID = in;
    }

    public String getName () {
        return _strName;
    }
    public void setName ( String in ) {
        _strName = in;
    }

    public String getJob () {
        return _strJob;
    }
    public void setJob ( String in ) {
        _strJob = in;
    }

    public java.sql.Date getHireDate () {
        return _dtHireDate;
    }
    public void setHireDate ( java.sql.Date in ) {
        _dtHireDate = in;
    }

    public double getSal () {
        return _dSal;
    }
    public void setSal ( double in ) {
        _dSal = in;
    }

    public String getComm () {
        return _strComm;
    }
    public void setComm ( String in ) {
        _strComm = in;
    }

    public String getDeptID () {
        return _strDeptID;
    }
    public void setDeptID ( String in ) {
        _strDeptID = in;
    }
    //设定属性、读取属性 结束

    public void setModel ( EmployeeModel in ) {
        _strID = in.getID();
        _strName = in.getName();
        _strJob = in.getJob();
        _dtHireDate = in.getHireDate();
        _dSal = in.getSal();
        _strComm = in.getComm();
        _strDeptID = in.getDeptID();
    }

    public EmployeeModel() {
    }
    public static void main(String[] args) {
        EmployeeModel employeeModel1 = new EmployeeModel();
    }

}
写一个EJB的公共类:EjbCommon.java。非常重要的代码!

package ejbsample;

/**
 * Title: (no title)
 * Description: 这是写ejb的时候需要用到的公共类,比如JNDI名称、取home接口。当进行大型开发,有很多ejb的时候,这个类是很有必要的
 * Copyright: Copyright (c) 2003
 * Company: Ebuilds
 * @author Alex
 * @version 1.0
 */
import java.util.*;
import javax.naming.*;
import javax.ejb.*;
import javax.rmi.PortableRemoteObject;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import weblogic.jndi.Environment;
import javax.sql.*;
import java.sql.*;

public class EjbCommon {

    //这里存放所有的JNDI名。如果JNDI名很多,建议可以将它们单独放到一个文件中去。
    //说明:JNDI名在这里找到:JB的"project content"中,双击"EbnEmployee",可以看到"Local Home JNDI Name",就是了。
    public static final String E_EMPLOYEE_JNDI = "EbnEmployee";
    public static final String S_EMPLOYEE_JNDI = "SbnEmployee";
    public static final String DATASOURCE_JNDI = "ejbDS";


    //以下是取home接口相关的函数
    private static Context context = null;

    /**
     * 取得InitialContext,供后面的取home接口使用
     * @return
     * @throws NamingException
     */
    protected static Context getInitialContext() throws NamingException {
        String user = null;
        String password = null;
        Properties properties = null;
        try {
            properties = new Properties();
            properties.put(Context.INITIAL_CONTEXT_FACTORY, "weblogic.jndi.WLInitialContextFactory");
            if (user != null) {
                properties.put(Context.SECURITY_PRINCIPAL, user);
                properties.put(Context.SECURITY_CREDENTIALS, password == null ? "" : password);
            }
            return new InitialContext(properties);
        }
        catch(NamingException e) {
            throw e;
        }
    }


    /**
     *用于取得远程home接口。一般来说,session bean的接口是远程的(不是local),所以,取得session bean的home接口要用到这个函数
     * @param lookupName
     * @param homeClass
     * @return
     */
    public static Object getRemoteEJBHome(String lookupName, Class homeClass) throws NamingException {
        try {
            if (context==null) {
                context = getInitialContext();
            }

            Object home = PortableRemoteObject.narrow(
                                context.lookup(lookupName),
                                homeClass);

            return home;
        } catch (NamingException ne) {
            //throw new EJBException(ne.getMessage());
            throw ne;
        }
    }

    /**
     * 用于取得本地home接口。一般来说,实体bean的接口是本地(local)的,所以,取得实体bean的home接口要用到这个函数。
     * @param lookupName
     * @return
     */
    public static Object getLocalEJBHome(String lookupName) throws NamingException{
        try {
            if (context==null) {
                context = getInitialContext();
            }
            Object home = context.lookup(lookupName);
            return home;
        } catch (NamingException ne) {
            //throw new EJBException(ne.getMessage());
            throw ne;
        }
    }


    //下面的是关于数据库的操作。一个重要的,用完了getConnection()之后,记得释放connection!

    /**
     * 从定义好的datasource里面取出一个connection
     * @return
     */
    public static Connection getConnection() throws NamingException, SQLException{
        Connection con=null;
        try {
            if ( context == null ){
                context = getInitialContext();
            }
            DataSource datasource=(DataSource)context.lookup( DATASOURCE_JNDI );
            con = datasource.getConnection();
        } catch (NamingException ex) {
            throw ex;
        } catch (SQLException ex) {
            throw ex;
        }
        return con;
    }

    /**
     * 这是取连接的远程版本。但是好像不需要用它。
     * @return
     */
    public static Connection getConnection_remote() throws NamingException, SQLException{
        try {
            if (context==null) {
                context = getInitialContext();
            }
            DataSource ds = (DataSource)PortableRemoteObject.narrow(
                                context.lookup(DATASOURCE_JNDI),
                                DataSource.class);
            return ds.getConnection();
        } catch (NamingException ne) {
            //throw new EJBException(ne.getMessage());
            throw ne;
        } catch (SQLException e) {
            //throw new EJBException(e.getMessage());
            throw e;
        }
    }


    /**
     * 作用:用html格式将strmsg输入到c:/strlogfile文件中去
     * 将会输出类似这样的语句:
     * [2003-四月-29 04:44:03] 被调试文件:vwDetail.jsp 被调试函数:(开始设置projectID) 调试描述:
取得的projectID为ERPPM200212110000000658310000E8E7FF69
*
     * Added by daihua 2003-4-29 11:16
     * @param strMsg
     */
    public static void logOneLineToFile ( String strLogFile, String strDebugFileName, String strDebugFuncName, String strDebugMsg ){
        //如果不需要debug输出的话,直接返回
        /*if ( ! debuggingOn )
            return;
         */
        java.io.File fd = new java.io.File ( "c://debug" );
        if ( !fd.exists() ) {
            fd.mkdirs();
        }

        //根据当前的日期自动生成debug的文件名,比如:c:/20030506debug.html
        /*SimpleDateFormat sdfF = new SimpleDateFormat ( "yyyyMMdd" );
        String strLogFileName = "c://debug//" + sdfF.format( new Date() ) + "debug.html" ;
        */

        String strLogFileName = "c://debug//" + strLogFile;  //还是由程序指定debug的文件名
        java.text.SimpleDateFormat bartDateFormat =  new java.text.SimpleDateFormat("yyyy-MMMM-dd hh:mm:ss");
        java.util.Date date = new java.util.Date();
        java.io.FileWriter out = null;
        try
        {
            java.io.File f = new java.io.File ( strLogFileName );
            if ( !f.exists() ){
                f.createNewFile();
            }
            //out = new RandomAccessFile ( f, "rw" );
            out = new java.io.FileWriter ( strLogFileName, true );  //To be ready for append
            //out.seek( out.length() );
            String str1 = "<p style=/"font-size:10.5pt; line-height:15pt/">" +  "<font color=/"#999999/">[" + bartDateFormat.format(date) + "] 被调试文件:</font>";
            String str2 = "<font color=/"#3333FF/">" + strDebugFileName + "</font>";
            String str3 = "<font color=/"#999999/"> 被调试函数:</font><font color=/"#3333FF/">" + strDebugFuncName + "</font>";
            String str4 = "<font color=/"#999999/"> 调试描述:</font><br>/r/n";
            strDebugMsg = "<font color=red>" + strDebugMsg + "</font></p>/r/n";            strDebugMsg = str1 + str2 + str3 + str4 + strDebugMsg;
            //out.writeChars( "[" + bartDateFormat.format(date) + "] " + strMsg + "/r/n");

            out.write( strDebugMsg );
            }catch ( Exception e )
            {
                e.printStackTrace();
            }
            finally{
                try{
                    if ( out != null )
                        out.close();
                }catch ( Exception ex ){
                    ex.printStackTrace();
                }
            }
    }

    public EjbCommon() {
    }
    public static void main(String[] args) {
        EjbCommon ejbCommon1 = new EjbCommon();
    }

}
编辑完成实体bean

打开EbnEmployee、EbnEmployeeHome、EbnEmployeeBean,首先import一下:
import ejbsample.employee.EmployeeModel;
然后开始编辑EbnEmployeeBean,完成EJB设计器里面设计的函数

void setModel(EmployeeModel model)函数:

    public void setModel(EmployeeModel model) {
        this.setId ( model.getID() );
        this.setName ( model.getName() );
        this.setJob ( model.getJob() );
        this.setHiredate ( model.getHireDate() );
        this.setSal ( model.getSal() );
        this.setComm ( model.getComm() );
        this.setDeptid ( model.getDeptID() );
    }
EmployeeModel getModel()函数

    public EmployeeModel getModel() {
        EmployeeModel data = new EmployeeModel();
        data.setID( this.getId());
        data.setName( this.getName());
        data.setJob( this.getJob() );
        data.setHireDate( this.getHiredate() );
        data.setSal( this.getSal() );
        data.setComm( this.getComm() );
        data.setDeptID( this.getDeptid() );
        return data;
    }
java.lang.String ejbCreate(EmployeeModel model)

    public java.lang.String ejbCreate(EmployeeModel model) throws CreateException {
     //说明:这个函数非常重要,每次创建实体bean的时候,都会自动调用ejbCreate,所以如果没有完成这个函数的话,实体bean中将无法赋值
        setModel ( model );
        return null;
    }
编辑完成session bean类SbnEmployeeBean.java,如下

package ejbsample.employee.session;

import javax.ejb.*;
import ejbsample.employee.EmployeeModel;
import ejbsample.EjbCommon;
import java.util.ArrayList;
import ejbsample.employee.entity.*;
import javax.naming.NamingException;
import java.sql.*;
import java.rmi.*;

public class SbnEmployeeBean implements SessionBean {
    SessionContext sessionContext;
    public void ejbCreate() throws CreateException {
        /**@todo Complete this method*/
    }
    public void ejbRemove() {
        /**@todo Complete this method*/
    }
    public void ejbActivate() {
        /**@todo Complete this method*/
    }
    public void ejbPassivate() {
        /**@todo Complete this method*/
    }
    public void setSessionContext(SessionContext sessionContext) {
        this.sessionContext = sessionContext;
    }
    public EmployeeModel insert(EmployeeModel model) throws CreateException,NamingException,RemoteException{
        try {
            //利用EjbCommon类得到实体bean的home接口
            EbnEmployeeHome objHome = (EbnEmployeeHome) EjbCommon.getLocalEJBHome( EjbCommon.E_EMPLOYEE_JNDI );
            EbnEmployee objRemote=objHome.create(model);
            return model;
        }
        catch(CreateException e) {
            throw e;
        }
        catch(NamingException e) {
            throw e;
        }

    }

    public EmployeeModel update(EmployeeModel model) throws FinderException, NamingException, RemoteException {
        try {
            //利用EjbCommon类得到实体bean的home接口
            EbnEmployeeHome objHome = (EbnEmployeeHome) EjbCommon.getLocalEJBHome(EjbCommon.E_EMPLOYEE_JNDI);
            EbnEmployee objLocal = objHome.findByPrimaryKey(model.getID());
            //调用model的取属性函数,将实体bean更新
            //objLocal.setModel(model);  //不能这么写。具体为什么,我也不知道。好像没有道理啊
            objLocal.setName( model.getName() );
            objLocal.setJob( model.getJob() );
            objLocal.setHiredate( model.getHireDate() );
            objLocal.setSal( model.getSal() );
            objLocal.setComm( model.getComm() );
            objLocal.setDeptid( model.getDeptID() );
            return model;
        }
        catch (FinderException e) {
            throw e;
        }
        catch (NamingException e) {
            throw e;
        }

    }

    public boolean del(String pk) throws RemoveException,FinderException,EJBException,NamingException ,RemoteException {
        try {
            //利用EjbCommon类得到实体bean的home接口
            EbnEmployeeHome objHome = (EbnEmployeeHome) EjbCommon.getLocalEJBHome(
                EjbCommon.E_EMPLOYEE_JNDI);
            EbnEmployee objLocal = objHome.findByPrimaryKey(pk);
            objLocal.remove();
            return true;
        }
        catch (RemoveException e) {
            throw e;
        }
        catch (FinderException e) {
            throw e;
        }
        catch (EJBException e) {
            throw e;
        }
        catch (NamingException e) {
            throw e;
        }


    }

    public EmployeeModel findByPk(String pk) throws FinderException, NamingException, RemoteException {
        try {
            //利用EjbCommon类得到实体bean的home接口
            EbnEmployeeHome objHome = (EbnEmployeeHome) EjbCommon.getLocalEJBHome(EjbCommon.E_EMPLOYEE_JNDI);
            EmployeeModel model = new EmployeeModel();
            EbnEmployee objLocal = objHome.findByPrimaryKey(pk);
            model = objLocal.getModel();
            return model;
        }
        catch (FinderException e) {
            throw e;
        }
        catch (NamingException e) {
            throw e;
        }
    }

    public boolean delBatch(String[] sid) throws NamingException, SQLException,RemoteException{
        String[] sID = null;
        sID = sid;
        String sql = "delete FROM tmp_emp WHERE ID='" ; //Note: statmachine is the table name connected with our work
        String id = new String();
        Connection conn = null;
        Statement st = null;
        boolean b = false;

        try {
            conn = EjbCommon.getConnection();
            conn.setAutoCommit(false);
            st = conn.createStatement();
            for(int i = 1;i <= sID.length ;i++ ){
                id = sID[i-1];
                st.execute(sql + id + "'");
            }
            conn.commit();
            b = true;
            return b;
        }catch ( NamingException e ){
            throw e;
        }catch(SQLException e){
            System.err.print( "delBatch() function error: concerning with database");
            try {
                conn.rollback();
            }catch(SQLException sqle){
                throw sqle;
            }
            throw e;
        }finally{
            try {
                st.close();
                conn.close();
            }catch(SQLException e){
                throw e;
            }
            //return b;  //说明:不要在finally里面return,否则,捕捉到的错误不会throw出去!!!
        }

    }

    public java.util.ArrayList queryBySql(String strSql)  throws NamingException, SQLException,RemoteException{
        ArrayList arrayList = null;
        EmployeeModel item;
        Connection conn = null;
        Statement st = null;
        ResultSet rs = null;
        try {
            conn=EjbCommon.getConnection();
            st=conn.createStatement();
            rs=st.executeQuery("SELECT * FROM tmp_emp WHERE " + strSql); //Of course, you can change the sql statement according your condition
            System.out.println("queryBySql函数的sql=" + "SELECT * FROM tmp_emp WHERE " + strSql);
            arrayList = new ArrayList();
            while (rs.next()) {
                item=new EmployeeModel();

                //从数据库里面读取值
                item.setID( rs.getString( "ID" ));
                item.setName( rs.getString( "NAME" ));
                item.setJob( rs.getString( "JOB" ));
                item.setHireDate( rs.getDate( "HIREDATE" ));
                item.setSal( rs.getDouble( "SAL" ));
                item.setComm( rs.getString( "COMM" ));
                item.setDeptID( rs.getString( "DEPTID" ));

                arrayList.add(item);
            }
            if ( arrayList.size() <= 0 ){
                return null;
            }else{
                return arrayList;
            }

        }catch(SQLException e){
            System.out.println("queryBySql函数出现了SQL错误:" + e.toString() + ",将返回的ArrayList设置为Null");
            throw e;
        }catch(NamingException e1){
            throw e1;
        }
        finally{
            System.out.println("queryBySql函数进入finally子块,关闭连接");
            try {
                if (rs!=null)
                    rs.close();
            }catch(SQLException e){
                throw e;
            }
            try {
                if (st!=null)
                    st.close();
            }catch(SQLException e){
                throw e;
            }
            try {
                if (conn!=null)
                    conn.close();
            }catch(SQLException e){
                throw e;
            }
            //return arrayList;  //说明:不要在finally里面return,否则,捕捉到的错误不会throw出去!!!
        }
    }

}
编制EmployeeAction.java。这个类包装了EJB,是与jsp页面打交道的类。(这个action类,以及前面的model类,是两个主要和jsp页面打交道的类;而action类包装了EJB,model类包装了jsp页面显示元素)
新建一个class,命名为EmployeeAction,package定义为ejbsample.employee。内容如下:
package ejbsample.employee;

/**
 * Title: (no title)
 * Description: xxAction类基本上是EJB的包装。
 * Copyright: Copyright (c) 2003
 * Company: Ebuilds
 * @author Alex
 * @version 1.0
 */
import ejbsample.SequenceUtil;
import ejbsample.EjbCommon;
import ejbsample.employee.EmployeeModel;
import ejbsample.employee.entity.*;
import ejbsample.employee.session.*;
import javax.ejb.*;
import javax.naming.NamingException;
import java.rmi.RemoteException;
import java.util.ArrayList;
import java.sql.*;

public class EmployeeAction {

    /**
     * 传入一个model(没有ID这个属性),自动加一个唯一的ID,然后往数据库里面加一条记录
     * @param model
     * @return
     * @throws NamingException
     * @throws RemoteException
     * @throws CreateException
     */
    public EmployeeModel add( EmployeeModel model ) throws NamingException, RemoteException,
        CreateException {
        model.setID(SequenceUtil.getUniteCode()); //getUniteCode()的作用是:得到一个唯一的ID号。可以随便怎么写这个函数,比如可以用当前的时间作为ID:getTime();或者用网卡物理地址加上当前时间等等
        try {
            SbnEmployeeHome objHome = (SbnEmployeeHome) EjbCommon.
                                      getRemoteEJBHome(EjbCommon.
                S_EMPLOYEE_JNDI, SbnEmployeeHome.class);
            SbnEmployee objRemote = objHome.create();
            //从上面的两行代码可以看出session bean编码的格式:首先得到home接口;然后调用create()函数得到接口
            return objRemote.insert(model);
        }
        //关于错误处理:千万不要在catch里面什么都不做,要么把catch到的错误throw出去,要么显示一些信息出来;否则的话,程序将会无法调试!
        catch (NamingException e) {
            throw e;
        }
        catch (RemoteException e) {
            throw e;
        }
        catch (CreateException e) {
            throw e;
        }
    }

    /**
     * 根据传入的主键,删除数据库里面的一条记录。
     * @param strPk
     * @return
     * @throws NamingException
     * @throws RemoteException
     * @throws CreateException
     */
    public boolean delete(String strPk) throws NamingException, RemoteException, CreateException,RemoveException,FinderException {
        try {
            SbnEmployeeHome objHome = (SbnEmployeeHome) EjbCommon.
                                      getRemoteEJBHome(EjbCommon.
                S_EMPLOYEE_JNDI, SbnEmployeeHome.class);
            SbnEmployee objRemote = objHome.create();
            boolean b = objRemote.del(strPk);
            return b;
        }
        //关于错误处理:必须这么一个一个地catch错误,然后throw出去!
        catch (NamingException e) {
            throw e;
        }
        catch (RemoteException e) {
            throw e;
        }
        catch (CreateException e) {
            throw e;
        }
        catch (RemoveException e) {
            throw e;
        }
        catch (FinderException e) {
            throw e;
        }

    }


    /**
     * 根据传入的model,更新数据库里面的一条记录
     * @param model
     * @return
     * @throws NamingException
     * @throws RemoteException
     * @throws CreateException
     */
    public EmployeeModel update(EmployeeModel model) throws NamingException, RemoteException, CreateException,FinderException
    {
        try {
            SbnEmployeeHome objHome = (SbnEmployeeHome) EjbCommon.
                                      getRemoteEJBHome(EjbCommon.
                S_EMPLOYEE_JNDI, SbnEmployeeHome.class);
            SbnEmployee objRemote = objHome.create();
            return objRemote.update(model);
        }
        catch (NamingException e) {
            throw e;
        }
        catch (RemoteException e) {
            throw e;
        }
        catch (CreateException e) {
            throw e;
        }
        catch (FinderException e) {
            throw e;
        }

    }

    /**
     * 根据传入的主键,返回一个model
     * @param strPk
     * @return
     * @throws NamingException
     * @throws RemoteException
     * @throws CreateException
     */
    public EmployeeModel findByPk(String strPk)  throws NamingException, RemoteException, CreateException,FinderException
    {
        try {
            SbnEmployeeHome objHome = (SbnEmployeeHome) EjbCommon.
                                      getRemoteEJBHome(EjbCommon.
                S_EMPLOYEE_JNDI, SbnEmployeeHome.class);
            SbnEmployee objRemote = objHome.create();
            return objRemote.findByPk(strPk );
        }
        catch (NamingException e) {
            throw e;
        }
        catch (RemoteException e) {
            throw e;
        }
        catch (CreateException e) {
            throw e;
        }
        catch (FinderException e) {
            throw e;
        }


    }


    /**
     * 根据传入的sql(注意不是完整的sql语句),得到所有满足条件的model,放到一个ArrayList里面返回
     * @param sql
     * @return
     * @throws NamingException
     * @throws RemoteException
     * @throws CreateException
     */
    public ArrayList queryBySql(String sql)  throws NamingException, RemoteException, CreateException,SQLException
    {
        try {
            SbnEmployeeHome objHome = (SbnEmployeeHome) EjbCommon.
                                      getRemoteEJBHome(EjbCommon.
                S_EMPLOYEE_JNDI, SbnEmployeeHome.class);
            SbnEmployee objRemote = objHome.create();

            return objRemote.queryBySql(sql);
        }
        catch (NamingException e) {
            throw e;
        }
        catch (RemoteException e) {
            throw e;
        }
        catch (CreateException e) {
            throw e;
        }
        catch (SQLException e) {
            throw e;
        }

    }

    /**
     * 根据传入的主键数组,批量删除记录
     * @param sId
     * @return
     * @throws NamingException
     * @throws RemoteException
     * @throws CreateException
     */
    public boolean deleteBatch(String[] sId) throws NamingException, RemoteException, CreateException{
        boolean b = false;
        try {
            SbnEmployeeHome objHome = (SbnEmployeeHome) EjbCommon.
                                      getRemoteEJBHome(EjbCommon.
                S_EMPLOYEE_JNDI, SbnEmployeeHome.class);
            SbnEmployee objRemote = objHome.create();

            b = objRemote.delBatch(sId);
        }
        catch (NamingException e) {
            throw e;
        }
        catch (RemoteException e) {
            throw e;
        }
        catch (CreateException e) {
            throw e;
        }
        finally{
            return b;
        }
    }


    public EmployeeAction() {
    }
    public static void main(String[] args) {
        EmployeeAction action = new EmployeeAction();
        //以下是调试代码。注意:最好在EJB发布到weblogic之前,将session bean里面的所有方法调试一遍,
        //确保不会有比较低级的错误。否则,如果到了jsp页面再去调试,无疑是nightmare

        EmployeeModel data = new EmployeeModel();

        //说明:1)要调试的话,只要将“测试xx方法”前面加上/就可以了。
        //      2)有时候EJB运行比较慢,JBuilder里面半天没有反应。这是可以在前面的方法里面加一些
        //         输出语句,让你知道程序是在正确运行。

        //*测试add()方法
        for (int i = 0; i < 6; i++) {
            data.setName("name" + i);
            data.setJob("job1");
            data.setHireDate(java.sql.Date.valueOf( "2003-07-21") );
            try {
                action.add(data);
            }
            catch (Exception e) {
                e.printStackTrace();
            }
        }
        //**/


        /*测试delete()方法
         try {
             action.delete("ID_2003072504CB077B81059114950140"); //这个主键的值是都数据库里面找的。
         }
         catch (Exception e) {
             e.printStackTrace();
         }
        //*/

        /*测试deleteBatch()方法
        String[] strSID = { "ID_2003072504CB077B81059116383421", "ID_2003072504CB077B81059116474625", "ID_2003072504CB077B81059116477218" };
        try {
            action.deleteBatch( strSID );
        }
        catch ( Exception e ) {
            e.printStackTrace();
        }
        //*/


        /*测试findByPk()方法
        String strPK = "ID_2003072504CB077B81059116477328";
        try{
            data = action.findByPk( strPK );
            System.out.println("找到的name=" + data.getName());
        }
        catch ( Exception e ) {
            e.printStackTrace();
        }
        //*/

        /*测试queryBySql()方法
        String strSql = "job1='job1'";
        ArrayList alRet = null;
        try{
            alRet = action.queryBySql( strSql );
            if ( alRet != null && alRet.size() > 0) {
                for ( int i = 0; i < alRet.size(); i ++ ){
                    data = ( EmployeeModel ) alRet.get( i );
                    System.out.println("找到符合条件的第" + (i+1) + "个记录,name=" + data.getName());
                }
            }else{
                System.out.println("没有找到记录");
            }
        }
        catch ( Exception e ) {
            e.printStackTrace();
        }
        //*/

        /*调试update()函数
        String strPK1 = "ID_2003072504CB077B81059118072859";
        try{
            data = action.findByPk( strPK1 );
            System.out.println("找到的旧的name=" + data.getName());
            data.setName( "new name" );
            action.update( data );
        }
        catch ( Exception e ) {
            e.printStackTrace();
        }
        //*/

        System.out.println("*********Final!");

    }

}
调试EJB:
调试方法是运行EmployeeAction。注意在运行之前,必须启动weblogic,并且保证EJB已经正确发布了。事实上,EJB的发布也要调试很长时间的。调试注意事项:

调试EJB是很麻烦的,而且非常耗费内存。如果内存不是512M以上,就等着痛苦降临吧:)我现在就是这样,简直有砸电脑的欲望。
有时候,所有的步骤都正确,但是总是有一些奇怪的错误。(比如我写这个例子的时候)这时,一般先shutdown weblogic,然后将weblogic目录下的所有临时目录(一般以TMP开头)全部删掉,然后重启一下weblogic。问题往往能够得到解决。不要问为什么,估计bea公司的人也不知道。
在JBuilder中,最好把EJB module的"Always creating JAR when building the project"去掉。免得每次都要重复编译ejb的.jar文件。
有时候编译出来的.jar文件很大(比如1M、2M;一般几十、几百KB是比较正常的),就要看EJB module的属性设置是否正确。主要是content是否包含所有的类,一般应该选择只包含用到的类。
用JBuilder发布的时候,有时候可能会碰到它提示“超过4分钟,时间超时,发布不成功”等等之类的提示。但是事实证明发布却是成功的,如果碰到这种情况,不理它就是了。
FAQ:

Q:得到这样的错误javax.naming.NameNotFoundException: Unable to resolve 'SbnEmployee' Resolved: '' Unresolved:'SbnEmployee' ; remaining name 'SbnEmployee'
A:没有正确发布EJB。请先启动weblogic,然后在JBuilder中右击ejb module,选择deploy。
Q:调试老通不过
A:重启weblogic,然后再试试吧。
Q:我改动了session bean,为什么没有效果?
A:修改EJB的任何一个部分,都要重新发布EJB才能生效。这个问题的症结很可能在这里。不过要记住,在JBuilder里面,此时要用Reploy这个选项,不要用Deploy。
Q:我在EJB里面System.out.println了一下,为什么看不到输出?
A:EJB的输出在weblogic里面。要注意的是,System.out.println的输出,有时候在JBuilder里面,有时候又在weblogic里面,有时候还可能到java的控制台里面(比如applet的输出,不过这是题外话了)。
Q:我的EJB写的都是正确的啊,为什么老是出现发布的错误?
A:试试:打开EJB module的属性,将“discriptors in module”里面的weblogic-ejb-jar.xml删除掉,然后重新发布。问题往往可能会在这里,特别是你用来调试的weblogic的版本变化的时候。
说明:这个条目可以放心删除,JBuilder在编译EJB的时候,会自动根据当前的设置加上这个条目。

多源动态最优潮流的分布鲁棒优化方法(IEEE118节点)(Matlab代码实现)内容概要:本文介绍了基于Matlab实现的多源动态最优潮流的分布鲁棒优化方法,适用于IEEE118节点电力系统。该方法旨在应对电力系统中源荷不确定性带来的挑战,通过构建分布鲁棒优化模型,有效处理多源输入下的动态最优潮流问题,提升系统运行的安全性和经济性。文中详细阐述了模型的数学 formulation、求解算法及仿真验证过程,并提供了完整的Matlab代码实现,便于读者复现与应用。该研究属于电力系统优化调度领域的高水平技术复现,具有较强的工程实用价值。; 适合人群:具备电力系统基础知识和Matlab编程能力的研究生、科研人员及从事电力系统优化调度的工程技术人员,尤其适合致力于智能电网、鲁棒优化、能源调度等领域研究的专业人士。; 使用场景及目标:①用于电力系统多源环境下动态最优潮流的建模与求解;②支撑含可再生能源接入的电网调度决策;③作为鲁棒优化方法在实际电力系统中应用的教学与科研案例;④为IEEE118节点系统的仿真研究提供可复现的技术支持。; 阅读建议:建议结合提供的Matlab代码逐模块分析,重点关注不确定变量的分布鲁棒建模、目标函数构造及求解器调用方式。读者应具备一定的凸优化和电力系统分析基础,推荐配合YALMIP工具包与主流求解器(如CPLEX、Gurobi)进行调试与扩展实验。
内容概要:本文系统介绍了物联网与云计算的基本概念、发展历程、技术架构、应用场景及产业生态。文章阐述了物联网作为未来互联网的重要组成部分,通过RFID、传感器网络、M2M通信等技术实现物理世界与虚拟世界的深度融合,并展示了其在智能交通、医疗保健、能源管理、环境监测等多个领域的实际应用案例。同时,文章强调云计算作为物联网的支撑平台,能够有效应对海量数据处理、资源弹性调度和绿色节能等挑战,推动物联网规模化发展。文中还详细分析了物联网的体系结构、标准化进展(如IEEE 1888、ITU-T、ISO/IEC等)、关键技术(中间件、QoS、路由协议)以及中国运营商在M2M业务中的实践。; 适合人群:从事物联网、云计算、通信网络及相关信息技术领域的研究人员、工程师、高校师生以及政策制定者。; 使用场景及目标:①了解物联网与云计算的技术融合路径及其在各行业的落地模式;②掌握物联网体系结构、标准协议与关键技术实现;③为智慧城市、工业互联网、智能物流等应用提供技术参考与方案设计依据;④指导企业和政府在物联网战略布局中的技术选型与生态构建。; 阅读建议:本文内容详实、覆盖面广,建议结合具体应用场景深入研读,关注技术标准与产业协同发展趋势,同时结合云计算平台实践,理解其对物联网数据处理与服务能力的支撑作用。
标题基于Java的停车场管理系统设计与实现研究AI更换标题第1章引言介绍停车场管理系统研究背景、意义,分析国内外现状,阐述论文方法与创新点。1.1研究背景与意义分析传统停车场管理问题,说明基于Java系统开发的重要性。1.2国内外研究现状综述国内外停车场管理系统的发展现状及技术特点。1.3研究方法以及创新点介绍本文采用的研究方法以及系统开发中的创新点。第2章相关理论总结Java技术及停车场管理相关理论,为系统开发奠定基础。2.1Java编程语言特性阐述Java的面向对象、跨平台等特性及其在系统开发中的应用。2.2数据库管理理论介绍数据库设计原则、SQL语言及在系统中的数据存储与管理。2.3软件工程理论说明软件开发生命周期、设计模式在系统开发中的运用。第3章基于Java的停车场管理系统设计详细介绍系统的整体架构、功能模块及数据库设计方案。3.1系统架构设计阐述系统的层次结构、模块划分及模块间交互方式。3.2功能模块设计介绍车辆进出管理、车位管理、计费管理等核心功能模块设计。3.3数据库设计给出数据库表结构、字段设计及数据关系图。第4章系统实现与测试系统实现过程,包括开发环境、关键代码及测试方法。4.1开发环境与工具介绍系统开发所使用的Java开发环境、数据库管理系统等工具。4.2关键代码实现展示系统核心功能的部分关键代码及实现逻辑。4.3系统测试方法与结果阐述系统测试方法,包括单元测试、集成测试等,并展示测试结果。第5章研究结果与分析呈现系统运行效果,分析系统性能、稳定性及用户满意度。5.1系统运行效果展示通过截图或视频展示系统实际操作流程及界面效果。5.2系统性能分析从响应时间、吞吐量等指标分析系统性能。5.3用户满意度调查通过问卷调查等方式收集用户反馈,分析用户满意度。第6章结论与展望总结研究成果,提出系统改进方向及未来发展趋势。6.1研究结论概括基于Java的停车场管理
根据原作 https://pan.quark.cn/s/a4b39357ea24 的源码改编 QT作为一个功能强大的跨平台应用程序开发框架,为开发者提供了便利,使其能够借助C++语言编写一次代码,便可在多个操作系统上运行,例如Windows、Linux、macOS等。 QT5.12是QT框架中的一个特定版本,该版本引入了诸多改进与新增特性,包括性能的提升、API支持的扩展以及对现代C++标准的兼容性。 在QT5.12环境下实现后台对鼠标侧键的监控,主要涉及以下几个关键知识点:1. **信号与槽(Signals & Slots)机制**:这一机制是QT的核心,主要用于实现对象之间的通信。 在监测鼠标事件时,可以通过定义信号和槽函数来处理鼠标的点击行为,比如,当鼠标侧键被触发时,会触发一个信号,然后将其连接至相应的槽函数以执行处理。 2. **QEvent类**:在QT中,QEvent类代表了多种类型的事件,涵盖了键盘事件、鼠标事件等。 在处理鼠标侧键时,需要关注`QEvent::MouseButtonPress`和`QEvent::MouseButtonRelease`事件,尤其是针对鼠标侧键的独特标识。 3. **QMouseEvent类**:每当鼠标事件发生,系统会发送一个QMouseEvent对象。 通过这个对象,可以获取到鼠标的按钮状态、位置、点击类型等信息。 在处理侧键时,可以检查`QMouseEvent::button()`返回的枚举值,例如`Qt::MiddleButton`表示的是鼠标中键(即侧键)。 4. **安装事件过滤器(Event Filter)**:为了在后台持续监控鼠标,可能需要为特定的窗口或对象安装事件过滤器。 通过实现`QObject::eventFilter...
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值