SNMP не работает в Java хранимой процедуре - PullRequest
0 голосов
/ 27 апреля 2020

Я пытаюсь выполнить Java процедуру в Oracle JVM. Эта процедура отправляет SNMP-запрос на принтер, чтобы узнать его имя; он использует библиотеку SNMP4j

import java.io.IOException;
import org.snmp4j.CommunityTarget;
import org.snmp4j.PDU;
import org.snmp4j.Snmp;
import org.snmp4j.Target;
import org.snmp4j.TransportMapping;
import org.snmp4j.event.ResponseEvent;
import org.snmp4j.mp.SnmpConstants;
import org.snmp4j.smi.Address;
import org.snmp4j.smi.GenericAddress;
import org.snmp4j.smi.OID;
import org.snmp4j.smi.OctetString;
import org.snmp4j.smi.VariableBinding;
import org.snmp4j.transport.DefaultUdpTransportMapping;


public class Get_ink_levels_devices {

Snmp snmp = null;
String address = null;

/**
* Constructor
* @param add
*/
public Get_ink_levels_devices(String add)
{
address = add;
}


public static void main(String[] args) throws IOException {
/**
* Port 161 is used for Read and Other operations
* Port 162 is used for the trap generation
*/
Get_ink_levels_devices client = new Get_ink_levels_devices("udp:192.168.115.77/161");
client.start();
/**
* OID - .1.3.6.1.2.1.1.1.0 => SysDec
* OID - .1.3.6.1.2.1.1.5.0 => SysName
*.1.3.6.1.2.1.1.1.0
*.1.3.6.1.2.1.25.3.2.1.3.1
* => MIB explorer will be usefull here, as discussed in previous article
*/
String sysDescr = client.getAsString(new OID("1.3.6.1.2.1.25.3.2.1.3.1"));
System.out.println(sysDescr);
}

private void start() throws IOException {
TransportMapping transport = new DefaultUdpTransportMapping();
snmp = new Snmp(transport);
// Do not forget this line!
transport.listen();
}

/**
* Method which takes a single OID and returns the response from the agent as a String.
* @param oid
* @return
* @throws IOException
*/
public String getAsString(OID oid) throws IOException {
    ResponseEvent event = get(new OID[]{oid});
    if(event.getResponse() != null){
        return event.getResponse().get(0).getVariable().toString();
    } else {
        return "no target";
    }
}

/**
* This method is capable of handling multiple OIDs
* @param oids
* @return
* @throws IOException
*/
public ResponseEvent get(OID oids[]) throws IOException {
PDU pdu = new PDU();
for (OID oid : oids) {
pdu.add(new VariableBinding(oid));
}
pdu.setType(PDU.GET);
ResponseEvent event = snmp.send(pdu, getTarget(), null);
if(event != null) {
return event;
}
throw new RuntimeException("GET timed out");
}

/**
* This method returns a Target, which contains information about
* where the data should be fetched and how.
* @return
*/
private Target getTarget() {
Address targetAddress = GenericAddress.parse(address);
CommunityTarget target = new CommunityTarget();
target.setCommunity(new OctetString("public"));
target.setAddress(targetAddress);
target.setRetries(2);
target.setTimeout(5000);
target.setVersion(SnmpConstants.version1);
return target;
}

}

Здравствуйте, я пытаюсь выполнить Java процедуру в Oracle JVM. Эта процедура отправляет SNMP-запрос на принтер, чтобы узнать его имя; он использует библиотеку SNMP4j. Я использую Oracle 19 c, я скомпилировал эту процедуру, используя javac --release 8, после того как я загрузил библиотеку snmp4j-2.8.3.jar в базу данных, используя load java, а затем я загрузил сама процедура. Затем я создал процедуру в sqlplus CREATE OR REPLACE Procedure Test_ink AS LANGUAGE JAVA NAME 'Get_ink_levels_devices.main (java.lang.String [])'; и установил разрешения exec dbms_java.grant_permission (grantee => 'ADMIN', permission_type => 'SYS: java.net.SocketPermission', permission_name => '192.168.115.77:161',permission_action =>' accept, connect, listen, resolve '); и предоставил

GRANT JAVASYSPRIV TO Admin rights;
GRANT JAVAUSERPRIV TO Admin;
GRANT JAVAIDPRIV TO Admin;
exec dbms_network_acl_admin.create_acl('network_acl.xml','Test','ADMIN',TRUE,'connect',SYSTIMESTAMP,NULL)
exec DBMS_NETWORK_ACL_ADMIN.ADD_PRIVILEGE('network_acl.xml','ADMIN',TRUE,'connect',NULL,SYSTIMESTAMP,NULL)
exec DBMS_NETWORK_ACL_ADMIN.ASSIGN_ACL('network_acl.xml','*',1,65535);

Я запускаю процедуру следующим образом:

set serveroutput on;
call dbms_java.set_output (1000000);
exec Test_ink;

Но она не возвращает имя принтера, но возвращает «no traget», хотя, если я запускаю программу в консоли, она возвращает имя. Я не понимаю, что я делаю не так. Я не указал необходимые разрешения для Java или есть проблема в другом?

Добавление В общем, я пытался выполнить удаленную отладку этой процедуры с помощью SQL Developer, используя CALL DBMS_DEBUG_JDWP.CONNECT_TCP. В результате я получил сообщение The debbuger has hit an exception breackpoint, but it cannot find the source file.Unable to find source file for package java.net,filename DualStackPlainDatagramSocketImpl.java.Project IdeConnections%23OEC.jpr and its dependencies have already been searched. Насколько я понимаю, он не может найти файл с пакетом java, поскольку он встроен в саму СУБД Oracle, также было сообщение

An unknown, invalid, or unsupported parameter or level was specified to call getsockopt or setsockopt.```
I took a simple procedure that simply sends a UDP diagram to a given address and port:
```import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;


public class udp {

    public static void main(String[] args){
        System.out.println(udp.send("192.168.112.77","53","Test"));
    }

    public static String send(String ip,String port,String msg){
        try{
            int int_port=Integer.parseInt(port);    
            DatagramSocket ds = new DatagramSocket();
            DatagramPacket dp = new DatagramPacket(msg.getBytes(), msg.length(), InetAddress.getByName(ip), int_port);
            ds.send(dp);
            ds.close();
            return "Successfully";
        }catch(Exception e){
            return "Failed";
        }
    }
}

И в случае успеха отображает сообщение и снова все нормально в консоли, при выполнении в базе данных возвращает «Failed». В SQL Developer, та же ошибка снова. Я не понимаю Java и просто пытаюсь, но основываясь на всем этом, могу ли я предположить, что это какая-то ошибка в Oracle JVM при работе с UDP, у меня JDK версии 1.8.0_201 в Oracle, или все еще проблема с Java разрешениями, но я не могу себе представить, в какой, поскольку я разрешил все, что возможно с точки зрения работы с Java сетью.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...