先貼上自己的代碼,以後在講解,很幼稚的設計思路,隻是個雛形,可貴的是完成了SNMPv123的測試
隻有一個Main類:
import org.snmp4j.*;
import org.snmp4j.event.ResponseEvent;
import org.snmp4j.mp.MPv3;
import org.snmp4j.mp.SnmpConstants;
import org.snmp4j.security.*;
import org.snmp4j.smi.*;
import org.snmp4j.transport.DefaultUdpTransportMapping;
import org.snmp4j.util.DefaultPDUFactory;
import org.snmp4j.util.TableEvent;
import org.snmp4j.util.TableUtils;
import java.io.IOException;
import java.util.List;
import java.util.Scanner;
import java.util.Vector;
public class Main {
public static void main(String[] args) throws IOException {
Scanner input = new Scanner(System.in);
System.out.println("請設定snmp版本:");
int version = input.nextInt();
System.out.println("設定的snmp版本為:" + version);
if (1==version||2==version){
try {
Main a = new Main();
a.getRequest();
} catch (IOException e) {
e.printStackTrace();
}
}else if (3==version){
String nmsAdmin = "";
String AuthKey="";
String nmsPrivKey="";
String ip ="";
long timeout = 0;
int retry = 0;
Snmp snmp = new Snmp(new DefaultUdpTransportMapping());
USM usm = new USM(SecurityProtocols.getInstance(), new OctetString(MPv3.createLocalEngineID()), 0);
SecurityModels.getInstance().addSecurityModel(usm);
snmp.listen();
// 執行個體化user,并設定屬性
Scanner set = new Scanner(System.in);
System.out.println("請輸入檢測對象的IP:");
ip = input.next();
System.out.println("請輸入使用者名稱:");
nmsAdmin = set.next();
System.out.println("請輸入認證秘鑰:");
AuthKey = set.next();
System.out.println("請輸入加密秘鑰");
nmsPrivKey = set.next();
System.out.println("請設定逾時時間:");
long timeout0 = input.nextInt();
timeout = timeout0 * 1000L;
System.out.println("設定的逾時時間為:" + timeout0 + "秒");
System.out.println("請設定重試次數:");
retry = input.nextInt();
UsmUser user = new UsmUser(
new OctetString(nmsAdmin), // 安全名稱
AuthMD5.ID, // 認證協定
new OctetString(AuthKey), // 認證秘鑰
PrivDES.ID, // 加密算法
new OctetString(nmsPrivKey)); // 加密密鑰
snmp.getUSM().addUser(new OctetString(nmsAdmin), user);
// 構造發送目标,SNMPv 1/2,執行個體化一個CommunityTarget對象。如果是SNMPv3,則需要執行個體化一個UserTarget對象。
UserTarget target = new UserTarget();
// 設定target
target.setVersion(SnmpConstants.version3); // 設定版本
target.setAddress(new UdpAddress(ip+"/161")); // 目的IP、端口号
target.setTimeout(timeout); // 等待延時
target.setRetries(retry); // 重試次數
target.setSecurityLevel(SecurityLevel.AUTH_PRIV); // 安全級别-v3特有
target.setSecurityName(new OctetString(nmsAdmin)); // 安全名稱-v3特有
OctetString contextEngineId = new OctetString("0002651100[02]"); // 初始化上下文引擎ID
sendRequest(snmp, createGetPdu(contextEngineId), target); // 發送請求封包
snmpWalk(snmp, target, contextEngineId);
}
}
public void getRequest()throws IOException{
String protocol = "udp";
int port = 161;
String ip ="";
String community ="";
long timeout = 0;
int retry = 0;
Scanner input = new Scanner(System.in);
System.out.println("請輸入檢測對象的IP:");
ip = input.next();
System.out.println("檢測對象IP:" + ip);
System.out.println("請輸入community:");
community = input.next();
System.out.println("團體名:" + community);
System.out.println("請設定逾時時間:");
long timeout0 = input.nextInt();
timeout = timeout0 * 1000L;
System.out.println("設定的逾時時間為:" + timeout0 + "秒");
System.out.println("請設定重試次數:");
retry = input.nextInt();
System.out.println("設定的重試次數為:" + retry + "次");
System.out.println("選擇要采集的對象:");
String oid = input.next();
//System.out.println("要采集的對象為:" + oid );
//建立對象transport
TransportMapping transport = new DefaultUdpTransportMapping();
//建立并初始化對象snmpClient
Snmp snmpClient = new Snmp(transport);
transport.listen();
//建立并初始化對象address
Address address = GenericAddress.parse(protocol+":"+ip+"/"+port);
//建立并初始化對象target
Target target = new CommunityTarget(address,new OctetString(community));
//對象調用方法,來設定SNMP版本-version2c、嘗試次數、逾時時間
target.setVersion(SnmpConstants.version2c);
target.setRetries(retry);
target.setTimeout(timeout);
//建立對象request
PDU request = new PDU();
//設定類型-GET
request.setType(PDU.GET);
//添加OID
request.add(new VariableBinding(new OID(oid)));
//建立并初始化對象:響應事件
ResponseEvent respEvent = snmpClient.send(request,target);
//建立對象response接收響應
PDU response = respEvent.getResponse();
if (null!=response){
if (response.size()>0){
//建立對象變量,來接收響應結果
VariableBinding vbi = response.get(0);
System.out.println("采集結果為:"+vbi.getVariable().toString());
}
}
}
private static PDU createGetPdu(OctetString contextEngineId) {
ScopedPDU pdu = new ScopedPDU(); // 構造pdu
pdu.setType(PDU.GET); // 設定請求類型
pdu.setContextEngineID(contextEngineId); // 如果不設定, 将會是SNMP引擎ID
//pdu.setContextName(contextName); // 設定上下文名稱,必須和代理的一樣
//設定OID,即要通路的對象
pdu.add(new VariableBinding(new OID("1.3.6.1.2.1.1.3.0"))); // sysUpTime
pdu.add(new VariableBinding(new OID("1.3.6.1.2.1.1.5.0"))); // sysName
pdu.add(new VariableBinding(new OID("1.3.6.1.2.1.1.5"))); // expect an no_such_instance error
return pdu;
}
/*
* 同步模式發送消息後便等待響應的到達,到達之後會傳回一個ResponseEvent對象,該對象中包含了響應的相應資訊。
* 異步模式發送消息之後便會繼續執行,當收到響應消息時便會調用監聽對象的OnResponse函數。
*/
private static void sendRequest(Snmp snmp, PDU pdu, UserTarget target)
throws IOException {
ResponseEvent responseEvent = snmp.send(pdu, target); // 将pdu發送給target,傳回一個response
PDU response = responseEvent.getResponse(); // 傳回的response
if (response == null) { // 如果response為空
System.out.println("TimeOut...");
} else { // 如果response不為空
if (response.getErrorStatus() == PDU.noError) {
Vector<? extends VariableBinding> vbs = response.getVariableBindings();
for (VariableBinding vb : vbs) {
System.out.println(vb + " ," + vb.getVariable().getSyntaxString());
}
} else {
System.out.println("Error:" + response.getErrorStatusText());
}
}
}
private static void snmpWalk(Snmp snmp, UserTarget target, OctetString contextEngineId) {
TableUtils utils = new TableUtils(snmp,
new MyDefaultPDUFactory(PDU.GETNEXT, //GETNEXT or GETBULK)
contextEngineId));
utils.setMaxNumRowsPerPDU(5); //only for GETBULK, set max-repetitions, default is 10
OID[] columnOids = new OID[] {
new OID("1.3.6.1.2.1.1.9.1.2"), //sysORID
new OID("1.3.6.1.2.1.1.9.1.3") //sysORDescr
};
// If not null, all returned rows have an index in a range (lowerBoundIndex, upperBoundIndex]
List<TableEvent> l = utils.getTable(target, columnOids, new OID("3"), new OID("10"));
for (TableEvent e : l) {
System.err.println(e);
}
}
private static class MyDefaultPDUFactory extends DefaultPDUFactory {
private OctetString contextEngineId = null;
public MyDefaultPDUFactory(int pduType, OctetString contextEngineId) {
super(pduType);
this.contextEngineId = contextEngineId;
}
@Override
public PDU createPDU(Target target) {
PDU pdu = super.createPDU(target);
if (target.getVersion() == SnmpConstants.version3) {
((ScopedPDU) pdu).setContextEngineID(contextEngineId);
}
return pdu;
}
}
}