Skip to content

[aws-cpp-sdk-s3-crt]: TransferManager for S3CrtClient #2380

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 9 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Next Next commit
Initial set of files (compile-tested only)
  • Loading branch information
grrtrr committed Mar 6, 2023
commit 587966675ebab29ffe68393307bd3354d886b70c
2 changes: 1 addition & 1 deletion cmake/sdks.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ include(sdksCommon)

set(SDK_DEPENDENCY_BUILD_LIST "")

set(NON_GENERATED_CLIENT_LIST access-management text-to-speech core queues s3-encryption identity-management transfer) ## Manually generated code with a name mimicking client name
set(NON_GENERATED_CLIENT_LIST access-management text-to-speech core queues s3-encryption identity-management transfer transfer-crt) ## Manually generated code with a name mimicking client name

if(REGENERATE_CLIENTS OR REGENERATE_DEFAULTS)
message(STATUS "Checking for SDK generation requirements")
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
/**
* Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
* SPDX-License-Identifier: Apache-2.0.
*/
#pragma once

#include <aws/core/utils/memory/AWSMemory.h>
#include <aws/core/utils/memory/stl/AWSString.h>
#include <functional>
#include <iostream>
#include <memory>
#include <mutex>
#include <streambuf>
#include <utility>

namespace Aws {
namespace TransferCrt {

// Used by the classes below to notify the receiver of low-level file errors.
using ErrorCallback = std::function<void(Aws::String someDescriptiveErrorMessage)>;

// Default size for the put buffer (which is bypassed when xsputn is used).
// Measurements in "The Linux Programming Interface" show that a minimum 4096B is
// required when O_SYNC is enabled. Use a larger value to aggregate small writes.
constexpr size_t DEFAULT_BUFSIZE = 1 << 20;

// Helper class for DownloadStream.
//
// This implements only what DownloadStream needs: a simple, file-descriptor based streambuf.
// Hence many std::streambuf operations, such as seekoff/pos, are not supported.
// The expected use-case is that mostly xsputn(const char *, size_t) will be called.
//
// The ErrorCallback that is passed into the constructor is invoked when encountering a
// low-level write error, receiving a string describing the error cause (based on errno).
class FileDescriptorBuf : public std::streambuf {
public:
// Class does not own the file descriptor @fd - caller is responsible for closing it.
FileDescriptorBuf(int fd, ErrorCallback errorCallback, size_t bufsize = DEFAULT_BUFSIZE)
: fd_{fd}, errorCallback_{errorCallback}, buffer_{Aws::MakeUniqueArray<char>(bufsize, "FdBuf")} {
setp(buffer_.get(), buffer_.get() + bufsize);
}

protected:
int sync() override;
int overflow(int_type c) override;
std::streamsize xsputn(const char *data, std::streamsize datalen) override;

private:
int fd_;
ErrorCallback errorCallback_;
Aws::UniqueArrayPtr<char> buffer_;
};

// Download output stream class for a given @dstPath.
//
// This takes an Error Callback which gets invoked with descriptive error message when a failure
// occurs in either this class, or the contained FileDescriptorBuf.
//
// The constructor does the following:
// 1. Create any missing directory components of @dstPath.
// 2. Generate a temporary .partial file to write to. This file will be renamed into @dstPath
// upon successful completion, or removed on failure. The implementation uses mkostemp(3),
// which is the reason we are using a file-descriptor based backend.
// 3. Open a file descriptor to the temporary file and advise the kernel about its use.
// 4. Complete the construction of the iostream, using a FileDescriptorBuf as rdbuf.
//
// The Error Callback @ec may be invoked already before the constructor call returns.
// It is also invoked by the contained FileDescriptorBuf, and during close().
class DownloadStream final : public std::iostream {
public:
// Create a DownloadStream for @dstPath, calling @ec if any failure happens.
// Enabling O_SYNC via @sync_always is optional, as it degrades download performance.
DownloadStream(const Aws::String &dstPath, ErrorCallback ec, bool sync_always = false);
~DownloadStream();

// Set eof, close the temporary file and atomically rename it into @dstPath.
void close() noexcept;

private:
void _error(Aws::String msg) {
setstate(std::ios::badbit);
errorCallback_(std::move(msg));
}

private:
const Aws::String dstPath_;
Aws::String dstTempPath_;
ErrorCallback errorCallback_;

int fd_ = -1;
Aws::UniquePtr<FileDescriptorBuf> buf_;
std::mutex close_mutex_;
};

} // namespace TransferCrt
} // namespace Aws
99 changes: 99 additions & 0 deletions src/aws-cpp-sdk-transfer-crt/include/aws/transfer-crt/Metadata.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
/**
* Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
* SPDX-License-Identifier: Apache-2.0.
*/

#pragma once

#include <aws/core/utils/memory/stl/AWSString.h>
#include <aws/core/utils/memory/stl/AWSMap.h>
#include <chrono>
#include <utility>

namespace Aws {
namespace TransferCrt {

// WriteMetadata specifies blob metadata information.
// @uri: destination URI of the blob, in <scheme>://<bucket>/<path> format.
// @content_type: MIME type of the @uri content.
// @content_encoding: content encoding that was applied.
// @metadata: metadata key/value pairs.
struct WriteMetadata {
// Constructor for the default case - just create a blob at @uri.
explicit WriteMetadata(Aws::String uri) : WriteMetadata(uri, "", "") {}

WriteMetadata(Aws::String uri,
Aws::String content_type,
Aws::String content_encoding,
Aws::Map<Aws::String, Aws::String> metadata = {})
: uri{uri},
content_type{content_type},
content_encoding{content_encoding},
metadata{metadata} {}

// Destination URI of the blob, in <scheme>://<bucket>/<path> format.
Aws::String uri;

// Content-Type (MIME type) of @uri.
Aws::String content_type;

// Content-Encoding (if any) of @uri.
Aws::String content_encoding;

// Metadata key/value pairs.
Aws::Map<Aws::String, Aws::String> metadata;

// S3 Object Tagging key/value pairs (S3 objects only).
// These require s3:PutObjectTagging permissions on @uri, otherwise requests fail with 403.
// The tags also have to satisfy the following syntax restrictions and limits:
// * https://docs.aws.amazon.com/AmazonS3/latest/userguide/tagging-managing.html
// * https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/Using_Tags.html
// * https://docs.aws.amazon.com/awsaccountbilling/latest/aboutv2/allocation-tag-restrictions.html
Aws::Map<Aws::String, Aws::String> tags;
};

// ReadMetadata encapsulates the metadata associated with a given blob.
struct ReadMetadata {
// URI of the blob.
Aws::String uri;

// Size of @path in bytes.
size_t size = 0;

// Date/time the blob was last modified.
std::chrono::system_clock::time_point last_modified;

// MIME type of the blob.
Aws::String content_type;

// Indicates whether the data at @path is stored in compressed format (RFC 7231, 3.1.2.2).
Aws::String content_encoding;

// ETag value.
Aws::String etag;

// Metadata key/value pairs.
Aws::Map<Aws::String, Aws::String> metadata;
};

static inline std::ostream &operator<<(std::ostream &os, const ReadMetadata &md) {
os << "ReadMetadata(\"" << md.uri << "\", " << md.size;

time_t lm = std::chrono::system_clock::to_time_t(md.last_modified);
if (lm) { // Format: "Wed Jun 30 21:49:08 1993\n" - truncate before " 1993\n":
os << ", " << Aws::String{ctime(&lm), 19};
}
if (!md.etag.empty()) os << ", " << md.etag;
if (!md.content_type.empty()) {
os << ", " << md.content_type;
if (!md.content_encoding.empty()) os << " (" << md.content_encoding << ")";
}
if (!md.metadata.empty()) {
os << ",";
for (const auto &e : md.metadata) os << " " << e.first << "=" << e.second;
}
return os << ")";
}

} // namespace TransferCrt
} // namespace Aws
Loading
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy