flow.record 3.17.dev5__tar.gz → 3.17.dev6__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.
Files changed (84) hide show
  1. {flow_record-3.17.dev5/flow.record.egg-info → flow_record-3.17.dev6}/PKG-INFO +1 -1
  2. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/fieldtypes/net/ip.py +37 -18
  3. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/version.py +2 -2
  4. {flow_record-3.17.dev5 → flow_record-3.17.dev6/flow.record.egg-info}/PKG-INFO +1 -1
  5. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_fieldtype_ip.py +15 -0
  6. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/COPYRIGHT +0 -0
  7. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/LICENSE +0 -0
  8. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/MANIFEST.in +0 -0
  9. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/README.md +0 -0
  10. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/examples/filesystem.py +0 -0
  11. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/examples/passivedns.py +0 -0
  12. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/examples/records.json +0 -0
  13. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/examples/tcpconn.py +0 -0
  14. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/__init__.py +0 -0
  15. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/__init__.py +0 -0
  16. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/archive.py +0 -0
  17. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/avro.py +0 -0
  18. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/broker.py +0 -0
  19. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/csvfile.py +0 -0
  20. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/duckdb.py +0 -0
  21. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/elastic.py +0 -0
  22. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/jsonfile.py +0 -0
  23. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/line.py +0 -0
  24. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/mongo.py +0 -0
  25. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/split.py +0 -0
  26. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/splunk.py +0 -0
  27. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/sqlite.py +0 -0
  28. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/stream.py +0 -0
  29. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/text.py +0 -0
  30. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/adapter/xlsx.py +0 -0
  31. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/base.py +0 -0
  32. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/exceptions.py +0 -0
  33. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/fieldtypes/__init__.py +0 -0
  34. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/fieldtypes/credential.py +0 -0
  35. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/fieldtypes/net/__init__.py +0 -0
  36. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/fieldtypes/net/ipv4.py +0 -0
  37. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/fieldtypes/net/tcp.py +0 -0
  38. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/fieldtypes/net/udp.py +0 -0
  39. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/jsonpacker.py +0 -0
  40. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/packer.py +0 -0
  41. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/selector.py +0 -0
  42. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/stream.py +0 -0
  43. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/tools/__init__.py +0 -0
  44. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/tools/geoip.py +0 -0
  45. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/tools/rdump.py +0 -0
  46. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/utils.py +0 -0
  47. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow/record/whitelist.py +0 -0
  48. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow.record.egg-info/SOURCES.txt +0 -0
  49. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow.record.egg-info/dependency_links.txt +0 -0
  50. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow.record.egg-info/entry_points.txt +0 -0
  51. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow.record.egg-info/requires.txt +0 -0
  52. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/flow.record.egg-info/top_level.txt +0 -0
  53. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/pyproject.toml +0 -0
  54. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/setup.cfg +0 -0
  55. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/__init__.py +0 -0
  56. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/_utils.py +0 -0
  57. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/docs/Makefile +0 -0
  58. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/docs/conf.py +0 -0
  59. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/docs/index.rst +0 -0
  60. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/selector_explain_example.py +0 -0
  61. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/standalone_test.py +0 -0
  62. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_adapter_line.py +0 -0
  63. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_adapter_text.py +0 -0
  64. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_avro.py +0 -0
  65. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_avro_adapter.py +0 -0
  66. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_compiled_selector.py +0 -0
  67. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_csv_adapter.py +0 -0
  68. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_deprecations.py +0 -0
  69. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_elastic_adapter.py +0 -0
  70. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_fieldtypes.py +0 -0
  71. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_json_packer.py +0 -0
  72. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_json_record_adapter.py +0 -0
  73. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_multi_timestamp.py +0 -0
  74. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_packer.py +0 -0
  75. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_rdump.py +0 -0
  76. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_record.py +0 -0
  77. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_record_adapter.py +0 -0
  78. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_record_descriptor.py +0 -0
  79. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_regression.py +0 -0
  80. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_selector.py +0 -0
  81. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_splunk_adapter.py +0 -0
  82. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_sqlite_duckdb_adapter.py +0 -0
  83. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tests/test_xlsx_adapter.py +0 -0
  84. {flow_record-3.17.dev5 → flow_record-3.17.dev6}/tox.ini +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: flow.record
3
- Version: 3.17.dev5
3
+ Version: 3.17.dev6
4
4
  Summary: A library for defining and creating structured data (called records) that can be streamed to disk or piped to other tools that use flow.record
5
5
  Author-email: Dissect Team <dissect@fox-it.com>
6
6
  License: Affero General Public License v3
@@ -1,38 +1,54 @@
1
- from ipaddress import ip_address, ip_network
1
+ from __future__ import annotations
2
+
3
+ from ipaddress import (
4
+ IPv4Address,
5
+ IPv4Network,
6
+ IPv6Address,
7
+ IPv6Network,
8
+ ip_address,
9
+ ip_network,
10
+ )
11
+ from typing import Union
2
12
 
3
13
  from flow.record.base import FieldType
4
14
  from flow.record.fieldtypes import defang
5
15
 
16
+ _IPNetwork = Union[IPv4Network, IPv6Network]
17
+ _IPAddress = Union[IPv4Address, IPv6Address]
18
+
6
19
 
7
20
  class ipaddress(FieldType):
8
21
  val = None
9
22
  _type = "net.ipaddress"
10
23
 
11
- def __init__(self, addr):
24
+ def __init__(self, addr: str | int | bytes):
12
25
  self.val = ip_address(addr)
13
26
 
14
- def __eq__(self, b):
27
+ def __eq__(self, b: str | int | bytes | _IPAddress) -> bool:
15
28
  try:
16
29
  return self.val == ip_address(b)
17
30
  except ValueError:
18
31
  return False
19
32
 
20
- def __str__(self):
33
+ def __hash__(self) -> int:
34
+ return hash(self.val)
35
+
36
+ def __str__(self) -> str:
21
37
  return str(self.val)
22
38
 
23
- def __repr__(self):
24
- return "{}({!r})".format(self._type, str(self))
39
+ def __repr__(self) -> str:
40
+ return f"{self._type}({str(self)!r})"
25
41
 
26
- def __format__(self, spec):
42
+ def __format__(self, spec: str) -> str:
27
43
  if spec == "defang":
28
44
  return defang(str(self))
29
45
  return str.__format__(str(self), spec)
30
46
 
31
- def _pack(self):
47
+ def _pack(self) -> int:
32
48
  return int(self.val)
33
49
 
34
50
  @staticmethod
35
- def _unpack(data):
51
+ def _unpack(data: int) -> ipaddress:
36
52
  return ipaddress(data)
37
53
 
38
54
 
@@ -40,17 +56,20 @@ class ipnetwork(FieldType):
40
56
  val = None
41
57
  _type = "net.ipnetwork"
42
58
 
43
- def __init__(self, addr):
59
+ def __init__(self, addr: str | int | bytes):
44
60
  self.val = ip_network(addr)
45
61
 
46
- def __eq__(self, b):
62
+ def __eq__(self, b: str | int | bytes | _IPNetwork) -> bool:
47
63
  try:
48
64
  return self.val == ip_network(b)
49
65
  except ValueError:
50
66
  return False
51
67
 
68
+ def __hash__(self) -> int:
69
+ return hash(self.val)
70
+
52
71
  @staticmethod
53
- def _is_subnet_of(a, b):
72
+ def _is_subnet_of(a: _IPNetwork, b: _IPNetwork) -> bool:
54
73
  try:
55
74
  # Always false if one is v4 and the other is v6.
56
75
  if a._version != b._version:
@@ -59,23 +78,23 @@ class ipnetwork(FieldType):
59
78
  except AttributeError:
60
79
  raise TypeError("Unable to test subnet containment " "between {} and {}".format(a, b))
61
80
 
62
- def __contains__(self, b):
81
+ def __contains__(self, b: str | int | bytes | _IPAddress) -> bool:
63
82
  try:
64
83
  return self._is_subnet_of(ip_network(b), self.val)
65
84
  except (ValueError, TypeError):
66
85
  return False
67
86
 
68
- def __str__(self):
87
+ def __str__(self) -> str:
69
88
  return str(self.val)
70
89
 
71
- def __repr__(self):
72
- return "{}({!r})".format(self._type, str(self))
90
+ def __repr__(self) -> str:
91
+ return f"{self._type}({str(self)!r})"
73
92
 
74
- def _pack(self):
93
+ def _pack(self) -> str:
75
94
  return self.val.compressed
76
95
 
77
96
  @staticmethod
78
- def _unpack(data):
97
+ def _unpack(data: str) -> ipnetwork:
79
98
  return ipnetwork(data)
80
99
 
81
100
 
@@ -12,5 +12,5 @@ __version__: str
12
12
  __version_tuple__: VERSION_TUPLE
13
13
  version_tuple: VERSION_TUPLE
14
14
 
15
- __version__ = version = '3.17.dev5'
16
- __version_tuple__ = version_tuple = (3, 17, 'dev5')
15
+ __version__ = version = '3.17.dev6'
16
+ __version_tuple__ = version_tuple = (3, 17, 'dev6')
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: flow.record
3
- Version: 3.17.dev5
3
+ Version: 3.17.dev6
4
4
  Summary: A library for defining and creating structured data (called records) that can be streamed to disk or piped to other tools that use flow.record
5
5
  Author-email: Dissect Team <dissect@fox-it.com>
6
6
  License: Affero General Public License v3
@@ -48,12 +48,19 @@ def test_record_ipaddress():
48
48
  assert TestRecord("0.0.0.0").ip == "0.0.0.0"
49
49
  assert TestRecord("192.168.0.1").ip == "192.168.0.1"
50
50
  assert TestRecord("255.255.255.255").ip == "255.255.255.255"
51
+ assert hash(TestRecord("192.168.0.1").ip) == hash(net.ipaddress("192.168.0.1"))
51
52
 
52
53
  # ipv6
53
54
  assert TestRecord("::1").ip == "::1"
54
55
  assert TestRecord("2001:4860:4860::8888").ip == "2001:4860:4860::8888"
55
56
  assert TestRecord("2001:4860:4860::4444").ip == "2001:4860:4860::4444"
56
57
 
58
+ # Test whether it functions in a set
59
+ data = {TestRecord(ip).ip for ip in ["192.168.0.1", "192.168.0.1", "::1", "::1"]}
60
+ assert len(data) == 2
61
+ assert net.ipaddress("::1") in data
62
+ assert net.ipaddress("192.168.0.1") in data
63
+
57
64
  # instantiate from different types
58
65
  assert TestRecord(1).ip == "0.0.0.1"
59
66
  assert TestRecord(0x7F0000FF).ip == "127.0.0.255"
@@ -90,6 +97,7 @@ def test_record_ipnetwork():
90
97
  assert "192.168.1.1" not in r.subnet
91
98
  assert isinstance(r.subnet, net.ipnetwork)
92
99
  assert repr(r.subnet) == "net.ipnetwork('192.168.0.0/24')"
100
+ assert hash(r.subnet) == hash(net.ipnetwork("192.168.0.0/24"))
93
101
 
94
102
  r = TestRecord("192.168.1.1/32")
95
103
  assert r.subnet == "192.168.1.1"
@@ -111,6 +119,13 @@ def test_record_ipnetwork():
111
119
  assert "64:ff9b::0.0.0.0" in r.subnet
112
120
  assert "64:ff9b::255.255.255.255" in r.subnet
113
121
 
122
+ # Test whether it functions in a set
123
+ data = {TestRecord(x).subnet for x in ["192.168.0.0/24", "192.168.0.0/24", "::1", "::1"]}
124
+ assert len(data) == 2
125
+ assert net.ipnetwork("::1") in data
126
+ assert net.ipnetwork("192.168.0.0/24") in data
127
+ assert "::1" not in data
128
+
114
129
 
115
130
  @pytest.mark.parametrize("PSelector", [Selector, CompiledSelector])
116
131
  def test_selector_ipaddress(PSelector):
File without changes
File without changes