将JT400设置为使用端口23连接到IBM i(AS400)

Moh*_*rie 2 java jt400 ibm-midrange

我试图从我的Java程序连接到IBM中型(AS400)计算机,然后重设用户密码。使用Jt400.jar,我设法做到了。但是问题是,我需要将端口设置为专门使用端口23。我希望它按照tn5250的方式连接到AS400。从IBM网站在这里,我知道我可以利用这样做as400.connectToPort(23)

令我感到困惑的是,当我添加该方法时,我得到了一个java.lang.RuntimeException: java.lang.NegativeArraySizeException。我曾尝试寻找什么导致此异常导致我在这里和更多的解释在这里。这是我的代码:

public void executeSetPassword(final String userName, final GuardedString password)  {

    if ((userName != null) && (password != null)) {
        final String host = configuration.getHost();
        final String remoteUser = configuration.getRemoteUser();
        GuardedString passwd = configuration.getPassword();
        boolean isSuccessful;

        final AS400 as400 = new AS400();

        try {
            as400.setSystemName(host);
            as400.setUserId(remoteUser);

            passwd.access(new Accessor(){
                @Override
                public void access(char[] clearChars) {
                    try {
                        as400.setPassword(new String(clearChars));
                    }catch (Exception e) {
                        e.printStackTrace();
                    }
                }});

            as400.setGuiAvailable(false);
            as400.connectToPort(23);

            final CommandCall cc = new CommandCall(as400);
            final StringBuilder command = new StringBuilder();
            password.access(new Accessor(){
                    @Override
                    public void access(char[] clearChars) {
                            command.append("CHGUSRPRF USRPRF(" + userName + ") PASSWORD(" + new String(clearChars) + ")");
                    }});
            try {
                isSuccessful = cc.run(command.toString());


                logger.info("command status is = " + isSuccessful);
                // getMessageList returns an array of AS400Message objects
                for(AS400Message msg : cc.getMessageList()){
                    logger.info(
                            "  msg: " + msg.getID() + ": " + msg.getText());
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        } catch (Exception e){
            throw new RuntimeException(e);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

这是日志文件:

Thread Id: 1    Time: 2015-06-29 14:27:05.592   Class: com.mastersam.connectors.AS400.AS400ConnectorTests   Method: updateTest(AS400ConnectorTests.java:150)    Level: INFO Message: Running Update Test
Thread Id: 1    Time: 2015-06-29 14:27:05.705   Class: org.identityconnectors.framework.api.operations.UpdateApiOp  Method: update  Level: OK   Message: Enter: update(ObjectClass: __ACCOUNT__, Attribute: {Name=__UID__, Value=[fikrie1]}, [Attribute: {Name=__PASSWORD__, Value=[org.identityconnectors.common.security.GuardedString@408a7bb8]}], OperationOptions: {})
Thread Id: 1    Time: 2015-06-29 14:27:07.749   Class: org.identityconnectors.framework.api.operations.UpdateApiOp  Method: update  Level: OK   Message: Exception: 
java.lang.RuntimeException: java.lang.NegativeArraySizeException
at com.mastersam.connectors.AS400.AS400Connector.executeSetPassword(AS400Connector.java:261)
at com.mastersam.connectors.AS400.AS400Connector.update(AS400Connector.java:199)
at org.identityconnectors.framework.impl.api.local.operations.UpdateImpl.update(UpdateImpl.java:88)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.local.operations.ConnectorAPIOperationRunnerProxy.invoke(ConnectorAPIOperationRunnerProxy.java:97)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.local.operations.ThreadClassLoaderManagerProxy.invoke(ThreadClassLoaderManagerProxy.java:96)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.DelegatingTimeoutProxy.invoke(DelegatingTimeoutProxy.java:98)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.LoggingProxy.invoke(LoggingProxy.java:76)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at org.identityconnectors.framework.impl.api.AbstractConnectorFacade.update(AbstractConnectorFacade.java:176)
at com.mastersam.connectors.AS400.AS400ConnectorTests.updateTest(AS400ConnectorTests.java:156)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.testng.internal.MethodInvocationHelper.invokeMethod(MethodInvocationHelper.java:84)
at org.testng.internal.Invoker.invokeMethod(Invoker.java:714)
at org.testng.internal.Invoker.invokeTestMethod(Invoker.java:901)
at org.testng.internal.Invoker.invokeTestMethods(Invoker.java:1231)
at org.testng.internal.TestMethodWorker.invokeTestMethods(TestMethodWorker.java:127)
at org.testng.internal.TestMethodWorker.run(TestMethodWorker.java:111)
at org.testng.TestRunner.privateRun(TestRunner.java:767)
at org.testng.TestRunner.run(TestRunner.java:617)
at org.testng.SuiteRunner.runTest(SuiteRunner.java:334)
at org.testng.SuiteRunner.runSequentially(SuiteRunner.java:329)
at org.testng.SuiteRunner.privateRun(SuiteRunner.java:291)
at org.testng.SuiteRunner.run(SuiteRunner.java:240)
at org.testng.SuiteRunnerWorker.runSuite(SuiteRunnerWorker.java:52)
at org.testng.SuiteRunnerWorker.run(SuiteRunnerWorker.java:86)
at org.testng.TestNG.runSuitesSequentially(TestNG.java:1224)
at org.testng.TestNG.runSuitesLocally(TestNG.java:1149)
at org.testng.TestNG.run(TestNG.java:1057)
at org.testng.remote.RemoteTestNG.run(RemoteTestNG.java:111)
at org.testng.remote.RemoteTestNG.initAndRun(RemoteTestNG.java:204)
at org.testng.remote.RemoteTestNG.main(RemoteTestNG.java:175)
Caused by: java.lang.NegativeArraySizeException
at com.ibm.as400.access.AS400XChgRandSeedReplyDS.read(AS400XChgRandSeedReplyDS.java:58)
at com.ibm.as400.access.AS400ImplRemote.getConnection(AS400ImplRemote.java:823)
at com.ibm.as400.access.AS400ImplRemote.connectToPort(AS400ImplRemote.java:408)
at com.ibm.as400.access.AS400.connectToPort(AS400.java:1152)
at com.mastersam.connectors.AS400.AS400Connector.executeSetPassword(AS400Connector.java:239)
... 52 more
FAILED: updateTest
java.lang.RuntimeException: java.lang.NegativeArraySizeException
at com.mastersam.connectors.AS400.AS400Connector.executeSetPassword(AS400Connector.java:261)
at com.mastersam.connectors.AS400.AS400Connector.update(AS400Connector.java:199)
at org.identityconnectors.framework.impl.api.local.operations.UpdateImpl.update(UpdateImpl.java:88)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.local.operations.ConnectorAPIOperationRunnerProxy.invoke(ConnectorAPIOperationRunnerProxy.java:97)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.local.operations.ThreadClassLoaderManagerProxy.invoke(ThreadClassLoaderManagerProxy.java:96)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.DelegatingTimeoutProxy.invoke(DelegatingTimeoutProxy.java:98)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.identityconnectors.framework.impl.api.LoggingProxy.invoke(LoggingProxy.java:76)
at com.sun.proxy.$Proxy10.update(Unknown Source)
at org.identityconnectors.framework.impl.api.AbstractConnectorFacade.update(AbstractConnectorFacade.java:176)
at com.mastersam.connectors.AS400.AS400ConnectorTests.updateTest(AS400ConnectorTests.java:156)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.testng.internal.MethodInvocationHelper.invokeMethod(MethodInvocationHelper.java:84)
at org.testng.internal.Invoker.invokeMethod(Invoker.java:714)
at org.testng.internal.Invoker.invokeTestMethod(Invoker.java:901)
at org.testng.internal.Invoker.invokeTestMethods(Invoker.java:1231)
at org.testng.internal.TestMethodWorker.invokeTestMethods(TestMethodWorker.java:127)
at org.testng.internal.TestMethodWorker.run(TestMethodWorker.java:111)
at org.testng.TestRunner.privateRun(TestRunner.java:767)
at org.testng.TestRunner.run(TestRunner.java:617)
at org.testng.SuiteRunner.runTest(SuiteRunner.java:334)
at org.testng.SuiteRunner.runSequentially(SuiteRunner.java:329)
at org.testng.SuiteRunner.privateRun(SuiteRunner.java:291)
at org.testng.SuiteRunner.run(SuiteRunner.java:240)
at org.testng.SuiteRunnerWorker.runSuite(SuiteRunnerWorker.java:52)
at org.testng.SuiteRunnerWorker.run(SuiteRunnerWorker.java:86)
at org.testng.TestNG.runSuitesSequentially(TestNG.java:1224)
at org.testng.TestNG.runSuitesLocally(TestNG.java:1149)
at org.testng.TestNG.run(TestNG.java:1057)
at org.testng.remote.RemoteTestNG.run(RemoteTestNG.java:111)
at org.testng.remote.RemoteTestNG.initAndRun(RemoteTestNG.java:204)
at org.testng.remote.RemoteTestNG.main(RemoteTestNG.java:175)
Caused by: java.lang.NegativeArraySizeException
at com.ibm.as400.access.AS400XChgRandSeedReplyDS.read(AS400XChgRandSeedReplyDS.java:58)
at com.ibm.as400.access.AS400ImplRemote.getConnection(AS400ImplRemote.java:823)
at com.ibm.as400.access.AS400ImplRemote.connectToPort(AS400ImplRemote.java:408)
at com.ibm.as400.access.AS400.connectToPort(AS400.java:1152)
at com.mastersam.connectors.AS400.AS400Connector.executeSetPassword(AS400Connector.java:239)
... 52 more
Run Code Online (Sandbox Code Playgroud)

那么,为什么从jt400添加一个方法会导致NegativeArraySizeException?

在寻找替代方法时,我在这里找到了有关JT400方法的更多信息,然后尝试使用as400.connectService()。从这里开始,我假设我应该使用的服务是COMMANDSIGNON。尝试此方法后,这是我的代码的一部分:

final AS400 as400 = new AS400();                
        try {

            as400.setSystemName(host);
            as400.setUserId(remoteUser);
            passwd.access(new Accessor(){
                @Override
                public void access(char[] clearChars) {
                    try {
                        as400.setPassword(new String(clearChars));
                    }catch (Exception e) {
                        e.printStackTrace();
                    }
                }});
            as400.setGuiAvailable(false);

            as400.connectService(7);      //I added this
            as400.setServicePort(7, 23);  //I added this
            as400.setServicePort(6, 23);  //I added this
            logger.info("port is = " + as400.getServicePort(7));
            final CommandCall cc = new CommandCall(as400);
            final StringBuilder command = new StringBuilder();
            password.access(new Accessor(){
                    @Override
                    public void access(char[] clearChars) {
                            command.append("CHGUSRPRF USRPRF(" + userName + ") PASSWORD(" + new String(clearChars) + ")");
                    }});
            try {

                isSuccessful = cc.run(command.toString());
                as400.setServicePort(2, 23); //I added this
                logger.info("port is = " + as400.getServicePort(2));
}
Run Code Online (Sandbox Code Playgroud)

根据日志,该端口为23。但是当我使用Wireshark应用程序仔细检查时,该端口用于连接AS400的端口不是23。如果我在任何地方做错了,请指导我。

我尝试过的另一件事,

  1. as400.connectService()与之间交换线as400.setServicePort()

    • 引起与上一个相同的错误:java.lang.NegativeArraySizeException
  2. 检查端口23是否可用。使用tn5250连接到AS400。连接正常。

  3. 设置为400.connectToPort()以使用其他端口。

    • 导致与使用端口23相同的错误。

Buc*_*bro 5

connectToPort()返回一个Socket对象,而不是AS400对象。因此,您不能使用任何AS400类与返回的Socket对象进行交互。

您可能考虑使用changePassword()而不是尝试将命令填充到telnet端口。

changePassword

public void changePassword(java.lang.String oldPassword,
                  java.lang.String newPassword)
                    throws AS400SecurityException,
                           java.io.IOException

Changes the user profile password. The system name and user profile name need to be set prior to calling this method.

Parameters:
    oldPassword - The old user profile password.
    newPassword - The new user profile password.
Throws:
    AS400SecurityException - If a security or authority error occurs.
    java.io.IOException - If an error occurs while communicating with the system.
Run Code Online (Sandbox Code Playgroud)