trigger 2.3.1__tar.gz → 2.3.3__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {trigger-2.3.1/trigger.egg-info → trigger-2.3.3}/PKG-INFO +2 -2
- {trigger-2.3.1 → trigger-2.3.3}/pyproject.toml +5 -2
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_acl.py +71 -0
- trigger-2.3.3/tests/test_tls_deps.py +31 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/support.py +16 -4
- {trigger-2.3.1 → trigger-2.3.3/trigger.egg-info}/PKG-INFO +2 -2
- {trigger-2.3.1 → trigger-2.3.3}/trigger.egg-info/SOURCES.txt +1 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger.egg-info/requires.txt +1 -1
- {trigger-2.3.1 → trigger-2.3.3}/AUTHORS.md +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/LICENSE.md +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/README.md +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/setup.cfg +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_acl_db.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_acl_queue.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_changemgmt.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_except.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_netdevices.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_scripts.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_tacacsrc.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_templates.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_twister.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_twister2.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/tests/test_utils.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/autoacl.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/db.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/dicts.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/grammar.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/ios.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/junos.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/models.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/parser.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/queue.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/acl/tools.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/acl.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/acl_script.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/aclconv.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/check_access.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/check_syntax.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/fe.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/find_access.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/gnng.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/gong.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/load_acl.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/load_config.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/netdev.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/optimizer.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/bin/run_cmds.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/changemgmt/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/changemgmt/bounce.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/cmds.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/conf/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/conf/global_settings.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/contrib/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/exceptions.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/gorc.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/netdevices/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/netdevices/loader.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/netscreen.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/packages/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/packages/peewee.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/rancid.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/tacacsrc.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/twister.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/twister2.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/__init__.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/cli.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/importlib.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/network.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/rcs.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/templates.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/url.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger/utils/xmltodict.py +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger.egg-info/dependency_links.txt +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger.egg-info/entry_points.txt +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/trigger.egg-info/top_level.txt +0 -0
- {trigger-2.3.1 → trigger-2.3.3}/twisted/plugins/trigger_xmlrpc.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: trigger
|
|
3
|
-
Version: 2.3.
|
|
3
|
+
Version: 2.3.3
|
|
4
4
|
Summary: Network automation toolkit for managing network devices
|
|
5
5
|
Author-email: Jathan McCollum <jathan@gmail.com>
|
|
6
6
|
License-Expression: BSD-3-Clause
|
|
@@ -15,7 +15,7 @@ License-File: LICENSE.md
|
|
|
15
15
|
License-File: AUTHORS.md
|
|
16
16
|
Requires-Dist: netaddr<2,>=1.0.0
|
|
17
17
|
Requires-Dist: cryptography>=41.0.0
|
|
18
|
-
Requires-Dist: Twisted>=22.10.0
|
|
18
|
+
Requires-Dist: Twisted[tls]>=22.10.0
|
|
19
19
|
Requires-Dist: crochet>=2.0.0
|
|
20
20
|
Requires-Dist: pyasn1>=0.4.8
|
|
21
21
|
Requires-Dist: pyparsing>=3.1.0
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "trigger"
|
|
7
|
-
version = "2.3.
|
|
7
|
+
version = "2.3.3"
|
|
8
8
|
description = "Network automation toolkit for managing network devices"
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
license = "BSD-3-Clause"
|
|
@@ -20,7 +20,7 @@ classifiers = [
|
|
|
20
20
|
dependencies = [
|
|
21
21
|
"netaddr>=1.0.0,<2",
|
|
22
22
|
"cryptography>=41.0.0",
|
|
23
|
-
"Twisted>=22.10.0",
|
|
23
|
+
"Twisted[tls]>=22.10.0",
|
|
24
24
|
"crochet>=2.0.0",
|
|
25
25
|
"pyasn1>=0.4.8",
|
|
26
26
|
"pyparsing>=3.1.0",
|
|
@@ -119,6 +119,9 @@ ignore = [
|
|
|
119
119
|
|
|
120
120
|
# --- Kept from v2.0.0 baseline ---
|
|
121
121
|
"E501", # line-too-long (handled by formatter)
|
|
122
|
+
"PLR0917", # too-many-positional-arguments (newly enforced in ruff 0.16;
|
|
123
|
+
# incompatible with Twisted-style long method signatures
|
|
124
|
+
# used throughout the codebase)
|
|
122
125
|
]
|
|
123
126
|
|
|
124
127
|
[tool.ruff.lint.pydocstyle]
|
|
@@ -392,6 +392,77 @@ ipv4 access-list BLAHBLAH
|
|
|
392
392
|
self.assertRaises(exceptions.BadACLName, a.output_ios)
|
|
393
393
|
|
|
394
394
|
|
|
395
|
+
class CheckStringification(unittest.TestCase):
|
|
396
|
+
"""Test str() and family kwarg tolerance of ACL output methods.
|
|
397
|
+
|
|
398
|
+
Regression tests for issue #397: ACL.__str__ always forwards
|
|
399
|
+
``family=self.family`` through ACL.output(), but only output_junos()
|
|
400
|
+
accepted it, so str() raised TypeError for every other format.
|
|
401
|
+
"""
|
|
402
|
+
|
|
403
|
+
def setUp(self):
|
|
404
|
+
super().setUp()
|
|
405
|
+
self.a = acl.ACL(name="BLAHBLAH")
|
|
406
|
+
self.t1 = acl.Term(name="p99")
|
|
407
|
+
self.t1.match["protocol"] = ["tcp"]
|
|
408
|
+
self.t1.match["source-address"] = ["192.0.2.0/24"]
|
|
409
|
+
self.t1.match["destination-port"] = [22]
|
|
410
|
+
self.t1.action = "accept"
|
|
411
|
+
self.a.terms.append(self.t1)
|
|
412
|
+
|
|
413
|
+
def _check_str(self, fmt, name="BLAHBLAH", term_name="p99"):
|
|
414
|
+
"""Helper: str() renders without TypeError for the given format."""
|
|
415
|
+
self.a.format = fmt
|
|
416
|
+
self.a.name = name
|
|
417
|
+
self.t1.name = term_name
|
|
418
|
+
lines = str(self.a).splitlines()
|
|
419
|
+
self.assertTrue(lines)
|
|
420
|
+
return lines
|
|
421
|
+
|
|
422
|
+
def testStrJunOS(self):
|
|
423
|
+
"""Test str() on a JunOS ACL"""
|
|
424
|
+
self._check_str("junos", "100j")
|
|
425
|
+
|
|
426
|
+
def testStrIOS(self):
|
|
427
|
+
"""Test str() on a traditional IOS ACL"""
|
|
428
|
+
self._check_str("ios", "100", term_name=None)
|
|
429
|
+
|
|
430
|
+
def testStrIOSNamed(self):
|
|
431
|
+
"""Test str() on a named IOS ACL (the #397 crash)"""
|
|
432
|
+
lines = self._check_str("ios_named")
|
|
433
|
+
self.assertEqual(lines[0], "ip access-list extended BLAHBLAH")
|
|
434
|
+
|
|
435
|
+
def testStrIOSXR(self):
|
|
436
|
+
"""Test str() on an IOS XR ACL"""
|
|
437
|
+
self._check_str("iosxr", term_name=None)
|
|
438
|
+
|
|
439
|
+
def testStrIOSBrocade(self):
|
|
440
|
+
"""Test str() on a Brocade-flavored IOS ACL"""
|
|
441
|
+
self._check_str("ios_brocade", "100", term_name=None)
|
|
442
|
+
|
|
443
|
+
def testParseStrRoundTrip(self):
|
|
444
|
+
"""Test str() on a parsed named IOS ACL round-trips (issue #397 repro)"""
|
|
445
|
+
text = "ip access-list extended SMOKE\n permit tcp host 10.20.30.40 any eq 22\n deny ip any any log\n"
|
|
446
|
+
a = acl.parse(text)
|
|
447
|
+
self.assertEqual(str(a), text.strip())
|
|
448
|
+
|
|
449
|
+
def testFamilyKwargAccepted(self):
|
|
450
|
+
"""Test ACL-level output methods accept and ignore family kwarg"""
|
|
451
|
+
for fmt, name, term_name in (
|
|
452
|
+
("junos", "100j", "p99"),
|
|
453
|
+
("ios", "100", None),
|
|
454
|
+
("ios_named", "BLAHBLAH", "p99"),
|
|
455
|
+
("iosxr", "BLAHBLAH", None),
|
|
456
|
+
("ios_brocade", "100", None),
|
|
457
|
+
):
|
|
458
|
+
self.a.format = fmt
|
|
459
|
+
self.a.name = name
|
|
460
|
+
self.t1.name = term_name
|
|
461
|
+
with_family = self.a.output(family="inet")
|
|
462
|
+
without_family = self.a.output()
|
|
463
|
+
self.assertEqual(with_family, without_family, f"format={fmt}")
|
|
464
|
+
|
|
465
|
+
|
|
395
466
|
class CheckIOSParseAndOutput(unittest.TestCase):
|
|
396
467
|
"""Test parsing of IOS ACLs"""
|
|
397
468
|
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
"""Regression tests for TLS dependency availability (issue #398).
|
|
2
|
+
|
|
3
|
+
pyOpenSSL used to arrive transitively (old service-identity hard-required
|
|
4
|
+
it; Twisted only ships it with the ``[tls]`` extra). When that changed,
|
|
5
|
+
fresh installs got a trigger whose Twisted TLS paths failed with
|
|
6
|
+
``ModuleNotFoundError: No module named 'OpenSSL'``. These tests keep the
|
|
7
|
+
TLS stack import-honest.
|
|
8
|
+
"""
|
|
9
|
+
|
|
10
|
+
import pytest
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
def test_pyopenssl_installed():
|
|
14
|
+
"""Test that pyOpenSSL is importable."""
|
|
15
|
+
OpenSSL = pytest.importorskip("OpenSSL")
|
|
16
|
+
assert OpenSSL.__version__
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
def test_twisted_tls_stack():
|
|
20
|
+
"""Test that Twisted's TLS context factory is importable.
|
|
21
|
+
|
|
22
|
+
DefaultOpenSSLContextFactory is the code path used by
|
|
23
|
+
trigger.contrib.xmlrpc.server.
|
|
24
|
+
"""
|
|
25
|
+
ssl = pytest.importorskip("twisted.internet.ssl")
|
|
26
|
+
assert hasattr(ssl, "DefaultOpenSSLContextFactory")
|
|
27
|
+
|
|
28
|
+
|
|
29
|
+
def test_service_identity_pyopenssl_hooks():
|
|
30
|
+
"""Test that service_identity's pyOpenSSL verification hooks load."""
|
|
31
|
+
pytest.importorskip("service_identity.pyopenssl")
|
|
@@ -758,10 +758,13 @@ class ACL:
|
|
|
758
758
|
|
|
759
759
|
return out
|
|
760
760
|
|
|
761
|
-
def output_ios(self, replace=False):
|
|
761
|
+
def output_ios(self, replace=False, family=None):
|
|
762
762
|
"""Output the ACL in IOS traditional format.
|
|
763
763
|
|
|
764
764
|
:param replace: If set the ACL is preceded by a ``no access-list`` line.
|
|
765
|
+
:param family: Accepted for signature compatibility with
|
|
766
|
+
:meth:`~ACL.output_junos`, but ignored -- ``family inet/inet6``
|
|
767
|
+
wrapping is a JunOS-only concept.
|
|
765
768
|
"""
|
|
766
769
|
if self.name is None:
|
|
767
770
|
msg = "IOS format requires a name"
|
|
@@ -785,7 +788,7 @@ class ACL:
|
|
|
785
788
|
out += [x for x in t.output_ios(prefix)]
|
|
786
789
|
return out
|
|
787
790
|
|
|
788
|
-
def output_ios_brocade(self, replace=False, receive_acl=False):
|
|
791
|
+
def output_ios_brocade(self, replace=False, receive_acl=False, family=None):
|
|
789
792
|
"""Output the ACL in Brocade-flavored IOS format.
|
|
790
793
|
|
|
791
794
|
The difference between this and "traditional" IOS are:
|
|
@@ -796,6 +799,9 @@ class ACL:
|
|
|
796
799
|
:param replace: If set the ACL is preceded by a ``no access-list`` line.
|
|
797
800
|
:param receive_acl: If set the ACL is suffixed with a ``ip
|
|
798
801
|
rebind-receive-acl' instead of ``ip rebind-acl``.
|
|
802
|
+
:param family: Accepted for signature compatibility with
|
|
803
|
+
:meth:`~ACL.output_junos`, but ignored -- ``family inet/inet6``
|
|
804
|
+
wrapping is a JunOS-only concept.
|
|
799
805
|
"""
|
|
800
806
|
self.strip_comments()
|
|
801
807
|
|
|
@@ -812,10 +818,13 @@ class ACL:
|
|
|
812
818
|
|
|
813
819
|
return out
|
|
814
820
|
|
|
815
|
-
def output_ios_named(self, replace=False):
|
|
821
|
+
def output_ios_named(self, replace=False, family=None):
|
|
816
822
|
"""Output the ACL in IOS named format.
|
|
817
823
|
|
|
818
824
|
:param replace: If set the ACL is preceded by a ``no access-list`` line.
|
|
825
|
+
:param family: Accepted for signature compatibility with
|
|
826
|
+
:meth:`~ACL.output_junos`, but ignored -- ``family inet/inet6``
|
|
827
|
+
wrapping is a JunOS-only concept.
|
|
819
828
|
"""
|
|
820
829
|
if self.name is None:
|
|
821
830
|
msg = "IOS format requires a name"
|
|
@@ -831,10 +840,13 @@ class ACL:
|
|
|
831
840
|
out += [x for x in t.output_ios_named(" ")]
|
|
832
841
|
return out
|
|
833
842
|
|
|
834
|
-
def output_iosxr(self, replace=False):
|
|
843
|
+
def output_iosxr(self, replace=False, family=None):
|
|
835
844
|
"""Output the ACL in IOS XR format.
|
|
836
845
|
|
|
837
846
|
:param replace: If set the ACL is preceded by a ``no ipv4 access-list`` line.
|
|
847
|
+
:param family: Accepted for signature compatibility with
|
|
848
|
+
:meth:`~ACL.output_junos`, but ignored -- ``family inet/inet6``
|
|
849
|
+
wrapping is a JunOS-only concept.
|
|
838
850
|
"""
|
|
839
851
|
if self.name is None:
|
|
840
852
|
msg = "IOS XR format requires a name"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: trigger
|
|
3
|
-
Version: 2.3.
|
|
3
|
+
Version: 2.3.3
|
|
4
4
|
Summary: Network automation toolkit for managing network devices
|
|
5
5
|
Author-email: Jathan McCollum <jathan@gmail.com>
|
|
6
6
|
License-Expression: BSD-3-Clause
|
|
@@ -15,7 +15,7 @@ License-File: LICENSE.md
|
|
|
15
15
|
License-File: AUTHORS.md
|
|
16
16
|
Requires-Dist: netaddr<2,>=1.0.0
|
|
17
17
|
Requires-Dist: cryptography>=41.0.0
|
|
18
|
-
Requires-Dist: Twisted>=22.10.0
|
|
18
|
+
Requires-Dist: Twisted[tls]>=22.10.0
|
|
19
19
|
Requires-Dist: crochet>=2.0.0
|
|
20
20
|
Requires-Dist: pyasn1>=0.4.8
|
|
21
21
|
Requires-Dist: pyparsing>=3.1.0
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|