koi-net 1.2.0b1__py3-none-any.whl → 1.2.0b2__py3-none-any.whl

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.

Potentially problematic release.


This version of koi-net might be problematic. Click here for more details.

Files changed (40) hide show
  1. koi_net/__init__.py +2 -1
  2. koi_net/assembler.py +82 -0
  3. koi_net/context.py +5 -13
  4. koi_net/core.py +51 -206
  5. koi_net/effector.py +26 -14
  6. koi_net/handshaker.py +3 -3
  7. koi_net/identity.py +2 -3
  8. koi_net/interfaces/entrypoint.py +5 -0
  9. koi_net/{worker.py → interfaces/worker.py} +7 -0
  10. koi_net/lifecycle.py +40 -32
  11. koi_net/logger.py +176 -0
  12. koi_net/network/error_handler.py +6 -6
  13. koi_net/network/event_queue.py +8 -6
  14. koi_net/network/graph.py +8 -8
  15. koi_net/network/poll_event_buffer.py +26 -0
  16. koi_net/network/request_handler.py +23 -28
  17. koi_net/network/resolver.py +13 -13
  18. koi_net/network/response_handler.py +74 -9
  19. koi_net/poller.py +7 -5
  20. koi_net/processor/event_worker.py +14 -18
  21. koi_net/processor/{default_handlers.py → handlers.py} +26 -25
  22. koi_net/processor/kobj_queue.py +3 -3
  23. koi_net/{kobj_worker.py → processor/kobj_worker.py} +12 -13
  24. koi_net/processor/{knowledge_pipeline.py → pipeline.py} +24 -27
  25. koi_net/protocol/api_models.py +5 -2
  26. koi_net/protocol/envelope.py +5 -6
  27. koi_net/protocol/model_map.py +61 -0
  28. koi_net/protocol/secure.py +8 -8
  29. koi_net/secure.py +5 -5
  30. koi_net/sentry.py +13 -0
  31. koi_net/server.py +36 -86
  32. {koi_net-1.2.0b1.dist-info → koi_net-1.2.0b2.dist-info}/METADATA +2 -1
  33. koi_net-1.2.0b2.dist-info/RECORD +52 -0
  34. koi_net/behaviors.py +0 -51
  35. koi_net/models.py +0 -14
  36. koi_net/poll_event_buffer.py +0 -17
  37. koi_net-1.2.0b1.dist-info/RECORD +0 -49
  38. {koi_net-1.2.0b1.dist-info → koi_net-1.2.0b2.dist-info}/WHEEL +0 -0
  39. {koi_net-1.2.0b1.dist-info → koi_net-1.2.0b2.dist-info}/entry_points.txt +0 -0
  40. {koi_net-1.2.0b1.dist-info → koi_net-1.2.0b2.dist-info}/licenses/LICENSE +0 -0
@@ -1,4 +1,4 @@
1
- import logging
1
+ import structlog
2
2
  import httpx
3
3
  from rid_lib import RID
4
4
  from rid_lib.core import RIDType
@@ -13,7 +13,7 @@ from ..protocol.api_models import ErrorResponse
13
13
  from ..identity import NodeIdentity
14
14
  from ..config import NodeConfig
15
15
 
16
- logger = logging.getLogger(__name__)
16
+ log = structlog.stdlib.get_logger()
17
17
 
18
18
 
19
19
  class NetworkResolver:
@@ -45,7 +45,7 @@ class NetworkResolver:
45
45
  def get_state_providers(self, rid_type: RIDType) -> list[KoiNetNode]:
46
46
  """Returns list of node RIDs which provide state for specified RID type."""
47
47
 
48
- logger.debug(f"Looking for state providers of {rid_type}")
48
+ log.debug(f"Looking for state providers of {rid_type}")
49
49
  provider_nodes = []
50
50
  for node_rid in self.cache.list_rids(rid_types=[KoiNetNode]):
51
51
  if node_rid == self.identity.rid:
@@ -56,17 +56,17 @@ class NetworkResolver:
56
56
  node_profile = node_bundle.validate_contents(NodeProfile)
57
57
 
58
58
  if (node_profile.node_type == NodeType.FULL) and (rid_type in node_profile.provides.state):
59
- logger.debug(f"Found provider {node_rid!r}")
59
+ log.debug(f"Found provider {node_rid!r}")
60
60
  provider_nodes.append(node_rid)
61
61
 
62
62
  if not provider_nodes:
63
- logger.debug("Failed to find providers")
63
+ log.debug("Failed to find providers")
64
64
  return provider_nodes
65
65
 
66
66
  def fetch_remote_bundle(self, rid: RID) -> tuple[Bundle | None, KoiNetNode | None]:
67
67
  """Attempts to fetch a bundle by RID from known peer nodes."""
68
68
 
69
- logger.debug(f"Fetching remote bundle {rid!r}")
69
+ log.debug(f"Fetching remote bundle {rid!r}")
70
70
  remote_bundle, node_rid = None, None
71
71
  for node_rid in self.get_state_providers(type(rid)):
72
72
  payload = self.request_handler.fetch_bundles(
@@ -74,18 +74,18 @@ class NetworkResolver:
74
74
 
75
75
  if payload.bundles:
76
76
  remote_bundle = payload.bundles[0]
77
- logger.debug(f"Got bundle from {node_rid!r}")
77
+ log.debug(f"Got bundle from {node_rid!r}")
78
78
  break
79
79
 
80
80
  if not remote_bundle:
81
- logger.warning("Failed to fetch remote bundle")
81
+ log.warning("Failed to fetch remote bundle")
82
82
 
83
83
  return remote_bundle, node_rid
84
84
 
85
85
  def fetch_remote_manifest(self, rid: RID) -> tuple[Bundle | None, KoiNetNode | None]:
86
86
  """Attempts to fetch a manifest by RID from known peer nodes."""
87
87
 
88
- logger.debug(f"Fetching remote manifest {rid!r}")
88
+ log.debug(f"Fetching remote manifest {rid!r}")
89
89
  remote_manifest, node_rid = None, None
90
90
  for node_rid in self.get_state_providers(type(rid)):
91
91
  payload = self.request_handler.fetch_manifests(
@@ -93,11 +93,11 @@ class NetworkResolver:
93
93
 
94
94
  if payload.manifests:
95
95
  remote_manifest = payload.manifests[0]
96
- logger.debug(f"Got bundle from {node_rid!r}")
96
+ log.debug(f"Got bundle from {node_rid!r}")
97
97
  break
98
98
 
99
99
  if not remote_manifest:
100
- logger.warning("Failed to fetch remote bundle")
100
+ log.warning("Failed to fetch remote bundle")
101
101
 
102
102
  return remote_manifest, node_rid
103
103
 
@@ -136,12 +136,12 @@ class NetworkResolver:
136
136
  continue
137
137
 
138
138
  if payload.events:
139
- logger.debug(f"Received {len(payload.events)} events from {node_rid!r}")
139
+ log.debug(f"Received {len(payload.events)} events from {node_rid!r}")
140
140
 
141
141
  event_dict[node_rid] = payload.events
142
142
 
143
143
  except httpx.ConnectError:
144
- logger.debug(f"Failed to reach node {node_rid!r}")
144
+ log.debug(f"Failed to reach node {node_rid!r}")
145
145
  continue
146
146
 
147
147
  return event_dict
@@ -1,10 +1,20 @@
1
- import logging
1
+ import structlog
2
2
  from rid_lib import RID
3
3
  from rid_lib.types import KoiNetNode
4
4
  from rid_lib.ext import Manifest, Cache
5
5
  from rid_lib.ext.bundle import Bundle
6
6
 
7
+ from koi_net.network.poll_event_buffer import PollEventBuffer
8
+ from koi_net.processor.kobj_queue import KobjQueue
9
+ from koi_net.protocol.consts import BROADCAST_EVENTS_PATH, FETCH_BUNDLES_PATH, FETCH_MANIFESTS_PATH, FETCH_RIDS_PATH, POLL_EVENTS_PATH
10
+ from koi_net.protocol.envelope import SignedEnvelope
11
+ from koi_net.protocol.model_map import API_MODEL_MAP
12
+ from koi_net.secure import Secure
13
+
7
14
  from ..protocol.api_models import (
15
+ ApiModels,
16
+ EventsPayload,
17
+ PollEvents,
8
18
  RidsPayload,
9
19
  ManifestsPayload,
10
20
  BundlesPayload,
@@ -13,30 +23,81 @@ from ..protocol.api_models import (
13
23
  FetchBundles,
14
24
  )
15
25
 
16
- logger = logging.getLogger(__name__)
26
+ log = structlog.stdlib.get_logger()
17
27
 
18
28
 
19
29
  class ResponseHandler:
20
30
  """Handles generating responses to requests from other KOI nodes."""
21
31
 
22
32
  cache: Cache
33
+ kobj_queue: KobjQueue
34
+ poll_event_buf: PollEventBuffer
23
35
 
24
36
  def __init__(
25
37
  self,
26
- cache: Cache,
38
+ cache: Cache,
39
+ kobj_queue: KobjQueue,
40
+ poll_event_buf: PollEventBuffer,
41
+ secure: Secure
27
42
  ):
28
43
  self.cache = cache
44
+ self.kobj_queue = kobj_queue
45
+ self.poll_event_buf = poll_event_buf
46
+ self.secure = secure
47
+
48
+ def handle_response(self, path: str, req: SignedEnvelope):
49
+ self.secure.validate_envelope(req)
50
+
51
+ response_map = {
52
+ BROADCAST_EVENTS_PATH: self.broadcast_events_handler,
53
+ POLL_EVENTS_PATH: self.poll_events_handler,
54
+ FETCH_RIDS_PATH: self.fetch_rids_handler,
55
+ FETCH_MANIFESTS_PATH: self.fetch_manifests_handler,
56
+ FETCH_BUNDLES_PATH: self.fetch_bundles_handler
57
+ }
58
+
59
+ response = response_map[path](req.payload, req.source_node)
60
+
61
+ if response is None:
62
+ return
63
+
64
+ return self.secure.create_envelope(
65
+ payload=response,
66
+ target=req.source_node
67
+ )
29
68
 
30
- def fetch_rids(self, req: FetchRids, source: KoiNetNode) -> RidsPayload:
69
+ def broadcast_events_handler(self, req: EventsPayload, source: KoiNetNode):
70
+ log.info(f"Request to broadcast events, received {len(req.events)} event(s)")
71
+
72
+ for event in req.events:
73
+ self.kobj_queue.put_kobj(event=event, source=source)
74
+
75
+ def poll_events_handler(
76
+ self,
77
+ req: PollEvents,
78
+ source: KoiNetNode
79
+ ) -> EventsPayload:
80
+ log.info(f"Request to poll events")
81
+ events = self.poll_event_buf.flush(source, limit=req.limit)
82
+ return EventsPayload(events=events)
83
+
84
+ def fetch_rids_handler(
85
+ self,
86
+ req: FetchRids,
87
+ source: KoiNetNode
88
+ ) -> RidsPayload:
31
89
  """Returns response to fetch RIDs request."""
32
- logger.info(f"Request to fetch rids, allowed types {req.rid_types}")
90
+ log.info(f"Request to fetch rids, allowed types {req.rid_types}")
33
91
  rids = self.cache.list_rids(req.rid_types)
34
92
 
35
93
  return RidsPayload(rids=rids)
36
94
 
37
- def fetch_manifests(self, req: FetchManifests, source: KoiNetNode) -> ManifestsPayload:
95
+ def fetch_manifests_handler(self,
96
+ req: FetchManifests,
97
+ source: KoiNetNode
98
+ ) -> ManifestsPayload:
38
99
  """Returns response to fetch manifests request."""
39
- logger.info(f"Request to fetch manifests, allowed types {req.rid_types}, rids {req.rids}")
100
+ log.info(f"Request to fetch manifests, allowed types {req.rid_types}, rids {req.rids}")
40
101
 
41
102
  manifests: list[Manifest] = []
42
103
  not_found: list[RID] = []
@@ -50,9 +111,13 @@ class ResponseHandler:
50
111
 
51
112
  return ManifestsPayload(manifests=manifests, not_found=not_found)
52
113
 
53
- def fetch_bundles(self, req: FetchBundles, source: KoiNetNode) -> BundlesPayload:
114
+ def fetch_bundles_handler(
115
+ self,
116
+ req: FetchBundles,
117
+ source: KoiNetNode
118
+ ) -> BundlesPayload:
54
119
  """Returns response to fetch bundles request."""
55
- logger.info(f"Request to fetch bundles, requested rids {req.rids}")
120
+ log.info(f"Request to fetch bundles, requested rids {req.rids}")
56
121
 
57
122
  bundles: list[Bundle] = []
58
123
  not_found: list[RID] = []
koi_net/poller.py CHANGED
@@ -1,15 +1,17 @@
1
1
 
2
2
  import time
3
- import logging
3
+ import structlog
4
+
5
+ from koi_net.interfaces.entrypoint import EntryPoint
4
6
  from .processor.kobj_queue import KobjQueue
5
7
  from .lifecycle import NodeLifecycle
6
8
  from .network.resolver import NetworkResolver
7
9
  from .config import NodeConfig
8
10
 
9
- logger = logging.getLogger(__name__)
11
+ log = structlog.stdlib.get_logger()
10
12
 
11
13
 
12
- class NodePoller:
14
+ class NodePoller(EntryPoint):
13
15
  """Manages polling based event loop for partial nodes."""
14
16
  kobj_queue: KobjQueue
15
17
  lifecycle: NodeLifecycle
@@ -18,10 +20,10 @@ class NodePoller:
18
20
 
19
21
  def __init__(
20
22
  self,
21
- kobj_queue: KobjQueue,
23
+ config: NodeConfig,
22
24
  lifecycle: NodeLifecycle,
25
+ kobj_queue: KobjQueue,
23
26
  resolver: NetworkResolver,
24
- config: NodeConfig
25
27
  ):
26
28
  self.kobj_queue = kobj_queue
27
29
  self.lifecycle = lifecycle
@@ -1,21 +1,20 @@
1
1
  import queue
2
2
  import traceback
3
3
  import time
4
- import logging
4
+ import structlog
5
5
 
6
6
  from rid_lib.ext import Cache
7
7
  from rid_lib.types import KoiNetNode
8
8
 
9
9
  from koi_net.config import NodeConfig
10
- from koi_net.models import END, QueuedEvent
11
- from koi_net.network.event_queue import EventQueue
10
+ from koi_net.network.event_queue import EventQueue, QueuedEvent
12
11
  from koi_net.network.request_handler import RequestHandler
13
- from koi_net.poll_event_buffer import PollEventBuffer
12
+ from koi_net.network.poll_event_buffer import PollEventBuffer
14
13
  from koi_net.protocol.event import Event
15
14
  from koi_net.protocol.node import NodeProfile, NodeType
16
- from koi_net.worker import ThreadWorker
15
+ from koi_net.interfaces.worker import ThreadWorker, STOP_WORKER
17
16
 
18
- logger = logging.getLogger(__name__)
17
+ log = structlog.stdlib.get_logger()
19
18
 
20
19
 
21
20
  class EventProcessingWorker(ThreadWorker):
@@ -28,10 +27,7 @@ class EventProcessingWorker(ThreadWorker):
28
27
  request_handler: RequestHandler,
29
28
  config: NodeConfig,
30
29
  cache: Cache,
31
- poll_event_buf: PollEventBuffer,
32
- queue_timeout: float = 0.1,
33
- max_buf_len: int = 5,
34
- max_wait_time: float = 1.0
30
+ poll_event_buf: PollEventBuffer
35
31
  ):
36
32
  self.event_queue = event_queue
37
33
  self.request_handler = request_handler
@@ -40,9 +36,9 @@ class EventProcessingWorker(ThreadWorker):
40
36
  self.cache = cache
41
37
  self.poll_event_buf = poll_event_buf
42
38
 
43
- self.timeout = queue_timeout
44
- self.max_buf_len = max_buf_len
45
- self.max_wait_time = max_wait_time
39
+ self.timeout: float = 0.1
40
+ self.max_buf_len: int = 5
41
+ self.max_wait_time: float = 1.0
46
42
 
47
43
  self.event_buffer = dict()
48
44
  self.buffer_times = dict()
@@ -74,25 +70,25 @@ class EventProcessingWorker(ThreadWorker):
74
70
  return True
75
71
 
76
72
  else:
77
- logger.warning(f"Couldn't handle event {item.event!r} in queue, node {item.target!r} unknown to me")
73
+ log.warning(f"Couldn't handle event {item.event!r} in queue, node {item.target!r} unknown to me")
78
74
  return False
79
75
 
80
76
 
81
77
  def run(self):
82
- logger.info("Started event worker")
78
+ log.info("Started event worker")
83
79
  while True:
84
80
  now = time.time()
85
81
  try:
86
82
  item = self.event_queue.q.get(timeout=self.timeout)
87
83
 
88
84
  try:
89
- if item is END:
90
- logger.info("Received 'END' signal, flushing buffer...")
85
+ if item is STOP_WORKER:
86
+ log.info(f"Received 'STOP_WORKER' signal, flushing buffer...")
91
87
  for target in self.event_buffer.keys():
92
88
  self.flush_buffer(target, self.event_buffer[target])
93
89
  return
94
90
 
95
- logger.info(f"Dequeued {item.event!r} -> {item.target!r}")
91
+ log.info(f"Dequeued {item.event!r} -> {item.target!r}")
96
92
 
97
93
  if not self.decide_event(item):
98
94
  continue
@@ -1,6 +1,6 @@
1
1
  """Implementation of default knowledge handlers."""
2
2
 
3
- import logging
3
+ import structlog
4
4
  from rid_lib.ext import Bundle
5
5
  from rid_lib.ext.utils import sha256_hash
6
6
  from rid_lib.types import KoiNetNode, KoiNetEdge
@@ -9,10 +9,11 @@ from .handler import KnowledgeHandler, HandlerType, STOP_CHAIN
9
9
  from .knowledge_object import KnowledgeObject
10
10
  from ..context import HandlerContext
11
11
  from ..protocol.event import Event, EventType
12
- from ..protocol.edge import EdgeProfile, EdgeStatus, EdgeType, generate_edge_bundle
12
+ from ..protocol.edge import EdgeProfile, EdgeStatus, EdgeType
13
13
  from ..protocol.node import NodeProfile
14
14
 
15
- logger = logging.getLogger(__name__)
15
+ log = structlog.stdlib.get_logger()
16
+
16
17
 
17
18
  # RID handlers
18
19
 
@@ -24,7 +25,7 @@ def basic_rid_handler(ctx: HandlerContext, kobj: KnowledgeObject):
24
25
  RID is known to this node.
25
26
  """
26
27
  if (kobj.rid == ctx.identity.rid and kobj.source):
27
- logger.debug("Don't let anyone else tell me who I am!")
28
+ log.debug("Don't let anyone else tell me who I am!")
28
29
  return STOP_CHAIN
29
30
 
30
31
  if kobj.event_type == EventType.FORGET:
@@ -45,17 +46,17 @@ def basic_manifest_handler(ctx: HandlerContext, kobj: KnowledgeObject):
45
46
 
46
47
  if prev_bundle:
47
48
  if kobj.manifest.sha256_hash == prev_bundle.manifest.sha256_hash:
48
- logger.debug("Hash of incoming manifest is same as existing knowledge, ignoring")
49
+ log.debug("Hash of incoming manifest is same as existing knowledge, ignoring")
49
50
  return STOP_CHAIN
50
51
  if kobj.manifest.timestamp <= prev_bundle.manifest.timestamp:
51
- logger.debug("Timestamp of incoming manifest is the same or older than existing knowledge, ignoring")
52
+ log.debug("Timestamp of incoming manifest is the same or older than existing knowledge, ignoring")
52
53
  return STOP_CHAIN
53
54
 
54
- logger.debug("RID previously known to me, labeling as 'UPDATE'")
55
+ log.debug("RID previously known to me, labeling as 'UPDATE'")
55
56
  kobj.normalized_event_type = EventType.UPDATE
56
57
 
57
58
  else:
58
- logger.debug("RID previously unknown to me, labeling as 'NEW'")
59
+ log.debug("RID previously unknown to me, labeling as 'NEW'")
59
60
  kobj.normalized_event_type = EventType.NEW
60
61
 
61
62
  return kobj
@@ -78,7 +79,7 @@ def secure_profile_handler(ctx: HandlerContext, kobj: KnowledgeObject):
78
79
  node_rid: KoiNetNode = kobj.rid
79
80
 
80
81
  if sha256_hash(node_profile.public_key) != node_rid.hash:
81
- logger.warning(f"Public key hash mismatch for {node_rid!r}!")
82
+ log.warning(f"Public key hash mismatch for {node_rid!r}!")
82
83
  return STOP_CHAIN
83
84
 
84
85
  @KnowledgeHandler.create(
@@ -104,13 +105,13 @@ def edge_negotiation_handler(ctx: HandlerContext, kobj: KnowledgeObject):
104
105
  if edge_profile.status != EdgeStatus.PROPOSED:
105
106
  return
106
107
 
107
- logger.debug("Handling edge negotiation")
108
+ log.debug("Handling edge negotiation")
108
109
 
109
110
  peer_rid = edge_profile.target
110
111
  peer_bundle = ctx.cache.read(peer_rid)
111
112
 
112
113
  if not peer_bundle:
113
- logger.warning(f"Peer {peer_rid!r} unknown to me")
114
+ log.warning(f"Peer {peer_rid!r} unknown to me")
114
115
  return STOP_CHAIN
115
116
 
116
117
  peer_profile = peer_bundle.validate_contents(NodeProfile)
@@ -125,11 +126,11 @@ def edge_negotiation_handler(ctx: HandlerContext, kobj: KnowledgeObject):
125
126
  abort = False
126
127
  if (edge_profile.edge_type == EdgeType.WEBHOOK and
127
128
  peer_profile.node_type == NodeType.PARTIAL):
128
- logger.debug("Partial nodes cannot use webhooks")
129
+ log.debug("Partial nodes cannot use webhooks")
129
130
  abort = True
130
131
 
131
132
  if not set(edge_profile.rid_types).issubset(provided_events):
132
- logger.debug("Requested RID types not provided by this node")
133
+ log.debug("Requested RID types not provided by this node")
133
134
  abort = True
134
135
 
135
136
  if abort:
@@ -139,7 +140,7 @@ def edge_negotiation_handler(ctx: HandlerContext, kobj: KnowledgeObject):
139
140
 
140
141
  else:
141
142
  # approve edge profile
142
- logger.debug("Approving proposed edge")
143
+ log.debug("Approving proposed edge")
143
144
  edge_profile.status = EdgeStatus.APPROVED
144
145
  updated_bundle = Bundle.generate(kobj.rid, edge_profile.model_dump())
145
146
 
@@ -148,7 +149,7 @@ def edge_negotiation_handler(ctx: HandlerContext, kobj: KnowledgeObject):
148
149
 
149
150
  elif edge_profile.target == ctx.identity.rid:
150
151
  if edge_profile.status == EdgeStatus.APPROVED:
151
- logger.debug("Edge approved by other node!")
152
+ log.debug("Edge approved by other node!")
152
153
 
153
154
 
154
155
  # Network handlers
@@ -176,8 +177,8 @@ def node_contact_handler(ctx: HandlerContext, kobj: KnowledgeObject):
176
177
  if not available_rid_types:
177
178
  return
178
179
 
179
- logger.info("Identified a coordinator!")
180
- logger.info("Proposing new edge")
180
+ log.info("Identified a coordinator!")
181
+ log.info("Proposing new edge")
181
182
 
182
183
  # already have an edge established
183
184
  edge_rid = ctx.graph.get_edge(
@@ -217,7 +218,7 @@ def node_contact_handler(ctx: HandlerContext, kobj: KnowledgeObject):
217
218
  edge_bundle = Bundle.generate(edge_rid, edge_profile.model_dump())
218
219
  ctx.kobj_queue.put_kobj(bundle=edge_bundle)
219
220
 
220
- logger.info("Catching up on network state")
221
+ log.info("Catching up on network state")
221
222
 
222
223
  payload = ctx.request_handler.fetch_rids(
223
224
  node=kobj.rid,
@@ -225,16 +226,16 @@ def node_contact_handler(ctx: HandlerContext, kobj: KnowledgeObject):
225
226
  )
226
227
  for rid in payload.rids:
227
228
  if rid == ctx.identity.rid:
228
- logger.info("Skipping myself")
229
+ log.info("Skipping myself")
229
230
  continue
230
231
  if ctx.cache.exists(rid):
231
- logger.info(f"Skipping known RID {rid!r}")
232
+ log.info(f"Skipping known RID {rid!r}")
232
233
  continue
233
234
 
234
235
  # marked as external since we are handling RIDs from another node
235
236
  # will fetch remotely instead of checking local cache
236
237
  ctx.kobj_queue.put_kobj(rid=rid, source=kobj.rid)
237
- logger.info("Done")
238
+ log.info("Done")
238
239
 
239
240
 
240
241
  @KnowledgeHandler.create(HandlerType.Network)
@@ -260,12 +261,12 @@ def basic_network_output_filter(ctx: HandlerContext, kobj: KnowledgeObject):
260
261
  edge_profile = kobj.bundle.validate_contents(EdgeProfile)
261
262
 
262
263
  if edge_profile.source == ctx.identity.rid:
263
- logger.debug(f"Adding edge target '{edge_profile.target!r}' to network targets")
264
+ log.debug(f"Adding edge target '{edge_profile.target!r}' to network targets")
264
265
  kobj.network_targets.update([edge_profile.target])
265
266
  involves_me = True
266
267
 
267
268
  elif edge_profile.target == ctx.identity.rid:
268
- logger.debug(f"Adding edge source '{edge_profile.source!r}' to network targets")
269
+ log.debug(f"Adding edge source '{edge_profile.source!r}' to network targets")
269
270
  kobj.network_targets.update([edge_profile.source])
270
271
  involves_me = True
271
272
 
@@ -276,7 +277,7 @@ def basic_network_output_filter(ctx: HandlerContext, kobj: KnowledgeObject):
276
277
  allowed_type=type(kobj.rid)
277
278
  )
278
279
 
279
- logger.debug(f"Updating network targets with '{type(kobj.rid)}' subscribers: {subscribers}")
280
+ log.debug(f"Updating network targets with '{type(kobj.rid)}' subscribers: {subscribers}")
280
281
  kobj.network_targets.update(subscribers)
281
282
 
282
283
  return kobj
@@ -294,5 +295,5 @@ def forget_edge_on_node_deletion(ctx: HandlerContext, kobj: KnowledgeObject):
294
295
  edge_profile = edge_bundle.validate_contents(EdgeProfile)
295
296
 
296
297
  if kobj.rid in (edge_profile.source, edge_profile.target):
297
- logger.debug("Identified edge with forgotten node")
298
+ log.debug("Identified edge with forgotten node")
298
299
  ctx.kobj_queue.put_kobj(rid=edge_rid, event_type=EventType.FORGET)
@@ -1,4 +1,4 @@
1
- import logging
1
+ import structlog
2
2
  from queue import Queue
3
3
  from rid_lib.core import RID
4
4
  from rid_lib.ext import Bundle, Manifest
@@ -6,7 +6,7 @@ from rid_lib.types import KoiNetNode
6
6
  from ..protocol.event import Event, EventType
7
7
  from .knowledge_object import KnowledgeObject
8
8
 
9
- logger = logging.getLogger(__name__)
9
+ log = structlog.stdlib.get_logger()
10
10
 
11
11
 
12
12
  class KobjQueue:
@@ -48,4 +48,4 @@ class KobjQueue:
48
48
  raise ValueError("One of 'rid', 'manifest', 'bundle', 'event', or 'kobj' must be provided")
49
49
 
50
50
  self.q.put(_kobj)
51
- logger.debug(f"Queued {_kobj!r}")
51
+ log.debug(f"Queued {_kobj!r}")
@@ -1,38 +1,37 @@
1
1
  import queue
2
2
  import traceback
3
- import logging
3
+ import structlog
4
4
 
5
- from koi_net.models import END
6
- from koi_net.processor.knowledge_pipeline import KnowledgePipeline
7
- from koi_net.processor.kobj_queue import KobjQueue
8
- from koi_net.worker import ThreadWorker
5
+ from .pipeline import KnowledgePipeline
6
+ from .kobj_queue import KobjQueue
7
+ from koi_net.interfaces.worker import ThreadWorker, STOP_WORKER
9
8
 
10
- logger = logging.getLogger(__name__)
9
+ log = structlog.stdlib.get_logger()
11
10
 
12
11
 
13
12
  class KnowledgeProcessingWorker(ThreadWorker):
14
13
  def __init__(
15
14
  self,
16
15
  kobj_queue: KobjQueue,
17
- pipeline: KnowledgePipeline,
18
- timeout: float = 0.1
16
+ pipeline: KnowledgePipeline
19
17
  ):
20
18
  self.kobj_queue = kobj_queue
21
19
  self.pipeline = pipeline
22
- self.timeout = timeout
20
+ self.timeout: float = 0.1
21
+
23
22
  super().__init__()
24
23
 
25
24
  def run(self):
26
- logger.info("Started kobj worker")
25
+ log.info("Started kobj worker")
27
26
  while True:
28
27
  try:
29
28
  item = self.kobj_queue.q.get(timeout=self.timeout)
30
29
  try:
31
- if item is END:
32
- logger.info("Received 'END' signal, shutting down...")
30
+ if item is STOP_WORKER:
31
+ log.info("Received 'STOP_WORKER' signal, shutting down...")
33
32
  return
34
33
 
35
- logger.info(f"Dequeued {item!r}")
34
+ log.info(f"Dequeued {item!r}")
36
35
 
37
36
  self.pipeline.process(item)
38
37
  finally: