This is an automated email from the ASF dual-hosted git repository.

xuanwo pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/incubator-opendal.git


The following commit(s) were added to refs/heads/main by this push:
     new 1aa43a9dc docs: Add comments for blocking layer (#3117)
1aa43a9dc is described below

commit 1aa43a9dc7063630ab71e9837f2417b48301e99f
Author: Xuanwo <[email protected]>
AuthorDate: Mon Sep 18 20:31:37 2023 +0800

    docs: Add comments for blocking layer (#3117)
    
    * Format code
    
    Signed-off-by: Xuanwo <[email protected]>
    
    * Update opendal.h
    
    Signed-off-by: Xuanwo <[email protected]>
    
    ---------
    
    Signed-off-by: Xuanwo <[email protected]>
---
 bindings/c/include/opendal.h                 |  35 ++++++++-
 bindings/java/src/lib.rs                     |   6 +-
 bindings/java/src/operator.rs                |   3 +-
 core/src/layers/blocking.rs                  | 109 ++++++++++++++++++++++++++-
 core/src/services/atomicserver/backend.rs    |   9 +--
 core/src/types/operator/blocking_operator.rs |  35 ++++++++-
 core/tests/behavior/blocking_append.rs       |   4 +-
 7 files changed, 186 insertions(+), 15 deletions(-)

diff --git a/bindings/c/include/opendal.h b/bindings/c/include/opendal.h
index bc47bf5b5..95c0be52d 100644
--- a/bindings/c/include/opendal.h
+++ b/bindings/c/include/opendal.h
@@ -96,6 +96,8 @@ typedef struct BlockingLister BlockingLister;
  *
  * # Examples
  *
+ * ## Init backends
+ *
  * Read more backend init examples in [`services`]
  *
  * ```
@@ -103,8 +105,8 @@ typedef struct BlockingLister BlockingLister;
  * use opendal::services::Fs;
  * use opendal::BlockingOperator;
  * use opendal::Operator;
- * #[tokio::main]
- * async fn main() -> Result<()> {
+ *
+ * fn main() -> Result<()> {
  *     // Create fs backend builder.
  *     let mut builder = Fs::default();
  *     // Set the root for fs, all operations will happen under this root.
@@ -118,6 +120,35 @@ typedef struct BlockingLister BlockingLister;
  *     Ok(())
  * }
  * ```
+ *
+ * ## Init backends with blocking layer
+ *
+ * Some services like s3, gcs doesn't have native blocking supports, we can 
use [`layers::BlockingLayer`]
+ * to wrap the async operator to make it blocking.
+ *
+ * ```rust
+ * # use anyhow::Result;
+ * use opendal::layers::BlockingLayer;
+ * use opendal::services::S3;
+ * use opendal::BlockingOperator;
+ * use opendal::Operator;
+ *
+ * #[tokio::main]
+ * async fn main() -> Result<()> {
+ *     // Create fs backend builder.
+ *     let mut builder = S3::default();
+ *     builder.bucket("test");
+ *     builder.region("us-east-1");
+ *
+ *     // Build an `BlockingOperator` with blocking layer to start operating 
the storage.
+ *     let _: BlockingOperator = Operator::new(builder)?
+ *         .layer(BlockingLayer::create()?)
+ *         .finish()
+ *         .blocking();
+ *
+ *     Ok(())
+ * }
+ * ```
  */
 typedef struct BlockingOperator BlockingOperator;
 
diff --git a/bindings/java/src/lib.rs b/bindings/java/src/lib.rs
index e1703b527..353855d4c 100644
--- a/bindings/java/src/lib.rs
+++ b/bindings/java/src/lib.rs
@@ -19,10 +19,10 @@ use std::cell::RefCell;
 use std::collections::HashMap;
 use std::ffi::c_void;
 
-use crate::error::Error;
+use jni::objects::JMap;
 use jni::objects::JObject;
 use jni::objects::JString;
-use jni::objects::{JMap, JValue};
+use jni::objects::JValue;
 use jni::sys::jint;
 use jni::sys::JNI_VERSION_1_8;
 use jni::JNIEnv;
@@ -32,6 +32,8 @@ use opendal::raw::PresignedRequest;
 use tokio::runtime::Builder;
 use tokio::runtime::Runtime;
 
+use crate::error::Error;
+
 mod blocking_operator;
 mod error;
 mod metadata;
diff --git a/bindings/java/src/operator.rs b/bindings/java/src/operator.rs
index f18a3cb0a..6787810f0 100644
--- a/bindings/java/src/operator.rs
+++ b/bindings/java/src/operator.rs
@@ -31,10 +31,11 @@ use opendal::raw::PresignedRequest;
 use opendal::Operator;
 use opendal::Scheme;
 
+use crate::get_current_env;
 use crate::get_global_runtime;
 use crate::jmap_to_hashmap;
+use crate::make_presigned_request;
 use crate::Result;
-use crate::{get_current_env, make_presigned_request};
 
 #[no_mangle]
 pub extern "system" fn Java_org_apache_opendal_Operator_constructor(
diff --git a/core/src/layers/blocking.rs b/core/src/layers/blocking.rs
index 701191490..9fbf7c006 100644
--- a/core/src/layers/blocking.rs
+++ b/core/src/layers/blocking.rs
@@ -29,7 +29,114 @@ use crate::*;
 ///
 /// # Notes
 ///
-/// Please only enable this layer when the underlying service does not support 
blocking.
+/// - Please only enable this layer when the underlying service does not 
support blocking.
+///
+/// # Examples
+///
+/// ## In async context
+///
+/// BlockingLayer will use current async context's runtime to handle the async 
calls.
+///
+/// ```rust
+/// # use anyhow::Result;
+/// use opendal::layers::BlockingLayer;
+/// use opendal::services::S3;
+/// use opendal::BlockingOperator;
+/// use opendal::Operator;
+///
+/// #[tokio::main]
+/// async fn main() -> Result<()> {
+///     // Create fs backend builder.
+///     let mut builder = S3::default();
+///     builder.bucket("test");
+///     builder.region("us-east-1");
+///
+///     // Build an `BlockingOperator` with blocking layer to start operating 
the storage.
+///     let _: BlockingOperator = Operator::new(builder)?
+///         .layer(BlockingLayer::create()?)
+///         .finish()
+///         .blocking();
+///
+///     Ok(())
+/// }
+/// ```
+///
+/// ## In async context with blocking functions
+///
+/// If `BlockingLayer` is called in blocking function, please fetch a 
[`tokio::runtime::EnterGuard`]
+/// first. You can use [`Handle::try_current`] first to get the handle and 
than call [`Handle::enter`].
+/// This often happens in the case that async function calls blocking function.
+///
+/// ```rust
+/// use opendal::layers::BlockingLayer;
+/// use opendal::services::S3;
+/// use opendal::BlockingOperator;
+/// use opendal::Operator;
+/// use opendal::Result;
+///
+/// #[tokio::main]
+/// async fn main() -> Result<()> {
+///     let _ = blocking_fn()?;
+///     Ok(())
+/// }
+///
+/// fn blocking_fn() -> Result<BlockingOperator> {
+///     // Create fs backend builder.
+///     let mut builder = S3::default();
+///     builder.bucket("test");
+///     builder.region("us-east-1");
+///
+///     let handle = tokio::runtime::Handle::try_current().unwrap();
+///     let _guard = handle.enter();
+///     // Build an `BlockingOperator` with blocking layer to start operating 
the storage.
+///     let op: BlockingOperator = Operator::new(builder)?
+///         .layer(BlockingLayer::create()?)
+///         .finish()
+///         .blocking();
+///     Ok(op)
+/// }
+/// ```
+///
+/// ## In blocking context
+///
+/// In a pure blocking context, we can create a runtime and use it to create 
the `BlockingLayer`.
+///
+/// > The following code uses a global statically created runtime as an 
example, please manage the
+/// runtime on demand.
+///
+/// ```rust
+/// use once_cell::sync::Lazy;
+/// use opendal::layers::BlockingLayer;
+/// use opendal::services::S3;
+/// use opendal::BlockingOperator;
+/// use opendal::Operator;
+/// use opendal::Result;
+///
+/// static RUNTIME: Lazy<tokio::runtime::Runtime> = Lazy::new(|| {
+///     tokio::runtime::Builder::new_multi_thread()
+///         .enable_all()
+///         .build()
+///         .unwrap()
+/// });
+/// ///
+///
+/// fn main() -> Result<()> {
+///     // Create fs backend builder.
+///     let mut builder = S3::default();
+///     builder.bucket("test");
+///     builder.region("us-east-1");
+///
+///     // Fetch the `EnterGuard` from global runtime.
+///     let _guard = RUNTIME.enter();
+///     // Build an `BlockingOperator` with blocking layer to start operating 
the storage.
+///     let _: BlockingOperator = Operator::new(builder)?
+///         .layer(BlockingLayer::create()?)
+///         .finish()
+///         .blocking();
+///
+///     Ok(())
+/// }
+/// ```
 #[derive(Debug, Clone)]
 pub struct BlockingLayer {
     handle: Handle,
diff --git a/core/src/services/atomicserver/backend.rs 
b/core/src/services/atomicserver/backend.rs
index 24893b270..80146af1d 100644
--- a/core/src/services/atomicserver/backend.rs
+++ b/core/src/services/atomicserver/backend.rs
@@ -15,22 +15,21 @@
 // specific language governing permissions and limitations
 // under the License.
 
-use bytes::Bytes;
 use std::collections::HashMap;
 use std::fmt::Debug;
 use std::fmt::Formatter;
 
 use async_trait::async_trait;
+use atomic_lib::agents::Agent;
+use atomic_lib::client::get_authentication_headers;
+use atomic_lib::commit::sign_message;
+use bytes::Bytes;
 use http::header::CONTENT_DISPOSITION;
 use http::header::CONTENT_TYPE;
 use http::Request;
 use serde::Deserialize;
 use serde::Serialize;
 
-use atomic_lib::agents::Agent;
-use atomic_lib::client::get_authentication_headers;
-use atomic_lib::commit::sign_message;
-
 use crate::raw::adapters::kv;
 use crate::raw::new_json_deserialize_error;
 use crate::raw::new_json_serialize_error;
diff --git a/core/src/types/operator/blocking_operator.rs 
b/core/src/types/operator/blocking_operator.rs
index 1dea4b622..3dfa0d121 100644
--- a/core/src/types/operator/blocking_operator.rs
+++ b/core/src/types/operator/blocking_operator.rs
@@ -30,6 +30,8 @@ use crate::*;
 ///
 /// # Examples
 ///
+/// ## Init backends
+///
 /// Read more backend init examples in [`services`]
 ///
 /// ```
@@ -37,8 +39,8 @@ use crate::*;
 /// use opendal::services::Fs;
 /// use opendal::BlockingOperator;
 /// use opendal::Operator;
-/// #[tokio::main]
-/// async fn main() -> Result<()> {
+///
+/// fn main() -> Result<()> {
 ///     // Create fs backend builder.
 ///     let mut builder = Fs::default();
 ///     // Set the root for fs, all operations will happen under this root.
@@ -52,6 +54,35 @@ use crate::*;
 ///     Ok(())
 /// }
 /// ```
+///
+/// ## Init backends with blocking layer
+///
+/// Some services like s3, gcs doesn't have native blocking supports, we can 
use [`layers::BlockingLayer`]
+/// to wrap the async operator to make it blocking.
+///
+/// ```rust
+/// # use anyhow::Result;
+/// use opendal::layers::BlockingLayer;
+/// use opendal::services::S3;
+/// use opendal::BlockingOperator;
+/// use opendal::Operator;
+///
+/// #[tokio::main]
+/// async fn main() -> Result<()> {
+///     // Create fs backend builder.
+///     let mut builder = S3::default();
+///     builder.bucket("test");
+///     builder.region("us-east-1");
+///
+///     // Build an `BlockingOperator` with blocking layer to start operating 
the storage.
+///     let _: BlockingOperator = Operator::new(builder)?
+///         .layer(BlockingLayer::create()?)
+///         .finish()
+///         .blocking();
+///
+///     Ok(())
+/// }
+/// ```
 #[derive(Clone, Debug)]
 pub struct BlockingOperator {
     accessor: FusedAccessor,
diff --git a/core/tests/behavior/blocking_append.rs 
b/core/tests/behavior/blocking_append.rs
index ccb89f786..d402d97e5 100644
--- a/core/tests/behavior/blocking_append.rs
+++ b/core/tests/behavior/blocking_append.rs
@@ -15,13 +15,13 @@
 // specific language governing permissions and limitations
 // under the License.
 
+use std::io::BufReader;
+use std::io::Cursor;
 use std::vec;
 
 use anyhow::Result;
 use sha2::Digest;
 use sha2::Sha256;
-use std::io::BufReader;
-use std::io::Cursor;
 
 use crate::*;
 

Reply via email to