Jboss之JMX实例:上传文件到Jboss目录中

    这几天实现了一个向远程Jboss服务器中部署文件的程序,是采用Jboss 的 JMX 远程调用方法来实现的,方法比较简单,略微修改就可以把文件传送到远程启动了Jboss服务器的机器上,希望与大家分享,此处贴上了全部实例代码,配置好后即可运行。

 

实现步骤如下:

 

1、下载安装Jboss服务器

 

2、新建立java项目,引入jboss安装目录 server\default\lib 中的 jboss.jar 和 jmx-adaptor-plugin.jar 包到classpath中

 

3、建立 RMIAdaptorHelper.java 类,用于处理远程调用,代码如下:

 

package com.sample.jmxagent.jboss;

 

import java.io.Serializable;
import java.util.Properties;

import javax.management.ObjectName;
import javax.naming.CommunicationException;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;

import org.jboss.jmx.adaptor.rmi.RMIAdaptor;

 

public class RMIAdaptorHelper
{
   private String  _rmiHost = "127.0.0.1";
   private int   _rmiPort = 1099;
   private int   _timeout = 2000; 
// ms
   private RMIAdaptor _server;

   public RMIAdaptorHelper(String rmiHost, int rmiPort, int timeout)
       throws CommunicationException, NamingException
   {
      this._rmiHost = rmiHost;
      this._rmiPort = rmiPort;
      this._timeout = timeout;
   }

   /**
    * 远程调用 MBEAN
    */

   public Object invoke(RmiInvokeObject rmido) throws Exception
   {
      ObjectName name = new ObjectName(rmido.getJndiname());
      return _server.invoke(name, rmido.getMethodname(), rmido
        .getMethodArgs(), rmido.getMethodArgsType());
   }

   /**
    * 连接 Jboss rmi 服务器
    */

   public void connect() throws NamingException, CommunicationException
   {
      Properties prop = System.getProperties();
      prop.put(Context.INITIAL_CONTEXT_FACTORY,
         "org.jnp.interfaces.NamingContextFactory");
      prop.put(Context.URL_PKG_PREFIXES,
         "org.jboss.naming:org.jnp.interfaces");
      prop.put(Context.PROVIDER_URL, "jnp://" + _rmiHost + ":" + _rmiPort);

      prop.put("jnp.discoveryTimeout", String.valueOf(_timeout));

      InitialContext ic = new InitialContext(prop);
      if (_server != null)
      {
         System.out.println("RMIAdaptorHelper not null");
         _server = null;
      }
      Object o = ic.lookup("jmx/rmi/RMIAdaptor");
      _server = (RMIAdaptor) o;

   }

   /**
    * 远程调用的对象类
    */

   public class RmiInvokeObject implements Serializable
   {
       private String  jndiname;
       private String  methodname;
       private Object[] methodArgs;
       private String[] methodArgsType;

 

       public String getJndiname()
       {
          return jndiname;
       }

       public void setJndiname(String mbeanName)
       {
          this.jndiname = mbeanName;
       }

       public Object[] getMethodArgs()
       {
          return methodArgs;
       }

       public void setMethodArgs(Object[] methodArgs)
       {
          this.methodArgs = methodArgs;
       }

       public String[] getMethodArgsType()
       {
          return methodArgsType;
       }

       public void setMethodArgsType(String[] methodArgsType)
       {
          this.methodArgsType = methodArgsType;
       }

       public String getMethodname()
       {
          return methodname;
       }

       public void setMethodname(String methodname)
       {
          this.methodname = methodname;
       }
     }
  }

 

4、建立 FileObject.java 类,用于存储所要传输的文件内容,代码如下:

 

package com.sample.upload.mbean;

 

import java.io.Serializable;

 

public class FileObject implements Serializable
{
     public byte[] fileContent;
}

 

5、建立 FileUploadMBean.java 接口,用于 Jboss 调用,代码如下:

package com.sample.upload.mbean;

 

public interface FileUploadMBean
{
    public boolean uploadFile(String fileName, FileObject fo) throws Exception;
}

6、建立 FileUpload.java 类,用于实现FileUploadMBean 接口,代码如下:

 

package com.sample.upload.mbean;

 

import java.io.File;
import java.io.FileOutputStream;
import java.net.URI;

 

public class FileUpload implements FileUploadMBean
{
    public static final String JBOSS_SERVER_BASE_URL = "jboss.server.base.url";
    public static final String JBOSS_SERVER_NAME = "jboss.server.name";
    public static final String JBOSS_SERVER_PATH = System.getProperty(JBOSS_SERVER_BASE_URL)+ System.getProperty(JBOSS_SERVER_NAME);
    public static final String NODE_ADAPTOR_PATH = JBOSS_SERVER_PATH + "/";
   
    private FileOutputStream fos = null;
    private File    f = null;

 

    public boolean uploadFile(String fileName, FileObject fo) throws Exception
    {
       boolean returnValue = false;
       try
       {
          // 在 Jboss 的 server\default 目录下新建立文件
          f = new File(new URI( NODE_ADAPTOR_PATH + fileName));
          f.createNewFile();
          fos = new FileOutputStream(f);
          fos.write(fo.fileContent);
          returnValue = true;
       }
       catch (Exception ex)
       {
          ex.printStackTrace();
          throw ex;
       }
       finally
       {
          if (fos != null)
          {
             try
             {
                fos.close();
             }
             catch (Exception ee)
             {
                ee.printStackTrace();
             }
          }
      }
      return returnValue;
   }
}

 

7、建立 TestFileUpload.java 类,用于测试文件上传,代码如下:

 

package com.sample.upload.test;

 

import java.io.File;
import java.io.FileInputStream;

import com.sample.jmxagent.jboss.RMIAdaptorHelper;
import com.sample.upload.mbean.FileObject;

 

public class TestFileUpload
{
   private static RMIAdaptorHelper rah;

 

   /**
    * 向 Jboss 上传指定目录的文件
    */

   public static void uploadFile(String fileName) throws Exception
   {
      File f = new File(fileName);
      byte[] b = new byte[(int) f.length()];
      FileInputStream fis = new FileInputStream(f);
      try
      {
         fis.read(b);
         FileObject fo = new FileObject();
         fo.fileContent = b;

         RMIAdaptorHelper.RmiInvokeObject rmido = rah.new RmiInvokeObject();
         rmido.setJndiname("com.sample.remotedeploy.mbean.control:service=FileUpload");
         rmido.setMethodname("uploadFile");
         rmido.setMethodArgsType(new String[]{"java.lang.String",
            "com.sample.upload.mbean.FileObject"});
         rmido.setMethodArgs(new Object[]{f.getName(), fo});
         rah.invoke(rmido);
      }
      catch (Exception ex)
      {
         ex.printStackTrace();
      }
      finally
      {
         if (fis != null)
         {
            try
            {
               fis.close();
            }
            catch (Exception ee)
            {
               ee.printStackTrace();
            }
         }
      }
   }

 

   public static void main(String[] args)
   {
      try
      {
         rah = new RMIAdaptorHelper("127.0.0.1", 1099, 5000);
         // 连接 Jboss rmi 服务器
         rah.connect();
         // 向 Jboss 上传指定目录的文件
         uploadFile(args[0]);
      }
      catch (Exception e)
      {
         e.printStackTrace();
      }
      System.exit(0);
   }
}

 

8、在Jboss的安装目录server\default\deploy下建立 com.sample.sar\META-INF目录,并在其下建立两个文件jboss-service.xml 和 MANIFEST.MF ,用于把方法部署到Jboss中,jboss-service.xml 代码如下:

 

<?xml version="1.0" encoding="UTF-8"?>
<server>
 <mbean
  code="com.sample.upload.mbean.FileUpload"
  name="com.sample.remotedeploy.mbean.control:service=FileUpload">
 
  <depends>jboss.system:service=Logging,type=Log4jService</depends>

  <!-- jboss.rmi -->
  <depends>jboss.rmi:type=RMIClassLoader</depends>

  <!-- jboss jmx -->
  <depends>jboss.jmx:name=Invoker,type=adaptor</depends>
  <depends>jboss.jmx:name=Invoker,protocol=jrmp,service=proxyFactory,type=adaptor</depends>
  <depends>jboss.jmx:alias=jmx/rmi/RMIAdaptor</depends>

  <!-- jboss.security -->
  <depends>jboss.security:service=JaasSecurityManager</depends>
  <depends>jboss.security:service=SecurityConfig</depends>
  <depends>jboss.security:service=XMLLoginConfig</depends>

  <!-- jboss -->
  <depends>jboss:service=ClientUserTransaction</depends>
  <depends>jboss:service=Naming</depends>
  <depends>jboss:service=ClientUserTransaction</depends>
  <depends>jboss:service=TransactionManager</depends>
  <depends>jboss:service=UUIDKeyGeneratorFactory</depends>
  <depends>jboss:service=invoker,type=jrmp</depends>
  <depends>jboss:service=proxyFactory,target=ClientUserTransaction</depends>
  <depends>jboss:service=proxyFactory,target=ClientUserTransactionFactory</depends>

 </mbean>
</server>

9、MANIFEST.MF 代码如下:

 

Manifest-Version: 1.0
Ant-Version: Apache Ant 1.6.2
Created-By: 1.4.2_05-b04 (Sun Microsystems Inc.)

 

10、此时把所有Java编译后的class文件打包成 com.sample.jar 并拷贝到Jboss安装目录 server\default\lib 下,启动Jboss(即运行bin目录下的run.bat),再运行 TestFileUpload.java 程序进行测试(带入参数为要上传文件及完整目录名,如 java com.sample.upload.test.TestFileUpload E:\test.txt 注意引入-Classpath变量),则文件会上传到Jboss的server\default目录中。

 

希望大家有所收获。

 

(编辑注:本文未测试。)


如果给你带来帮助,欢迎微信或支付宝扫一扫,赞一下。