Exemplo n.º 1
0
    def __init__(self, *args, **kwargs):
        '''
        __init__ instantiates a single connection instance.
        '''
        # set defaults
        kwargs.setdefault('timeout', 30)

        # instanciate BaseConnection
        # (could use super...)
        BaseConnection.__init__(self, *args, **kwargs)

        # shortwire Ncclient device handling portion
        # and create just the DeviceHandler
        device_handler = DefaultDeviceHandler()

        # create the session instance
        session = transport.SSHSession(device_handler)

        # load known_hosts file (if available)
        session.load_known_hosts()

        # instanciate ncclient Manager
        # (can't use super due to mro change)
        manager.Manager.__init__(self, session = session,
                                       device_handler = device_handler,
                                       timeout = self.timeout)
Exemplo n.º 2
0
def connect(ns):
    password = ns.password
    if password is None:
        password = getpass.getpass()
    connect_args = dict(host=ns.host,
                        port=ns.port,
                        username=ns.username,
                        password=password,
                        key_filename=ns.privKeyFile,
                        hostkey_verify=False,
                        look_for_keys=False,
                        allow_agent=False)
    device_handler = manager.make_device_handler(None)
    if not ns.tcp and not ns.raw:
        # use the public API only
        session = transport.SSHSession(device_handler)
    elif ns.tcp:
        session = nctransport.TCPSession(device_handler, ns.raw)
    else:
        session = nctransport.SSHSession(device_handler, ns.raw)
    if not ns.tcp and ("hostkey_verify" not in connect_args
                       or connect_args["hostkey_verify"]):
        session.load_known_hosts()
    try:
        session.connect(**connect_args)
    except Exception:
        if session.transport:
            session.close()
        raise
    return manager.Manager(session, device_handler, **connect_args)
Exemplo n.º 3
0
    def test_rawrpc(self):
        from ncclient.operations.retrieve import GetReply

        h = DefaultDeviceHandler()
        self.rawrpc = yang.connector.netconf.RawRPC(
            session=transport.SSHSession(h), device_handler=h)
        self.rawrpc._event = MyEvent()
        self.rawrpc._session = MySSHSession()
        reply_raw = '''
            <rpc-reply message-id="101"
             xmlns="urn:ietf:params:xml:ns:netconf:base:1.0" >
            <data>
            <native xmlns="http://cisco.com/ns/yang/ned/ios">
            <version>16.3</version>
            </native>
            </data>
            </rpc-reply>
            '''
        self.rawrpc._reply = GetReply(reply_raw)
        r = '''
             <rpc message-id="101"
              xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
             <get>
             <filter>
             <native xmlns="http://cisco.com/ns/yang/ned/ios">
             <version>
             </version>
             </native>
             </filter>
             </get>
             </rpc>
            '''
        generated_value = self.rawrpc._request(r).xml
        expected_value = '''
            <rpc-reply message-id="101"
             xmlns="urn:ietf:params:xml:ns:netconf:base:1.0" >
            <data>
            <native xmlns="http://cisco.com/ns/yang/ned/ios">
            <version>16.3</version>
            </native>
            </data>
            </rpc-reply>
            '''
        self.assertEqual(generated_value, expected_value)
Exemplo n.º 4
0
def connect_ssh(*args, **kwds):
    """
    Initialize a :class:`Manager` over the SSH transport.
    For documentation of arguments see :meth:`ncclient.transport.SSHSession.connect`.

    The underlying :class:`ncclient.transport.SSHSession` is created with
        :data:`CAPABILITIES`. It is first instructed to
        :meth:`~ncclient.transport.SSHSession.load_known_hosts` and then
        all the provided arguments are passed directly to its implementation
        of :meth:`~ncclient.transport.SSHSession.connect`.

    To invoke advanced vendor related operation add device_params =
        {'name':'<vendor_alias>'} in connection paramerers. For the time,
        'junos' and 'nexus' are supported for Juniper and Cisco Nexus respectively.

    A custom device handler can be provided with device_params =
        {'handler':<handler class>} in connection paramerers.
    """
    # Extract device parameter dict, if it was passed into this function. Need to
    # remove it from kwds, since the session.connect() doesn't like extra stuff in
    # there.
    if "device_params" in kwds:
        device_params = kwds["device_params"]
        del kwds["device_params"]
    else:
        device_params = None

    device_handler = make_device_handler(device_params)
    device_handler.add_additional_ssh_connect_params(kwds)
    global VENDOR_OPERATIONS
    VENDOR_OPERATIONS.update(device_handler.add_additional_operations())
    session = transport.SSHSession(device_handler)
    if "hostkey_verify" not in kwds or kwds["hostkey_verify"]:
        session.load_known_hosts()

    try:
        session.connect(*args, **kwds)
    except Exception as ex:
        if session.transport:
            session.close()
        raise
    return Manager(session, device_handler, **kwds)
Exemplo n.º 5
0
def connect_ssh(*args, **kwds):
    """
    Initialize a :class:`Manager` over the SSH transport.
    For documentation of arguments see :meth:`ncclient.transport.SSHSession.connect`.

    The underlying :class:`ncclient.transport.SSHSession` is created with
    :data:`CAPABILITIES`. It is first instructed to
    :meth:`~ncclient.transport.SSHSession.load_known_hosts` and then
    all the provided arguments are passed directly to its implementation
    of :meth:`~ncclient.transport.SSHSession.connect`.

    To customize the :class:`Manager`, add a `manager_params` dictionary in connection
    parameters (e.g. `manager_params={'timeout': 60}` for a bigger RPC timeout parameter)

    To invoke advanced vendor related operation add
    `device_params={'name': '<vendor_alias>'}` in connection parameters. For the time,
    'junos' and 'nexus' are supported for Juniper and Cisco Nexus respectively.

    A custom device handler can be provided with
    `device_params={'handler':<handler class>}` in connection parameters.
    """
    # Extract device parameter and manager parameter dictionaries, if they were passed into this function.
    # Remove them from kwds (which should keep only session.connect() parameters).
    device_params = _extract_device_params(kwds)
    manager_params = _extract_manager_params(kwds)

    device_handler = make_device_handler(device_params)
    device_handler.add_additional_ssh_connect_params(kwds)
    global VENDOR_OPERATIONS
    VENDOR_OPERATIONS.update(device_handler.add_additional_operations())
    session = transport.SSHSession(device_handler)
    if "hostkey_verify" not in kwds or kwds["hostkey_verify"]:
        session.load_known_hosts()

    try:
        session.connect(*args, **kwds)
    except Exception as ex:
        if session.transport:
            session.close()
        raise
    return Manager(session, device_handler, **manager_params)
Exemplo n.º 6
0
def connect(*args, **kwargs):
    """
    Initialize a :class:`ModelDevice` over the SSH transport.
    For documentation of arguments see :meth:`ncclient.transport.SSHSession.connect`.
    The underlying :class:`ncclient.transport.SSHSession` is created with
        :data:`CAPABILITIES`. It is first instructed to
        :meth:`~ncclient.transport.SSHSession.load_known_hosts` and then
        all the provided arguments are passed directly to its implementation
        of :meth:`~ncclient.transport.SSHSession.connect`.
    """

    device_handler = DefaultDeviceHandler()
    session = transport.SSHSession(device_handler)
    if "hostkey_verify" not in kwargs or kwargs["hostkey_verify"]:
        session.load_known_hosts()

    try:
       session.connect(*args, **kwargs)
    except Exception as ex:
        if session.transport:
            session.close()
        raise
    return ModelDevice(session, device_handler, **kwargs)
Exemplo n.º 7
0
    def connect(self):
        '''connect

        High-level api: opens the NetConf connection and exchanges
        capabilities. Since topology YAML file is parsed by BaseConnection,
        the following parameters can be specified in your YAML file.

        Parameters
        ----------

        host : `string`
            Hostname or IP address to connect to.
        port : `int`, optional
            By default port is 830, but some devices use the default SSH port
            of 22 so this may need to be specified.
        timeout : `int`, optional
            An optional keyed argument to set timeout value in seconds. By
            default this value is 30 seconds.
        username : `string`
            The username to use for SSH authentication.
        password : `string`
            The password used if using password authentication, or the
            passphrase to use for unlocking keys that require it.
        key_filename : `string`
            a filename where a the private key to be used can be found.
        allow_agent : `boolean`
            Enables querying SSH agent (if found) for keys. The default value
            is True.
        hostkey_verify : `boolean`
            Enables hostkey verification from ~/.ssh/known_hosts. The default
            value is False.
        look_for_keys : `boolean`
            Enables looking in the usual locations for ssh keys
            (e.g. ~/.ssh/id_*). The default value is True.
        ssh_config : `string`
            Enables parsing of an OpenSSH configuration file, if set to its
            path, e.g. ~/.ssh/config or to True. If the value is True,
            ncclient uses ~/.ssh/config. The default value is None.

        Raises
        ------

        Exception
            If the YAML file does not have correct connections section, or
            establishing transport to ip:port is failed, ssh authentication is
            failed, or other transport failures.

        Note
        ----

        There is no return from this method. If something goes wrong, an
        exception will be raised.


        YAML Example::

            devices:
                asr22:
                    type: 'ASR'
                    tacacs:
                        login_prompt: "login:"******"Password:"******"admin"
                    passwords:
                        tacacs: admin
                        enable: admin
                        line: admin
                    connections:
                        a:
                            protocol: telnet
                            ip: "1.2.3.4"
                            port: 2004
                        vty:
                            protocol : telnet
                            ip : "2.3.4.5"
                        netconf:
                            class: yang.connector.Netconf
                            ip : "2.3.4.5"
                            port: 830
                            username: admin
                            password: admin

        Code Example::

            >>> from pyats.topology import loader
            >>> testbed = loader.load('/users/xxx/xxx/asr22.yaml')
            >>> device = testbed.devices['asr22']
            >>> device.connect(alias='nc', via='netconf')
            >>>

        Expected Results::

            >>> device.nc.connected
            True
            >>> for iter in device.nc.server_capabilities:
            ...     print(iter)
            ...
            urn:ietf:params:xml:ns:yang:smiv2:RFC-1215?module=RFC-1215
            urn:ietf:params:xml:ns:yang:smiv2:SNMPv2-TC?module=SNMPv2-TC
            ...
            >>>
        '''

        if self.connected:
            return

        logger.debug(self.session)
        if not self.session.is_alive():
            self._session = transport.SSHSession(self._device_handler)

        # default values
        defaults = {
            'host': None,
            'port': 830,
            'timeout': 30,
            'username': None,
            'password': None,
            'key_filename': None,
            'allow_agent': False,
            'hostkey_verify': False,
            'look_for_keys': False,
            'ssh_config': None,
            }
        defaults.update(self.connection_info)

        # remove items
        disregards = ['class', 'model', 'protocol',
                      'async_mode', 'raise_mode', 'credentials']
        defaults = {k: v for k, v in defaults.items() if k not in disregards}

        # rename ip -> host, cast to str type
        if 'ip' in defaults:
            defaults['host'] = str(defaults.pop('ip'))

        # rename user -> username
        if 'user' in defaults:
            defaults['username'] = str(defaults.pop('user'))

        # check credentials
        if self.connection_info.get('credentials'):
            try:
                defaults['username'] = str(self.connection_info['credentials']['netconf']['username'])
            except Exception:
                pass
            try:
                defaults['password'] = to_plaintext(self.connection_info['credentials']['netconf']['password'])
            except Exception:
                pass

        # support sshtunnel
        if 'sshtunnel' in defaults:
            from unicon.sshutils import sshtunnel
            try:
                tunnel_port = sshtunnel.auto_tunnel_add(self.device, self.via)
                if tunnel_port:
                    defaults['host'] = self.device.connections[self.via] \
                                           .sshtunnel.tunnel_ip
                    defaults['port'] = tunnel_port
            except AttributeError as err:
                raise AttributeError("Cannot add ssh tunnel. Connection %s may "
                                     "not have ip/host or port.\n%s" % (self.via, err))
            del defaults['sshtunnel']

        defaults = {k: getattr(self, k, v) for k, v in defaults.items()}

        try:
            self.session.connect(**defaults)
            logger.info(banner('NETCONF CONNECTED'))
        except Exception:
            if self.session.transport:
                self.session.close()
            raise

        @atexit.register
        def cleanup():
            if self.session.transport:
                self.session.close()