Commit Graph

2039 Commits (32b5210648d2c421ec384ed70cc17c5b7017d64c)

Author SHA1 Message Date
Guillermo Rodriguez 32b5210648
Important RingBuffBytesSender fix on non batched mode! & downgrade nix-shell python to lowest supported 2025-03-22 16:54:00 -03:00
Guillermo Rodriguez 0208a4728f
Catch trio cancellation on RingBuffReceiver bg eof listener task, add batched mode to RingBuffBytesSender 2025-03-22 16:39:43 -03:00
Guillermo Rodriguez 2d15b6bfb1
Add direct read method on EventFD
Type hint all ctx managers in _ringbuf.py
Remove unnecesary send lock on ring chan sender
Handle EOF on ring chan receiver
Rename ringbuf tests to make it less redundant
2025-03-22 16:39:43 -03:00
Guillermo Rodriguez 4523102869
Add direct ctx managers for RB channels 2025-03-22 16:39:43 -03:00
Guillermo Rodriguez 368e3ec34c
Improve test_ringbuf test, drop MsgTransport ring buf impl for now in favour of a trio.abc.Channel[bytes] impl, add docstrings 2025-03-22 16:39:43 -03:00
Guillermo Rodriguez 40ce518f1f
Switch `tractor.ipc.MsgTransport.stream` type to `trio.abc.Stream`
Add EOF signaling mechanism
Support proper `receive_some` end of stream semantics
Add StapledStream non-ipc test
Create MsgpackRBStream similar to MsgpackTCPStream for buffered whole-msg reads
Add EventFD.read cancellation on EventFD.close mechanism using cancel scope
Add test for eventfd cancellation
Improve and add docstrings
2025-03-22 16:39:43 -03:00
Guillermo Rodriguez 315e850598
Better encapsulate RingBuff ctx managment methods and support non ipc usage
Add trio.StrictFIFOLock on sender.send_all
Support max_bytes argument on receive_some, keep track of write_ptr on receiver
Add max_bytes receive test test_ringbuf_max_bytes
Add docstrings to all ringbuf tests
Remove EFD_NONBLOCK support, not necesary anymore since we can use abandon_on_cancel=True on trio.to_thread.run_sync
Close eventfd's after usage on open_ringbuf
2025-03-22 16:39:43 -03:00
Guillermo Rodriguez 3914db1c2a
Break out transport protocol and tcp specifics into their own submodules under tractor.ipc 2025-03-22 16:39:41 -03:00
Guillermo Rodriguez de45ad8829
Add buf_size to RBToken and add sender cancel test, move disable_mantracker to its own _mp_bs module 2025-03-22 16:39:01 -03:00
Guillermo Rodriguez 8adde29e39
Make ring buf api use pickle-able RBToken 2025-03-22 16:39:01 -03:00
Guillermo Rodriguez 36d35680f7
Address some of fomo\'s comments 2025-03-22 16:39:01 -03:00
Guillermo Rodriguez f552a3f8f5
Handle cancelation on EventFD.read 2025-03-22 16:39:01 -03:00
Guillermo Rodriguez f764abac58
Add module headers and fix spacing on tractor._ipc._linux 2025-03-22 16:39:01 -03:00
Guillermo Rodriguez 2f23c8ca15
Move RingBuffSender|Receiver to its own tractor.ipc._ringbuf module 2025-03-22 16:39:00 -03:00
Guillermo Rodriguez a85c26017e
Move linux specifics from tractor.ipc._shm into tractor.ipc._linux 2025-03-22 16:39:00 -03:00
Guillermo Rodriguez ff1f4fa805
Move tractor._shm to tractor.ipc._shm 2025-03-22 16:39:00 -03:00
Guillermo Rodriguez 5962c9fa0f
move tractor._ipc.py into tractor.ipc._chan.py 2025-03-22 16:39:00 -03:00
Guillermo Rodriguez 66c1d09ad4
General improvements
EventFD class now expects the fd to already be init with open_eventfd
RingBuff Sender and Receiver fully manage SharedMemory and EventFD lifecycles, no aditional ctx mngrs needed
Separate ring buf tests into its own test bed
Add parametrization to test and cancellation
Add docstrings
Add simple testing data gen module .samples
2025-03-22 16:39:00 -03:00
Guillermo Rodriguez 8c82a05f4b
IPC ring bug impl with async read 2025-03-22 16:38:51 -03:00
Tyler Goodlet caa76eb30d Updates from latest `piker.data._sharedmem` changes 2025-03-22 15:02:56 -04:00
Tyler Goodlet f09460e6d2 Add `numpy` for testing optional integrated shm API layer 2025-03-22 15:02:56 -04:00
Tyler Goodlet 8c29ce3724 Pass `str` dtype for `use_str` case 2025-03-22 15:02:56 -04:00
Tyler Goodlet e0430cb81c Allocate size-specced "empty" sequence from default values by type 2025-03-22 15:02:56 -04:00
Tyler Goodlet 2f4539720f Mod define `_USE_POSIX`, add a of of todos 2025-03-22 15:02:56 -04:00
Tyler Goodlet 917e6fa2b2 Parametrize rw test with variable frame sizes
Demonstrates fixed size frame-oriented reads by the child where the
parent only transmits a "read" stream msg on "frame fill events" such
that the child incrementally reads the shm list data (much like in
a real-time-buffered streaming system).
2025-03-22 15:02:56 -04:00
Tyler Goodlet 58cd01a0f2 Add `ShmList` slice support in `.__getitem__()` 2025-03-22 15:02:56 -04:00
Tyler Goodlet a69a89c540 Rename token type to `NDToken` in the style of `nptyping` 2025-03-22 15:02:56 -04:00
Tyler Goodlet eb8f562ee9 Don't require runtime (for now), type annot fixing 2025-03-22 15:02:56 -04:00
Tyler Goodlet 3ced3108c4 Add repetitive attach to existing segment test 2025-03-22 15:02:56 -04:00
Tyler Goodlet b9091b7caa Add initial readers-writer shm list tests 2025-03-22 15:02:56 -04:00
Tyler Goodlet c709a4ad72 Add `ShmList` wrapping the stdlib's `ShareableList`
First attempt at getting `multiprocessing.shared_memory.ShareableList`
working; we wrap the stdlib type with a readonly attr and a `.key` for
cross-actor lookup. Also, rename all `numpy` specific routines to have
a `ndarray` suffix in the func names.
2025-03-22 15:02:56 -04:00
Tyler Goodlet 25a333816f Initial module import from `piker.data._sharemem`
More or less a verbatim copy-paste minus some edgy variable naming and
internal `piker` module imports. There is a bunch of OHLC related
defaults that need to be dropped and we need to adjust to an optional
dependence on `numpy` by supporting shared lists as per the mp docs.
2025-03-22 15:02:56 -04:00
Tyler Goodlet 3d54885981 Continue supporting py3.11+
Apparently the only thing needing a guard was use of
`asyncio.Queue.shutdown()` and the paired `QueueShutDown` exception?

Cool.
2025-03-22 14:36:12 -04:00
Tyler Goodlet bd19942328 Bump up to `pytest>=8.3.5` to match "GH actions"
Ensure it's only for the `--dev` optional deps.
2025-03-22 14:36:12 -04:00
Tyler Goodlet 9919edc4bb Mask top level import of `.hilevel`
Since it isn't required until the landing of the new service-manager
stuff in #12; was an oversight
from commit `0607a31dddeba032a2cf7d9fe605edd9d7bb4846`.
2025-03-22 14:36:12 -04:00
Tyler Goodlet 888a3ae760 Add `.runtime()`-emit to `._invoke()` to report final result msg in the child 2025-03-22 14:36:12 -04:00
Tyler Goodlet 68d71c2df1 Add `MsgStream._stop_msg` use new `PldRx` API
In particular ensuring we use `ctx._pld_rx.recv_msg_nowait()` from
`.receive_nowait()` (which is called from `.aclose()`) such that we
ALWAYS (can) set the surrounding `Context._result/._outcome_msg` attrs
on reception of a final `Return`!!

This fixes a final stream-teardown-race-condition-bug where prior we
normally didn't set the `Context._result/._outcome_msg` in such cases.
This is **precisely because**  `.receive_nowait()` only returns the
`pld` and when called from `.aclose()` this value is discarded, meaning
so is its boxing `Return` despite consuming it from the underlying
`._rx_chan`..

Longer term this should be solved differently by ensuring such races
cases are handled at a higher scope like inside `Context._deliver_msg()`
or the `Portal.open_context()` enter/exit blocks? Add a detailed warning
note and todos for all this around the special case block!
2025-03-22 14:36:12 -04:00
Tyler Goodlet f0c5b6fb18 Add `Context._outcome_msg` use new `PldRx` API
Such that any `Return` is always capture for each ctx instance and set
in `._deliver_msg()` normally; ensures we can at least introspect for it
when missing (like in a recently discovered stream teardown race bug).
Yes this augments the already existing `._result` which is dedicated for
the `._outcome_msg.pld` in the non-error case; we might want to see if
there's a nicer way to directly proxy ref to that without getting the
pre-pld-decoded `Raw` form with `msgspec`?

Also use the new `ctx._pld_rx.recv_msg()` and drop assigning
`pld_rx._ctx`.
2025-03-22 14:36:12 -04:00
Tyler Goodlet 7d19c58373 Slight `PldRx` rework to simplify
Namely renaming and tweaking the `MsgType` receiving methods,
- `.recv_msg()` from what was `.recv_msg_w_pld()` which both receives
  the IPC msg from the underlying `._rx_chan` and then decodes its
  payload with `.decode_pld()`; it now also log reports on the different
  "stage of SC dialog protocol" msg types via a `match/case`.
- a new `.recv_msg_nowait()` sync equivalent of ^ (*was*
  `.recv_pld_nowait()`) who's use was the source of a recently
  discovered bug where any final `Return.pld` is being
  consumed-n-discarded by by `MsgStream.aclose()` depending on
  ctx/stream teardown race conditions..

Also,
- remove all the "instance persistent" ipc-ctx attrs, specifically the
  optional `_ipc`, `_ctx` and the `.wraps_ipc()` cm, since none of them
  were ever really needed/used; all methods which require
  a `Context/MsgStream` are explicitly always passed.
- update a buncha typing namely to use the more generic-styled
  `PayloadT` over `Any` and obviously `MsgType[PayloadT]`.
2025-03-22 14:36:12 -04:00
Tyler Goodlet 830be005ea Rename ext-types with `msgspec` suite module 2025-03-22 14:36:12 -04:00
Tyler Goodlet 5018284db2 Complete rename to parent->child IPC ctx peers
Now changed in all comments docs **and** test-code content such that we
aren't using the "caller"->"callee" semantics anymore.
2025-03-22 14:36:12 -04:00
Tyler Goodlet 0a56f62748 Mk `tests/__init__.py`, not sure where it went?
I must have had a local touched file but never committed or something?
Seems that new `pytest` requires a top level `tests` pkg in order for
relative `.conftest` imports to work.
2025-03-22 14:36:12 -04:00
Tyler Goodlet f999f8228a Fix msg-draining on `parent_never_opened_stream`!
Repairs a bug in `drain_to_final_msg()` where in the `Yield()` case
block we weren't guarding against the `ctx._stream is None` edge case
which should be treated a `continue`-draining (not a `break` or
attr-error!!) situation since the peer task maybe be continuing to send
`Yield` but has not yet sent an outcome msg (one of
`Return/Error/ContextCancelled`) to terminate the loop. Ensure we
explicitly warn about this case as well as `.cancel()` emit on a taskc.

Thanks again to @guille for discovering this!

Also add temporary `.info()`s around rxed `Return` msgs as part of
trying to debug a different bug discovered while updating the
context-semantics test suite (in a prior commit).
2025-03-22 14:36:12 -04:00
Tyler Goodlet 87e04c9311 Extend ctx semantics suite for streaming edge cases!
Muchas grax to @guilledk for finding the first issue which kicked of
this further scrutiny of the `tractor.Context` and `MsgStream` semantics
test suite with a strange edge case where,
- if the parent opened and immediately closed a stream while the remote
  child task started and continued (without terminating) to send msgs
  the parent's `open_context().__aexit__()` would **not block** on the
  child to complete!
=> this was seemingly due to a bug discovered inside the
  `.msg._ops.drain_to_final_msg()` stream handling case logic where we
  are NOT checking if `Context._stream` is non-`None`!

As such this,
- extends the `test_caller_closes_ctx_after_callee_opens_stream` (now
  renamed, see below) to include cases for all combinations of the child
  and parent sending before receiving on the stream as well as all
  placements of `Context.cancel()` in the parent before, around and after
  the stream open.
- uses the new `expect_ctxc()` for expecting the taskc (`trio.Task`
  cancelled)` cases.
- also extends the `test_callee_closes_ctx_after_stream_open` (also
  renamed) to include the case where the parent sends a msg before it
  receives.
=> this case has unveiled yet-another-bug where somehow the underlying
  `MsgStream._rx_chan: trio.ReceiveMemoryChannel` is allowing the
  child's `Return[None]` msg be consumed and NOT in a place where it is
  correctly set as `Context._result` resulting in the parent hanging
  forever inside `._ops.drain_to_final_msg()`..

Alongside,
- start renaming using the new "remote-task-peer-side" semantics
  throughout the test module: "caller" -> "parent", "callee" -> "child".
2025-03-22 14:36:12 -04:00
Tyler Goodlet e7cc91763c Deliver a `MaybeBoxedError` from `.expect_ctxc()`
Just like we do from the `.devx._debug.open_crash_handler()`, this
allows checking various attrs on the raised `ContextCancelled` much like
`with pytest.raises() as excinfo:`.
2025-03-22 14:36:12 -04:00
Tyler Goodlet 723a25b74d Support `ctx: UnionType` annots for `@tractor.context` eps 2025-03-22 14:36:12 -04:00
Tyler Goodlet 49ecdc4d73 Avoid attr-err when `._ipc_msg==None`
Seems this can happen in particular when we raise a `MessageTypeError`
on the sender side of a `Context`, since there isn't any msg relayed
from the other side (though i'm wondering if MTE should derive from RAE
then considering this case?).

Means `RemoteActorError.boxed_type = None` in such cases instead of
raising an attr-error for the `None.boxed_type_str`.
2025-03-22 14:36:12 -04:00
Tyler Goodlet defae151ec Facepalm, fix logic misstep on child side
Namely that `add_hooks: bool` should be the same as on the rent side..
Also, just drop the now unused `iter_maybe_sends`.

This makes the suite entire greeeeen btw, including the new sub-suite
which i hadn't runt before Bo
2025-03-22 14:36:12 -04:00
Tyler Goodlet c48d153375 Rework IPC-using `test_caps_basesd_msging` tests
Namely renaming and massively simplifying it to a new
`test_ext_types_over_ipc` which avoids all the wacky "parent dictates
what sender should be able to send beforehand"..

Instead keep it simple and just always try to send the same small set of
types over the wire with expect-logic to handle each case,

- use the new `dec_hook`/`ext_types` args to `mk_[co]dec()` routines for
  pld-spec ipc transport.
- always try to stream a small set of types from the child with logic to
  handle the cases expected to error.

Other,
- draft a `test_pld_limiting_usage` to check runtime raising of bad API
  usage; haven't run it yet tho.
- move `test_custom_extension_types` to top of mod so that the
  `enc/dec_nsp()` hooks can be reffed from test parametrizations.
- comment out (and maybe remove) the old routines for
  `iter_maybe_sends`, `test_limit_msgspec`, `chk_pld_type`.

XXX TODO, turns out the 2 failing cases from this suite have exposed an
an actual bug with `MsgTypeError` unpacking where the `ipc_msg=` input
is being set to `None` ?? -> see the comment at the bottom of
`._exceptions._mk_recv_mte()` which seems to describe the likely
culprit?
2025-03-22 14:36:12 -04:00
Tyler Goodlet 123683d442 Raise RTE from `limit_plds()` on no `curr_ctx`
Since it should only be used from within a `Portal.open_context()`
scope, make sure the caller knows that!

Also don't hide the frame in tb if the immediate function errors..
2025-03-22 14:36:12 -04:00