From 8cbf2dd47a2cd71e90348bd0de87fd00c3aa691fc8c1e60f4191b508c0fa08b3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mark=C3=A9ta=20Machov=C3=A1?= Date: Wed, 15 Jan 2025 12:49:55 +0000 Subject: [PATCH] - do not require six for build - added patches fix https://github.com/ncclient/ncclient/commit/59ccaac8e01e63f776fb4bf3b68a02e33d24bb20 + python-ncclient-no-python2.patch OBS-URL: https://build.opensuse.org/package/show/devel:languages:python/python-ncclient?expand=0&rev=19 --- .gitattributes | 23 + .gitignore | 1 + allow_old_sphinx.patch | 11 + intersphinx-mapping.patch | 25 + ncclient-0.6.15.tar.gz | 3 + ncclient-0.6.16.tar.gz | 3 + python-ncclient-no-python2.patch | 963 +++++++++++++++++++++++++++++++ python-ncclient.changes | 316 ++++++++++ python-ncclient.spec | 92 +++ 9 files changed, 1437 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 allow_old_sphinx.patch create mode 100644 intersphinx-mapping.patch create mode 100644 ncclient-0.6.15.tar.gz create mode 100644 ncclient-0.6.16.tar.gz create mode 100644 python-ncclient-no-python2.patch create mode 100644 python-ncclient.changes create mode 100644 python-ncclient.spec diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..9b03811 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,23 @@ +## Default LFS +*.7z filter=lfs diff=lfs merge=lfs -text +*.bsp filter=lfs diff=lfs merge=lfs -text +*.bz2 filter=lfs diff=lfs merge=lfs -text +*.gem filter=lfs diff=lfs merge=lfs -text +*.gz filter=lfs diff=lfs merge=lfs -text +*.jar filter=lfs diff=lfs merge=lfs -text +*.lz filter=lfs diff=lfs merge=lfs -text +*.lzma filter=lfs diff=lfs merge=lfs -text +*.obscpio filter=lfs diff=lfs merge=lfs -text +*.oxt filter=lfs diff=lfs merge=lfs -text +*.pdf filter=lfs diff=lfs merge=lfs -text +*.png filter=lfs diff=lfs merge=lfs -text +*.rpm filter=lfs diff=lfs merge=lfs -text +*.tbz filter=lfs diff=lfs merge=lfs -text +*.tbz2 filter=lfs diff=lfs merge=lfs -text +*.tgz filter=lfs diff=lfs merge=lfs -text +*.ttf filter=lfs diff=lfs merge=lfs -text +*.txz filter=lfs diff=lfs merge=lfs -text +*.whl filter=lfs diff=lfs merge=lfs -text +*.xz filter=lfs diff=lfs merge=lfs -text +*.zip filter=lfs diff=lfs merge=lfs -text +*.zst filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..57affb6 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.osc diff --git a/allow_old_sphinx.patch b/allow_old_sphinx.patch new file mode 100644 index 0000000..0dfe343 --- /dev/null +++ b/allow_old_sphinx.patch @@ -0,0 +1,11 @@ +--- a/docs/source/conf.py ++++ b/docs/source/conf.py +@@ -19,7 +19,7 @@ import sys, os + sys.path.insert(0, os.path.abspath("../..")) + + # -- General configuration ----------------------------------------------------- +-needs_sphinx = '2.0' ++# needs_sphinx = '2.0' + + # Add any Sphinx extension module names here, as strings. They can be extensions + # coming with Sphinx (named 'sphinx.ext.*') or your custom ones. diff --git a/intersphinx-mapping.patch b/intersphinx-mapping.patch new file mode 100644 index 0000000..3cf82c5 --- /dev/null +++ b/intersphinx-mapping.patch @@ -0,0 +1,25 @@ +--- + docs/source/conf.py | 6 +++++- + 1 file changed, 5 insertions(+), 1 deletion(-) + +--- a/docs/source/conf.py ++++ b/docs/source/conf.py +@@ -12,6 +12,7 @@ + # serve to show the default. + + import sys, os ++import sphinx + + # If extensions (or modules to document with autodoc) are in another directory, + # add these directories to sys.path here. If the directory is relative to the +@@ -196,6 +197,9 @@ latex_logo = "_static/logo.png" + + + # Example configuration for intersphinx: refer to the Python standard library. +-intersphinx_mapping = {'http://docs.python.org/': None} ++if sphinx.version_info[0] < 8: ++ intersphinx_mapping = {"http://docs.python.org/": None} ++else: ++ intersphinx_mapping = {'python': ('https://docs.python.org/', None)} + + autoclass_content = 'both' diff --git a/ncclient-0.6.15.tar.gz b/ncclient-0.6.15.tar.gz new file mode 100644 index 0000000..d83b9af --- /dev/null +++ b/ncclient-0.6.15.tar.gz @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:7bdf1c995426d7727a9224c3706ce5fe43ab77c20aaaccfca40427abdadcbfdc +size 140680 diff --git a/ncclient-0.6.16.tar.gz b/ncclient-0.6.16.tar.gz new file mode 100644 index 0000000..21546f0 --- /dev/null +++ b/ncclient-0.6.16.tar.gz @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:893b3d6dd9dfc76af0344e1e27ecaaad8ebc2b81f0c2d06f66984824108daf35 +size 142880 diff --git a/python-ncclient-no-python2.patch b/python-ncclient-no-python2.patch new file mode 100644 index 0000000..d14347a --- /dev/null +++ b/python-ncclient-no-python2.patch @@ -0,0 +1,963 @@ +diff --git a/examples/base/nc08.py b/examples/base/nc08.py +index 40eab7f2..df3deec4 100644 +--- a/examples/base/nc08.py ++++ b/examples/base/nc08.py +@@ -5,7 +5,7 @@ + # + # $ ./nc08.py Paulo Seguel + +-import sys, os, warnings ++import sys, warnings + warnings.simplefilter("ignore", DeprecationWarning) + import datetime + from ncclient import manager +diff --git a/examples/vendor/cisco/nxosapi.py b/examples/vendor/cisco/nxosapi.py +index c423163b..55cb58b1 100644 +--- a/examples/vendor/cisco/nxosapi.py ++++ b/examples/vendor/cisco/nxosapi.py +@@ -116,13 +116,13 @@ def enable_vlan(mgr, vlanid, vlanname): + def enable_vlan_on_trunk_int(mgr, interface, vlanid): + confstr = cmd_vlan_int_snippet % (interface, vlanid) + confstr = exec_conf_prefix + confstr + exec_conf_postfix +- print confstr ++ print(confstr) + mgr.edit_config(target='running', config=confstr) + + + def disable_vlan_on_trunk_int(mgr, interface, vlanid): + confstr = cmd_no_vlan_int_snippet % (interface, vlanid) +- print confstr ++ print(confstr) + mgr.edit_config(target='running', config=confstr) + + +diff --git a/ncclient/__init__.py b/ncclient/__init__.py +index 50e7991d..17de7dce 100644 +--- a/ncclient/__init__.py ++++ b/ncclient/__init__.py +@@ -16,8 +16,8 @@ + + import sys + +-if sys.version_info < (2, 7): +- raise RuntimeError('You need Python 2.7+ for this module.') ++if sys.version_info < (3, 5): ++ raise RuntimeError('You need Python 3.5+ for this module.') + + class NCClientError(Exception): + "Base type for all NCClient errors" +diff --git a/ncclient/capabilities.py b/ncclient/capabilities.py +index 5d6eabeb..14fe6dbd 100644 +--- a/ncclient/capabilities.py ++++ b/ncclient/capabilities.py +@@ -13,7 +13,6 @@ + # limitations under the License. + + import logging +-import six + + + logger = logging.getLogger("ncclient.capabilities") +@@ -39,7 +38,7 @@ def schemes(url_uri): + "Given a URI that has a *scheme* query string (i.e. `:url` capability URI), will return a list of supported schemes." + return url_uri.partition("?scheme=")[2].split(",") + +-class Capabilities(object): ++class Capabilities: + + "Represents the set of capabilities available to a NETCONF client or server. It is initialized with a list of capability URI's." + +@@ -60,7 +59,7 @@ def __getitem__(self, key): + try: + return self._dict[key] + except KeyError: +- for capability in six.itervalues(self._dict): ++ for capability in self._dict.values(): + if key in capability.get_abbreviations(): + return capability + +@@ -69,12 +68,11 @@ def __getitem__(self, key): + def __len__(self): + return len(self._dict) + +- # python 2 and 3 compatible + def __iter__(self): +- return six.iterkeys(self._dict) ++ return self._dict.keys() + + def __repr__(self): +- return repr(six.iterkeys(self._dict)) ++ return repr(self._dict.keys()) + + def add(self, uri): + "Add a capability." +@@ -86,7 +84,7 @@ def remove(self, uri): + del self._dict[uri] + + +-class Capability(object): ++class Capability: + + """Represents a single capability""" + +@@ -135,7 +133,7 @@ def _parse_parameter_string(string, uri): + ) + + +-class _Parameter(object): ++class _Parameter: + + """Represents a parameter to a capability""" + +diff --git a/ncclient/devices/default.py b/ncclient/devices/default.py +index 675859cb..acd68079 100644 +--- a/ncclient/devices/default.py ++++ b/ncclient/devices/default.py +@@ -25,12 +25,8 @@ + + from ncclient.transport.parser import DefaultXMLParser + +-import sys +-if sys.version >= '3': +- xrange = range + +- +-class DefaultDeviceHandler(object): ++class DefaultDeviceHandler: + """ + Default handler for device specific information. + +@@ -68,7 +64,7 @@ def __init__(self, device_params=None): + self._exempt_errors_startwith_wildcard_match = [] + self._exempt_errors_endwith_wildcard_match = [] + self._exempt_errors_full_wildcard_match = [] +- for i in xrange(len(self._EXEMPT_ERRORS)): ++ for i in range(len(self._EXEMPT_ERRORS)): + e = self._EXEMPT_ERRORS[i].lower() + if e.startswith("*"): + if e.endswith("*"): +diff --git a/ncclient/devices/junos.py b/ncclient/devices/junos.py +index d7515608..5d293e4d 100644 +--- a/ncclient/devices/junos.py ++++ b/ncclient/devices/junos.py +@@ -122,11 +122,7 @@ def transform_reply(self): + + + ''' +- import sys +- if sys.version < '3': +- return reply +- else: +- return reply.encode('UTF-8') ++ return reply.encode('UTF-8') + + def get_xml_parser(self, session): + # use_filter in device_params can be used to enabled using SAX parsing +diff --git a/ncclient/manager.py b/ncclient/manager.py +index 12fe7c0c..a0cc9758 100644 +--- a/ncclient/manager.py ++++ b/ncclient/manager.py +@@ -212,7 +212,7 @@ def call_home(*args, **kwds): + kwds['sock'] = sock + return connect_ssh(*args, **kwds) + +-class Manager(object): ++class Manager: + + """ + For details on the expected behavior of the operations and their +diff --git a/ncclient/operations/lock.py b/ncclient/operations/lock.py +index 06738847..87c1473f 100644 +--- a/ncclient/operations/lock.py ++++ b/ncclient/operations/lock.py +@@ -49,7 +49,7 @@ def request(self, target="candidate"): + return self._request(node) + + +-class LockContext(object): ++class LockContext: + + """A context manager for the :class:`Lock` / :class:`Unlock` pair of RPC's. + +diff --git a/ncclient/operations/rpc.py b/ncclient/operations/rpc.py +index 2511b6f3..fa6af9cc 100644 +--- a/ncclient/operations/rpc.py ++++ b/ncclient/operations/rpc.py +@@ -44,7 +44,7 @@ def __init__(self, raw, errs=None): + if errs is None: + # Single RPCError + self._errlist = None +- for attr in six.itervalues(RPCError.tag_to_attr): ++ for attr in RPCError.tag_to_attr.values(): + setattr(self, attr, None) + for subele in raw: + attr = RPCError.tag_to_attr.get(subele.tag, None) +@@ -79,7 +79,7 @@ def __init__(self, raw, errs=None): + OperationError.__init__(self, self.message) + + def to_dict(self): +- return dict([ (attr[1:], getattr(self, attr)) for attr in six.itervalues(RPCError.tag_to_attr) ]) ++ return dict([ (attr[1:], getattr(self, attr)) for attr in RPCError.tag_to_attr.values() ]) + + @property + def xml(self): +@@ -128,7 +128,7 @@ def errlist(self): + return self._errlist + + +-class RPCReply(object): ++class RPCReply: + + """Represents an *rpc-reply*. Only concerns itself with whether the operation was successful. + +@@ -173,8 +173,7 @@ def parse(self): + except Exception as e: + if self._parsing_error_transform is None: + # re-raise as we have no workaround +- exc_type, exc_value, exc_traceback = sys.exc_info() +- six.reraise(exc_type, exc_value, exc_traceback) ++ raise e + + # Apply device specific workaround and try again + self._parsing_error_transform(root) +@@ -263,13 +262,13 @@ def callback(self, root, raw): + + def errback(self, err): + try: +- for rpc in six.itervalues(self._id2rpc): ++ for rpc in self._id2rpc.values(): + rpc.deliver_error(err) + finally: + self._id2rpc.clear() + + +-class RaiseMode(object): ++class RaiseMode: + """ + Define how errors indicated by RPC should be handled. + +@@ -288,7 +287,7 @@ class RaiseMode(object): + "Don't look at the `error-type`, always raise." + + +-class RPC(object): ++class RPC: + + """Base class for all operations, directly corresponding to *rpc* requests. Handles making the request, and taking delivery of the reply.""" + +diff --git a/ncclient/transport/notify.py b/ncclient/transport/notify.py +index 85490312..1d240639 100644 +--- a/ncclient/transport/notify.py ++++ b/ncclient/transport/notify.py +@@ -14,7 +14,7 @@ + + from ncclient.xml_ import to_ele + +-class Notification(object): ++class Notification: + def __init__(self, raw): + self._raw = raw + self._root_ele = to_ele(raw) +diff --git a/ncclient/transport/parser.py b/ncclient/transport/parser.py +index cb5b071c..4b68ddc5 100644 +--- a/ncclient/transport/parser.py ++++ b/ncclient/transport/parser.py +@@ -22,6 +22,7 @@ + except ImportError: + import selectors2 as selectors + ++from io import BytesIO as StringIO + from xml.sax.handler import ContentHandler + + from ncclient.transport.errors import NetconfFramingError +@@ -33,11 +34,6 @@ + import logging + logger = logging.getLogger("ncclient.transport.parser") + +-if sys.version < '3': +- from six import StringIO +-else: +- from io import BytesIO as StringIO +- + + PORT_NETCONF_DEFAULT = 830 + PORT_SSH_DEFAULT = 22 +@@ -61,12 +57,8 @@ + # + RE_NC11_DELIM = re.compile(r'\n(?:#([0-9]+)|(##))\n') + +-if sys.version < '3': +- def textify(buf): +- return buf +-else: +- def textify(buf): +- return buf.decode('UTF-8') ++def textify(buf): ++ return buf.decode('UTF-8') + + + class SAXParserHandler(SessionListener): +@@ -90,7 +82,7 @@ def __str__(self): + return "SAX filter input xml not provided for listener: %s" % self._listener + + +-class DefaultXMLParser(object): ++class DefaultXMLParser: + + def __init__(self, session): + """ +@@ -131,10 +123,7 @@ def _parse10(self): + buf.seek(0) + msg, _, remaining = buf.read().decode('UTF-8').partition(MSG_DELIM) + msg = msg.strip() +- if sys.version < '3': +- self._session._dispatch_message(msg.encode()) +- else: +- self._session._dispatch_message(msg) ++ self._session._dispatch_message(msg) + self._session._buffer = StringIO() + self._parsing_pos10 = 0 + if len(remaining.strip()) > 0: +diff --git a/ncclient/transport/session.py b/ncclient/transport/session.py +index 5e933756..6ebe96e8 100644 +--- a/ncclient/transport/session.py ++++ b/ncclient/transport/session.py +@@ -16,10 +16,8 @@ + + import logging + from threading import Thread, Lock, Event +-try: +- from Queue import Queue, Empty +-except ImportError: +- from queue import Queue, Empty ++from queue import Queue, Empty ++ + try: + import selectors + except ImportError: +@@ -42,7 +40,7 @@ + TICK = 0.1 + + +-class NetconfBase(object): ++class NetconfBase: + '''Netconf Base protocol version''' + BASE_10 = 1 + BASE_11 = 2 +@@ -292,7 +290,7 @@ def id(self): + return self._id + + +-class SessionListener(object): ++class SessionListener: + + """Base class for :class:`Session` listeners, which are notified when a new + NETCONF message is received or an error occurs. +@@ -349,11 +347,7 @@ def build(capabilities, device_handler): + hello = new_ele("hello", **xml_namespace_kwargs) + caps = sub_ele(hello, "capabilities") + def fun(uri): sub_ele(caps, "capability").text = uri +- #python3 changes +- if sys.version < '3': +- map(fun, capabilities) +- else: +- list(map(fun, capabilities)) ++ list(map(fun, capabilities)) + return to_xml(hello) + + @staticmethod +diff --git a/ncclient/transport/ssh.py b/ncclient/transport/ssh.py +index d1796807..79e9ba66 100644 +--- a/ncclient/transport/ssh.py ++++ b/ncclient/transport/ssh.py +@@ -17,11 +17,11 @@ + import getpass + import os + import re +-import six + import sys + import socket + import threading + from binascii import hexlify ++from io import BytesIO as StringIO + + try: + import selectors +@@ -77,12 +77,6 @@ def _colonify(fp): + return finga + + +-if sys.version < '3': +- from six import StringIO +-else: +- from io import BytesIO as StringIO +- +- + class SSHSession(Session): + + "Implements a :rfc:`4742` NETCONF session over SSH." +@@ -263,7 +257,7 @@ def connect( + proxycommand = config.get("proxycommand") + if proxycommand: + self.logger.debug("Configuring Proxy. %s", proxycommand) +- if not isinstance(proxycommand, six.string_types): ++ if not isinstance(proxycommand, str): + proxycommand = [os.path.expanduser(elem) for elem in proxycommand] + else: + proxycommand = os.path.expanduser(proxycommand) +@@ -287,11 +281,7 @@ def connect( + else: + raise SSHError("Could not open socket to %s:%s" % (host, port)) + elif sock is None: +- if sys.version_info[0] < 3: +- s = socket.fromfd(int(sock_fd), socket.AF_INET, socket.SOCK_STREAM) +- sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM, _sock=s) +- else: +- sock = socket.fromfd(int(sock_fd), socket.AF_INET, socket.SOCK_STREAM) ++ sock = socket.fromfd(int(sock_fd), socket.AF_INET, socket.SOCK_STREAM) + sock.settimeout(timeout) + + self._transport = paramiko.Transport(sock) +diff --git a/ncclient/transport/third_party/junos/ioproc.py b/ncclient/transport/third_party/junos/ioproc.py +index e1e63afd..60f83ff4 100644 +--- a/ncclient/transport/third_party/junos/ioproc.py ++++ b/ncclient/transport/third_party/junos/ioproc.py +@@ -1,20 +1,12 @@ + import sys + import re +-import six +- +-if sys.version < '3': +- from cStringIO import StringIO +-else: +- from io import BytesIO as StringIO +-if sys.version>='2.7': +- from subprocess import Popen, check_output, PIPE, STDOUT +-else: +- from subprocess import Popen, PIPE, STDOUT ++from io import BytesIO as StringIO ++from subprocess import Popen, check_output, PIPE, STDOUT + + from ncclient.transport.errors import SessionCloseError, TransportError, PermissionError + from ncclient.transport.ssh import SSHSession + +-MSG_DELIM = six.b("]]>]]>") ++MSG_DELIM = b"]]>]]>" + NETCONF_SHELL = 'netconf' + + +diff --git a/ncclient/transport/tls.py b/ncclient/transport/tls.py +index b7443f9c..27298098 100644 +--- a/ncclient/transport/tls.py ++++ b/ncclient/transport/tls.py +@@ -17,14 +17,10 @@ + import sys + import threading + ++from io import BytesIO as StringIO + from socket import AF_INET, SOCK_STREAM + from ssl import CERT_REQUIRED, SSLContext, SSLError + +-if sys.version < '3': +- from six import StringIO +-else: +- from io import BytesIO as StringIO +- + from ncclient.capabilities import Capabilities + from ncclient.logging_ import SessionLoggerAdapter + from ncclient.transport.errors import TLSError +diff --git a/ncclient/xml_.py b/ncclient/xml_.py +index 8f58b35a..f46ec025 100644 +--- a/ncclient/xml_.py ++++ b/ncclient/xml_.py +@@ -17,11 +17,9 @@ + + + import io +-import sys +-import six + import types +-from six import StringIO +-from io import BytesIO ++from io import BytesIO, StringIO ++ + from lxml import etree + + # In case issues come up with XML generation/parsing +@@ -91,7 +89,7 @@ def register_namespace(prefix, uri): + # cElementTree uses ElementTree's _namespace_map, so that's ok + ElementTree._namespace_map[uri] = prefix + +-for (ns, pre) in six.iteritems({ ++for (ns, pre) in { + BASE_NS_1_0: 'nc', + NETCONF_MONITORING_NS: 'ncm', + NXOS_1_0: 'nxos', +@@ -101,7 +99,7 @@ def register_namespace(prefix, uri): + CISCO_CPI_1_0: 'cpi', + FLOWMON_1_0: 'fm', + JUNIPER_1_1: 'junos', +-}): ++}.items(): + register_namespace(pre, ns) + + qualify = lambda tag, ns=BASE_NS_1_0: tag if ns is None else "{%s}%s" % (ns, tag) +@@ -111,11 +109,8 @@ def register_namespace(prefix, uri): + def to_xml(ele, encoding="UTF-8", pretty_print=False): + "Convert and return the XML for an *ele* (:class:`~xml.etree.ElementTree.Element`) with specified *encoding*." + xml = etree.tostring(ele, encoding=encoding, pretty_print=pretty_print) +- if sys.version < '3': +- return xml if xml.startswith('%s' % (encoding, xml) +- else: +- return xml.decode('UTF-8') if xml.startswith(b'%s' % (encoding, xml.decode('UTF-8')) ++ return xml.decode('UTF-8') if xml.startswith(b'%s' % (encoding, xml.decode('UTF-8')) + + + def to_ele(x, huge_tree=False): +@@ -123,18 +118,12 @@ def to_ele(x, huge_tree=False): + + *huge_tree*: parse XML with very deep trees and very long text content + """ +- if sys.version < '3': +- return x if etree.iselement(x) else etree.fromstring(x, parser=_get_parser(huge_tree)) +- else: +- return x if etree.iselement(x) else etree.fromstring(x.encode('UTF-8'), parser=_get_parser(huge_tree)) ++ return x if etree.iselement(x) else etree.fromstring(x.encode('UTF-8'), parser=_get_parser(huge_tree)) + + + def parse_root(raw): + "Efficiently parses the root element of a *raw* XML document, returning a tuple of its qualified name and attribute dictionary." +- if sys.version < '3': +- fp = StringIO(raw) +- else: +- fp = BytesIO(raw.encode('UTF-8')) ++ fp = BytesIO(raw.encode('UTF-8')) + for event, element in etree.iterparse(fp, events=('start',)): + return (element.tag, element.attrib) + +@@ -168,7 +157,7 @@ def validated_element(x, tags=None, attrs=None): + } + + +-class NCElement(object): ++class NCElement: + def __init__(self, result, transform_reply, huge_tree=False): + self.__result = result + self.__transform_reply = transform_reply +@@ -213,10 +202,7 @@ def findall(self, expression): + + def __str__(self): + """syntactic sugar for str() - alias to tostring""" +- if sys.version < '3': +- return self.tostring +- else: +- return self.tostring.decode('UTF-8') ++ return self.tostring.decode('UTF-8') + + @property + def tostring(self): +diff --git a/requirements.txt b/requirements.txt +index 64cf505d..3363b16e 100644 +--- a/requirements.txt ++++ b/requirements.txt +@@ -1,5 +1,3 @@ + setuptools>0.6 + paramiko>=1.15.0 + lxml>=3.3.0 +-selectors2>=2.0.1; python_version <= '3.4' +-six +diff --git a/setup.py b/setup.py +index 68e00412..32ad3b91 100644 +--- a/setup.py ++++ b/setup.py +@@ -18,7 +18,6 @@ + from distutils.command.install import install as _install + + import sys +-import platform + import codecs + import versioneer + +@@ -26,8 +25,8 @@ + __author_email__ = "shikhar@schmizz.net, lpoulopoulos@verisign.com, exa@dscp.org, einarnn@gmail.com" + __licence__ = "Apache 2.0" + +-if sys.version_info.major == 2 and sys.version_info.minor < 7: +- print ("Sorry, Python < 2.7 is not supported") ++if sys.version_info.major == 2 or sys.version_info.minor < 5: ++ print ("Sorry, Python < 3.5 is not supported") + exit() + + #parse requirements +@@ -55,10 +54,9 @@ + license=__licence__, + platforms=["Posix; OS X; Windows"], + keywords=['NETCONF', 'NETCONF Python client', 'Juniper Optimization', 'Cisco NXOS Optimization'], +- python_requires='>=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*', ++ python_requires='>=3.5', + classifiers=[ + 'Development Status :: 5 - Production/Stable', +- 'Programming Language :: Python :: 2.7', + 'Programming Language :: Python :: 3.5', + 'Programming Language :: Python :: 3.6', + 'Programming Language :: Python :: 3.7', +diff --git a/test/unit/devices/test_junos.py b/test/unit/devices/test_junos.py +index 97ac9ccf..50bc6d42 100644 +--- a/test/unit/devices/test_junos.py ++++ b/test/unit/devices/test_junos.py +@@ -1,12 +1,10 @@ + import unittest ++from unittest.mock import patch ++ ++import paramiko ++ + from ncclient.devices.junos import * + import ncclient.transport +-try: +- from unittest.mock import patch # Python 3.4 and later +-except ImportError: +- from mock import patch +-import paramiko +-import sys + + xml = ''' + +@@ -93,10 +91,7 @@ def test_additional_operations(self): + self.assertEqual(dict, self.obj.add_additional_operations()) + + def test_transform_reply(self): +- if sys.version >= '3': +- reply = xml.encode('utf-8') +- else: +- reply = xml ++ reply = xml.encode('utf-8') + self.assertEqual(self.obj.transform_reply(), reply) + + def test_perform_quality_check(self): +diff --git a/test/unit/operations/test_retrieve.py b/test/unit/operations/test_retrieve.py +index 21fa3092..d1b51104 100644 +--- a/test/unit/operations/test_retrieve.py ++++ b/test/unit/operations/test_retrieve.py +@@ -1,9 +1,11 @@ +-from ncclient.operations.retrieve import * ++import copy + import unittest +-try: +- from unittest.mock import patch # Python 3.4 and later +-except ImportError: +- from mock import patch ++from unittest.mock import patch ++ ++from xml.etree import ElementTree ++from lxml import etree ++ ++from ncclient.operations.retrieve import * + from ncclient import manager + import ncclient.manager + import ncclient.transport +@@ -11,10 +13,6 @@ + from ncclient.xml_ import * + from ncclient.operations import RaiseMode + from ncclient.operations.errors import MissingCapabilityError +-from xml.etree import ElementTree +-from lxml import etree +-import copy +-import six + + + class TestRetrieve(unittest.TestCase): +@@ -96,8 +94,7 @@ def test_get_with_defaults_not_supported(self, mock_request): + "Invalid 'with-defaults' mode 'report-all-tagged'; the server " + "only supports the following: explicit, report-all, trim" + ) +- six.assertRaisesRegex( +- self, ++ self.assertRaisesRegex( + WithDefaultsError, + expected_error, + obj.request, +diff --git a/test/unit/operations/test_rpc.py b/test/unit/operations/test_rpc.py +index 8d60700d..47767b0e 100644 +--- a/test/unit/operations/test_rpc.py ++++ b/test/unit/operations/test_rpc.py +@@ -1,9 +1,7 @@ +-from ncclient.operations.rpc import * + import unittest +-try: +- from unittest.mock import patch # Python 3.4 and later +-except ImportError: +- from mock import patch ++from unittest.mock import patch ++ ++from ncclient.operations.rpc import * + from ncclient import manager + import ncclient.manager + import ncclient.transport +@@ -11,12 +9,8 @@ + from ncclient.operations import RaiseMode + from ncclient.capabilities import Capabilities + from xml.sax.saxutils import escape +-import sys + +-if sys.version >= '3': +- patch_str = 'ncclient.operations.rpc.Event.is_set' +-else: +- patch_str = 'threading._Event.is_set' ++patch_str = 'ncclient.operations.rpc.Event.is_set' + + xml1 = """ + +diff --git a/test/unit/test_xml_.py b/test/unit/test_xml_.py +index 9e8c55a6..28d10113 100644 +--- a/test/unit/test_xml_.py ++++ b/test/unit/test_xml_.py +@@ -1,8 +1,9 @@ +-from ncclient import manager +-from ncclient.xml_ import * + import unittest + import os + import sys ++ ++from ncclient import manager ++from ncclient.xml_ import * + file_path = os.path.join(os.getcwd(), "test", "unit", "reply1") + + +@@ -18,8 +19,7 @@ def test_ncelement_reply_001(self): + transform_reply = device_handler.transform_reply() + result = NCElement(reply, transform_reply) + result_str = result.tostring +- if sys.version >= '3': +- result_str = result_str.decode('UTF-8') ++ result_str = result_str.decode('UTF-8') + self.assertEqual(str(result), result_str) + #data_xml != tostring + self.assertNotEqual(result_str, result.data_xml) +diff --git a/test/unit/transport/test_parser.py b/test/unit/transport/test_parser.py +index d06d2cb9..abe4a3d9 100644 +--- a/test/unit/transport/test_parser.py ++++ b/test/unit/transport/test_parser.py +@@ -1,10 +1,7 @@ + import os +- + import unittest +-try: +- from unittest.mock import patch # Python 3.4 and later +-except ImportError: +- from mock import patch ++from unittest.mock import patch ++ + import paramiko + + from ncclient import manager +@@ -21,7 +18,6 @@ + + class TestSession(unittest.TestCase): + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +@@ -50,7 +46,6 @@ def test_filter_xml_sax_on(self, mock_uuid4, mock_select, mock_session, mock_rec + # as filter_xml is not having software-information, response wont contain it + self.assertEqual(len(resp.xpath('multi-routing-engine-item/software-information')), 0) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +@@ -81,7 +76,6 @@ def test_filter_xml_sax_on_junos_rfc_compliant(self, mock_uuid4, mock_select, mo + # as filter_xml is not having software-information, response wont contain it + self.assertEqual(len(resp.xpath('multi-routing-engine-item/software-information')), 0) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +@@ -111,7 +105,6 @@ def test_filter_xml_delimiter_rpc_reply(self, mock_uuid4, mock_select, + self.assertEqual(len(resp.xpath('multi-routing-engine-item/re-name')), 2) + self.assertEqual(len(resp.xpath('multi-routing-engine-item/software-information')), 0) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +@@ -143,7 +136,6 @@ def test_filter_xml_delimiter_multiple_rpc_reply(self, mock_uuid4, mock_select, + self.assertEqual(len(resp.xpath('multi-routing-engine-item/re-name')), 2) + self.assertEqual(len(resp.xpath('multi-routing-engine-item/software-information')), 0) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +@@ -229,7 +221,6 @@ def test_filter_xml_delimiter_multiple_rpc_in_parallel(self, mock_uuid4, mock_se + resp = obj.request(rpc)._NCElement__doc[0] + self.assertEqual(len(resp.xpath('pfe-traffic-statistics')), 1) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +@@ -261,7 +252,6 @@ def test_filter_xml_delimiter_splited_rpc_reply(self, mock_uuid4, mock_select, + self.assertEqual(len(resp.xpath('multi-routing-engine-item/re-name')), 2) + self.assertEqual(len(resp.xpath('multi-routing-engine-item/software-information')), 0) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +@@ -292,7 +282,6 @@ def test_use_filter_xml_without_sax_input(self, mock_uuid4, mock_select, + self.assertEqual(len(resp.xpath('multi-routing-engine-item/re-name')), 2) + self.assertEqual(len(resp.xpath('multi-routing-engine-item/software-information')), 2) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.SSHSession.connected') + @patch('paramiko.channel.Channel.send_ready') + @patch('paramiko.channel.Channel.send') +diff --git a/test/unit/transport/test_ssh.py b/test/unit/transport/test_ssh.py +index 73a82be5..4d66130f 100644 +--- a/test/unit/transport/test_ssh.py ++++ b/test/unit/transport/test_ssh.py +@@ -1,14 +1,11 @@ + # -*- coding: utf-8 -*- + import unittest +-try: +- from unittest.mock import MagicMock, patch, call # Python 3.4 and later +-except ImportError: +- from mock import MagicMock, patch, call ++from unittest.mock import MagicMock, patch, call ++ + from ncclient.transport.ssh import SSHSession + from ncclient.transport import AuthenticationError, SessionCloseError, NetconfBase + import paramiko + from ncclient.devices.junos import JunosDeviceHandler +-import sys + + try: + import selectors +@@ -79,12 +76,8 @@ def _test_parsemethod(self, mock_dispatch, parsemethod, reply, ok_chunk, + expected_messages): + device_handler = JunosDeviceHandler({'name': 'junos'}) + obj = SSHSession(device_handler) +- if sys.version >= "3.0": +- obj._buffer.write(bytes(reply, "utf-8")) +- remainder = bytes(ok_chunk, "utf-8") +- else: +- obj._buffer.write(reply) +- remainder = ok_chunk ++ obj._buffer.write(bytes(reply, "utf-8")) ++ remainder = bytes(ok_chunk, "utf-8") + parsemethod(obj) + + for i in range(0, len(expected_messages)): +@@ -102,12 +95,8 @@ def test_parse(self, mock_dispatch): + def test_parse11(self, mock_dispatch): + device_handler = JunosDeviceHandler({'name': 'junos'}) + obj = SSHSession(device_handler) +- if sys.version >= "3.0": +- obj._buffer.write(bytes(rpc_reply11, "utf-8")) +- remainder = bytes(reply_ok_partial_chunk, "utf-8") +- else: +- obj._buffer.write(rpc_reply11) +- remainder = reply_ok_partial_chunk ++ obj._buffer.write(bytes(rpc_reply11, "utf-8")) ++ remainder = bytes(reply_ok_partial_chunk, "utf-8") + obj.parser._parse11() + + expected_messages = [reply_data, reply_ok] +@@ -121,22 +110,14 @@ def test_parse11(self, mock_dispatch): + def test_parse_incomplete_delimiter(self, mock_dispatch): + device_handler = JunosDeviceHandler({'name': 'junos'}) + obj = SSHSession(device_handler) +- if sys.version >= "3.0": +- b = bytes(rpc_reply_part_1, "utf-8") +- obj._buffer.write(b) +- obj._parse() +- self.assertFalse(mock_dispatch.called) +- b = bytes(rpc_reply_part_2, "utf-8") +- obj._buffer.write(b) +- obj._parse() +- self.assertTrue(mock_dispatch.called) +- else: +- obj._buffer.write(rpc_reply_part_1) +- obj._parse() +- self.assertFalse(mock_dispatch.called) +- obj._buffer.write(rpc_reply_part_2) +- obj._parse() +- self.assertTrue(mock_dispatch.called) ++ b = bytes(rpc_reply_part_1, "utf-8") ++ obj._buffer.write(b) ++ obj._parse() ++ self.assertFalse(mock_dispatch.called) ++ b = bytes(rpc_reply_part_2, "utf-8") ++ obj._buffer.write(b) ++ obj._parse() ++ self.assertTrue(mock_dispatch.called) + + @patch('paramiko.transport.Transport.auth_publickey') + @patch('paramiko.agent.AgentSSH.get_keys') +@@ -321,7 +302,6 @@ def test_ssh_known_hosts_2(self, mock_auth, mock_pc, + hk_inst.load.assert_called_once_with('file_name') + mock_os.mock_calls == [call('~/.ssh/config'), call('known_hosts_file')] + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + @patch('ncclient.transport.ssh.SSHSession.close') + @patch('paramiko.channel.Channel.recv') + @patch('selectors.DefaultSelector.select') +@@ -338,12 +318,10 @@ def test_run_receive_py3(self, mock_error, mock_selector, mock_recv, mock_close) + mock_error.call_args_list[0][0][0], + SessionCloseError)) + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + def test_run_send_py3_10(self): + self._test_run_send_py3(NetconfBase.BASE_10, + lambda msg: msg.encode() + b"]]>]]>") + +- @unittest.skipIf(sys.version_info.major == 2, "test not supported < Python3") + def test_run_send_py3_11(self): + def chunker(msg): + encmsg = msg.encode() +@@ -374,23 +352,6 @@ def _test_run_send_py3(self, base, chunker, mock_error, mock_selector, + mock_error.call_args_list[0][0][0], + SessionCloseError)) + +- @unittest.skipIf(sys.version_info.major >= 3, "test not supported >= Python3") +- @patch('ncclient.transport.ssh.SSHSession.close') +- @patch('paramiko.channel.Channel.recv') +- @patch('selectors2.DefaultSelector') +- @patch('ncclient.transport.ssh.Session._dispatch_error') +- def test_run_receive_py2(self, mock_error, mock_selector, mock_recv, mock_close): +- mock_selector.select.return_value = True +- mock_recv.return_value = 0 +- device_handler = JunosDeviceHandler({'name': 'junos'}) +- obj = SSHSession(device_handler) +- obj._channel = paramiko.Channel("c100") +- obj.run() +- self.assertTrue( +- isinstance( +- mock_error.call_args_list[0][0][0], +- SessionCloseError)) +- + @unittest.skip("test currently non-functional") + @patch('ncclient.transport.ssh.SSHSession.close') + @patch('paramiko.channel.Channel.send_ready') +diff --git a/test/unit/transport/test_tls.py b/test/unit/transport/test_tls.py +index e1530171..d6bdb4ca 100644 +--- a/test/unit/transport/test_tls.py ++++ b/test/unit/transport/test_tls.py +@@ -16,11 +16,7 @@ + import sys + import unittest + import socket +- +-try: +- from unittest.mock import MagicMock, patch, call +-except ImportError: +- from mock import MagicMock, patch, call ++from unittest.mock import MagicMock, patch, call + + try: + from ssl import PROTOCOL_TLS_CLIENT + diff --git a/python-ncclient.changes b/python-ncclient.changes new file mode 100644 index 0000000..3a1b79e --- /dev/null +++ b/python-ncclient.changes @@ -0,0 +1,316 @@ +------------------------------------------------------------------- +Tue Jan 14 14:54:22 UTC 2025 - pgajdos@suse.com + +- do not require six for build +- added patches + fix https://github.com/ncclient/ncclient/commit/59ccaac8e01e63f776fb4bf3b68a02e33d24bb20 + + python-ncclient-no-python2.patch + +------------------------------------------------------------------- +Sun Nov 10 19:50:09 UTC 2024 - Martin Hauke + +- Update to version 0.6.16 + * Add Ciena driver. + * Update session.py. + * call_home: timeout as argument. + * Introduce Unix Socket Transport. + * feat: Add support for Nokia SR OS private candidate mode. + * Fix support of .ssh/id_ed25519 keys. + +------------------------------------------------------------------- +Fri Oct 25 22:17:02 UTC 2024 - Matej Cepl + +- Add intersphinx-mapping.patch to allow working with Sphinx >= + 8.* (gh#ncclient/ncclient#604). + +------------------------------------------------------------------- +Wed Feb 28 04:55:02 UTC 2024 - Steve Kowalik + +- Switch to %patch macro. + +------------------------------------------------------------------- +Thu Dec 7 22:36:06 UTC 2023 - Dirk Müller + +- update to 0.6.15: + * reading correct user known_hosts files + * fix coveralls reporting + * Agent key selection + * Update session.py - Parameterize timeout for _post_connect + * update comment in _parse11 + * Fix missing timeout in ssh post_connect + * Migrate from nose to pytest + * Based on v0 6 13 fix for deprecation warnings threading + thread + * Introduce support for TLS + * remove - version of setting and replace with _ version + * permissive UTF-8 parsing for NC11 delimiter + * introduce python3.12 for ci + * Add commit comment capability support for SROS devices in + ncclient + +------------------------------------------------------------------- +Sun Jun 19 17:40:24 UTC 2022 - Dirk Müller + +- update to 0.6.13: + * Remove extraneous capability in default device + * Refactor deprecated unittest aliases for Python 3.11 compatibility + * Added support for environment variable + * Migrate from Travis to GitHub Actions + * Update Build Pill + * add netconf base namespace to edit-config config element if it is missing + +------------------------------------------------------------------- +Thu Mar 24 12:10:35 UTC 2022 - pgajdos@suse.com + +- python-mock is not required for build + +------------------------------------------------------------------- +Fri Jan 14 17:35:29 UTC 2022 - Ben Greiner + +- Specfile fix: + * Remove the Python 3.4 conditional. It the _nodots macro is not + known to the obs resolver. + * Also remove python2 lines for cleanup, not resolvable in 15.3 + in either case. + +------------------------------------------------------------------- +Tue Jan 11 20:42:01 UTC 2022 - Ben Greiner + +- python-selectors2 is only required for python <= 3.4 + +------------------------------------------------------------------- +Thu Oct 7 01:52:08 UTC 2021 - Steve Kowalik + +- Remove unneeded BuildRequires on nose. + +------------------------------------------------------------------- +Sat Jun 5 12:58:01 UTC 2021 - Martin Hauke + +- Update to version 0.6.12 + * Fix for unintentional breakage of JunOS ExecuteRPC +- Update to version 0.6.11 + * Support for custom client capabilities + * Restructuring/refactoring of example scripts + * Minor bugfixes + * Minor unit test refactoring +- Update to version 0.6.10 + * NETCONF call-home (RFC8071) support + * YANG 1.1 action support + * Nokia SR OS device handler support + * Removal of old ALU base-r13 API documentation + * Increased test coverage + * Variety of bugfixes and minor enhancements + +------------------------------------------------------------------- +Thu Jan 28 21:19:07 UTC 2021 - Matej Cepl + +- Add allow_old_sphinx.patch allowing building of documentation + on Leap 15 (bsc#1181270). + +------------------------------------------------------------------- +Sun Aug 9 14:03:46 UTC 2020 - Martin Hauke + +- Update to version 0.6.9 + * Fix for breaking API change +- Update to version 0.6.8 + * Support for namespace prefixes for XPath queries + * edit-config parameter validation + * Support for multiple RPC errors + * API to get supported device types + * Support for subtree filters with multiple top-level tags + +------------------------------------------------------------------- +Sat Dec 21 20:09:12 UTC 2019 - Martin Hauke + +- Update to version 0.6.7 + * Bugfix release + +------------------------------------------------------------------- +Wed Dec 4 21:46:22 UTC 2019 - Martin Hauke + +- Update to version 0.6.6: + * Read ssh timeout from config file if not specified in method + call + * Tox support + * Huge XML tree parser support + * Adding optional bind address to connect +- Update to version 0.6.5 + * Pin selectors2 to Python versions <= 3.4 + * Fix config examples to actually use the nc namespace + * fix: correctly set port for paramiko when using ssh_config file + * test: add test to check ProxyCommand uses correct port + * Update commits for py3 + * Enhance Alcatel-Lucent -support + * Juniper RPC: allow specifying format in CompareConfiguration + * Parsing of NETCONF 1.1 frames no longer decodes each chunk of + bytes... + * Fix filter in create_subscription + * Validate 'with-defaults' mode based on supported modes + advertised in capability URI +- Remove patch: + * sphinx-use-imgmath-extension.patch (fixed by upstream) +- Use tarball from github +- Run testsuite +- Drop not needed dependencies +- Minor fixes to make the rpm post-build-checks happy + +------------------------------------------------------------------- +Wed Apr 10 06:59:10 UTC 2019 - Dirk Mueller + +- update to v0.6.4: + * Use os.path.expanduser() on paths read from ssh_config. + * Proxycommand can be a list. Identityfile already performs ~ expansion in + * Enhance Alcatel-Lucent -support +- add sphinx-use-imgmath-extension.patch + +------------------------------------------------------------------- +Wed Mar 20 09:16:40 UTC 2019 - Thomas Bechtold + +- update to version v0.6.3 + * Housekeeping & Cleaning + * Log sent and received messages at level INFO. Fixes #167 + * - move known_hosts_lookup (the host entry in known_hosts, with optional port number appended) + * First draft of versioning with versioneer (#269) + * revert to raising SSHError + * fix: add missing placeholder in exception string + * Updates to re-enable Python 3.7 (#249) + * Updates for 0.5.4 and 0.6.0 + * SSH Host key checking (#280) + * check for transform_reply type (#270) + * Change superclass call style to keep tests happy + * SSH Host key checking + * Fix homepage link registered with PyPi (#274) + * more tests + * invoke self.parse() to ensure errors, if any, have been detetcted before check in ok() (#286) + * Avoid spurious SessionCloseError when intentionally closing session. (#268) + * Minor edits + * Revert "Fixes to unit tests to account for use of selectors" + * Close the channel when closing SSH session + * Revert "fixes to tests for python2.7" + * add Huawei device support through YANG (#1) (#242) + * Revert "use selectors instead of select; improve performance of base 1.0 or 1.1 selection" + * instructions for running unit tests locally + * updated README.md in preparation for 0.6.1 release + * netconf:base:1.1 parsing improvements (#267) + * Add session as extra context to session-related logs + * Include host in log message as well, as session-id is not globally unique + * fix: comments & whitespace tidy + * removed Manager class metaclass and modified operation lookup to __getattr__ (#200) + * Add support for loading host-specific known_hosts files via UserKnownHostsFile. (#255) + * Typo in log message + * selector changes (#260) + * use selectors instead of select; improve performance of base 1.0 or 1.1 selection + * Updated junos.py to resolve RestrictedUser error: (#283) + * change hostkey var name to be explicit on type hostkey_b64 + * Fixes to unit tests to account for use of selectors + * fixes to tests for python2.7 + * remove breaking test for incorrect host key padding + * check known_hosts only if hostkey_b64 not specified + * include selectors2 in requirements + * remove unused import + * Revert "include selectors2 in requirements" +- Drop pr-109.patch + +------------------------------------------------------------------- +Sat Sep 8 11:21:16 UTC 2018 - dmueller@suse.com + +- Update to 0.5.4 + * Python 3.6 support + +------------------------------------------------------------------- +Mon Aug 7 08:36:21 UTC 2017 - mardnh@gmx.de + +- Update to 0.5.3 + * Add notifications support + * Add support for ecdsa keys + * Various bug fixes +- Convert to singlespec +- Rebase patch: pr-109.patch + +------------------------------------------------------------------- +Sat Sep 3 20:52:24 UTC 2016 - mardnh@gmx.de + +- update to 0.5.2: + * Add support for Python 3 + * Improve Junos ioproc performance + * Performance improvements + * Updated test cases + * Many bug and performance fixes +- fix source-url +- rebase patch: pr-109.patch + +------------------------------------------------------------------- +Fri Feb 5 10:00:39 UTC 2016 - tbechtold@suse.com + +- switch to version from pypi + This is the version used by OpenStack networking-cisco +- update to 0.4.7: + * Add support for netconf 1.1 + * Fix multiple RPC error handling + * Add support for cancel-commit and persist param + * Add more examples + * Add Huawei device support + * Add cli command support for hpcomware v7 devices + * Add H3C support, Support H3C CLI,Action,Get_bulk,Save,Rollback,etc. + * Add alcatel lucent support + * Rewrite multiple error handling + * Add coveralls support, with shield in README.md + * Set severity level to higher when multiple + * Simplify logging and multi-error reporting + * Keep stacktrace of errors + * Check for known hosts on hostkey_verify only + * Add check for device sending back null error_text + * Fix RPC.raise_mode + * Specifying hostkey_verify=False should not load_known_hosts + * Check the correct field on rpc-error element + * Nexus exec_command operation + * Allow specifying multiple cmd elements in Cisco Nexus + * Update rpc for nested rpc-errors + * Prevent race condition in threading + * Prevent hanging in session close + * Support for paramiko ProxyCommand via ~/.ssh/config parsing + * Add Juniper-specific commit operations + * Add Huawei devices support + * Tests/Travis support + * ioproc transport support for Juniper devices + * Update Cisco CSR device handler + * Fix issue with locked method missing device handler + * Fix for namespace definition with lxml + * Add missing SessionError exception + * Update docs for Nexus device handler + * Docstring fixes + * Typos + * Minor bugfixes + * Add an example for Cisco CSR1000v +- Remove nexus-support.patch . Applied upstream. +- Adjust Requires according to requirements.txt +- Split documentation into extra -doc package +- Add pr-109.patch . This lowers the lxml requirement so this + package works with SLE12. +- Stop using openstack-suse-macros for now. This fixes the build + for openSUSE 13.2 and SLE11SP3 + +------------------------------------------------------------------- +Wed Jul 29 10:26:26 UTC 2015 - tbechtold@suse.com + +- Unify spec file. Use fedora compatible files macros + +------------------------------------------------------------------- +Mon Aug 26 14:59:37 UTC 2013 - rhafer@suse.com + +- added nexus-support.patch: this is required to make make ncclient + capable of accessing cisco nexus switches (for quantum's nexus + plugin) + +------------------------------------------------------------------- +Thu Aug 8 14:50:07 UTC 2013 - dmueller@suse.com + +- (rpm-wise) downgrade to a released version 0.3.2: + * http://ncclient.grnet.gr/0.3.2/ + +------------------------------------------------------------------- +Mon Jul 29 08:08:56 UTC 2013 - speilicke@suse.com + +- Require python-paramiko (for ssh transport) +- Build HTML documentation + diff --git a/python-ncclient.spec b/python-ncclient.spec new file mode 100644 index 0000000..baa0912 --- /dev/null +++ b/python-ncclient.spec @@ -0,0 +1,92 @@ +# +# spec file for package python-ncclient +# +# Copyright (c) 2025 SUSE LLC +# +# All modifications and additions to the file contributed by third parties +# remain the property of their copyright owners, unless otherwise agreed +# upon. The license for this file, and modifications and additions to the +# file, is the same license as for the pristine package itself (unless the +# license for the pristine package is not an Open Source License, in which +# case the license is the MIT License). An "Open Source License" is a +# license that conforms to the Open Source Definition (Version 1.9) +# published by the Open Source Initiative. + +# Please submit bugfixes or comments via https://bugs.opensuse.org/ +# + + +Name: python-ncclient +Version: 0.6.16 +Release: 0 +Summary: Python library for NETCONF clients +License: Apache-2.0 +URL: https://ncclient.readthedocs.io/en/latest/ +Source: https://github.com/ncclient/ncclient/archive/v%{version}.tar.gz#/ncclient-%{version}.tar.gz +# PATCH-FIX-OPENSUSE allow_old_sphinx.patch mcepl@suse.com +# Allow build with old Sphinx (< 2.0) on Leap +Patch0: allow_old_sphinx.patch +# PATCH-FIX-UPSTREAM intersphinx-mapping.patch gh#ncclient/ncclient#604 mcepl@suse.com +# use conditionally new form of intersphinx_mapping +Patch1: intersphinx-mapping.patch +# https://github.com/ncclient/ncclient/commit/59ccaac8e01e63f776fb4bf3b68a02e33d24bb20 +Patch2: python-ncclient-no-python2.patch +BuildRequires: %{python_module setuptools} +BuildRequires: fdupes +BuildRequires: python-rpm-macros +Requires: python-lxml >= 3.3.0 +Requires: python-paramiko >= 1.15.0 +Requires: python-setuptools > 0.6 +BuildArch: noarch +BuildRequires: %{python_module lxml >= 3.3.0} +BuildRequires: %{python_module paramiko >= 1.15.0} +BuildRequires: %{python_module pytest} +%python_subpackages + +%description +ncclient is a Python library that facilitates client-side scripting +and application development around the NETCONF protocol. + +%package -n python-ncclient-doc +Summary: Python NETCONF protocol library - Documentation +Group: Documentation/HTML +BuildRequires: %{python_module Sphinx-latex} +BuildRequires: %{python_module Sphinx} +BuildRequires: texlive-dvipng +Provides: %{python_module python-ncclient-doc = %{version}} + +%description -n python-ncclient-doc +This package contains documentation files for %{name}. + +%prep +%setup -q -n ncclient-%{version} +%if 0%{?suse_version} < 1550 +%patch -p 1 -P 0 +%endif +%patch -p 1 -P 1 +%patch -p 1 -P 2 + +find examples/ -name "*.py" -exec sed -i 's|#!/usr/bin/env python$|#!/usr/bin/python|g' {} \; +# drop shebang +find ncclient/operations/third_party/ -name "*.py" -exec sed -i '/^#!\//, 1d' {} \; + +%build +%python_build +cd docs && make %{?_smp_mflags} html && rm build/html/.buildinfo + +%install +%python_install +%fdupes %{buildroot} + +%check +%pytest + +%files %{python_files} +%license LICENSE +%{python_sitelib}/ncclient +%{python_sitelib}/ncclient-%{version}*-info + +%files -n python-ncclient-doc +%doc README.md README.rst examples docs/build/html + +%changelog