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

felipecrv pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/arrow.git


The following commit(s) were added to refs/heads/main by this push:
     new 4fc2a708ba GH-39718: [C++][FS][Azure] Remove StatusFromErrorResponse 
as it's not necessary (#39719)
4fc2a708ba is described below

commit 4fc2a708bac92614a42c07ea1f23b1a4a3af88cb
Author: Felipe Oliveira Carvalho <[email protected]>
AuthorDate: Mon Jan 22 17:23:54 2024 -0300

    GH-39718: [C++][FS][Azure] Remove StatusFromErrorResponse as it's not 
necessary (#39719)
    
    ### Rationale for this change
    
    Only the "*IfExists" functions from the Azure SDK ever set 
`response.Value.Deleted` to `false` to indicate that a resource wasn't found 
and the request succeeded without deleting anything.
    
    It's better that we use the `Delete()` versions of these functions instead 
of `DeleteIfExists` and check the `ErrorCode` ourselves to return an 
appropriate `Status` instead of something generic.
    
    ### What changes are included in this PR?
    
     - Removing `StatusFromErrorResponse`
     - Comments explaining the error handling decisions
     - Addition of a boolean parameter to `DeleteDirOnFileSystem` that controls 
how it fails when the directory being deleted doesn't exist
    
    ### Are these changes tested?
    
     - Yes, by the existing tests in `azurefs_test.cc`.
    * Closes: #39718
    
    Authored-by: Felipe Oliveira Carvalho <[email protected]>
    Signed-off-by: Felipe Oliveira Carvalho <[email protected]>
---
 cpp/src/arrow/filesystem/azurefs.cc | 62 +++++++++++++------------------------
 1 file changed, 22 insertions(+), 40 deletions(-)

diff --git a/cpp/src/arrow/filesystem/azurefs.cc 
b/cpp/src/arrow/filesystem/azurefs.cc
index 730adabd48..a5179c2219 100644
--- a/cpp/src/arrow/filesystem/azurefs.cc
+++ b/cpp/src/arrow/filesystem/azurefs.cc
@@ -305,31 +305,9 @@ Status ValidateFileLocation(const AzureLocation& location) 
{
   return internal::AssertNoTrailingSlash(location.path);
 }
 
-std::string_view BodyTextView(const Http::RawResponse& raw_response) {
-  const auto& body = raw_response.GetBody();
-#ifndef NDEBUG
-  auto& headers = raw_response.GetHeaders();
-  auto content_type = headers.find("Content-Type");
-  if (content_type != headers.end()) {
-    DCHECK_EQ(std::string_view{content_type->second}.substr(5), "text/");
-  }
-#endif
-  return std::string_view{reinterpret_cast<const char*>(body.data()), 
body.size()};
-}
-
-Status StatusFromErrorResponse(const std::string& url,
-                               const Http::RawResponse& raw_response,
-                               const std::string& context) {
-  // There isn't an Azure specification that response body on error
-  // doesn't contain any binary data but we assume it. We hope that
-  // error response body has useful information for the error.
-  auto body_text = BodyTextView(raw_response);
-  return Status::IOError(context, ": ", url, ": ", 
raw_response.GetReasonPhrase(), " (",
-                         static_cast<int>(raw_response.GetStatusCode()),
-                         "): ", body_text);
-}
-
 bool IsContainerNotFound(const Storage::StorageException& e) {
+  // In some situations, only the ReasonPhrase is set and the
+  // ErrorCode is empty, so we check both.
   if (e.ErrorCode == "ContainerNotFound" ||
       e.ReasonPhrase == "The specified container does not exist." ||
       e.ReasonPhrase == "The specified filesystem does not exist.") {
@@ -1515,13 +1493,9 @@ class AzureFileSystem::Impl {
     DCHECK(location.path.empty());
     try {
       auto response = container_client.Delete();
-      if (response.Value.Deleted) {
-        return Status::OK();
-      } else {
-        return StatusFromErrorResponse(
-            container_client.GetUrl(), *response.RawResponse,
-            "Failed to delete a container: " + location.container);
-      }
+      // Only the "*IfExists" functions ever set Deleted to false.
+      // All the others either succeed or throw an exception.
+      DCHECK(response.Value.Deleted);
     } catch (const Storage::StorageException& exception) {
       if (IsContainerNotFound(exception)) {
         return PathNotFound(location);
@@ -1530,6 +1504,7 @@ class AzureFileSystem::Impl {
                                "Failed to delete a container: ", 
location.container, ": ",
                                container_client.GetUrl());
     }
+    return Status::OK();
   }
 
   /// Deletes contents of a directory and possibly the directory itself
@@ -1649,23 +1624,29 @@ class AzureFileSystem::Impl {
   /// \pre location.container is not empty.
   /// \pre location.path is not empty.
   Status DeleteDirOnFileSystem(const DataLake::DataLakeFileSystemClient& 
adlfs_client,
-                               const AzureLocation& location) {
+                               const AzureLocation& location, bool recursive,
+                               bool require_dir_to_exist) {
     DCHECK(!location.container.empty());
     DCHECK(!location.path.empty());
     auto directory_client = adlfs_client.GetDirectoryClient(location.path);
-    // XXX: should "directory not found" be considered an error?
     try {
-      auto response = directory_client.DeleteRecursive();
-      if (response.Value.Deleted) {
+      auto response =
+          recursive ? directory_client.DeleteRecursive() : 
directory_client.DeleteEmpty();
+      // Only the "*IfExists" functions ever set Deleted to false.
+      // All the others either succeed or throw an exception.
+      DCHECK(response.Value.Deleted);
+    } catch (const Storage::StorageException& exception) {
+      if (exception.ErrorCode == "FilesystemNotFound" ||
+          exception.ErrorCode == "PathNotFound") {
+        if (require_dir_to_exist) {
+          return PathNotFound(location);
+        }
         return Status::OK();
-      } else {
-        return StatusFromErrorResponse(directory_client.GetUrl(), 
*response.RawResponse,
-                                       "Failed to delete a directory: " + 
location.path);
       }
-    } catch (const Storage::StorageException& exception) {
       return ExceptionToStatus(exception, "Failed to delete a directory: ", 
location.path,
                                ": ", directory_client.GetUrl());
     }
+    return Status::OK();
   }
 
   /// \pre location.container is not empty.
@@ -1855,7 +1836,8 @@ Status AzureFileSystem::DeleteDir(const std::string& 
path) {
     return PathNotFound(location);
   }
   if (hns_support == HNSSupport::kEnabled) {
-    return impl_->DeleteDirOnFileSystem(adlfs_client, location);
+    return impl_->DeleteDirOnFileSystem(adlfs_client, location, 
/*recursive=*/true,
+                                        /*require_dir_to_exist=*/true);
   }
   DCHECK_EQ(hns_support, HNSSupport::kDisabled);
   auto container_client = impl_->GetBlobContainerClient(location.container);

Reply via email to