netconf_rs/
lib.rs

1use crate::transport::Transport;
2use log::*;
3use serde_derive::Deserialize;
4use serde_xml_rs::from_str;
5use std::io;
6
7pub mod transport;
8pub mod vendor;
9
10#[derive(Debug, Deserialize)]
11struct Hello {
12    pub capabilities: Capabilities,
13}
14
15#[derive(Debug, Deserialize)]
16struct Capabilities {
17    pub capability: Vec<String>,
18}
19
20/// A connection to NETCONF server
21pub struct Connection {
22    pub(crate) transport: Box<dyn Transport + Send + 'static>,
23}
24
25impl Connection {
26    pub fn new(transport: impl Transport + 'static) -> io::Result<Connection> {
27        let mut res = Connection {
28            transport: Box::from(transport),
29        };
30        res.hello()?;
31        Ok(res)
32    }
33
34    fn hello(&mut self) -> io::Result<()> {
35        debug!("Get capabilities of NetConf server");
36        self.transport.write_xml(
37            r#"
38<?xml version="1.0" encoding="UTF-8"?>
39<hello xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
40    <capabilities>
41        <capability>
42            urn:ietf:params:netconf:base:1.0
43        </capability>
44    </capabilities>
45</hello>
46]]>]]>
47        "#,
48        )?;
49        let resp = self.transport.read_xml()?;
50        let hello: Hello = from_str(&resp.trim()).unwrap();
51        debug!("{:#?}", hello);
52        Ok(())
53    }
54
55    pub fn get_config(&mut self) -> io::Result<String> {
56        self.transport.write_xml(
57            r#"
58<?xml version="1.0" encoding="UTF-8"?>
59<rpc message-id="100"
60    xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
61    <get-config>
62        <source>
63            <running/>
64        </source>
65    </get-config>
66</rpc>
67        "#,
68        )?;
69        let resp = self.transport.read_xml()?;
70        Ok(resp)
71    }
72}