Java NetConf 使用

1. 参考资料

工具包GIT地址 : https://github.com/Juniper/netconf-java

使用教程 : https://www.juniper.net/documentation/cn/zh/software/junos/netconf-java-toolkit/topics/task/netconf-java-toolkit-program-creating-and-executing.html

2. 下载&编译工具包

在这里插入图片描述

# 1. 下载git地址中的工具包到本地, 用IDEA打开处理
- 此处为v2.1.1版本 
- https://github.com/Juniper/netconf-java/releases

# 2. 添加maven配置, 打包处理, 配置如下
- 将如下配置 到maven 的plugin中 解决不能将依赖打进来的问题
- 生成的jar包保存 `netconf-java-2.1.1.6-SNAPSHOT-jar-with-dependencies.jar`
<!-- Maven Assembly Plugin -->
<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-assembly-plugin</artifactId>
    <version>2.4.1</version>
    <configuration>
        <!-- get all project dependencies -->
        <descriptorRefs>
            <descriptorRef>jar-with-dependencies</descriptorRef>
        </descriptorRefs>
    </configuration>
    <executions>
        <execution>
            <id>make-assembly</id>
            <!-- bind to the packaging phase -->
            <phase>package</phase>
            <goals>
                <goal>single</goal>
            </goals>
        </execution>
    </executions>
</plugin>

3. 添加jar包到自己的类路径

# 在自己的项目中将该打包好的jar包右键选择 As a library

4. 编写工具类 NetconfUtils

# 编写该工具类
- NetconfUtils
import net.juniper.netconf.Device;
import net.juniper.netconf.NetconfException;
import net.juniper.netconf.XML;

public class NetconfUtils {

    private static final String HOSTNAME = "10.10.10.10";
    private static final String USERNAME = "admin";
    private static final String PASSWORD = "123456";
    private static final int NETCONF_PORT = 830;

    /**
     * 要发送的xml报文 例如:
     * <get>
     * <filter type="subtree">
     * <users xmlns="http://netconfcentral.org/ns/user">
     * <user>
     * <name>admin</name>
     * </user>
     * </users>
     * </filter>
     * </get>
     *
     * @param xmlContent
     * @return
     */
    public static XML send(String xmlContent) throws NetconfException {

        Device device = null;

        XML xmlReply = null;

        try {
            device = Device.builder().hostName(HOSTNAME)
                    .userName(USERNAME)
                    .password(PASSWORD)
                    .port(NETCONF_PORT)
                    .strictHostKeyChecking(false)
                    .hostKeysFileName(null)
                    .build();
            device.connect();

            xmlReply = device.executeRPC(xmlContent);
            device.close();
        } catch (Exception e) {
            e.printStackTrace();
            throw new NetconfException("报文发送失败");
        } finally {
            if (null != device) {
                device.close();
            }
        }
        return xmlReply;
    }


    public static XML send(String deviceHOSTNAME, String deviceUSERNAME, String devicePASSWORD, int deviceNETCONFPORT
            , String xmlContent) throws NetconfException {

        Device device = null;

        XML xmlReply = null;

        try {
            device = Device.builder().hostName(deviceHOSTNAME)
                    .userName(deviceUSERNAME)
                    .password(devicePASSWORD)
                    .port(deviceNETCONFPORT)
                    .strictHostKeyChecking(false)
                    .hostKeysFileName(null)
                    .build();
            device.connect();

            xmlReply = device.executeRPC(xmlContent);
            device.close();
        } catch (Exception e) {
            e.printStackTrace();
            throw new NetconfException("报文发送失败");
        } finally {
            if (null != device) {
                device.close();
            }
        }
        return xmlReply;
    }

}

5. 使用Test

使用之前打开对应设备的netconf功能

@Slf4j
public class TestMain {

    /**
     * 非启动Spring框架时取消slf4J的日志显示
     */
    static {
        LoggerContext loggerContext = (LoggerContext) LoggerFactory.getILoggerFactory();
        List<Logger> loggerList = loggerContext.getLoggerList();
        loggerList.forEach(logger -> {
            logger.setLevel(Level.ERROR);
        });
    }

    @Test
    public void test() throws NetconfException {
        XML send = NetconfUtils.send("<get>\n" +
                "<filter type=\"subtree\">\n" +
                "<users xmlns=\"http://netconfcentral.org/ns/user\">\n" +
                "<user>\n" +
                "<name>admin</name>\n" +
                "</user>\n" +
                "</users>\n" +
                "</filter>\n" +
                "</get>");
        System.out.println(send);

    }

}

结果

<rpc-reply xmlns="urn:ietf:params:xml:ns:netconf:base:1.0" xmlns:nc="urn:ietf:params:xml:ns:netconf:base:1.0" last-modified="2022-04-28T14:54:59Z" message-id="2">
  <data>
    <users xmlns="http://netconfcentral.org/ns/user">
      <user>
        <name>admin</name>
        <password>$1$ROky/q82$GKYA8rTVFVyYjLb8Sh27E1</password>
        <description/>
        <group-id>Super</group-id>
      </user>
    </users>
  </data>
</rpc-reply>
  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
以下是一个简单的 Java Netconf 客户端代码示例: ```java import java.io.IOException; import java.io.StringReader; import java.util.ArrayList; import java.util.List; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import org.xml.sax.InputSource; import org.xml.sax.SAXException; import org.xml.sax.helpers.DefaultHandler; import io.netty.bootstrap.Bootstrap; import io.netty.buffer.ByteBuf; import io.netty.buffer.Unpooled; import io.netty.channel.ChannelFuture; import io.netty.channel.ChannelHandlerContext; import io.netty.channel.ChannelInboundHandlerAdapter; import io.netty.channel.ChannelInitializer; import io.netty.channel.ChannelOption; import io.netty.channel.ChannelPipeline; import io.netty.channel.EventLoopGroup; import io.netty.channel.nio.NioEventLoopGroup; import io.netty.channel.socket.SocketChannel; import io.netty.channel.socket.nio.NioSocketChannel; import io.netty.handler.codec.ByteToMessageDecoder; import io.netty.handler.codec.MessageToByteEncoder; import io.netty.handler.codec.string.StringDecoder; import io.netty.handler.codec.string.StringEncoder; import io.netty.util.CharsetUtil; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.NodeList; public class NetconfClient { private static final String NETCONF_HELLO = "<hello xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\"><capabilities><capability>urn:ietf:params:netconf:base:1.0</capability></capabilities></hello>"; private static final String NETCONF_GET_TIME = "<rpc message-id=\"1\" xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\"><get><system-clock/></get></rpc>"; private static final String NETCONF_CLOSE = "<rpc message-id=\"2\" xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\"><close-session/></rpc>"; private static final String NETCONF_END_PATTERN = "]]>]]>"; private static final int MAX_FRAME_LENGTH = 1024; private static final String NETCONF_SERVER_IP = "localhost"; private static final int NETCONF_SERVER_PORT = 830; public static void main(String[] args) throws Exception { EventLoopGroup workerGroup = new NioEventLoopGroup(); try { Bootstrap b = new Bootstrap(); b.group(workerGroup); b.channel(NioSocketChannel.class); b.option(ChannelOption.TCP_NODELAY, true); b.handler(new ChannelInitializer<SocketChannel>() { @Override public void initChannel(SocketChannel ch) throws Exception { ChannelPipeline pipeline = ch.pipeline(); pipeline.addLast(new StringEncoder(CharsetUtil.UTF_8)); pipeline.addLast(new StringDecoder(CharsetUtil.UTF_8)); pipeline.addLast(new NetconfMessageDecoder()); pipeline.addLast(new NetconfMessageEncoder()); pipeline.addLast(new NetconfClientHandler()); } }); ChannelFuture f = b.connect(NETCONF_SERVER_IP, NETCONF_SERVER_PORT).sync(); f.channel().closeFuture().sync(); } finally { workerGroup.shutdownGracefully(); } } private static class NetconfMessageDecoder extends ByteToMessageDecoder { @Override protected void decode(ChannelHandlerContext ctx, ByteBuf in, List<Object> out) throws Exception { String message = in.toString(CharsetUtil.UTF_8); int end = message.indexOf(NETCONF_END_PATTERN); if (end != -1) { out.add(message.substring(0, end + NETCONF_END_PATTERN.length())); } } } private static class NetconfMessageEncoder extends MessageToByteEncoder<String> { @Override protected void encode(ChannelHandlerContext ctx, String msg, ByteBuf out) throws Exception { out.writeBytes(msg.getBytes()); out.writeBytes(NETCONF_END_PATTERN.getBytes()); } } private static class NetconfClientHandler extends ChannelInboundHandlerAdapter { @Override public void channelActive(ChannelHandlerContext ctx) { ctx.writeAndFlush(NETCONF_HELLO); ctx.writeAndFlush(NETCONF_GET_TIME); } @Override public void channelRead(ChannelHandlerContext ctx, Object msg) { String response = (String)msg; DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); DocumentBuilder builder = factory.newDocumentBuilder(); Document doc = builder.parse(new InputSource(new StringReader(response))); NodeList nodeList = doc.getElementsByTagName("system-clock"); if (nodeList.getLength() > 0) { Element clockElement = (Element)nodeList.item(0); String dateTime = clockElement.getChildNodes().item(0).getNodeValue(); System.out.println("System clock is: " + dateTime); ctx.writeAndFlush(NETCONF_CLOSE); } } @Override public void channelReadComplete(ChannelHandlerContext ctx) { ctx.close(); } @Override public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) { cause.printStackTrace(); ctx.close(); } } } ``` 该代码使用 Netty 实现了一个简单的 Netconf 客户端,可以连接到 Netconf 服务器并执行一些基本操作,例如获取系统时间。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值