Repository: ALU-Schumacher/AUDITOR (language: rust)

Issue:
RUSTSEC-2024-0399: rustls network-reachable panic in `Acceptor::accept`

> rustls network-reachable panic in `Acceptor::accept`

| Details             |                                                |
| ------------------- | ---------------------------------------------- |
| Package             | `rustls`                      |
| Version             | `0.23.16`                   |
| URL                 | [https://github.com/rustls/rustls/issues/2227](https://github.com/rustls/rustls/issues/2227) |
| Date                | 2024-11-22                         |
| Patched versions    | `>=0.23.18`                  |
| Unaffected versions | `>=0.23, <0.23.13,<0.23`               |

A bug introduced in rustls 0.23.13 leads to a panic if the received
TLS ClientHello is fragmented.  Only servers that use
`rustls::server::Acceptor::accept()` are affected.

Servers that use `tokio-rustls`&#39;s `LazyConfigAcceptor` API are affected.

Servers that use `tokio-rustls`&#39;s `TlsAcceptor` API are not affected.

Servers that use `rustls-ffi`&#39;s `rustls_acceptor_accept` API are affected.

See [advisory page](https://rustsec.org/advisories/RUSTSEC-2024-0399.html) for additional details.



Discussion / hints:

Fix patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 4b8e7c16c..c9b2dc5dd 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -10,13 +10,17 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
 - pyauditor + Apel plugin + HTCondor collector: drop support for Python 3.8 ([@dirksammel](https://github.com/dirksammel))
 
 ### Security
+- [RUSTSEC-2024-0363]: Update sqlx from 0.7.4 to 0.8.2 (missed some occurrences) ([@dirksammel](https://github.com/dirksammel))
+- [RUSTSEC-2024-0399]: Update rustls from 0.23.16 to 0.23.19 ([@dirksammel](https://github.com/dirksammel))
 
 ### Added
 - CI: Add workflow to test publishing to the PyPI test repo ([@dirksammel](https://github.com/dirksammel))
 
 ### Changed
 - Auditor Docker container: Switch from fixed to latest Rust version ([@dirksammel](https://github.com/dirksammel))
+- Dependencies: Switch from pyo3-asyncio 0.20.0 to pyo3-async-runtimes 0.22.0 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update crate-ci/typos from 1.26.8 to 1.27.3 ([@dirksammel](https://github.com/dirksammel))
+- Dependencies: Update pyo3 from 0.20.3 to 0.22.5 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update ruff from 0.7.1 to 0.7.3 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update setuptools from 75.3.0 to 75.4.0 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update sqlx from 0.7.4 to 0.8.2 (missed some occurrences) ([@dirksammel](https://github.com/dirksammel))
@@ -38,7 +42,6 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
 - CI: Add checks for import sorting and formatting to python linting workflow ([@dirksammel](https://github.com/dirksammel))
 
 ### Changed
-- Dependencies: Update sqlx from 0.7.4 to 0.8.2 ([@raghuvar-vijay](https://github.com/raghuvar-vijay))
 - Dependencies: Update black from 24.4.2 to 24.10.0 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update build from 1.2.1 to 1.2.2.post1 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update crate-ci/typos from 1.23.3 to 1.26.8 ([@dirksammel](https://github.com/dirksammel))
@@ -55,6 +58,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
 - Dependencies: Update serde_json from 1.0.121 to 1.0.132 ([@raghuvar-vijay](https://github.com/raghuvar-vijay))
 - Dependencies: Update setuptools from 71.1.0 to 75.3.0 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update shalzz/zola-deploy-action from 0.19.1 to 0.19.2 ([@dirksammel](https://github.com/dirksammel))
+- Dependencies: Update sqlx from 0.7.4 to 0.8.2 ([@raghuvar-vijay](https://github.com/raghuvar-vijay))
 - Dependencies: Update tarides/changelog-check-action from 2 to 3 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update types-pyyaml from 6.0.12.20240311 to 6.0.12.20240917 ([@dirksammel](https://github.com/dirksammel))
 - Dependencies: Update types-requests from 2.32.0.20240712 to 2.32.0.20241016 ([@dirksammel](https://github.com/dirksammel))
diff --git a/Cargo.lock b/Cargo.lock
index dbaa4f698..0c19dc56f 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -361,7 +361,6 @@ dependencies = [
  "once_cell",
  "opentelemetry 0.23.0",
  "opentelemetry-prometheus 0.16.0",
- "opentelemetry_api",
  "opentelemetry_sdk 0.23.0",
  "prometheus",
  "quickcheck",
@@ -434,7 +433,6 @@ dependencies = [
  "num-traits",
  "opentelemetry 0.23.0",
  "opentelemetry-prometheus 0.16.0",
- "opentelemetry_api",
  "opentelemetry_sdk 0.23.0",
  "prometheus",
  "serde",
@@ -2053,22 +2051,6 @@ version = "0.14.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f9ab5bd6c42fb9349dcf28af2ba9a0667f697f9bdcca045d39f2cec5543e2910"
 
-[[package]]
-name = "opentelemetry_api"
-version = "0.20.0"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "8a81f725323db1b1206ca3da8bb19874bbd3f57c3bcd59471bfb04525b265b9b"
-dependencies = [
- "futures-channel",
- "futures-util",
- "indexmap 1.9.3",
- "js-sys",
- "once_cell",
- "pin-project-lite",
- "thiserror",
- "urlencoding",
-]
-
 [[package]]
 name = "opentelemetry_sdk"
 version = "0.22.1"
@@ -2815,9 +2797,9 @@ dependencies = [
 
 [[package]]
 name = "rustls"
-version = "0.23.16"
+version = "0.23.19"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "eee87ff5d9b36712a58574e12e9f0ea80f915a5b0ac518d322b24a465617925e"
+checksum = "934b404430bb06b3fae2cba809eb45a1ab1aecd64491213d7c3301b88393f8d1"
 dependencies = [
  "once_cell",
  "ring",
diff --git a/Cargo.toml b/Cargo.toml
index 28a948228..b3538802b 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -29,8 +29,8 @@ opentelemetry = "0.23.0"
 opentelemetry-prometheus = "0.16.0"
 opentelemetry_sdk = "0.23.0"
 prometheus = "0.13.4"
-pyo3 = { version = "0.20.3", features = ["chrono", "extension-module", "anyhow"] }
-pyo3-asyncio = { version = "0.20.0", features = ["attributes", "tokio-runtime"] }
+pyo3 = { version = "0.22.5", features = ["chrono", "extension-module", "anyhow"] }
+pyo3-async-runtimes = { version = "0.22.0", features = ["attributes", "tokio-runtime"] }
 quickcheck = "1.0.3"
 quickcheck_macros = "1.0.0"
 rand = "0.8.5"
diff --git a/auditor-client/src/lib.rs b/auditor-client/src/lib.rs
index 47e4f2033..26a136fdc 100644
--- a/auditor-client/src/lib.rs
+++ b/auditor-client/src/lib.rs
@@ -892,7 +892,7 @@ impl Operator {
     }
 }
 
-/// Implementations of conversion traits for the `Value` enum.
+// Implementations of conversion traits for the `Value` enum.
 
 /// Conversion from chrono DateTime to Value::Datetime.
 impl From<chrono::DateTime<Utc>> for Value {
diff --git a/pyauditor/Cargo.toml b/pyauditor/Cargo.toml
index 2aa25fd8a..109856976 100644
--- a/pyauditor/Cargo.toml
+++ b/pyauditor/Cargo.toml
@@ -29,8 +29,8 @@ anyhow.workspace = true
 auditor-client.workspace = true
 auditor.workspace = true
 chrono.workspace = true
-pyo3-asyncio.workspace = true
 pyo3.workspace = true
+pyo3-async-runtimes.workspace = true
 serde.workspace = true
 serde_json.workspace = true
 tokio.workspace = true
diff --git a/pyauditor/src/blocking_client.rs b/pyauditor/src/blocking_client.rs
index 925dff18a..8029b543a 100644
--- a/pyauditor/src/blocking_client.rs
+++ b/pyauditor/src/blocking_client.rs
@@ -62,7 +62,10 @@ impl AuditorClientBlocking {
     ///
     ///     records = client.get_stopped_since(start_since)
     ///
-    fn get_started_since(self_: PyRef<'_, Self>, timestamp: &PyDateTime) -> PyResult<Vec<Record>> {
+    fn get_started_since(
+        self_: PyRef<'_, Self>,
+        timestamp: &Bound<'_, PyDateTime>,
+    ) -> PyResult<Vec<Record>> {
         let since: DateTime<Utc> = timestamp.extract()?;
         let query_string = auditor_client::QueryBuilder::new()
             .with_start_time(auditor_client::Operator::default().gte(since.into()))
@@ -99,7 +102,10 @@ impl AuditorClientBlocking {
     ///
     ///     records = client.get_stopped_since(stop_since)
     ///
-    fn get_stopped_since(self_: PyRef<'_, Self>, timestamp: &PyDateTime) -> PyResult<Vec<Record>> {
+    fn get_stopped_since(
+        self_: PyRef<'_, Self>,
+        timestamp: &Bound<'_, PyDateTime>,
+    ) -> PyResult<Vec<Record>> {
         let since: DateTime<Utc> = timestamp.extract()?;
         let query_string = auditor_client::QueryBuilder::new()
             .with_stop_time(auditor_client::Operator::default().gte(since.into()))
diff --git a/pyauditor/src/builder.rs b/pyauditor/src/builder.rs
index e58d684d7..c6bf0ca23 100644
--- a/pyauditor/src/builder.rs
+++ b/pyauditor/src/builder.rs
@@ -124,11 +124,11 @@ impl AuditorClientBuilder {
     }
 
     /// Build a ``QueuedAuditorClient`` from ``AuditorClientBuilder``
-    pub fn build_queued<'a>(&'a self, py: Python<'a>) -> PyResult<&'a PyAny> {
+    pub fn build_queued<'a>(&'a self, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         // Must clone here because `build` moves the builder, but python
         // does not allow that. Doesn't matter, Python is slow anyways.
         let builder = self.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(QueuedAuditorClient {
                 inner: builder
                     .build_queued()
diff --git a/pyauditor/src/client.rs b/pyauditor/src/client.rs
index 3567035c5..c992a33d2 100644
--- a/pyauditor/src/client.rs
+++ b/pyauditor/src/client.rs
@@ -58,7 +58,7 @@ impl Value {
     ///
     ///     value = Value.set_datetime(start_time)
     #[staticmethod]
-    fn set_datetime(datetime: &PyDateTime) -> Result<Self, Error> {
+    fn set_datetime(datetime: &Bound<'_, PyDateTime>) -> Result<Self, Error> {
         let date_time: DateTime<Utc> = datetime.extract()?;
         Ok(Value {
             inner: auditor_client::Value::Datetime(auditor_client::DateTimeUtcWrapper(date_time)),
@@ -606,9 +606,9 @@ pub struct AuditorClient {
 impl AuditorClient {
     /// health_check()
     /// Returns ``true`` if the Auditor instance is healthy, ``false`` otherwise
-    fn health_check<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn health_check<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner.health_check().await)
             // Ok(Python::with_gil(|py| py.None()))
         })
@@ -616,9 +616,9 @@ impl AuditorClient {
 
     /// get()
     /// Gets all records from the Auditors database
-    fn get<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn get<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .get()
                 .await
@@ -654,11 +654,11 @@ impl AuditorClient {
     ///
     fn get_started_since<'a>(
         self_: PyRef<'a, Self>,
-        timestamp: &PyDateTime,
+        timestamp: &Bound<'_, PyDateTime>,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
-        let message = py.get_type::<pyo3::exceptions::PyDeprecationWarning>();
-        PyErr::warn(py, message, "get_started_since is depreciated", 0)?;
+    ) -> PyResult<Bound<'a, PyAny>> {
+        let message = py.get_type_bound::<pyo3::exceptions::PyDeprecationWarning>();
+        PyErr::warn_bound(py, &message, "get_started_since is depreciated", 0)?;
 
         let since: DateTime<Utc> = timestamp.extract()?;
         let inner = self_.inner.clone();
@@ -666,7 +666,7 @@ impl AuditorClient {
             .with_start_time(auditor_client::Operator::default().gte(since.into()))
             .build();
 
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .advanced_query(query_string.to_string())
                 .await
@@ -702,18 +702,18 @@ impl AuditorClient {
     ///
     fn get_stopped_since<'a>(
         self_: PyRef<'a, Self>,
-        timestamp: &PyDateTime,
+        timestamp: &Bound<'_, PyDateTime>,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
-        let message = py.get_type::<pyo3::exceptions::PyDeprecationWarning>();
-        PyErr::warn(py, message, "get_stopped_since_since is depreciated", 0)?;
+    ) -> PyResult<Bound<'a, PyAny>> {
+        let message = py.get_type_bound::<pyo3::exceptions::PyDeprecationWarning>();
+        PyErr::warn_bound(py, &message, "get_stopped_since_since is depreciated", 0)?;
 
         let since: DateTime<Utc> = timestamp.extract()?;
         let inner = self_.inner.clone();
         let query_string = auditor_client::QueryBuilder::new()
             .with_stop_time(auditor_client::Operator::default().gte(since.into()))
             .build();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .advanced_query(query_string.to_string())
                 .await
@@ -744,9 +744,9 @@ impl AuditorClient {
         self_: PyRef<'a, Self>,
         query_string: String,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
+    ) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .advanced_query(query_string)
                 .await
@@ -773,9 +773,9 @@ impl AuditorClient {
         self_: PyRef<'a, Self>,
         record_id: String,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
+    ) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             inner
                 .get_single_record(record_id)
                 .await
@@ -786,9 +786,9 @@ impl AuditorClient {
 
     /// add(record: Record)
     /// Push a record to the Auditor instance
-    fn add<'a>(&self, record: Record, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn add<'a>(&self, record: Record, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             inner
                 .add(&auditor::domain::RecordAdd::try_from(record.inner)?)
                 .await
@@ -798,7 +798,7 @@ impl AuditorClient {
 
     /// add(record: Record)
     /// Push a list of records to the Auditor instance
-    fn bulk_insert<'a>(&self, records: Vec<Record>, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn bulk_insert<'a>(&self, records: Vec<Record>, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self.inner.clone();
 
         let bulk_insert_records: Result<Vec<auditor::domain::RecordAdd>, anyhow::Error> = records
@@ -806,7 +806,7 @@ impl AuditorClient {
             .map(|r| auditor::domain::RecordAdd::try_from(r.inner))
             .collect();
 
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             let bul = bulk_insert_records?;
             inner
                 .bulk_insert(&bul)
@@ -817,9 +817,9 @@ impl AuditorClient {
 
     /// update(record: Record)
     /// Update an existing record in the Auditor instance
-    fn update<'a>(&self, record: Record, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn update<'a>(&self, record: Record, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             inner
                 .update(&auditor::domain::RecordUpdate::try_from(record.inner)?)
                 .await
diff --git a/pyauditor/src/domain/record.rs b/pyauditor/src/domain/record.rs
index 59e7fc5d6..9568462dc 100644
--- a/pyauditor/src/domain/record.rs
+++ b/pyauditor/src/domain/record.rs
@@ -56,7 +56,7 @@ pub struct Record {
 #[pymethods]
 impl Record {
     #[new]
-    fn new(record_id: String, start_time: &PyDateTime) -> Result<Self, Error> {
+    fn new(record_id: String, start_time: &Bound<'_, PyDateTime>) -> Result<Self, Error> {
         let start_time: DateTime<Utc> = start_time.extract()?;
         Ok(Record {
             inner: auditor::domain::Record {
@@ -106,7 +106,7 @@ impl Record {
     /// :type stop_time: datetime.datetime
     fn with_stop_time<'a>(
         mut self_: PyRefMut<'a, Self>,
-        stop_time: &'a PyDateTime,
+        stop_time: &Bound<'a, PyDateTime>,
     ) -> Result<PyRefMut<'a, Self>, Error> {
         let stop_time: DateTime<Utc> = stop_time.extract()?;
         self_.inner.stop_time = Some(stop_time);
diff --git a/pyauditor/src/lib.rs b/pyauditor/src/lib.rs
index 9d69367fc..ac8647553 100644
--- a/pyauditor/src/lib.rs
+++ b/pyauditor/src/lib.rs
@@ -17,7 +17,7 @@ mod queued_client;
 
 /// pyauditor is a client for interacting with an Auditor instance via Python.
 #[pymodule]
-fn pyauditor(_py: Python, m: &PyModule) -> PyResult<()> {
+fn pyauditor(_py: Python, m: &Bound<'_, PyModule>) -> PyResult<()> {
     m.add_class::<crate::builder::AuditorClientBuilder>()?;
     m.add_class::<crate::client::AuditorClient>()?;
     m.add_class::<crate::client::Value>()?;
diff --git a/pyauditor/src/queued_client.rs b/pyauditor/src/queued_client.rs
index 30976b312..5ded4ef64 100644
--- a/pyauditor/src/queued_client.rs
+++ b/pyauditor/src/queued_client.rs
@@ -40,9 +40,9 @@ pub struct QueuedAuditorClient {
 impl QueuedAuditorClient {
     /// health_check()
     /// Returns ``true`` if the Auditor instance is healthy, ``false`` otherwise
-    fn health_check<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn health_check<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner.health_check().await)
             // Ok(Python::with_gil(|py| py.None()))
         })
@@ -50,9 +50,9 @@ impl QueuedAuditorClient {
 
     /// get()
     /// Gets all records from the Auditors database
-    fn get<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn get<'a>(self_: PyRef<'a, Self>, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .get()
                 .await
@@ -88,11 +88,11 @@ impl QueuedAuditorClient {
     ///
     fn get_started_since<'a>(
         self_: PyRef<'a, Self>,
-        timestamp: &PyDateTime,
+        timestamp: &Bound<'_, PyDateTime>,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
-        let message = py.get_type::<pyo3::exceptions::PyDeprecationWarning>();
-        PyErr::warn(py, message, "get_started_since is depreciated", 0)?;
+    ) -> PyResult<Bound<'a, PyAny>> {
+        let message = py.get_type_bound::<pyo3::exceptions::PyDeprecationWarning>();
+        PyErr::warn_bound(py, &message, "get_started_since is depreciated", 0)?;
 
         let since: DateTime<Utc> = timestamp.extract()?;
         let inner = self_.inner.clone();
@@ -100,7 +100,7 @@ impl QueuedAuditorClient {
             .with_start_time(auditor_client::Operator::default().gte(since.into()))
             .build();
 
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .advanced_query(query_string.to_string())
                 .await
@@ -136,18 +136,18 @@ impl QueuedAuditorClient {
     ///
     fn get_stopped_since<'a>(
         self_: PyRef<'a, Self>,
-        timestamp: &PyDateTime,
+        timestamp: &Bound<'_, PyDateTime>,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
-        let message = py.get_type::<pyo3::exceptions::PyDeprecationWarning>();
-        PyErr::warn(py, message, "get_stopped_since_since is depreciated", 0)?;
+    ) -> PyResult<Bound<'a, PyAny>> {
+        let message = py.get_type_bound::<pyo3::exceptions::PyDeprecationWarning>();
+        PyErr::warn_bound(py, &message, "get_stopped_since_since is depreciated", 0)?;
 
         let since: DateTime<Utc> = timestamp.extract()?;
         let inner = self_.inner.clone();
         let query_string = auditor_client::QueryBuilder::new()
             .with_stop_time(auditor_client::Operator::default().gte(since.into()))
             .build();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .advanced_query(query_string.to_string())
                 .await
@@ -178,9 +178,9 @@ impl QueuedAuditorClient {
         self_: PyRef<'a, Self>,
         query_string: String,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
+    ) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             Ok(inner
                 .advanced_query(query_string)
                 .await
@@ -207,9 +207,9 @@ impl QueuedAuditorClient {
         self_: PyRef<'a, Self>,
         record_id: String,
         py: Python<'a>,
-    ) -> PyResult<&'a PyAny> {
+    ) -> PyResult<Bound<'a, PyAny>> {
         let inner = self_.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             inner
                 .get_single_record(record_id)
                 .await
@@ -220,9 +220,9 @@ impl QueuedAuditorClient {
 
     /// add(record: Record)
     /// Push a record to the Auditor instance
-    fn add<'a>(&self, record: Record, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn add<'a>(&self, record: Record, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             inner
                 .add(&auditor::domain::RecordAdd::try_from(record.inner)?)
                 .await
@@ -232,7 +232,7 @@ impl QueuedAuditorClient {
 
     /// add(record: Record)
     /// Push a list of records to the Auditor instance
-    fn bulk_insert<'a>(&self, records: Vec<Record>, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn bulk_insert<'a>(&self, records: Vec<Record>, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self.inner.clone();
 
         let bulk_insert_records: Result<Vec<auditor::domain::RecordAdd>, anyhow::Error> = records
@@ -240,7 +240,7 @@ impl QueuedAuditorClient {
             .map(|r| auditor::domain::RecordAdd::try_from(r.inner))
             .collect();
 
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             let bul = bulk_insert_records?;
             inner
                 .bulk_insert(&bul)
@@ -251,9 +251,9 @@ impl QueuedAuditorClient {
 
     /// update(record: Record)
     /// Update an existing record in the Auditor instance
-    fn update<'a>(&self, record: Record, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn update<'a>(&self, record: Record, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let inner = self.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             inner
                 .update(&auditor::domain::RecordUpdate::try_from(record.inner)?)
                 .await
@@ -262,9 +262,9 @@ impl QueuedAuditorClient {
     }
 
     /// Stops the background sync task
-    fn stop<'a>(&self, py: Python<'a>) -> PyResult<&'a PyAny> {
+    fn stop<'a>(&self, py: Python<'a>) -> PyResult<Bound<'a, PyAny>> {
         let mut inner = self.inner.clone();
-        pyo3_asyncio::tokio::future_into_py(py, async move {
+        pyo3_async_runtimes::tokio::future_into_py(py, async move {
             inner
                 .stop()
                 .await


Test patch: