├── .editorconfig
├── .gitattributes
├── .github
├── FUNDING.yml
├── ISSUE_TEMPLATE
│ ├── bug_report.md
│ └── feature_request.md
└── workflows
│ ├── generic-build.yml
│ └── nuget-release.yml
├── .gitignore
├── .globalconfig
├── Config.json
├── Imports
├── Benchmarks.props
├── Console.props
├── Examples.props
├── Library.props
└── Tests.props
├── LICENSE.txt
├── Locals
├── Benchmarks.props
├── Console.props
├── Directory.Build.props
├── Directory.Packages.props
├── Examples.props
├── Library.props
└── Tests.props
├── README.md
├── SECURITY.md
├── SimpleS3.sln
├── SimpleS3.sln.DotSettings
└── Src
├── Directory.Build.props
├── Directory.Build.targets
├── Directory.Packages.Analyzers.props
├── Directory.Packages.props
├── ProviderTests
├── .globalconfig
├── Buckets
│ ├── BucketAccelerateConfigurationTests.cs
│ ├── BucketLifecycleConfigurationTests.cs
│ ├── BucketLockConfigurationTests.cs
│ ├── BucketPolicyTests.cs
│ ├── BucketTaggingTests.cs
│ ├── BucketVersioningTests.cs
│ ├── CreateBucketTests.cs
│ ├── DeleteBucketTests.cs
│ ├── HeadBucketTests.cs
│ ├── ListBucketsTests.cs
│ ├── MiscTests.cs
│ └── PutPublicAccessBlockTests.cs
├── Code
│ ├── MultipleProvidersAttribute.cs
│ ├── ProviderSetup.cs
│ ├── TestBase.cs
│ └── TestConstants.cs
├── Issues
│ ├── AmazonIssues.cs
│ └── BackBlazeIssues.cs
├── Misc
│ └── GetObjectTests.cs
├── Multipart
│ ├── AbortMultipartTests.cs
│ ├── ListMultipartUploadsTests.cs
│ ├── ListPartsTests.cs
│ └── MultipartTests.cs
├── Objects
│ ├── CopyObjectTests.cs
│ ├── DeleteObjectTests.cs
│ ├── DeleteObjectsTests.cs
│ ├── GetObjectTests.cs
│ ├── HeadObjectTests.cs
│ ├── ListObjectVersionsTests.cs
│ ├── ListObjectsTests.cs
│ ├── ObjectAclTests.cs
│ ├── ObjectLegalHoldTests.cs
│ ├── PutObjectTests.cs
│ └── RestoreObjectTests.cs
├── ProviderTests.csproj
├── README.md
└── Signed
│ └── SignedTests.cs
├── SimpleS3.AmazonS3.Tests
├── SimpleS3.AmazonS3.Tests.csproj
└── StaticCreatorTests.cs
├── SimpleS3.AmazonS3
├── AmazonS3Client.cs
├── Extensions
│ └── ServiceCollectionExtensions.cs
└── SimpleS3.AmazonS3.csproj
├── SimpleS3.BackBlazeB2.Tests
├── SimpleS3.BackBlazeB2.Tests.csproj
└── StaticCreatorTests.cs
├── SimpleS3.BackBlazeB2
├── BackBlazeB2Client.cs
├── Extensions
│ └── ServiceCollectionExtensions.cs
└── SimpleS3.BackBlazeB2.csproj
├── SimpleS3.Core.Abstracts
├── Authentication
│ ├── IAccessKey.cs
│ ├── IAccessKeyProtector.cs
│ ├── IAuthorizationBuilder.cs
│ ├── IChunkedSignatureBuilder.cs
│ ├── IScopeBuilder.cs
│ ├── ISignatureBuilder.cs
│ └── ISigningKeyBuilder.cs
├── Enums
│ ├── BucketNameValidationMode.cs
│ ├── ErrorCode.cs
│ ├── HttpMethodType.cs
│ ├── NamingMode.cs
│ ├── ObjectKeyValidationMode.cs
│ ├── SignatureMode.cs
│ └── ValidationStatus.cs
├── Factories
│ ├── IMarshalFactory.cs
│ ├── IPostMapperFactory.cs
│ └── IRequestValidatorFactory.cs
├── ICoreBuilder.cs
├── Provider
│ ├── IEndpointBuilder.cs
│ ├── IEndpointData.cs
│ └── IInputValidator.cs
├── Region
│ ├── IRegionConverter.cs
│ ├── IRegionData.cs
│ ├── IRegionInfo.cs
│ └── RegionInfo.cs
├── Request
│ ├── INetworkDriver.cs
│ ├── IRequest.cs
│ ├── IRequestHandler.cs
│ ├── IRequestMarshal.cs
│ ├── IResponseHandler.cs
│ └── ISignedRequestHandler.cs
├── Response
│ ├── HttpResponse.cs
│ ├── IError.cs
│ ├── IPostMapper.cs
│ ├── IResponse.cs
│ └── IResponseMarshal.cs
├── ServiceBuilderBase.cs
├── SimpleS3.Core.Abstracts.csproj
├── SimpleS3Config.cs
└── Wrappers
│ ├── IRequestStreamWrapper.cs
│ ├── IRequestWrapper.cs
│ ├── IResponseStreamWrapper.cs
│ └── IResponseWrapper.cs
├── SimpleS3.Core.Benchmarks
├── .globalconfig
├── Benchmarks
│ ├── AwsSignatureVersion4Benchmarks.cs
│ ├── CharHelperBenchmarks.cs
│ ├── EndpointBuilderBenchmarks.cs
│ ├── GenericsBenchmarks.cs
│ ├── KeyValueTupleBenchmarks.cs
│ ├── SignatureBenchmarks.cs
│ ├── StringBuilderBenchmarks.cs
│ ├── TypeLookupBenchmarks.cs
│ ├── XmlReaderBenchmarks.cs
│ └── XmlWriterBenchmarks.cs
├── Misc
│ └── DummyRequest.cs
├── Program.cs
└── SimpleS3.Core.Benchmarks.csproj
├── SimpleS3.Core.Common.Tests
├── Code
│ ├── TestEnum.cs
│ ├── TestInputValidator.cs
│ ├── TestRegion.cs
│ └── TestRegionData.cs
├── InputValidatorTests.cs
├── PropertyHelperTests.cs
├── RegionConverterTests.cs
├── SimpleS3.Core.Common.Tests.csproj
└── ValidatorTests.cs
├── SimpleS3.Core.Common
├── Authentication
│ ├── AccessKey.cs
│ ├── AccessKeyBase.cs
│ └── StringAccessKey.cs
├── Exceptions
│ ├── S3Exception.cs
│ └── S3RequestException.cs
├── Extensions
│ ├── RegionConverterExtensions.cs
│ ├── ServiceCollectionExtensions.cs
│ ├── StringExtensions.cs
│ └── ValidatorExtensions.cs
├── Helpers
│ ├── CharHelper.cs
│ ├── CryptoHelper.cs
│ ├── KeyHelper.cs
│ ├── ParallelHelper.cs
│ ├── PropertyHelper.cs
│ ├── TypeHelper.cs
│ └── UrlHelper.cs
├── HttpVersion.cs
├── Internal
│ └── Compat
│ │ ├── CallerArgumentExpressionAttribute.cs
│ │ ├── DoesNotReturnIfAttribute.cs
│ │ └── NotNullAttribute.cs
├── Marshal
│ ├── IHasBucketName.cs
│ └── IHasObjectKey.cs
├── Misc
│ ├── AmzHeaders.cs
│ ├── AmzParameters.cs
│ ├── Constants.cs
│ └── HttpHeaders.cs
├── Pools
│ └── StringBuilderPool.cs
├── RegionConverter.cs
├── SimpleS3.Core.Common.csproj
└── Validation
│ ├── InputValidatorBase.cs
│ ├── RequireException.cs
│ ├── ValidationMessages.cs
│ └── Validator.cs
├── SimpleS3.Core.TestBase
├── Code
│ └── NullNetworkDriver.cs
├── Helpers
│ └── ResourceHelper.cs
├── OfflineTestBase.cs
├── SimpleS3.Core.TestBase.csproj
└── UnitTestBase.cs
├── SimpleS3.Core.Tests
├── Code
│ ├── EndpointBuilderTests.cs
│ ├── Handlers
│ │ ├── BaseFailingHttpHandler.cs
│ │ ├── NetworkFailingHttpHandler.cs
│ │ ├── NonTransientFailingHttpHandler.cs
│ │ ├── SlowHttpHandler.cs
│ │ └── TransientFailingHttpHandler.cs
│ └── Streams
│ │ └── NonSeekableStream.cs
├── GenericTests
│ ├── Builders
│ │ ├── AclBuilderTests.cs
│ │ ├── KmsContextBuilderTests.cs
│ │ └── MetadataBuilderTests.cs
│ ├── FastXmlWriterTests.cs
│ ├── JsonHelperTests.cs
│ ├── PoolTypeTests.cs
│ ├── ProviderTests.cs
│ └── UrlHelperTests.cs
├── OfflineTests
│ ├── AuthenticationTests.cs
│ ├── NetworkErrorTests.cs
│ ├── NonSeekableStreamTests.cs
│ ├── NonTransientServerErrorTests.cs
│ ├── ReuseRequestTests.cs
│ ├── TimeoutTests.cs
│ └── TransientNetworkErrorTests.cs
└── SimpleS3.Core.Tests.csproj
├── SimpleS3.Core
├── Abstracts
│ ├── Clients
│ │ ├── IBucketClient.cs
│ │ ├── IMultipartClient.cs
│ │ ├── IObjectClient.cs
│ │ └── ISignedClient.cs
│ ├── Features
│ │ ├── IAutoMapConfig.cs
│ │ ├── IContainSensitiveMaterial.cs
│ │ ├── IContentMd5Config.cs
│ │ └── ISupportStreaming.cs
│ ├── IDownload.cs
│ ├── ISimpleClient.cs
│ ├── IUpload.cs
│ ├── Operations
│ │ ├── IBucketOperations.cs
│ │ ├── IMultipartOperations.cs
│ │ ├── IObjectOperations.cs
│ │ └── ISignedOperations.cs
│ └── Transfer
│ │ ├── IMultipartTransfer.cs
│ │ └── ITransfer.cs
├── Authentication
│ └── HeaderWhitelist.cs
├── Builders
│ ├── AclBuilder.cs
│ ├── KmsContextBuilder.cs
│ ├── MetadataBuilder.cs
│ ├── MfaAuthenticationBuilder.cs
│ ├── ObjectAclBuilder.cs
│ └── TagBuilder.cs
├── Enums
│ ├── BucketCannedAcl.cs
│ ├── ChecksumAlgorithm.cs
│ ├── ChecksumType.cs
│ ├── CompressionType.cs
│ ├── EncodingType.cs
│ ├── ExpressionType.cs
│ ├── GrantType.cs
│ ├── HeaderUsage.cs
│ ├── JsonType.cs
│ ├── LockMode.cs
│ ├── MetadataDirective.cs
│ ├── ObjectCannedAcl.cs
│ ├── ObjectOwnership.cs
│ ├── ObjectPermissions.cs
│ ├── Payer.cs
│ ├── PredefinedGroup.cs
│ ├── QuoteField.cs
│ ├── ReplicationStatus.cs
│ ├── RestoreRequestType.cs
│ ├── RetrievalTier.cs
│ ├── S3Permission.cs
│ ├── SseAlgorithm.cs
│ ├── SseCustomerAlgorithm.cs
│ ├── StorageClass.cs
│ └── TaggingDirective.cs
├── Extensions
│ ├── BucketClientExtensions.cs
│ ├── CoreBuilderExtensions.cs
│ ├── MultipartClientExtensions.cs
│ ├── ObjectClientExtensions.cs
│ ├── SimpleS3CoreServices.cs
│ └── StreamExtensions.cs
├── Internals
│ ├── Authentication
│ │ ├── ChunkedSignatureBuilder.cs
│ │ ├── ChunkedStream.cs
│ │ ├── ScopeBuilder.cs
│ │ ├── SignatureBuilder.cs
│ │ ├── SigningConstants.cs
│ │ └── SigningKeyBuilder.cs
│ ├── Builders
│ │ ├── HeaderAuthorizationBuilder.cs
│ │ └── QueryParameterAuthorizationBuilder.cs
│ ├── Clients
│ │ ├── BucketClient.cs
│ │ ├── MultipartClient.cs
│ │ ├── ObjectClient.cs
│ │ ├── PooledBucketClient.cs
│ │ ├── PooledMultipartClient.cs
│ │ ├── PooledObjectClient.cs
│ │ └── SignedClient.cs
│ ├── Compat
│ │ └── NotNullWhenAttribute.cs
│ ├── CoreBuilder.cs
│ ├── Enums
│ │ ├── BinaryEncoding.cs
│ │ └── DateTimeFormat.cs
│ ├── Errors
│ │ └── ErrorHandler.cs
│ ├── Extensions
│ │ ├── DictionaryExtensions.cs
│ │ ├── HexExtensions.cs
│ │ ├── QueueExtensions.cs
│ │ ├── RequestExtensions.cs
│ │ ├── StreamExtensions.cs
│ │ └── TypeExtensions.cs
│ ├── Fluent
│ │ ├── Download.cs
│ │ ├── MultipartTransfer.cs
│ │ ├── Transfer.cs
│ │ └── Upload.cs
│ ├── Helpers
│ │ ├── CopyHelper.cs
│ │ ├── JsonHelper.cs
│ │ ├── ParserHelper.cs
│ │ ├── RequestHelper.cs
│ │ ├── ValueHelper.cs
│ │ └── XmlHelper.cs
│ ├── Marshallers
│ │ ├── Requests
│ │ │ ├── Buckets
│ │ │ │ ├── CreateBucketRequestMarshal.cs
│ │ │ │ ├── DeleteBucketPolicyRequestMarshal.cs
│ │ │ │ ├── DeleteBucketTaggingRequestMarshal.cs
│ │ │ │ ├── GetBucketAccelerateConfigurationRequestMarshal.cs
│ │ │ │ ├── GetBucketLifecycleConfigurationRequestMarshal.cs
│ │ │ │ ├── GetBucketLockConfigurationRequestMarshal.cs
│ │ │ │ ├── GetBucketPolicyRequestMarshal.cs
│ │ │ │ ├── GetBucketTaggingRequestMarshal.cs
│ │ │ │ ├── GetBucketVersioningRequestMarshal.cs
│ │ │ │ ├── PutBucketAccelerateConfigurationRequestMarshal.cs
│ │ │ │ ├── PutBucketLifecycleConfigurationRequestMarshal.cs
│ │ │ │ ├── PutBucketLockConfigurationRequestMarshal.cs
│ │ │ │ ├── PutBucketPolicyRequestMarshal.cs
│ │ │ │ ├── PutBucketTaggingRequestMarshal.cs
│ │ │ │ ├── PutBucketVersioningRequestMarshal.cs
│ │ │ │ └── PutPublicAccessBlockRequestMarshal.cs
│ │ │ ├── GenericRequestMapper.cs
│ │ │ ├── Multipart
│ │ │ │ ├── CompleteMultipartUploadRequestMarshal.cs
│ │ │ │ ├── CreateMultipartUploadRequestMarshal.cs
│ │ │ │ ├── ListMultipartUploadsRequestMarshal.cs
│ │ │ │ └── ListPartsRequestMarshal.cs
│ │ │ └── Objects
│ │ │ │ ├── CopyObjectRequestMarshal.cs
│ │ │ │ ├── DeleteObjectsRequestMarshal.cs
│ │ │ │ ├── GetObjectAclRequestMarshal.cs
│ │ │ │ ├── GetObjectLegalHoldRequestMarshal.cs
│ │ │ │ ├── GetObjectRequestMarshal.cs
│ │ │ │ ├── HeadObjectRequestMarshal.cs
│ │ │ │ ├── ListObjectVersionsRequestMarshal.cs
│ │ │ │ ├── ListObjectsRequestMarshal.cs
│ │ │ │ ├── PutObjectAclRequestMarshal.cs
│ │ │ │ ├── PutObjectLegalHoldRequestMarshal.cs
│ │ │ │ └── RestoreObjectRequestMarshal.cs
│ │ └── Responses
│ │ │ ├── Buckets
│ │ │ ├── GetBucketAccelerateConfigurationResponseMarshal.cs
│ │ │ ├── GetBucketLifecycleConfigurationResponseMarshal.cs
│ │ │ ├── GetBucketLockConfigurationResponseMarshal.cs
│ │ │ ├── GetBucketPolicyResponseMarshal.cs
│ │ │ ├── GetBucketTaggingResponseMarshal.cs
│ │ │ ├── GetBucketVersioningResponseMarshal.cs
│ │ │ ├── ListBucketsResponseMarshal.cs
│ │ │ ├── PutBucketLockConfigurationResponseMarshal.cs
│ │ │ └── PutBucketVersioningResponseMarshal.cs
│ │ │ ├── Multipart
│ │ │ ├── AbortMultipartUploadResponseMarshal.cs
│ │ │ ├── CompleteMultipartUploadResponseMarshal.cs
│ │ │ ├── CreateMultipartUploadResponseMarshal.cs
│ │ │ ├── ListMultipartUploadsResponseMarshal.cs
│ │ │ ├── ListPartsResponseMarshal.cs
│ │ │ └── UploadPartResponseMarshal.cs
│ │ │ └── Objects
│ │ │ ├── CopyObjectResponseMarshal.cs
│ │ │ ├── DeleteObjectResponseMarshal.cs
│ │ │ ├── DeleteObjectsResponseMarshal.cs
│ │ │ ├── GetObjectAclResponseMarshal.cs
│ │ │ ├── GetObjectLegalHoldResponseMarshal.cs
│ │ │ ├── GetObjectResponseMarshal.cs
│ │ │ ├── HeadObjectResponseMarshal.cs
│ │ │ ├── ListObjectVersionsResponseMarshal.cs
│ │ │ ├── ListObjectsResponseMarshal.cs
│ │ │ ├── PutObjectAclResponseMarshal.cs
│ │ │ ├── PutObjectLegalHoldResponseMarshal.cs
│ │ │ ├── PutObjectResponseMarshal.cs
│ │ │ └── RestoreObjectResponseMarshal.cs
│ ├── Misc
│ │ ├── DateTimeFormats.cs
│ │ └── OrderedDictionary.cs
│ ├── Network
│ │ ├── ChunkedContentRequestStreamWrapper.cs
│ │ ├── DefaultRequestHandler.cs
│ │ ├── DefaultResponseHandler.cs
│ │ ├── DefaultSignedRequestHandler.cs
│ │ ├── EndpointBuilder.cs
│ │ ├── EndpointData.cs
│ │ ├── MarshalFactory.cs
│ │ ├── PostMapperFactory.cs
│ │ └── SignedRequest.cs
│ ├── NullInputValidator.cs
│ ├── Operations
│ │ ├── BucketOperations.cs
│ │ ├── MultipartOperations.cs
│ │ ├── ObjectOperations.cs
│ │ └── SignedOperations.cs
│ ├── Pools
│ │ ├── IPooledObject.cs
│ │ └── ObjectPool.cs
│ ├── PostMappers
│ │ └── UploadPartPostMapper.cs
│ ├── Validation
│ │ ├── ValidatorFactory.cs
│ │ └── Validators
│ │ │ ├── ConfigValidatorBase.cs
│ │ │ ├── Configs
│ │ │ ├── AccessKeyValidator.cs
│ │ │ └── ConfigValidator.cs
│ │ │ ├── RequestValidatorBase.cs
│ │ │ ├── Requests
│ │ │ ├── Bucket
│ │ │ │ └── PutBucketLifecycleConfigurationRequestValidator.cs
│ │ │ ├── Multipart
│ │ │ │ ├── CompleteMultipartUploadRequestValidator.cs
│ │ │ │ └── ListMultipartUploadsRequestValidator.cs
│ │ │ └── Objects
│ │ │ │ ├── DeleteObjectsRequestValidator.cs
│ │ │ │ └── ListObjectsRequestValidator.cs
│ │ │ └── ValidatorBase.cs
│ └── Xml
│ │ ├── FastXmlWriter.cs
│ │ ├── XmlCharMode.cs
│ │ └── XmlStandard.cs
├── Network
│ ├── Requests
│ │ ├── BaseRequest.cs
│ │ ├── Buckets
│ │ │ ├── CreateBucketRequest.cs
│ │ │ ├── DeleteBucketPolicyRequest.cs
│ │ │ ├── DeleteBucketRequest.cs
│ │ │ ├── DeleteBucketTaggingRequest.cs
│ │ │ ├── GetBucketAccelerateConfigurationRequest.cs
│ │ │ ├── GetBucketLifecycleConfigurationRequest.cs
│ │ │ ├── GetBucketLockConfigurationRequest.cs
│ │ │ ├── GetBucketPolicyRequest.cs
│ │ │ ├── GetBucketTaggingRequest.cs
│ │ │ ├── GetBucketVersioningRequest.cs
│ │ │ ├── HeadBucketRequest.cs
│ │ │ ├── ListBucketsRequest.cs
│ │ │ ├── PutBucketAccelerateConfigurationRequest.cs
│ │ │ ├── PutBucketLifecycleConfigurationRequest.cs
│ │ │ ├── PutBucketLockConfigurationRequest.cs
│ │ │ ├── PutBucketPolicyRequest.cs
│ │ │ ├── PutBucketTaggingRequest.cs
│ │ │ ├── PutBucketVersioningRequest.cs
│ │ │ └── PutPublicAccessBlockRequest.cs
│ │ ├── Interfaces
│ │ │ ├── IHasBucketAcl.cs
│ │ │ ├── IHasBypassGovernanceRetention.cs
│ │ │ ├── IHasCache.cs
│ │ │ ├── IHasCacheControl.cs
│ │ │ ├── IHasChecksum.cs
│ │ │ ├── IHasChecksumProperties.cs
│ │ │ ├── IHasContent.cs
│ │ │ ├── IHasContentMd5.cs
│ │ │ ├── IHasContentProps.cs
│ │ │ ├── IHasExpectedBucketOwner.cs
│ │ │ ├── IHasExpiresOn.cs
│ │ │ ├── IHasLegalHold.cs
│ │ │ ├── IHasLock.cs
│ │ │ ├── IHasMetadata.cs
│ │ │ ├── IHasMfa.cs
│ │ │ ├── IHasObjectAcl.cs
│ │ │ ├── IHasPartNumber.cs
│ │ │ ├── IHasRange.cs
│ │ │ ├── IHasRequestPayer.cs
│ │ │ ├── IHasResponseHeader.cs
│ │ │ ├── IHasSse.cs
│ │ │ ├── IHasSseCustomerKey.cs
│ │ │ ├── IHasStorageClass.cs
│ │ │ ├── IHasTags.cs
│ │ │ ├── IHasUploadId.cs
│ │ │ ├── IHasVersionId.cs
│ │ │ └── IHasWebsiteRedirect.cs
│ │ ├── Multipart
│ │ │ ├── AbortMultipartUploadRequest.cs
│ │ │ ├── CompleteMultipartUploadRequest.cs
│ │ │ ├── CreateMultipartUploadRequest.cs
│ │ │ ├── ListMultipartUploadsRequest.cs
│ │ │ ├── ListPartsRequest.cs
│ │ │ └── UploadPartRequest.cs
│ │ ├── Objects
│ │ │ ├── CopyObjectRequest.cs
│ │ │ ├── DeleteObjectRequest.cs
│ │ │ ├── DeleteObjectsRequest.cs
│ │ │ ├── GetObjectAclRequest.cs
│ │ │ ├── GetObjectLegalHoldRequest.cs
│ │ │ ├── GetObjectRequest.cs
│ │ │ ├── HeadObjectRequest.cs
│ │ │ ├── ListObjectVersionsRequest.cs
│ │ │ ├── ListObjectsRequest.cs
│ │ │ ├── PutObjectAclRequest.cs
│ │ │ ├── PutObjectLegalHoldRequest.cs
│ │ │ ├── PutObjectRequest.cs
│ │ │ └── RestoreObjectRequest.cs
│ │ └── S3Types
│ │ │ ├── S3AndCondition.cs
│ │ │ ├── S3CsvInputFormat.cs
│ │ │ ├── S3CsvOutputFormat.cs
│ │ │ ├── S3DeleteInfo.cs
│ │ │ ├── S3Expiration.cs
│ │ │ ├── S3Filter.cs
│ │ │ ├── S3InputFormat.cs
│ │ │ ├── S3JsonInputFormat.cs
│ │ │ ├── S3JsonOutputFormat.cs
│ │ │ ├── S3NonCurrentVersionTransition.cs
│ │ │ ├── S3OutputFormat.cs
│ │ │ ├── S3OutputLocation.cs
│ │ │ ├── S3ParquetInputFormat.cs
│ │ │ ├── S3PartInfo.cs
│ │ │ ├── S3Rule.cs
│ │ │ ├── S3SelectParameters.cs
│ │ │ └── S3Transition.cs
│ └── Responses
│ │ ├── BaseResponse.cs
│ │ ├── Buckets
│ │ ├── CreateBucketResponse.cs
│ │ ├── DeleteBucketPolicyResponse.cs
│ │ ├── DeleteBucketResponse.cs
│ │ ├── DeleteBucketTaggingResponse.cs
│ │ ├── GetBucketAccelerateConfigurationResponse.cs
│ │ ├── GetBucketLifecycleConfigurationResponse.cs
│ │ ├── GetBucketLockConfigurationResponse.cs
│ │ ├── GetBucketPolicyResponse.cs
│ │ ├── GetBucketTaggingResponse.cs
│ │ ├── GetBucketVersioningResponse.cs
│ │ ├── HeadBucketResponse.cs
│ │ ├── ListBucketsResponse.cs
│ │ ├── PutBucketAccelerateConfigurationResponse.cs
│ │ ├── PutBucketLifecycleConfigurationResponse.cs
│ │ ├── PutBucketLockConfigurationResponse.cs
│ │ ├── PutBucketPolicyResponse.cs
│ │ ├── PutBucketTaggingResponse.cs
│ │ ├── PutBucketVersioningResponse.cs
│ │ └── PutPublicAccessBlockResponse.cs
│ │ ├── Errors
│ │ ├── BucketAlreadyExistsError.cs
│ │ ├── BucketNotEmptyError.cs
│ │ ├── GenericError.cs
│ │ ├── HeadersNotSignedError.cs
│ │ ├── InvalidArgumentError.cs
│ │ ├── InvalidBucketNameError.cs
│ │ ├── MethodNotAllowedError.cs
│ │ ├── NoSuchBucketError.cs
│ │ ├── PreconditionFailedError.cs
│ │ ├── TooManyBucketsError.cs
│ │ └── XAmzContentSha256MismatchError.cs
│ │ ├── Interfaces
│ │ ├── IHasAbort.cs
│ │ ├── IHasCache.cs
│ │ ├── IHasContent.cs
│ │ ├── IHasDeleteMarker.cs
│ │ ├── IHasETag.cs
│ │ ├── IHasExpiration.cs
│ │ ├── IHasExpiresOn.cs
│ │ ├── IHasLastModified.cs
│ │ ├── IHasLegalHold.cs
│ │ ├── IHasLock.cs
│ │ ├── IHasMetadata.cs
│ │ ├── IHasReplicationStatus.cs
│ │ ├── IHasRequestCharged.cs
│ │ ├── IHasResponseContent.cs
│ │ ├── IHasRestoration.cs
│ │ ├── IHasSse.cs
│ │ ├── IHasSseContext.cs
│ │ ├── IHasSseCustomerKey.cs
│ │ ├── IHasStorageClass.cs
│ │ ├── IHasTruncated.cs
│ │ ├── IHasTruncatedExt.cs
│ │ ├── IHasUploadId.cs
│ │ ├── IHasVersionId.cs
│ │ └── IHasWebsiteRedirect.cs
│ │ ├── Multipart
│ │ ├── AbortMultipartUploadResponse.cs
│ │ ├── CompleteMultipartUploadResponse.cs
│ │ ├── CreateMultipartUploadResponse.cs
│ │ ├── ListMultipartUploadsResponse.cs
│ │ ├── ListPartsResponse.cs
│ │ └── UploadPartResponse.cs
│ │ ├── Objects
│ │ ├── CopyObjectResponse.cs
│ │ ├── DeleteObjectResponse.cs
│ │ ├── DeleteObjectsResponse.cs
│ │ ├── GetObjectAclResponse.cs
│ │ ├── GetObjectLegalHoldResponse.cs
│ │ ├── GetObjectResponse.cs
│ │ ├── HeadObjectResponse.cs
│ │ ├── ListObjectVersionsResponse.cs
│ │ ├── ListObjectsResponse.cs
│ │ ├── PutObjectAclResponse.cs
│ │ ├── PutObjectLegalHoldResponse.cs
│ │ ├── PutObjectResponse.cs
│ │ └── RestoreObjectResponse.cs
│ │ └── S3Types
│ │ ├── S3Bucket.cs
│ │ ├── S3DeleteError.cs
│ │ ├── S3DeleteMarker.cs
│ │ ├── S3DeletedObject.cs
│ │ ├── S3Grant.cs
│ │ ├── S3Grantee.cs
│ │ ├── S3Identity.cs
│ │ ├── S3Object.cs
│ │ ├── S3Part.cs
│ │ ├── S3Upload.cs
│ │ └── S3Version.cs
├── Properties
│ └── AssemblyInfo.cs
├── SimpleClient.cs
└── SimpleS3.Core.csproj
├── SimpleS3.Examples.Advanced
├── ClientSetup.cs
├── NetworkProxy.cs
├── NetworkRetryAndTimeout.cs
├── SetupDependencyInjection.cs
├── SimpleS3.Examples.Advanced.csproj
├── UsingCustomerKey.cs
└── UsingProfileManager.cs
├── SimpleS3.Examples
├── Program.cs
└── SimpleS3.Examples.csproj
├── SimpleS3.Extensions.AmazonS3.Tests
├── AmazonS3InputValidatorTests.cs
├── CanonicalRequestFileTests.cs
├── ChunkedSignatureTests.cs
├── Helpers
│ └── HttpHelper.cs
├── HttpHandler.cs
├── Resources
│ ├── README.md
│ ├── get-query-casing
│ │ ├── get-query-casing.creq
│ │ ├── get-query-casing.req.disabled
│ │ └── get-query-casing.sts
│ ├── get-query-order
│ │ ├── get-query-order.creq
│ │ ├── get-query-order.req
│ │ └── get-query-order.sts
│ ├── get-query-reserved
│ │ ├── get-query-reserved.creq
│ │ ├── get-query-reserved.req
│ │ └── get-query-reserved.sts
│ ├── get-query-utf8
│ │ ├── get-query-utf8.creq
│ │ ├── get-query-utf8.req
│ │ └── get-query-utf8.sts
│ ├── get-query
│ │ ├── get-query.creq
│ │ ├── get-query.req
│ │ └── get-query.sts
│ ├── get-reserved
│ │ ├── get-reserved.creq
│ │ ├── get-reserved.req
│ │ └── get-reserved.sts
│ ├── get-utf8
│ │ ├── get-utf8.creq
│ │ ├── get-utf8.req
│ │ └── get-utf8.sts
│ └── get
│ │ ├── get.creq
│ │ ├── get.req
│ │ └── get.sts
├── SignedUrlTests.cs
└── SimpleS3.Extensions.AmazonS3.Tests.csproj
├── SimpleS3.Extensions.AmazonS3
├── AmazonS3Config.cs
├── AmazonS3InputValidator.cs
├── AmazonS3Region.cs
├── AmazonS3RegionData.cs
├── Extensions
│ └── CoreBuilderExtensions.cs
├── Properties
│ └── AssemblyInfo.cs
├── README.md
└── SimpleS3.Extensions.AmazonS3.csproj
├── SimpleS3.Extensions.BackBlazeB2.Tests
├── BackblazeB2InputValidatorTests.cs
└── SimpleS3.Extensions.BackBlazeB2.Tests.csproj
├── SimpleS3.Extensions.BackBlazeB2
├── BackBlazeB2Config.cs
├── BackBlazeB2Region.cs
├── BackblazeB2InputValidator.cs
├── BackblazeB2RegionData.cs
├── Extensions
│ └── CoreBuilderExtensions.cs
├── Properties
│ └── AssemblyInfo.cs
├── README.md
└── SimpleS3.Extensions.BackBlazeB2.csproj
├── SimpleS3.Extensions.GenericS3.Tests
├── GenericS3InputValidatorTests.cs
├── GenericS3IssueTests.cs
└── SimpleS3.Extensions.GenericS3.Tests.csproj
├── SimpleS3.Extensions.GenericS3
├── Extensions
│ └── CoreBuilderExtensions.cs
├── GenericS3Config.cs
├── GenericS3InputValidator.cs
├── GenericS3RegionData.cs
├── README.md
└── SimpleS3.Extensions.GenericS3.csproj
├── SimpleS3.Extensions.GoogleCloudStorage.Tests
├── GoogleCloudStorageInputValidatorTests.cs
└── SimpleS3.Extensions.GoogleCloudStorage.Tests.csproj
├── SimpleS3.Extensions.GoogleCloudStorage
├── Extensions
│ └── CoreBuilderExtensions.cs
├── GoogleCloudStorageConfig.cs
├── GoogleCloudStorageInputValidator.cs
├── GoogleCloudStorageRegion.cs
├── GoogleCloudStorageRegionData.cs
├── Properties
│ └── AssemblyInfo.cs
├── README.md
└── SimpleS3.Extensions.GoogleCloudStorage.csproj
├── SimpleS3.Extensions.HttpClient
├── Extensions
│ ├── CoreBuilderExtensions.cs
│ └── HttpClientBuilderExtensions.cs
├── HttpBuilderActions.cs
├── HttpClientConfig.cs
├── HttpClientNetworkDriver.cs
├── IHttpClientBuilder.cs
├── Internal
│ ├── CustomHttpClientBuilder.cs
│ └── HttpRequestMessageExtensions.cs
├── README.md
└── SimpleS3.Extensions.HttpClient.csproj
├── SimpleS3.Extensions.HttpClientFactory.Polly
├── Extensions
│ └── HttpClientBuilderExtensions.cs
├── Internal
│ └── PollyHttpMessageHandler.cs
├── PollyConfig.cs
├── README.md
├── Retry
│ ├── RetryableBufferingStream.cs
│ └── RetryableBufferingStreamWrapper.cs
├── RetryMode.cs
└── SimpleS3.Extensions.HttpClientFactory.Polly.csproj
├── SimpleS3.Extensions.HttpClientFactory
├── Extensions
│ ├── CoreBuilderExtensions.cs
│ └── HttpClientBuilderExtensions.cs
├── HttpBuilderActions.cs
├── HttpClientFactoryConfig.cs
├── HttpClientFactoryNetworkDriver.cs
├── Internal
│ ├── CustomHttpClientFactoryBuilder.cs
│ └── HttpRequestMessageExtensions.cs
├── README.md
└── SimpleS3.Extensions.HttpClientFactory.csproj
├── SimpleS3.Extensions.ProfileManager
├── Abstracts
│ ├── IProfile.cs
│ ├── IProfileManager.cs
│ ├── IProfileManagerBuilder.cs
│ ├── IProfileSerializer.cs
│ ├── IProfileSetup.cs
│ └── IStorage.cs
├── DiskStorageOptions.cs
├── Extensions
│ ├── ConfigExtensions.cs
│ ├── CoreBuilderExtensions.cs
│ ├── ProfileAccessKey.cs
│ ├── ProfileManagerBuilderExtensions.cs
│ ├── ProfileManagerExtensions.cs
│ └── ProfileSetupExtensions.cs
├── Internal
│ ├── DataProtection
│ │ └── DataProtectionKeyProtector.cs
│ ├── Helpers
│ │ └── ConsoleHelper.cs
│ ├── Profile.cs
│ └── ProfileManagerBuilder.cs
├── ProfileManager.cs
├── ProfileManagerOptions.cs
├── README.md
├── Serializers
│ └── DefaultProfileSerializer.cs
├── Setup
│ └── ConsoleProfileSetup.cs
├── SimpleS3.Extensions.ProfileManager.csproj
└── Storage
│ └── DiskStorage.cs
├── SimpleS3.Extensions.Wasabi.Tests
├── SimpleS3.Extensions.Wasabi.Tests.csproj
└── WasabiInputValidatorTests.cs
├── SimpleS3.Extensions.Wasabi
├── Extensions
│ └── CoreBuilderExtensions.cs
├── Properties
│ └── AssemblyInfo.cs
├── README.md
├── SimpleS3.Extensions.Wasabi.csproj
├── WasabiConfig.cs
├── WasabiInputValidator.cs
├── WasabiRegion.cs
└── WasabiRegionData.cs
├── SimpleS3.GenericS3.Tests
├── SimpleS3.GenericS3.Tests.csproj
└── StaticCreatorTests.cs
├── SimpleS3.GenericS3
├── Extensions
│ └── ServiceCollectionExtensions.cs
├── GenericS3Client.cs
└── SimpleS3.GenericS3.csproj
├── SimpleS3.GoogleCloudStorage.Tests
├── SimpleS3.GoogleCloudStorage.Tests.csproj
└── StaticCreatorTests.cs
├── SimpleS3.GoogleCloudStorage
├── Extensions
│ └── ServiceCollectionExtensions.cs
├── GoogleCloudStorageClient.cs
└── SimpleS3.GoogleCloudStorage.csproj
├── SimpleS3.ProviderBase
├── Abstracts
│ └── IClientBuilder.cs
├── ClientBase.cs
├── ClientBuilder.cs
├── ErrorMessages.cs
├── NetworkConfig.cs
└── SimpleS3.ProviderBase.csproj
├── SimpleS3.Utility.S3Template
├── Api.txt
├── Enums
│ ├── ApiType.cs
│ └── DataType.cs
├── Program.cs
├── SimpleS3.Utility.S3Template.csproj
└── Templates
│ ├── RequestMarshalTemplate.txt
│ ├── RequestTemplate.txt
│ ├── ResponseMarshalTemplate.txt
│ └── ResponseTemplate.txt
├── SimpleS3.Utility.Shared
├── S3Provider.cs
├── SimpleS3.Utility.Shared.csproj
└── UtilityHelper.cs
├── SimpleS3.Utility.TestCleanup
├── Program.cs
└── SimpleS3.Utility.TestCleanup.csproj
├── SimpleS3.Utility.TestSetup
├── Program.cs
└── SimpleS3.Utility.TestSetup.csproj
├── SimpleS3.Wasabi.Tests
├── SimpleS3.Wasabi.Tests.csproj
└── StaticCreatorTests.cs
└── SimpleS3.Wasabi
├── Extensions
└── ServiceCollectionExtensions.cs
├── SimpleS3.Wasabi.csproj
└── WasabiClient.cs
/.github/FUNDING.yml:
--------------------------------------------------------------------------------
1 | github: [ Genbox ]
2 | custom: http://paypal.me/IanQvist
3 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/bug_report.md:
--------------------------------------------------------------------------------
1 | ---
2 | name: Bug report
3 | about: Report a bug
4 | title: ''
5 | labels: bug
6 | assignees: ''
7 |
8 | ---
9 |
10 | **Describe the bug**
11 | What is the bug about?
12 |
13 | **How to reproduce?**
14 | Describe steps to reproduce the bug. Please include code to reproduce if possible.
15 |
16 | **Expected behavior**
17 | Describe what you expected to happen.
18 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/feature_request.md:
--------------------------------------------------------------------------------
1 | ---
2 | name: Feature request
3 | about: Suggest a feature for this project
4 | title: ''
5 | labels: enhancement
6 | assignees: ''
7 |
8 | ---
9 |
10 | * [ ] I hereby verify that I am a sponsor.
11 |
12 | Sponsorship is required before you can submit feature requests. See https://github.com/sponsors/Genbox
13 |
14 | **Describe the feature**
15 | Provide a short description of the feature. Why would you like the feature?
16 | If the feature makes changes to an existing or new API please provide an example.
17 |
--------------------------------------------------------------------------------
/.github/workflows/generic-build.yml:
--------------------------------------------------------------------------------
1 | name: Generic build
2 |
3 | on:
4 | push:
5 | branches:
6 | - 'master'
7 | tags-ignore:
8 | - '**'
9 |
10 | env:
11 | DOTNET_EnableDiagnostics: 0
12 | DOTNET_SKIP_FIRST_TIME_EXPERIENCE: true
13 | DOTNET_NOLOGO: true
14 | DOTNET_CLI_TELEMETRY_OPTOUT: true
15 | DOTNET_GENERATE_ASPNET_CERTIFICATE: false
16 |
17 | jobs:
18 | build:
19 | runs-on: ubuntu-latest
20 |
21 | steps:
22 | - uses: actions/checkout@v4.2.2
23 | - name: Setup .NET Core 9.0
24 | uses: actions/setup-dotnet@v4.3.1
25 | with:
26 | dotnet-version: '9.0.x'
27 | - name: Build
28 | run: dotnet build -c Release SimpleS3.sln
--------------------------------------------------------------------------------
/.github/workflows/nuget-release.yml:
--------------------------------------------------------------------------------
1 | name: Nuget release
2 |
3 | on:
4 | push:
5 | tags:
6 | - '[0-9]+.[0-9]+.[0-9]+**'
7 |
8 | env:
9 | DOTNET_EnableDiagnostics: 0
10 | DOTNET_SKIP_FIRST_TIME_EXPERIENCE: true
11 | DOTNET_NOLOGO: true
12 | DOTNET_CLI_TELEMETRY_OPTOUT: true
13 | DOTNET_GENERATE_ASPNET_CERTIFICATE: false
14 |
15 | jobs:
16 | build:
17 | runs-on: ubuntu-latest
18 |
19 | steps:
20 | - uses: actions/checkout@v4.2.2
21 | - name: Setup .NET Core 9.0
22 | uses: actions/setup-dotnet@v4.3.1
23 | with:
24 | dotnet-version: '9.0.x'
25 | - name: Pack release
26 | run: dotnet pack -c Release -o tmp SimpleS3.sln
27 | - name: Upload to nuget
28 | run: dotnet nuget push --skip-duplicate -k ${{secrets.NUGET_KEY}} -s https://api.nuget.org/v3/index.json tmp/*
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Build results
2 | [Bb]in/
3 | [Oo]bj/
4 | [Ll]og/
5 |
6 | # NuGet Packages
7 | *.nupkg
8 | *.snupkg
9 |
10 | # Others
11 | *.pfx
12 | *.publishsettings
13 |
14 | # SQL Server files
15 | *.mdf
16 | *.ldf
17 | *.ndf
18 |
19 | # Visual Studio cache folder
20 | .vs/
21 |
22 | # Jetbrains Rider cache folder
23 | .idea/
24 | *.sln.DotSettings.user
25 |
--------------------------------------------------------------------------------
/Config.json:
--------------------------------------------------------------------------------
1 | {
2 | "Proxy": {
3 | "UseProxy": false,
4 | "ProxyAddress": "http://127.0.0.1:8888"
5 | },
6 |
7 | "Logging": {
8 | "LogLevel": {
9 | "Default": "Information" //Critical, Error, Warning, Information, Debug, Trace
10 | }
11 | }
12 | }
--------------------------------------------------------------------------------
/Imports/Benchmarks.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Exe
5 | false
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
--------------------------------------------------------------------------------
/Imports/Console.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Exe
5 | false
6 |
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/Imports/Examples.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Exe
5 | false
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/Locals/Benchmarks.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | net9.0
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Locals/Console.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | net9.0
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Locals/Directory.Build.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | A simple, secure and high-performance library to communicate with Amazon S3 compatible APIs.
5 | AmazonS3 BackBlaze Wasabi GCS GoogleCloudStorage
6 | false
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Locals/Examples.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | net9.0
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Locals/Library.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | netstandard2.0
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Locals/Tests.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | net9.0
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/SECURITY.md:
--------------------------------------------------------------------------------
1 | # Security Policy
2 |
3 | ## Reporting a Vulnerability
4 |
5 | If you find a security vulnerability, please report it as an issue with [SECURITY] in the issue name.
6 | If the vulnerability is sensitive in nature, send an e-mail to qvistian@gmail.com
7 |
--------------------------------------------------------------------------------
/Src/Directory.Packages.props:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/Src/ProviderTests/.globalconfig:
--------------------------------------------------------------------------------
1 | dotnet_diagnostic.CA1515.severity = none # Consider making public types internal
2 | dotnet_diagnostic.CS8618.severity = none # Non-nullable field must contain a non-null value when exiting constructor. Consider declaring as nullable.
3 | dotnet_diagnostic.CA1822.severity = none # Mark members as static
4 |
--------------------------------------------------------------------------------
/Src/ProviderTests/Buckets/HeadBucketTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.ProviderTests.Code;
2 | using Genbox.ProviderTests.Misc;
3 | using Genbox.SimpleS3.Core.Abstracts;
4 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
5 | using Genbox.SimpleS3.Utility.Shared;
6 |
7 | namespace Genbox.ProviderTests.Buckets;
8 |
9 | public class HeadBucketTests : TestBase
10 | {
11 | [Theory]
12 | [MultipleProviders(S3Provider.All)]
13 | public async Task HeadBucket(S3Provider _, string bucket, ISimpleClient client)
14 | {
15 | HeadBucketResponse headResp = await client.HeadBucketAsync(bucket);
16 | Assert.Equal(200, headResp.StatusCode);
17 |
18 | headResp = await client.HeadBucketAsync(GetTemporaryBucket());
19 | Assert.False(headResp.IsSuccess);
20 | }
21 | }
--------------------------------------------------------------------------------
/Src/ProviderTests/Buckets/ListBucketsTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.ProviderTests.Code;
2 | using Genbox.ProviderTests.Misc;
3 | using Genbox.SimpleS3.Core.Abstracts;
4 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
5 | using Genbox.SimpleS3.Utility.Shared;
6 |
7 | namespace Genbox.ProviderTests.Buckets;
8 |
9 | public class ListBucketsTests : TestBase
10 | {
11 | [Theory]
12 | [MultipleProviders(S3Provider.All)]
13 | public async Task ListBuckets(S3Provider _, string bucket, ISimpleClient client)
14 | {
15 | ListBucketsResponse listResp = await client.ListBucketsAsync();
16 | Assert.True(listResp.Buckets.Count > 0);
17 | Assert.Single(listResp.Buckets, x => x.BucketName == bucket);
18 | }
19 | }
--------------------------------------------------------------------------------
/Src/ProviderTests/Buckets/PutPublicAccessBlockTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.ProviderTests.Code;
2 | using Genbox.ProviderTests.Misc;
3 | using Genbox.SimpleS3.Core.Abstracts;
4 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
5 | using Genbox.SimpleS3.Utility.Shared;
6 |
7 | namespace Genbox.ProviderTests.Buckets;
8 |
9 | public class PutPublicAccessBlockTests : TestBase
10 | {
11 | [Theory]
12 | [MultipleProviders(S3Provider.AmazonS3)]
13 | public async Task PutPublicAccessBlockRequest(S3Provider provider, string _, ISimpleClient client)
14 | {
15 | await CreateTempBucketAsync(provider, client, async tempBucket =>
16 | {
17 | PutPublicAccessBlockResponse resp = await client.PutPublicAccessBlockAsync(tempBucket);
18 | Assert.Equal(200, resp.StatusCode);
19 | });
20 | }
21 | }
--------------------------------------------------------------------------------
/Src/ProviderTests/Code/TestConstants.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.ProviderTests.Code;
2 |
3 | internal static class TestConstants
4 | {
5 | public const string TestUsername = "qvistian";
6 | public const string TestEmail = "qvistian@gmail.com";
7 | public const string TestUserId = "c5c6efaa2ab5d42d85f044a90bfb0bfcfc1daa322d725a2aeff1915fb31717ce";
8 | }
--------------------------------------------------------------------------------
/Src/ProviderTests/Misc/GetObjectTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.ProviderTests.Code;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Extensions;
4 | using Genbox.SimpleS3.Utility.Shared;
5 |
6 | namespace Genbox.ProviderTests.Misc;
7 |
8 | public class MiscTests : TestBase
9 | {
10 | [Theory]
11 | [MultipleProviders(S3Provider.AmazonS3)]
12 | public async Task IsEncodingCorrect(S3Provider _, string bucket, ISimpleClient client)
13 | {
14 | //This tests if '=' is NOT encoded. S3 does not use encoding of paths in signed requests, but all other AWS APIs do
15 | var putResp = await client.PutObjectStringAsync(bucket, "a=a", "hello");
16 | Assert.Equal(200, putResp.StatusCode);
17 | }
18 | }
--------------------------------------------------------------------------------
/Src/ProviderTests/Objects/DeleteObjectTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.ProviderTests.Code;
2 | using Genbox.ProviderTests.Misc;
3 | using Genbox.SimpleS3.Core.Abstracts;
4 | using Genbox.SimpleS3.Core.Network.Responses.Objects;
5 | using Genbox.SimpleS3.Utility.Shared;
6 |
7 | namespace Genbox.ProviderTests.Objects;
8 |
9 | public class DeleteObjectTests : TestBase
10 | {
11 | [Theory]
12 | [MultipleProviders(S3Provider.All)]
13 | public async Task DeleteObject(S3Provider provider, string bucket, ISimpleClient client)
14 | {
15 | PutObjectResponse putResp = await client.PutObjectAsync(bucket, nameof(DeleteObject), null);
16 | Assert.Equal(200, putResp.StatusCode);
17 |
18 | DeleteObjectResponse delREsp = await client.DeleteObjectAsync(bucket, nameof(DeleteObject));
19 | Assert.Equal(204, delREsp.StatusCode);
20 |
21 | if (provider == S3Provider.AmazonS3)
22 | Assert.True(delREsp.IsDeleteMarker);
23 | }
24 | }
--------------------------------------------------------------------------------
/Src/ProviderTests/ProviderTests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | PreserveNewest
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/Src/ProviderTests/README.md:
--------------------------------------------------------------------------------
1 | To use the ProviderTests project you will need to setup the test profiles. Run the utility 'TestSetup' to create the profiles.
2 |
3 | For Amazon S3 tests to work, update the TestConstants.cs file with the values specific to your account.
--------------------------------------------------------------------------------
/Src/SimpleS3.AmazonS3.Tests/SimpleS3.AmazonS3.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Src/SimpleS3.AmazonS3.Tests/StaticCreatorTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.TestBase.Code;
2 | using Genbox.SimpleS3.Extensions.AmazonS3;
3 |
4 | namespace Genbox.SimpleS3.AmazonS3.Tests;
5 |
6 | public class StaticCreatorTests
7 | {
8 | [Fact]
9 | public async Task StaticClient()
10 | {
11 | NullNetworkDriver driver = new NullNetworkDriver();
12 |
13 | AmazonS3Config config = new AmazonS3Config("ExampleKeyId00000000", "wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLEKEY", AmazonS3Region.UsEast1);
14 | using AmazonS3Client client = new AmazonS3Client(config, driver);
15 |
16 | await client.GetObjectAsync("testbucket", "GetObjectAsync");
17 | Assert.Equal("https://testbucket.s3.us-east-1.amazonaws.com/GetObjectAsync", driver.LastUrl);
18 | }
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.AmazonS3/SimpleS3.AmazonS3.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/Src/SimpleS3.BackBlazeB2.Tests/SimpleS3.BackBlazeB2.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Src/SimpleS3.BackBlazeB2.Tests/StaticCreatorTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.TestBase.Code;
2 | using Genbox.SimpleS3.Extensions.BackBlazeB2;
3 |
4 | namespace Genbox.SimpleS3.BackBlazeB2.Tests;
5 |
6 | public class StaticCreatorTests
7 | {
8 | [Fact]
9 | public async Task StaticClient()
10 | {
11 | NullNetworkDriver driver = new NullNetworkDriver();
12 |
13 | BackBlazeB2Config config = new BackBlazeB2Config("ExampleKeyId00000000", "wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLEKEY", BackBlazeB2Region.UsWest001);
14 | using BackBlazeB2Client client = new BackBlazeB2Client(config, driver);
15 |
16 | await client.GetObjectAsync("testbucket", "GetObjectAsync");
17 | Assert.Equal("https://testbucket.s3.us-west-001.backblazeb2.com/GetObjectAsync", driver.LastUrl);
18 | }
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.BackBlazeB2/SimpleS3.BackBlazeB2.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Authentication/IAccessKey.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Authentication;
2 |
3 | public interface IAccessKey
4 | {
5 | string KeyId { get; }
6 | byte[] SecretKey { get; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Authentication/IAccessKeyProtector.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Authentication;
2 |
3 | public interface IAccessKeyProtector
4 | {
5 | byte[] ProtectKey(byte[] key);
6 | byte[] UnprotectKey(byte[] key);
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Authentication/IAuthorizationBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Authentication;
4 |
5 | public interface IAuthorizationBuilder
6 | {
7 | void BuildAuthorization(IRequest request);
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Authentication/IChunkedSignatureBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Authentication;
4 |
5 | public interface IChunkedSignatureBuilder
6 | {
7 | byte[] CreateChunkSignature(IRequest request, byte[] previousSignature, byte[] content, int offset, int length);
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Authentication/IScopeBuilder.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Authentication;
2 |
3 | public interface IScopeBuilder
4 | {
5 | string CreateScope(string service, DateTimeOffset date);
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Authentication/ISignatureBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Authentication;
4 |
5 | public interface ISignatureBuilder
6 | {
7 | byte[] CreateSignature(IRequest request, bool enablePayloadSignature = true);
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Authentication/ISigningKeyBuilder.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Authentication;
2 |
3 | public interface ISigningKeyBuilder
4 | {
5 | byte[] CreateSigningKey(DateTimeOffset dateTime);
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Enums/HttpMethodType.cs:
--------------------------------------------------------------------------------
1 | // ReSharper disable InconsistentNaming
2 | namespace Genbox.SimpleS3.Core.Abstracts.Enums;
3 |
4 | public enum HttpMethodType
5 | {
6 | Unknown = 0,
7 | GET,
8 | PUT,
9 | HEAD,
10 | DELETE,
11 | POST
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Enums/NamingMode.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Enums;
2 |
3 | public enum NamingMode
4 | {
5 | Unknown = 0,
6 | VirtualHost,
7 | PathStyle
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Enums/SignatureMode.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Enums;
2 |
3 | public enum SignatureMode : byte
4 | {
5 | Unknown = 0,
6 | Unsigned,
7 | FullSignature,
8 | StreamingSignature
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Enums/ValidationStatus.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Enums;
2 |
3 | public enum ValidationStatus
4 | {
5 | Unknown = 0,
6 | Ok,
7 | NullInput,
8 | WrongLength,
9 | WrongFormat,
10 | ReservedName
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Factories/IMarshalFactory.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 |
4 | namespace Genbox.SimpleS3.Core.Abstracts.Factories;
5 |
6 | public interface IMarshalFactory
7 | {
8 | Stream? MarshalRequest(SimpleS3Config config, TRequest request) where TRequest : IRequest;
9 | void MarshalResponse(SimpleS3Config config, TResponse response, IDictionary headers, Stream responseStream) where TResponse : IResponse;
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Factories/IPostMapperFactory.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 |
4 | namespace Genbox.SimpleS3.Core.Abstracts.Factories;
5 |
6 | public interface IPostMapperFactory
7 | {
8 | void PostMap(SimpleS3Config config, TRequest request, TResponse response) where TRequest : IRequest where TResponse : IResponse;
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Factories/IRequestValidatorFactory.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Factories;
4 |
5 | public interface IRequestValidatorFactory
6 | {
7 | void ValidateAndThrow(T obj) where T : IRequest;
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/ICoreBuilder.cs:
--------------------------------------------------------------------------------
1 | using Microsoft.Extensions.DependencyInjection;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts;
4 |
5 | public interface ICoreBuilder
6 | {
7 | IServiceCollection Services { get; }
8 |
9 | string Name { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Provider/IEndpointBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Provider;
4 |
5 | public interface IEndpointBuilder
6 | {
7 | IEndpointData GetEndpoint(IRequest request);
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Provider/IEndpointData.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Provider;
2 |
3 | public interface IEndpointData
4 | {
5 | string Host { get; }
6 | string Endpoint { get; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Provider/IInputValidator.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Provider;
4 |
5 | public interface IInputValidator
6 | {
7 | bool TryValidateKeyId(string? keyId, out ValidationStatus status, out string? message);
8 | bool TryValidateAccessKey(byte[]? accessKey, out ValidationStatus status, out string? message);
9 | bool TryValidateBucketName(string? bucketName, BucketNameValidationMode mode, out ValidationStatus status, out string? message);
10 | bool TryValidateObjectKey(string? objectKey, ObjectKeyValidationMode mode, out ValidationStatus status, out string? message);
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Region/IRegionConverter.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Region;
2 |
3 | public interface IRegionConverter
4 | {
5 | IRegionInfo GetRegion(int enumValue);
6 | IRegionInfo GetRegion(string regionCode);
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Region/IRegionData.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Region;
2 |
3 | public interface IRegionData
4 | {
5 | IEnumerable GetRegions();
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Region/IRegionInfo.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Region;
2 |
3 | public interface IRegionInfo
4 | {
5 | Enum EnumValue { get; }
6 | string Code { get; }
7 | string Name { get; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Region/RegionInfo.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Region;
2 |
3 | public class RegionInfo(Enum enumValue, string code, string name) : IRegionInfo
4 | {
5 | public Enum EnumValue { get; } = enumValue;
6 | public string Code { get; } = code;
7 | public string Name { get; } = name;
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Request/INetworkDriver.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Request;
4 |
5 | public interface INetworkDriver
6 | {
7 | Task SendRequestAsync(IRequest request, string url, Stream? requestStream, CancellationToken cancellationToken = default) where T : IResponse;
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Request/IRequestHandler.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Request;
4 |
5 | public interface IRequestHandler
6 | {
7 | Task SendRequestAsync(TReq request, CancellationToken token = default) where TReq : IRequest where TResp : IResponse, new();
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Request/IRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Request;
4 |
5 | [UsedImplicitly(ImplicitUseTargetFlags.WithInheritors)]
6 | public interface IRequestMarshal;
7 |
8 | public interface IRequestMarshal : IRequestMarshal where T : IRequest
9 | {
10 | Stream? MarshalRequest(T request, SimpleS3Config config);
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Request/IResponseHandler.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Request;
4 |
5 | public interface IResponseHandler
6 | {
7 | Task HandleResponseAsync(TReq request, string url, Stream? requestStream, CancellationToken token) where TReq : IRequest where TResp : IResponse, new();
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Request/ISignedRequestHandler.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 |
4 | namespace Genbox.SimpleS3.Core.Abstracts.Request;
5 |
6 | public interface ISignedRequestHandler
7 | {
8 | string SignRequest(TReq request, TimeSpan expiresIn) where TReq : IRequest;
9 |
10 | Task SendRequestAsync(string url, HttpMethodType httpMethod, Stream? content = null, CancellationToken token = default) where TResp : IResponse, new();
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Response/HttpResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | public readonly struct HttpResponse(Stream? content, IDictionary headers, int statusCode)
4 | {
5 | public Stream? Content { get; } = content;
6 | public IDictionary Headers { get; } = headers;
7 | public int StatusCode { get; } = statusCode;
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Response/IError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Response;
4 |
5 | public interface IError
6 | {
7 | /// Contains the error code returned from AWS S3
8 | ErrorCode Code { get; }
9 |
10 | /// Contains the message returned from AWS S3
11 | string Message { get; }
12 |
13 | /// Additional info that was returned from the error
14 | IDictionary Data { get; }
15 |
16 | /// Returns a string with the most important fields. This only works if the error is a specialized subtype of the GenericError class
17 | string GetErrorDetails();
18 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Response/IPostMapper.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Abstracts.Response;
5 |
6 | [UsedImplicitly(ImplicitUseTargetFlags.WithInheritors)]
7 | public interface IPostMapper;
8 |
9 | public interface IPostMapper : IPostMapper where TRequest : IRequest where TResponse : IResponse
10 | {
11 | void PostMap(TRequest request, TResponse response);
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Response/IResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Response;
4 |
5 | [UsedImplicitly(ImplicitUseTargetFlags.WithInheritors)]
6 | public interface IResponseMarshal;
7 |
8 | public interface IResponseMarshal : IResponseMarshal where TResponse : IResponse
9 | {
10 | void MarshalResponse(SimpleS3Config config, TResponse response, IDictionary headers, Stream responseStream);
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/ServiceBuilderBase.cs:
--------------------------------------------------------------------------------
1 | using Microsoft.Extensions.DependencyInjection;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts;
4 |
5 | public abstract class ServiceBuilderBase(IServiceCollection services, string? name = null)
6 | {
7 | public static string DefaultName => string.Empty;
8 |
9 | public IServiceCollection Services { get; } = services;
10 |
11 | public string Name { get; } = name ?? DefaultName;
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/SimpleS3.Core.Abstracts.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Wrappers/IRequestStreamWrapper.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Wrappers;
4 |
5 | /// Interface for stateless wrappers. USe this when you want to wrap streams on a low level before sending to the S3 API.
6 | public interface IRequestStreamWrapper
7 | {
8 | bool IsSupported(IRequest request);
9 |
10 | Stream Wrap(Stream input, IRequest request);
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Wrappers/IRequestWrapper.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Request;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Wrappers;
4 |
5 | /// Interface for defining stateful wrappers. This is used for when you wish to wrap the whole request stream.
6 | public interface IRequestWrapper
7 | {
8 | bool IsSupported(IRequest request);
9 |
10 | Stream Wrap(Stream input, IRequest request);
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Wrappers/IResponseStreamWrapper.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Wrappers;
4 |
5 | public interface IResponseStreamWrapper
6 | {
7 | bool IsSupported(IResponse response);
8 |
9 | Stream Wrap(Stream input, IResponse response);
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Abstracts/Wrappers/IResponseWrapper.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Wrappers;
4 |
5 | public interface IResponseWrapper
6 | {
7 | bool IsSupported(IResponse response);
8 |
9 | Stream Wrap(Stream input, IResponse response);
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Benchmarks/.globalconfig:
--------------------------------------------------------------------------------
1 | dotnet_diagnostic.CA1515.severity = none # Consider making public types internal
2 | dotnet_diagnostic.CS8618.severity = none # Non-nullable field must contain a non-null value when exiting constructor. Consider declaring as nullable.
3 | dotnet_diagnostic.CA1822.severity = none # Mark members as static
4 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Benchmarks/Benchmarks/CharHelperBenchmarks.cs:
--------------------------------------------------------------------------------
1 | using System.Diagnostics.CodeAnalysis;
2 | using Genbox.SimpleS3.Core.Common.Helpers;
3 |
4 | namespace Genbox.SimpleS3.Core.Benchmarks.Benchmarks;
5 |
6 | [SuppressMessage("ReSharper", "ConvertToConstant.Local")]
7 | public class CharHelperBenchmarks
8 | {
9 | [Benchmark]
10 | public bool CharRangeWithOr()
11 | {
12 | char c = 'f';
13 | return c is >= 'a' or <= '<';
14 | }
15 |
16 | [Benchmark]
17 | public bool CharRangeWithHelper()
18 | {
19 | char c = 'f';
20 | return CharHelper.InRange(c, 'a', 'z');
21 | }
22 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Benchmarks/Benchmarks/TypeLookupBenchmarks.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Benchmarks.Benchmarks;
2 |
3 | public class TypeLookupBenchmarks
4 | {
5 | private readonly HashSet _stringDict = new HashSet();
6 | private readonly Type _type = typeof(TypeLookupBenchmarks);
7 | private readonly HashSet _typeDict = new HashSet();
8 |
9 | [IterationCleanup]
10 | public void Cleanup()
11 | {
12 | _stringDict.Clear();
13 | _typeDict.Clear();
14 | }
15 |
16 | [Benchmark]
17 | public void AddWithString()
18 | {
19 | _stringDict.Add(_type.Name);
20 | }
21 |
22 | [Benchmark]
23 | public bool LookupWithString() => _stringDict.Contains(_type.Name);
24 |
25 | [Benchmark]
26 | public void AddWithType()
27 | {
28 | _typeDict.Add(_type);
29 | }
30 |
31 | [Benchmark]
32 | public bool LookupWithType() => _typeDict.Contains(_type);
33 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Benchmarks/Misc/DummyRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Network.Requests;
3 |
4 | namespace Genbox.SimpleS3.Core.Benchmarks.Misc;
5 |
6 | public class DummyRequest() : BaseRequest(HttpMethodType.GET);
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Benchmarks/SimpleS3.Core.Benchmarks.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common.Tests/Code/TestEnum.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Tests.Code;
4 |
5 | internal enum TestEnum
6 | {
7 | Unknown = 0,
8 | Value1 = 1,
9 | Value2 = 2,
10 |
11 | [Display(Name = "Value3-FromAttribute")]
12 | Value3 = 3
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common.Tests/Code/TestRegion.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common.Tests.Code;
2 |
3 | internal enum TestRegion
4 | {
5 | RegionOne,
6 | RegionTwo
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common.Tests/Code/TestRegionData.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Region;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Tests.Code;
4 |
5 | internal sealed class TestRegionData : IRegionData
6 | {
7 | public IEnumerable GetRegions()
8 | {
9 | yield return new RegionInfo(TestRegion.RegionOne, "Region-One", "The first region");
10 | yield return new RegionInfo(TestRegion.RegionTwo, "Region-Two", "The second region");
11 | }
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common.Tests/SimpleS3.Core.Common.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Authentication/AccessKey.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common.Authentication;
2 |
3 | /// Stores an access key in raw format. This is more secure than using as the backing byte array can be garbage collected.
4 | public class AccessKey(string keyId, byte[] secretKey) : AccessKeyBase(keyId, secretKey);
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Authentication/AccessKeyBase.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Authentication;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Authentication;
4 |
5 | /// Provides a common base for access keys
6 | public abstract class AccessKeyBase(string keyId, byte[] secretKey) : IAccessKey
7 | {
8 | public string KeyId { get; } = keyId;
9 | public byte[] SecretKey { get; } = secretKey;
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Authentication/StringAccessKey.cs:
--------------------------------------------------------------------------------
1 | using System.Text;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Authentication;
4 |
5 | /// Provides a convenient way to provide an access key as string. However, it is insecure as you store the key as a string that does not get garbage collected.
6 | public class StringAccessKey(string keyId, string secretKey) : AccessKeyBase(keyId, Encoding.UTF8.GetBytes(secretKey));
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Exceptions/S3Exception.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common.Exceptions;
2 |
3 | public class S3Exception(string? message = null, Exception? innException = null) : Exception(message, innException);
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Exceptions/S3RequestException.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Exceptions;
4 |
5 | public class S3RequestException(IResponse response, string? message = null, Exception? innerException = null) : S3Exception(message, innerException)
6 | {
7 | public IResponse Response { get; } = response;
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Extensions/RegionConverterExtensions.cs:
--------------------------------------------------------------------------------
1 | using System.Globalization;
2 | using Genbox.SimpleS3.Core.Abstracts.Region;
3 |
4 | namespace Genbox.SimpleS3.Core.Common.Extensions;
5 |
6 | public static class RegionConverterExtensions
7 | {
8 | public static IRegionInfo GetRegion(this IRegionConverter converter, Enum enumValue)
9 | {
10 | int intVal = (int)Convert.ChangeType(enumValue, typeof(int), NumberFormatInfo.InvariantInfo);
11 | return converter.GetRegion(intVal);
12 | }
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Extensions/StringExtensions.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common.Extensions;
2 |
3 | public static class StringExtensions
4 | {
5 | public static bool Contains(this string str, string value, StringComparison comparison) => str.IndexOf(value, comparison) >= 0;
6 |
7 | public static bool Contains(this string str, char value) => str.IndexOf(value) >= 0;
8 |
9 | public static bool EndsWith(this string str, char character)
10 | {
11 | if (str.Length == 0)
12 | return false;
13 |
14 | return str[str.Length - 1] == character;
15 | }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Helpers/CharHelper.cs:
--------------------------------------------------------------------------------
1 | using System.Runtime.CompilerServices;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Helpers;
4 |
5 | public static class CharHelper
6 | {
7 | [MethodImpl(MethodImplOptions.AggressiveInlining)]
8 | public static bool InRange(char c, char min, char max) => unchecked((uint)(c - min) <= (uint)(max - min));
9 |
10 | public static bool OneOf(char c, params char[] chars)
11 | {
12 | foreach (char ch in chars)
13 | {
14 | if (c == ch)
15 | return true;
16 | }
17 |
18 | return false;
19 | }
20 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Helpers/KeyHelper.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Authentication;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Helpers;
4 |
5 | public static class KeyHelper
6 | {
7 | public static byte[] ProtectKey(byte[] key, IAccessKeyProtector? protector, bool clearKey = true)
8 | {
9 | if (protector == null)
10 | return key;
11 |
12 | byte[] previous = key;
13 | key = protector.ProtectKey(key);
14 |
15 | if (clearKey)
16 | Array.Clear(previous, 0, previous.Length);
17 |
18 | return key;
19 | }
20 |
21 | public static byte[] UnprotectKey(byte[] key, IAccessKeyProtector? protector)
22 | {
23 | if (protector == null)
24 | return key;
25 |
26 | return protector.UnprotectKey(key);
27 | }
28 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/HttpVersion.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common;
2 |
3 | public enum HttpVersion
4 | {
5 | Unknown,
6 | Http1,
7 | Http2,
8 | Http3
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Internal/Compat/CallerArgumentExpressionAttribute.cs:
--------------------------------------------------------------------------------
1 | #if NETSTANDARD2_0
2 |
3 | // ReSharper disable All
4 | namespace System.Runtime.CompilerServices;
5 |
6 | [AttributeUsage(AttributeTargets.Parameter, AllowMultiple = false, Inherited = false)]
7 | internal sealed class CallerArgumentExpressionAttribute : Attribute
8 | {
9 | public CallerArgumentExpressionAttribute(string parameterName)
10 | {
11 | ParameterName = parameterName;
12 | }
13 |
14 | public string ParameterName { get; }
15 | }
16 | #endif
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Internal/Compat/DoesNotReturnIfAttribute.cs:
--------------------------------------------------------------------------------
1 | #if NETSTANDARD2_0
2 |
3 | // ReSharper disable All
4 | namespace System.Diagnostics.CodeAnalysis;
5 |
6 | [AttributeUsage(AttributeTargets.Parameter)]
7 | internal sealed class DoesNotReturnIfAttribute : Attribute
8 | {
9 | public DoesNotReturnIfAttribute(bool notUsed) {}
10 | }
11 | #endif
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Internal/Compat/NotNullAttribute.cs:
--------------------------------------------------------------------------------
1 | #if NETSTANDARD2_0
2 |
3 | // ReSharper disable All
4 | namespace System.Diagnostics.CodeAnalysis;
5 |
6 | [AttributeUsage(AttributeTargets.Parameter)]
7 | internal sealed class NotNullAttribute : Attribute
8 | {
9 | public NotNullAttribute() {}
10 | }
11 | #endif
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Marshal/IHasBucketName.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common.Marshal;
2 |
3 | public interface IHasBucketName
4 | {
5 | string BucketName { get; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Marshal/IHasObjectKey.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common.Marshal;
2 |
3 | public interface IHasObjectKey
4 | {
5 | string ObjectKey { get; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Misc/Constants.cs:
--------------------------------------------------------------------------------
1 | using System.Text;
2 |
3 | namespace Genbox.SimpleS3.Core.Common.Misc;
4 |
5 | public static class Constants
6 | {
7 | public const string EmptySha256 = "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855";
8 | public const string AmzMetadata = "x-amz-meta-";
9 | public static readonly string DefaultUserAgent = "SimpleS3 library " + typeof(Constants).Assembly.GetName().Version;
10 | public static readonly string EmptyMd5 = "d41d8cd98f00b204e9800998ecf8427e";
11 | public static readonly byte[] EmptyMd5Bytes = [0xd4, 0x1d, 0x8c, 0xd9, 0x8f, 0x00, 0xb2, 0x04, 0xe9, 0x80, 0x09, 0x98, 0xec, 0xf8, 0x42, 0x7e];
12 | public static readonly UTF8Encoding Utf8NoBom = new UTF8Encoding(false);
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/SimpleS3.Core.Common.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Common/Validation/RequireException.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Common.Validation;
2 |
3 | public class RequireException(string callerArgument, string callerMember, int lineNumber, string? message = null) : Exception(message)
4 | {
5 | public string CallerArgument { get; } = callerArgument;
6 | public string CallerMember { get; } = callerMember;
7 | public int LineNumber { get; } = lineNumber;
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.TestBase/Code/NullNetworkDriver.cs:
--------------------------------------------------------------------------------
1 | using System.Diagnostics.CodeAnalysis;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Abstracts.Response;
4 |
5 | namespace Genbox.SimpleS3.Core.TestBase.Code;
6 |
7 | [SuppressMessage("Maintainability", "CA1515:Consider making public types internal")]
8 | public class NullNetworkDriver : INetworkDriver
9 | {
10 | public string? LastUrl { get; private set; }
11 |
12 | public Task SendRequestAsync(IRequest request, string url, Stream? requestStream, CancellationToken cancellationToken = default) where T : IResponse
13 | {
14 | LastUrl = url;
15 | return Task.FromResult(new HttpResponse(null, new Dictionary(), 200));
16 | }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Tests/GenericTests/Builders/KmsContextBuilderTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Builders;
2 |
3 | namespace Genbox.SimpleS3.Core.Tests.GenericTests.Builders;
4 |
5 | public class KmsContextBuilderTests
6 | {
7 | [Fact]
8 | public void DisallowSpecialChars()
9 | {
10 | KmsContextBuilder b = new KmsContextBuilder();
11 | Assert.Throws(() => b.AddEntry("!", "¤"));
12 | }
13 |
14 | [Fact]
15 | public void GenericTest()
16 | {
17 | KmsContextBuilder b = new KmsContextBuilder();
18 | Assert.Null(b.Build());
19 |
20 | b.AddEntry("SomeKey", "SomeValue");
21 |
22 | Assert.Equal("\"SomeKey\":\"SomeValue\"", b.Build());
23 |
24 | b.AddEntry("SomeOtherKey", "SomeOtherValue");
25 |
26 | Assert.Equal("\"SomeKey\":\"SomeValue\",\"SomeOtherKey\":\"SomeOtherValue\"", b.Build());
27 | }
28 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Tests/GenericTests/Builders/MetadataBuilderTests.cs:
--------------------------------------------------------------------------------
1 | using System.Globalization;
2 | using Genbox.SimpleS3.Core.Builders;
3 |
4 | namespace Genbox.SimpleS3.Core.Tests.GenericTests.Builders;
5 |
6 | public class MetadataBuilderTests
7 | {
8 | [Fact]
9 | public void InvalidChars()
10 | {
11 | MetadataBuilder b = new MetadataBuilder();
12 |
13 | foreach (char invalidChar in "\t\0\n")
14 | Assert.Throws(() => { b.Add("a", invalidChar.ToString(CultureInfo.InvariantCulture)); });
15 | }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core.Tests/SimpleS3.Core.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/Clients/ISignedClient.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Abstracts.Response;
4 |
5 | namespace Genbox.SimpleS3.Core.Abstracts.Clients;
6 |
7 | public interface ISignedClient
8 | {
9 | string SignRequest(TReq request, TimeSpan expiresIn) where TReq : IRequest;
10 | Task SendSignedRequestAsync(string url, HttpMethodType httpMethod, Stream? content = null, CancellationToken token = default) where TResp : IResponse, new();
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/Features/IAutoMapConfig.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Features;
2 |
3 | public interface IAutoMapConfig
4 | {
5 | Func AutoMapDisabledFor { get; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/Features/IContainSensitiveMaterial.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Features;
2 |
3 | public interface IContainSensitiveMaterial
4 | {
5 | void ClearSensitiveMaterial();
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/Features/IContentMd5Config.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Abstracts.Features;
4 |
5 | public interface IContentMd5Config : IHasContentMd5
6 | {
7 | Func ForceContentMd5 { get; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/Features/ISupportStreaming.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Features;
2 |
3 | public interface ISupportStreaming;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/ISimpleClient.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Clients;
2 | using Genbox.SimpleS3.Core.Abstracts.Transfer;
3 |
4 | namespace Genbox.SimpleS3.Core.Abstracts;
5 |
6 | public interface ISimpleClient : IBucketClient, IObjectClient, IMultipartClient, ITransfer, IMultipartTransfer, ISignedClient;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/Operations/ISignedOperations.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Abstracts.Response;
4 |
5 | namespace Genbox.SimpleS3.Core.Abstracts.Operations;
6 |
7 | public interface ISignedOperations
8 | {
9 | string SignRequest(TReq request, TimeSpan expiresIn) where TReq : IRequest;
10 | Task SendSignedRequestAsync(string url, HttpMethodType httpMethod, Stream? content = null, CancellationToken token = default) where TResp : IResponse, new();
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Abstracts/Transfer/ITransfer.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Abstracts.Transfer;
2 |
3 | public interface ITransfer
4 | {
5 | IUpload CreateUpload(string bucket, string objectKey);
6 | IDownload CreateDownload(string bucket, string objectKey);
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Builders/MfaAuthenticationBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.HttpBuilders.Abstracts;
2 |
3 | namespace Genbox.SimpleS3.Core.Builders;
4 |
5 | public class MfaAuthenticationBuilder : IHttpHeaderBuilder
6 | {
7 | private string? _serialNumber;
8 | private string? _value;
9 |
10 | public string? HeaderName => null;
11 |
12 | public string? Build()
13 | {
14 | if (!HasData())
15 | return null;
16 |
17 | return $"{_serialNumber} {_value}";
18 | }
19 |
20 | public void Reset()
21 | {
22 | _serialNumber = null;
23 | _value = null;
24 | }
25 |
26 | public bool HasData() => _serialNumber != null;
27 |
28 | public void SetAuth(string serialNumber, string value)
29 | {
30 | _serialNumber = serialNumber;
31 | _value = value;
32 | }
33 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/ChecksumAlgorithm.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | /// Indicates the algorithm that you want Amazon S3 to use to create the checksum for the object. For more information, see https://docs.aws.amazon.com/AmazonS3/latest/userguide/checking-object-integrity.html
7 | [FastEnum]
8 | public enum ChecksumAlgorithm
9 | {
10 | Unknown = 0,
11 | [Display(Name = "CRC32")]Crc32,
12 | [Display(Name = "CRC32C")]Crc32C,
13 | [Display(Name = "SHA1")]Sha1,
14 | [Display(Name = "SHA256")]Sha256,
15 | [Display(Name = "CRC64NVME")]Crc64Nvme,
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/ChecksumType.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | /// Indicates the checksum type that you want Amazon S3 to use to calculate the object’s checksum value. For more information, see https://docs.aws.amazon.com/AmazonS3/latest/userguide/checking-object-integrity.html
7 | [FastEnum]
8 | public enum ChecksumType
9 | {
10 | Unknown = 0,
11 | [Display(Name = "COMPOSITE")]Composite,
12 | [Display(Name = "FULL_OBJECT")]FullObject
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/CompressionType.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum CompressionType
8 | {
9 | Unknown = 0,
10 | [Display(Name = "NONE")]None,
11 | [Display(Name = "GZIP")]Gzip,
12 | [Display(Name = "BZIP2")]Bzip
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/EncodingType.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | /// Used to specify the encoding of responses when using certain APIs that are based on XML.
7 | [FastEnum]
8 | public enum EncodingType
9 | {
10 | Unknown = 0,
11 | [Display(Name = "url")]Url
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/ExpressionType.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum ExpressionType
8 | {
9 | Unknown = 0,
10 | [Display(Name = "SQL")]Sql
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/GrantType.cs:
--------------------------------------------------------------------------------
1 | using Genbox.FastEnum;
2 |
3 | namespace Genbox.SimpleS3.Core.Enums;
4 |
5 | [FastEnum]
6 | public enum GrantType
7 | {
8 | Unknown = 0,
9 | Group,
10 | CanonicalUser,
11 | AmazonCustomerByEmail
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/HeaderUsage.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum HeaderUsage
8 | {
9 | Unknown = 0,
10 | [Display(Name = "NONE")]None,
11 | [Display(Name = "IGNORE")]Ignore,
12 | [Display(Name = "USE")]Use
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/JsonType.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum JsonType
8 | {
9 | Unknown = 0,
10 | [Display(Name = "DOCUMENT")]Document,
11 | [Display(Name = "LINES")]Lines
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/MetadataDirective.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum MetadataDirective
8 | {
9 | Unknown = 0,
10 | [Display(Name = "COPY")]Copy,
11 | [Display(Name = "REPLACE")]Replace
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/ObjectPermissions.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Enums;
2 |
3 | [Flags]
4 | public enum ObjectPermissions
5 | {
6 | None = 0,
7 |
8 | /// Equivalent to s3:GetObject, s3:GetObjectVersion, and s3:GetObjectTorrent
9 | Read = 1,
10 |
11 | /// Equivalent to s3:GetObjectAcl and s3:GetObjectVersionAcl
12 | ReadAcl = 2,
13 |
14 | /// Equivalent to s3:PutObjectAcl and s3:PutObjectVersionAcl
15 | WriteAcl = 4,
16 |
17 | /// Equivalent to granting Read, ReadAcl, and WriteAcl permissions.
18 | FullControl = 8
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/Payer.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Enums;
2 |
3 | public enum Payer
4 | {
5 | Unknown = 0,
6 | Requester,
7 | Me
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/QuoteField.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum QuoteField
8 | {
9 | Unknown = 0,
10 | [Display(Name = "ALWAYS")]Always,
11 | [Display(Name = "ASNEEDED")]AsNeeded
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/ReplicationStatus.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum ReplicationStatus
8 | {
9 | Unknown = 0,
10 | [Display(Name = "PENDING")]Pending,
11 | [Display(Name = "COMPLETED")]Completed,
12 | [Display(Name = "FAILED")]Failed,
13 | [Display(Name = "REPLICA")]Replica
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/RestoreRequestType.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum RestoreRequestType
8 | {
9 | Unknown = 0,
10 | [Display(Name = "SELECT")]Select
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/S3Permission.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum S3Permission
8 | {
9 | Unknown = 0,
10 | [Display(Name = "FULL_CONTROL")]FullControl,
11 | [Display(Name = "READ")]Read,
12 | [Display(Name = "WRITE")]Write
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/SseCustomerAlgorithm.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum SseCustomerAlgorithm
8 | {
9 | Unknown = 0,
10 | [Display(Name = "AES256")]Aes256
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Enums/TaggingDirective.cs:
--------------------------------------------------------------------------------
1 | using System.ComponentModel.DataAnnotations;
2 | using Genbox.FastEnum;
3 |
4 | namespace Genbox.SimpleS3.Core.Enums;
5 |
6 | [FastEnum]
7 | public enum TaggingDirective
8 | {
9 | Unknown = 0,
10 | [Display(Name = "COPY")]Copy,
11 | [Display(Name = "REPLACE")]Replace
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Extensions/CoreBuilderExtensions.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Clients;
3 | using Genbox.SimpleS3.Core.Internals.Clients;
4 | using Microsoft.Extensions.DependencyInjection;
5 | using Microsoft.Extensions.DependencyInjection.Extensions;
6 |
7 | namespace Genbox.SimpleS3.Core.Extensions;
8 |
9 | public static class CoreBuilderExtensions
10 | {
11 | public static ICoreBuilder UsePooledClients(this ICoreBuilder builder)
12 | {
13 | builder.Services.Replace(ServiceDescriptor.Singleton());
14 | builder.Services.Replace(ServiceDescriptor.Singleton());
15 | builder.Services.Replace(ServiceDescriptor.Singleton());
16 | return builder;
17 | }
18 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Authentication/ScopeBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Authentication;
3 | using Genbox.SimpleS3.Core.Internals.Enums;
4 | using Genbox.SimpleS3.Core.Internals.Helpers;
5 | using Microsoft.Extensions.Options;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Authentication;
8 |
9 | internal sealed class ScopeBuilder(IOptions options) : IScopeBuilder
10 | {
11 | private readonly SimpleS3Config _options = options.Value;
12 |
13 | public string CreateScope(string service, DateTimeOffset date) => $"{ValueHelper.DateToString(date, DateTimeFormat.Iso8601Date)}/{_options.RegionCode}/{service}/aws4_request";
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Authentication/SigningConstants.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Authentication;
2 |
3 | internal static class SigningConstants
4 | {
5 | public const string Scheme = "AWS4";
6 | public const string AlgorithmTag = Scheme + "-" + Algorithm;
7 | public const string ChunkedAlgorithmTag = AlgorithmTag + "-PAYLOAD";
8 | public const string AmazonHeaderPrefix = "x-amz-";
9 | public const string Algorithm = "HMAC-SHA256";
10 | public const char Colon = ':';
11 | public const char SemiColon = ';';
12 | public const char Newline = '\n';
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Builders/QueryParameterAuthorizationBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Authentication;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Common.Validation;
5 | using Genbox.SimpleS3.Core.Internals.Extensions;
6 | using Microsoft.Extensions.Logging;
7 |
8 | namespace Genbox.SimpleS3.Core.Internals.Builders;
9 |
10 | internal sealed class QueryParameterAuthorizationBuilder(ISignatureBuilder builder, ILogger logger) : IAuthorizationBuilder
11 | {
12 | public void BuildAuthorization(IRequest request)
13 | {
14 | Validator.RequireNotNull(request);
15 |
16 | logger.LogTrace("Building parameter based authorization");
17 | request.SetQueryParameter(AmzParameters.XAmzSignature, builder.CreateSignature(request, false).HexEncode());
18 | }
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Clients/SignedClient.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Clients;
2 | using Genbox.SimpleS3.Core.Abstracts.Enums;
3 | using Genbox.SimpleS3.Core.Abstracts.Operations;
4 | using Genbox.SimpleS3.Core.Abstracts.Request;
5 | using Genbox.SimpleS3.Core.Abstracts.Response;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Clients;
8 |
9 | internal class SignedClient(ISignedOperations operations) : ISignedClient
10 | {
11 | public string SignRequest(TReq request, TimeSpan expiresIn) where TReq : IRequest => operations.SignRequest(request, expiresIn);
12 |
13 | public Task SendSignedRequestAsync(string url, HttpMethodType httpMethod, Stream? content = null, CancellationToken token = default) where TResp : IResponse, new() => operations.SendSignedRequestAsync(url, httpMethod, content, token);
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Compat/NotNullWhenAttribute.cs:
--------------------------------------------------------------------------------
1 | // ReSharper disable All
2 | #if NETSTANDARD2_0
3 | namespace System.Diagnostics.CodeAnalysis;
4 |
5 | /// Specifies that when a method returns , the parameter will not be null even if the corresponding type allows it.
6 | [AttributeUsage(AttributeTargets.Parameter, Inherited = false)]
7 | internal sealed class NotNullWhenAttribute : Attribute
8 | {
9 | /// Initializes the attribute with the specified return value condition.
10 | ///
11 | /// The return value condition. If the method returns this value, the associated parameter will not be null.
12 | ///
13 | public NotNullWhenAttribute(bool returnValue) => ReturnValue = returnValue;
14 |
15 | /// Gets the return value condition.
16 | public bool ReturnValue { get; }
17 | }
18 | #endif
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/CoreBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Microsoft.Extensions.DependencyInjection;
3 |
4 | namespace Genbox.SimpleS3.Core.Internals;
5 |
6 | internal sealed class CoreBuilder(IServiceCollection services, string? name = null) : ServiceBuilderBase(services, name), ICoreBuilder;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Enums/BinaryEncoding.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Enums;
2 |
3 | internal enum BinaryEncoding
4 | {
5 | Unknown = 0,
6 | Hex,
7 | Base64
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Enums/DateTimeFormat.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Enums;
2 |
3 | internal enum DateTimeFormat
4 | {
5 | Unknown = 0,
6 | Iso8601Date,
7 | Iso8601DateTime,
8 | Iso8601DateTimeExt,
9 | Rfc1123
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Extensions/QueueExtensions.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Extensions;
2 |
3 | /// This class is only necessary as long as we target .NET Standard 2.0
4 | internal static class QueueExtensions
5 | {
6 | public static bool TryDequeue(this Queue queue, out T? value) where T : class
7 | {
8 | if (queue.Count > 0)
9 | {
10 | value = queue.Dequeue();
11 | return true;
12 | }
13 |
14 | value = null;
15 | return false;
16 | }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Extensions/TypeExtensions.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Extensions;
2 |
3 | internal static class TypeExtensions
4 | {
5 | internal static Type[] GetTypeArguments(this Type type)
6 | {
7 | Type[]? args = null;
8 |
9 | foreach (Type intType in type.GetInterfaces())
10 | {
11 | args = intType.GetGenericArguments();
12 |
13 | if (args.Length != 0)
14 | break;
15 | }
16 |
17 | if (args == null)
18 | throw new InvalidOperationException("Unable to find generic arguments");
19 |
20 | return args;
21 | }
22 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Fluent/Transfer.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Operations;
3 | using Genbox.SimpleS3.Core.Abstracts.Transfer;
4 |
5 | namespace Genbox.SimpleS3.Core.Internals.Fluent;
6 |
7 | internal sealed class Transfer(IObjectOperations operations, IMultipartTransfer transfer) : ITransfer
8 | {
9 | public IUpload CreateUpload(string bucket, string objectKey) => new Upload(operations, transfer, bucket, objectKey);
10 |
11 | public IDownload CreateDownload(string bucket, string objectKey) => new Download(operations, transfer, bucket, objectKey);
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Helpers/CopyHelper.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Helpers;
2 |
3 | internal static class CopyHelper
4 | {
5 | public static byte[]? CopyWithNull(byte[]? input)
6 | {
7 | if (input == null)
8 | return null;
9 |
10 | byte[] arr = new byte[input.Length];
11 | Array.Copy(input, 0, arr, 0, input.Length);
12 | return arr;
13 | }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Helpers/XmlHelper.cs:
--------------------------------------------------------------------------------
1 | using System.Xml;
2 |
3 | namespace Genbox.SimpleS3.Core.Internals.Helpers;
4 |
5 | internal static class XmlHelper
6 | {
7 | public static IEnumerable ReadElements(XmlReader xmlReader, string? tagName = null)
8 | {
9 | //Support closed tags:
10 | if (xmlReader.IsEmptyElement && xmlReader.Name == tagName)
11 | yield break;
12 |
13 | while (xmlReader.Read())
14 | {
15 | if (tagName != null && xmlReader.NodeType == XmlNodeType.EndElement && xmlReader.Name == tagName)
16 | break;
17 |
18 | if (xmlReader.NodeType != XmlNodeType.Element)
19 | continue;
20 |
21 | yield return xmlReader.Name;
22 | }
23 | }
24 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/DeleteBucketPolicyRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class DeleteBucketPolicyRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(DeleteBucketPolicyRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Policy, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/DeleteBucketTaggingRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class DeleteBucketTaggingRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(DeleteBucketTaggingRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Tagging, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/GetBucketAccelerateConfigurationRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class GetBucketAccelerateConfigurationRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetBucketAccelerateConfigurationRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Accelerate, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/GetBucketLifecycleConfigurationRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class GetBucketLifecycleConfigurationRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetBucketLifecycleConfigurationRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Lifecycle, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/GetBucketLockConfigurationRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class GetBucketLockConfigurationRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetBucketLockConfigurationRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.ObjectLock, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/GetBucketPolicyRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class GetBucketPolicyRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetBucketPolicyRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Policy, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/GetBucketTaggingRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class GetBucketTaggingRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetBucketTaggingRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Tagging, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/GetBucketVersioningRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
7 |
8 | internal sealed class GetBucketVersioningRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetBucketVersioningRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Versioning, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Buckets/PutBucketPolicyRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using System.Text;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Request;
4 | using Genbox.SimpleS3.Core.Common.Misc;
5 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Buckets;
8 |
9 | internal sealed class PutBucketPolicyRequestMarshal : IRequestMarshal
10 | {
11 | public Stream MarshalRequest(PutBucketPolicyRequest request, SimpleS3Config config)
12 | {
13 | request.SetQueryParameter(AmzParameters.Policy, string.Empty);
14 | request.SetHeader(AmzHeaders.XAmzConfirmRemoveSelfBucketAccess, request.ConfirmRemoveSelfBucketAccess ? "true" : "false");
15 |
16 | byte[] bytes = Encoding.UTF8.GetBytes(request.Policy);
17 | return new MemoryStream(bytes);
18 | }
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Multipart/CreateMultipartUploadRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Multipart;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Multipart;
7 |
8 | internal sealed class CreateMultipartUploadRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(CreateMultipartUploadRequest request, SimpleS3Config config)
11 | {
12 | //This is required for multipart uploads
13 | request.SetQueryParameter(AmzParameters.Uploads, string.Empty);
14 | return null;
15 | }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Objects/GetObjectAclRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Objects;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Objects;
7 |
8 | internal sealed class GetObjectAclRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetObjectAclRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Acl, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Objects/GetObjectLegalHoldRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Objects;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Objects;
7 |
8 | internal sealed class GetObjectLegalHoldRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetObjectLegalHoldRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.LegalHold, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Objects/GetObjectRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Objects;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Objects;
7 |
8 | internal sealed class GetObjectRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(GetObjectRequest request, SimpleS3Config config)
11 | {
12 | if (request.EnableChecksum)
13 | request.SetHeader(AmzHeaders.XAmzChecksumMode, "ENABLED");
14 |
15 | return null;
16 | }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Objects/HeadObjectRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Objects;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Objects;
7 |
8 | internal sealed class HeadObjectRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(HeadObjectRequest request, SimpleS3Config config)
11 | {
12 | if (request.EnableChecksum)
13 | request.SetHeader(AmzHeaders.XAmzChecksumMode, "ENABLED");
14 |
15 | return null;
16 | }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Requests/Objects/PutObjectAclRequestMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Requests.Objects;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.Objects;
7 |
8 | internal sealed class PutObjectAclRequestMarshal : IRequestMarshal
9 | {
10 | public Stream? MarshalRequest(PutObjectAclRequest request, SimpleS3Config config)
11 | {
12 | request.SetQueryParameter(AmzParameters.Acl, string.Empty);
13 | return null;
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Buckets/GetBucketAccelerateConfigurationResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using System.Xml;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Response;
4 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Buckets;
7 |
8 | internal sealed class GetBucketAccelerateConfigurationResponseMarshal : IResponseMarshal
9 | {
10 | public void MarshalResponse(SimpleS3Config config, GetBucketAccelerateConfigurationResponse response, IDictionary headers, Stream responseStream)
11 | {
12 | using XmlTextReader xmlReader = new XmlTextReader(responseStream);
13 | xmlReader.ReadToDescendant("AccelerateConfiguration");
14 |
15 | if (xmlReader.Read())
16 | response.AccelerateEnabled = xmlReader.ReadElementContentAsString() == "Enabled";
17 | }
18 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Buckets/GetBucketPolicyResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using System.Text;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Response;
4 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Buckets;
7 |
8 | internal sealed class GetBucketPolicyResponseMarshal : IResponseMarshal
9 | {
10 | public void MarshalResponse(SimpleS3Config config, GetBucketPolicyResponse response, IDictionary headers, Stream responseStream)
11 | {
12 | using MemoryStream ms = new MemoryStream();
13 | responseStream.CopyTo(ms);
14 | ms.Position = 0;
15 |
16 | response.Policy = Encoding.UTF8.GetString(ms.ToArray());
17 | }
18 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Buckets/PutBucketLockConfigurationResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Buckets;
7 |
8 | internal sealed class PutBucketLockConfigurationResponseMarshal : IResponseMarshal
9 | {
10 | public void MarshalResponse(SimpleS3Config config, PutBucketLockConfigurationResponse response, IDictionary headers, Stream responseStream)
11 | {
12 | response.RequestCharged = headers.ContainsKey(AmzHeaders.XAmzRequestCharged);
13 | }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Buckets/PutBucketVersioningResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
4 |
5 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Buckets;
6 |
7 | internal sealed class PutBucketVersioningResponseMarshal : IResponseMarshal
8 | {
9 | public void MarshalResponse(SimpleS3Config config, PutBucketVersioningResponse response, IDictionary headers, Stream responseStream)
10 | {
11 | // The docs says there is an XML response, but there is none from the API.
12 | }
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Multipart/AbortMultipartUploadResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Responses.Multipart;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Multipart;
7 |
8 | internal sealed class AbortMultipartUploadResponseMarshal : IResponseMarshal
9 | {
10 | public void MarshalResponse(SimpleS3Config config, AbortMultipartUploadResponse response, IDictionary headers, Stream responseStream)
11 | {
12 | response.RequestCharged = headers.ContainsKey(AmzHeaders.XAmzRequestCharged);
13 | }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Objects/DeleteObjectResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Internals.Extensions;
5 | using Genbox.SimpleS3.Core.Network.Responses.Objects;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Objects;
8 |
9 | internal sealed class DeleteObjectResponseMarshal : IResponseMarshal
10 | {
11 | public void MarshalResponse(SimpleS3Config config, DeleteObjectResponse response, IDictionary headers, Stream responseStream)
12 | {
13 | response.IsDeleteMarker = headers.GetHeaderBool(AmzHeaders.XAmzDeleteMarker);
14 | response.VersionId = headers.GetOptionalValue(AmzHeaders.XAmzVersionId);
15 | response.RequestCharged = headers.ContainsKey(AmzHeaders.XAmzRequestCharged);
16 | }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Objects/GetObjectLegalHoldResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using System.Xml;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Response;
4 | using Genbox.SimpleS3.Core.Common.Misc;
5 | using Genbox.SimpleS3.Core.Network.Responses.Objects;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Objects;
8 |
9 | internal sealed class GetObjectLegalHoldResponseMarshal : IResponseMarshal
10 | {
11 | public void MarshalResponse(SimpleS3Config config, GetObjectLegalHoldResponse response, IDictionary headers, Stream responseStream)
12 | {
13 | response.RequestCharged = headers.ContainsKey(AmzHeaders.XAmzRequestCharged);
14 |
15 | using XmlTextReader reader = new XmlTextReader(responseStream);
16 | reader.ReadToDescendant("Status");
17 | reader.Read();
18 | response.LegalHold = reader.Value == "ON";
19 | }
20 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Objects/PutObjectAclResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Responses.Objects;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Objects;
7 |
8 | internal sealed class PutObjectAclResponseMarshal : IResponseMarshal
9 | {
10 | public void MarshalResponse(SimpleS3Config config, PutObjectAclResponse response, IDictionary headers, Stream responseStream)
11 | {
12 | response.RequestCharged = headers.ContainsKey(AmzHeaders.XAmzRequestCharged);
13 | }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Objects/PutObjectLegalHoldResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Network.Responses.Objects;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Objects;
7 |
8 | internal sealed class PutObjectLegalHoldResponseMarshal : IResponseMarshal
9 | {
10 | public void MarshalResponse(SimpleS3Config config, PutObjectLegalHoldResponse response, IDictionary headers, Stream responseStream)
11 | {
12 | response.RequestCharged = headers.ContainsKey(AmzHeaders.XAmzRequestCharged);
13 | }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Marshallers/Responses/Objects/RestoreObjectResponseMarshal.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Response;
3 | using Genbox.SimpleS3.Core.Common.Misc;
4 | using Genbox.SimpleS3.Core.Internals.Extensions;
5 | using Genbox.SimpleS3.Core.Network.Responses.Objects;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.Objects;
8 |
9 | internal sealed class RestoreObjectResponseMarshal : IResponseMarshal
10 | {
11 | public void MarshalResponse(SimpleS3Config config, RestoreObjectResponse response, IDictionary headers, Stream responseStream)
12 | {
13 | response.RequestCharged = headers.ContainsKey(AmzHeaders.XAmzRequestCharged);
14 | response.RestoreOutputPath = headers.GetOptionalValue(AmzHeaders.XAmzRestoreOutputPath);
15 | }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Misc/DateTimeFormats.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Misc;
2 |
3 | internal static class DateTimeFormats
4 | {
5 | public const string Iso8601Date = "yyyyMMdd";
6 | public const string Iso8601DateTime = @"yyyyMMdd\THHmmssZ";
7 | public const string Iso8601DateTimeExtended = @"yyyy-MM-dd\THH:mm:ss.FFFFFFFZ"; //F = up to N fractional seconds
8 | public const string Rfc1123 = "R";
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Network/EndpointData.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Provider;
2 |
3 | namespace Genbox.SimpleS3.Core.Internals.Network;
4 |
5 | internal class EndpointData(string host, string? bucket, string regionCode, string endpoint) : IEndpointData
6 | {
7 | public string? Bucket { get; } = bucket;
8 | public string RegionCode { get; } = regionCode;
9 | public string Host { get; } = host;
10 | public string Endpoint { get; } = endpoint;
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Network/SignedRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Network.Requests;
3 |
4 | namespace Genbox.SimpleS3.Core.Internals.Network;
5 |
6 | internal sealed class SignedRequest(HttpMethodType method) : BaseRequest(method);
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Operations/SignedOperations.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Abstracts.Operations;
3 | using Genbox.SimpleS3.Core.Abstracts.Request;
4 | using Genbox.SimpleS3.Core.Abstracts.Response;
5 |
6 | namespace Genbox.SimpleS3.Core.Internals.Operations;
7 |
8 | internal class SignedOperations(ISignedRequestHandler handler) : ISignedOperations
9 | {
10 | public string SignRequest(TReq request, TimeSpan expiresIn) where TReq : IRequest => handler.SignRequest(request, expiresIn);
11 | public Task SendSignedRequestAsync(string url, HttpMethodType httpMethod, Stream? content = null, CancellationToken token = default) where TResp : IResponse, new() => handler.SendRequestAsync(url, httpMethod, content, token);
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Pools/IPooledObject.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Pools;
2 |
3 | internal interface IPooledObject
4 | {
5 | void Reset();
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/PostMappers/UploadPartPostMapper.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 | using Genbox.SimpleS3.Core.Network.Requests.Multipart;
3 | using Genbox.SimpleS3.Core.Network.Responses.Multipart;
4 |
5 | namespace Genbox.SimpleS3.Core.Internals.PostMappers;
6 |
7 | internal sealed class UploadPartPostMapper : IPostMapper
8 | {
9 | public void PostMap(UploadPartRequest request, UploadPartResponse response)
10 | {
11 | if (request.PartNumber.HasValue)
12 | response.PartNumber = request.PartNumber.Value;
13 | }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Validation/Validators/ConfigValidatorBase.cs:
--------------------------------------------------------------------------------
1 | using FluentValidation.Results;
2 | using Microsoft.Extensions.Options;
3 |
4 | namespace Genbox.SimpleS3.Core.Internals.Validation.Validators;
5 |
6 | internal abstract class ConfigValidatorBase : ValidatorBase, IValidateOptions where T : class
7 | {
8 | public ValidateOptionsResult Validate(string? name, T options)
9 | {
10 | ValidationResult? results = base.Validate(options);
11 |
12 | if (results.IsValid)
13 | return ValidateOptionsResult.Success;
14 |
15 | return ValidateOptionsResult.Fail(results.Errors.Select(x => x.ErrorMessage));
16 | }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Validation/Validators/Requests/Multipart/ListMultipartUploadsRequestValidator.cs:
--------------------------------------------------------------------------------
1 | using FluentValidation;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Provider;
4 | using Genbox.SimpleS3.Core.Network.Requests.Multipart;
5 | using Microsoft.Extensions.Options;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Validation.Validators.Requests.Multipart;
8 |
9 | internal sealed class ListMultipartUploadsRequestValidator : RequestValidatorBase
10 | {
11 | public ListMultipartUploadsRequestValidator(IInputValidator validator, IOptions config) : base(validator, config)
12 | {
13 | RuleFor(x => x.MaxUploads).GreaterThan(0).LessThanOrEqualTo(1000).When(x => x.MaxUploads != null);
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Validation/Validators/Requests/Objects/DeleteObjectsRequestValidator.cs:
--------------------------------------------------------------------------------
1 | using FluentValidation;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Provider;
4 | using Genbox.SimpleS3.Core.Network.Requests.Objects;
5 | using Microsoft.Extensions.Options;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Validation.Validators.Requests.Objects;
8 |
9 | internal sealed class DeleteObjectsRequestValidator : RequestValidatorBase
10 | {
11 | public DeleteObjectsRequestValidator(IInputValidator validator, IOptions config) : base(validator, config)
12 | {
13 | RuleFor(x => x.Objects).NotEmpty();
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Validation/Validators/Requests/Objects/ListObjectsRequestValidator.cs:
--------------------------------------------------------------------------------
1 | using FluentValidation;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Provider;
4 | using Genbox.SimpleS3.Core.Network.Requests.Objects;
5 | using Microsoft.Extensions.Options;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Validation.Validators.Requests.Objects;
8 |
9 | internal sealed class ListObjectsRequestValidator : RequestValidatorBase
10 | {
11 | public ListObjectsRequestValidator(IInputValidator validator, IOptions config) : base(validator, config)
12 | {
13 | RuleFor(x => x.MaxKeys).GreaterThan(0).LessThanOrEqualTo(1000).When(x => x.MaxKeys != null);
14 | }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Validation/Validators/ValidatorBase.cs:
--------------------------------------------------------------------------------
1 | using FluentValidation;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Internals.Validation.Validators;
5 |
6 | [UsedImplicitly(ImplicitUseTargetFlags.WithInheritors)]
7 | internal abstract class ValidatorBase : AbstractValidator;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Xml/XmlCharMode.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Xml;
2 |
3 | internal enum XmlCharMode
4 | {
5 | Unknown = 0,
6 | EntityEncode,
7 | Omit,
8 | ThrowException
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Internals/Xml/XmlStandard.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Internals.Xml;
2 |
3 | internal enum XmlStandard
4 | {
5 | Unknown = 0,
6 | Xml10,
7 | Xml11
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/DeleteBucketPolicyRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Builders;
3 | using Genbox.SimpleS3.Core.Common.Marshal;
4 | using Genbox.SimpleS3.Core.Enums;
5 | using Genbox.SimpleS3.Core.Network.Requests.Interfaces;
6 |
7 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
8 |
9 | public class DeleteBucketPolicyRequest : BaseRequest, IHasBucketName
10 | {
11 | internal DeleteBucketPolicyRequest() : base(HttpMethodType.DELETE) {}
12 |
13 | public DeleteBucketPolicyRequest(string bucketName) : this()
14 | {
15 | Initialize(bucketName);
16 | }
17 |
18 | public string BucketName { get; set; }
19 |
20 | internal void Initialize(string bucketName)
21 | {
22 | BucketName = bucketName;
23 | }
24 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/DeleteBucketRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Common.Marshal;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | /// Deletes a bucket. All objects (including all object versions and delete markers) in the bucket must be deleted before the bucket itself can be deleted.
7 | public class DeleteBucketRequest : BaseRequest, IHasBucketName
8 | {
9 | internal DeleteBucketRequest() : base(HttpMethodType.DELETE) {}
10 |
11 | public DeleteBucketRequest(string bucketName) : this()
12 | {
13 | Initialize(bucketName);
14 | }
15 |
16 | public string BucketName { get; set; } = null!;
17 |
18 | internal void Initialize(string bucketName)
19 | {
20 | BucketName = bucketName;
21 | }
22 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/DeleteBucketTaggingRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Common.Marshal;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | ///
7 | /// Deletes the tags from the bucket. o use this operation, you must have permission to perform the s3:PutBucketTagging action. By default, the bucket owner has this
8 | /// permission and can grant this permission to others.
9 | ///
10 | public class DeleteBucketTaggingRequest : BaseRequest, IHasBucketName
11 | {
12 | internal DeleteBucketTaggingRequest() : base(HttpMethodType.DELETE) {}
13 |
14 | public DeleteBucketTaggingRequest(string bucketName) : this()
15 | {
16 | Initialize(bucketName);
17 | }
18 |
19 | public string BucketName { get; set; } = null!;
20 |
21 | internal void Initialize(string bucketName)
22 | {
23 | BucketName = bucketName;
24 | }
25 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/GetBucketLifecycleConfigurationRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Common.Marshal;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | /// Returns the lifecycle configuration information set on the bucket.
7 | public class GetBucketLifecycleConfigurationRequest : BaseRequest, IHasBucketName
8 | {
9 | internal GetBucketLifecycleConfigurationRequest() : base(HttpMethodType.GET) {}
10 |
11 | public GetBucketLifecycleConfigurationRequest(string bucketName) : this()
12 | {
13 | Initialize(bucketName);
14 | }
15 |
16 | public string BucketName { get; set; } = null!;
17 |
18 | internal void Initialize(string bucketName)
19 | {
20 | BucketName = bucketName;
21 | }
22 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/GetBucketLockConfigurationRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Common.Marshal;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | ///
7 | /// Gets the Object Lock configuration for a bucket. The rule specified in the Object Lock configuration will be applied by default to every new object placed in the
8 | /// specified bucket.
9 | ///
10 | public class GetBucketLockConfigurationRequest : BaseRequest, IHasBucketName
11 | {
12 | internal GetBucketLockConfigurationRequest() : base(HttpMethodType.GET) {}
13 |
14 | public GetBucketLockConfigurationRequest(string bucketName) : this()
15 | {
16 | Initialize(bucketName);
17 | }
18 |
19 | public string BucketName { get; set; } = null!;
20 |
21 | internal void Initialize(string bucketName)
22 | {
23 | BucketName = bucketName;
24 | }
25 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/GetBucketPolicyRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Builders;
3 | using Genbox.SimpleS3.Core.Common.Marshal;
4 | using Genbox.SimpleS3.Core.Enums;
5 | using Genbox.SimpleS3.Core.Network.Requests.Interfaces;
6 |
7 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
8 |
9 | public class GetBucketPolicyRequest : BaseRequest, IHasBucketName
10 | {
11 | internal GetBucketPolicyRequest() : base(HttpMethodType.GET) {}
12 |
13 | public GetBucketPolicyRequest(string bucketName) : this()
14 | {
15 | Initialize(bucketName);
16 | }
17 |
18 | public string BucketName { get; set; }
19 |
20 | internal void Initialize(string bucketName)
21 | {
22 | BucketName = bucketName;
23 | }
24 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/GetBucketTaggingRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Common.Marshal;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | ///
7 | /// Returns the tag set associated with the bucket. To use this operation, you must have permission to perform the s3:GetBucketTagging action. By default, the bucket owner
8 | /// has this permission and can grant this permission to others.
9 | ///
10 | public class GetBucketTaggingRequest : BaseRequest, IHasBucketName
11 | {
12 | internal GetBucketTaggingRequest() : base(HttpMethodType.GET) {}
13 |
14 | public GetBucketTaggingRequest(string bucketName) : this()
15 | {
16 | Initialize(bucketName);
17 | }
18 |
19 | public string BucketName { get; set; } = null!;
20 |
21 | internal void Initialize(string bucketName)
22 | {
23 | BucketName = bucketName;
24 | }
25 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/GetBucketVersioningRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Common.Marshal;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 |
6 | public class GetBucketVersioningRequest : BaseRequest, IHasBucketName
7 | {
8 | internal GetBucketVersioningRequest() : base(HttpMethodType.GET) {}
9 |
10 | public GetBucketVersioningRequest(string bucketName) : this()
11 | {
12 | Initialize(bucketName);
13 | }
14 |
15 | public string BucketName { get; set; } = null!;
16 |
17 | internal void Initialize(string bucketName)
18 | {
19 | BucketName = bucketName;
20 | }
21 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Buckets/ListBucketsRequest.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Buckets;
4 |
5 | /// This implementation of the GET operation returns a list of all buckets owned by the authenticated sender of the request.
6 | public class ListBucketsRequest() : BaseRequest(HttpMethodType.GET);
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasBypassGovernanceRetention.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasBypassGovernanceRetention
4 | {
5 | /// Specifies whether you want to delete this object even if it has a Governance-type Object Lock in place. You must have sufficient permissions to perform this operation.
6 | bool? BypassGovernanceRetention { get; set; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasCacheControl.cs:
--------------------------------------------------------------------------------
1 | using Genbox.HttpBuilders;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
5 |
6 | [PublicAPI]
7 | public interface IHasCacheControl
8 | {
9 | /// Can be used to specify caching behavior along the request/reply chain.
10 | CacheControlBuilder CacheControl { get; }
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasChecksum.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
4 |
5 | public interface IHasChecksum
6 | {
7 | public ChecksumAlgorithm ChecksumAlgorithm { get; set; }
8 | public ChecksumType ChecksumType { get; set; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasChecksumProperties.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
4 |
5 | public interface IHasChecksumProperties
6 | {
7 | ChecksumAlgorithm ChecksumAlgorithm { get; }
8 | byte[]? Checksum { get; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasContent.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
4 |
5 | [PublicAPI]
6 | public interface IHasContent
7 | {
8 | Stream? Content { get; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasContentMd5.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasContentMd5
4 | {
5 | ///
6 | /// 128-bit MD5 digest of the data. This property can be used as a message integrity check to verify that the data is the same data that was originally sent. Although it is
7 | /// optional, we recommend using the Content-MD5 mechanism as an end-to-end integrity check.
8 | ///
9 | byte[]? ContentMd5 { get; set; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasContentProps.cs:
--------------------------------------------------------------------------------
1 | using Genbox.HttpBuilders;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
5 |
6 | [PublicAPI]
7 | public interface IHasContentProps
8 | {
9 | /// Specifies presentational information for the object.
10 | ContentDispositionBuilder ContentDisposition { get; }
11 |
12 | ///
13 | /// Specifies what content encodings have been applied to the object and thus what decoding mechanisms must be applied to obtain the media-type referenced by the Content-Type
14 | /// header field.
15 | ///
16 | ContentEncodingBuilder ContentEncoding { get; }
17 |
18 | /// A standard MIME type describing the format of the contents.
19 | ContentTypeBuilder ContentType { get; }
20 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasExpectedBucketOwner.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasExpectedBucketOwner
4 | {
5 | /// The account id of the expected bucket owner. If the bucket is owned by a different account, the request will fail with an HTTP 403 (Access Denied) error.
6 | string? ExpectedBucketOwner { get; set; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasExpiresOn.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasExpiresOn
4 | {
5 | /// The date and time at which the object is no longer able to be cached.
6 | DateTimeOffset? ExpiresOn { get; set; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasLegalHold.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasLegalHold
4 | {
5 | /// Specifies whether a legal hold will be applied to this object.
6 | bool? LockLegalHold { get; set; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasLock.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
5 |
6 | [PublicAPI]
7 | public interface IHasLock
8 | {
9 | /// The Object Lock mode, if any, that should be applied to this object.
10 | LockMode LockMode { get; set; }
11 |
12 | /// The date and time when the Object Lock retention period will expire.
13 | DateTimeOffset? LockRetainUntil { get; set; }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasMetadata.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Builders;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
4 |
5 | public interface IHasMetadata
6 | {
7 | ///
8 | /// Header starting with this prefix are user-defined metadata. Each one is stored and returned as a set of key-value pairs. Amazon S3 doesn't validate or interpret
9 | /// user-defined metadata.
10 | ///
11 | MetadataBuilder Metadata { get; }
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasMfa.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Builders;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
4 |
5 | public interface IHasMfa
6 | {
7 | /// If multi-factor approval is activated, you need to supply MFA information.
8 | MfaAuthenticationBuilder Mfa { get; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasPartNumber.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasPartNumber
4 | {
5 | ///
6 | /// Part number of the object part being read. This is a positive integer between 1 and the maximum number of parts supported. Only objects uploaded using the multipart
7 | /// upload API have part numbers. For information about multipart uploads, see Multipart Upload Overview in the Amazon Simple Storage Service Developer Guide.
8 | ///
9 | int? PartNumber { get; set; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasRange.cs:
--------------------------------------------------------------------------------
1 | using Genbox.HttpBuilders;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
5 |
6 | [PublicAPI]
7 | public interface IHasRange
8 | {
9 | /// Downloads the specified range bytes of an object. For more information about the HTTP Range header, go to http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.35.
10 | RangeBuilder Range { get; }
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasRequestPayer.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
4 |
5 | public interface IHasRequestPayer
6 | {
7 | /// When true, confirms that the requester knows that she or he will be charged for the request. Bucket owners need not specify this parameter in their requests.
8 | Payer RequestPayer { get; set; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasStorageClass.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
5 |
6 | [PublicAPI]
7 | public interface IHasStorageClass
8 | {
9 | /// Provides storage class information of the object. Amazon S3 returns this header for all objects except for Standard storage class objects.
10 | StorageClass StorageClass { get; set; }
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasTags.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Builders;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
4 |
5 | public interface IHasTags
6 | {
7 | ///
8 | /// Specifies a set of one or more tags to associate with the object. These tags are stored in the tagging subresource that is associated with the object. To specify tags on
9 | /// an object, the requester must have s3:PutObjectTagging included in the list of permitted actions in their IAM policy.
10 | ///
11 | TagBuilder Tags { get; }
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasUploadId.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasUploadId
4 | {
5 | string UploadId { get; set; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasVersionId.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasVersionId
4 | {
5 | ///
6 | /// The version of the object. When you enable versioning, S3 generates a random number for objects added to a bucket. When you put an object in a bucket where versioning has
7 | /// been suspended, is always null.
8 | ///
9 | string? VersionId { get; set; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/Interfaces/IHasWebsiteRedirect.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.Interfaces;
2 |
3 | public interface IHasWebsiteRedirect
4 | {
5 | ///
6 | /// f the bucket is configured as a website, redirects requests for this object to another object in the same bucket or to an external URL. Amazon S3 stores the value of this
7 | /// header in the object metadata.
8 | ///
9 | string? WebsiteRedirectLocation { get; set; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3AndCondition.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
2 |
3 | public class S3AndCondition
4 | {
5 | public string? Prefix { get; set; }
6 | public IList> Tags { get; internal set; } = new List>();
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3Filter.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
2 |
3 | /// The Filter is used to identify objects that a Lifecycle Rule applies to. A Filter must have exactly one of Prefix, Tag, or conditions specified.
4 | public class S3Filter
5 | {
6 | public string? Prefix { get; set; }
7 |
8 | public KeyValuePair? Tag { get; set; }
9 |
10 | public S3AndCondition? AndConditions { get; set; }
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3InputFormat.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
5 |
6 | [UsedImplicitly(ImplicitUseTargetFlags.WithInheritors | ImplicitUseTargetFlags.WithMembers)]
7 | public abstract class S3InputFormat
8 | {
9 | public CompressionType CompressionType { get; set; }
10 |
11 | internal abstract void Reset();
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3JsonInputFormat.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
4 |
5 | public class S3JsonInputFormat(JsonType jsonType) : S3InputFormat
6 | {
7 | public JsonType JsonType { get; set; } = jsonType;
8 |
9 | internal override void Reset()
10 | {
11 | JsonType = JsonType.Unknown;
12 | }
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3JsonOutputFormat.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
2 |
3 | public class S3JsonOutputFormat(string recordDelimiter) : S3OutputFormat
4 | {
5 | public string RecordDelimiter { get; set; } = recordDelimiter;
6 |
7 | internal override void Reset()
8 | {
9 | RecordDelimiter = string.Empty;
10 | }
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3NonCurrentVersionTransition.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
4 |
5 | public class S3NonCurrentVersionTransition(int nonCurrentDays, StorageClass storageClass)
6 | {
7 | /// Specifies the number of days an object is noncurrent before Amazon S3 can perform the associated action.
8 | public int NonCurrentDays { get; } = nonCurrentDays;
9 |
10 | /// The class of storage used to store the object.
11 | public StorageClass StorageClass { get; } = storageClass;
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3OutputFormat.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
2 |
3 | public abstract class S3OutputFormat
4 | {
5 | internal abstract void Reset();
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3ParquetInputFormat.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
2 |
3 | public class S3ParquetInputFormat : S3InputFormat
4 | {
5 | internal override void Reset() {}
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3PartInfo.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
5 |
6 | [PublicAPI]
7 | public class S3PartInfo(string eTag, int partNumber, byte[]? checksum = null, ChecksumAlgorithm checksumAlgorithm = ChecksumAlgorithm.Unknown)
8 | {
9 | public string ETag { get; } = eTag;
10 | public int PartNumber { get; } = partNumber;
11 | public byte[]? Checksum { get; } = checksum;
12 | public ChecksumAlgorithm ChecksumAlgorithm { get; } = checksumAlgorithm;
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Requests/S3Types/S3SelectParameters.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Requests.S3Types;
4 |
5 | public class S3SelectParameters(string expression, S3InputFormat? inputFormat, S3OutputFormat outputFormat)
6 | {
7 | public string Expression { get; } = expression;
8 | public ExpressionType ExpressionType { get; set; }
9 | public S3InputFormat? InputFormat { get; } = inputFormat;
10 | public S3OutputFormat OutputFormat { get; } = outputFormat;
11 |
12 | internal void Reset()
13 | {
14 | ExpressionType = ExpressionType.Unknown;
15 | InputFormat?.Reset();
16 | OutputFormat.Reset();
17 | }
18 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/BaseResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Response;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses;
4 |
5 | public abstract class BaseResponse : IResponse
6 | {
7 | public int StatusCode { get; set; }
8 |
9 | public IError? Error { get; set; }
10 |
11 | public long ContentLength { get; set; }
12 |
13 | public bool ConnectionClosed { get; set; }
14 |
15 | public DateTimeOffset Date { get; set; }
16 |
17 | public string? Server { get; set; }
18 |
19 | public string? ResponseId { get; set; }
20 |
21 | public string? RequestId { get; set; }
22 |
23 | public bool IsSuccess { get; set; }
24 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/CreateBucketResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class CreateBucketResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/DeleteBucketPolicyResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class DeleteBucketPolicyResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/DeleteBucketResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class DeleteBucketResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/DeleteBucketTaggingResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class DeleteBucketTaggingResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/GetBucketAccelerateConfigurationResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | /// GetBucketAccelerateConfiguration
4 | public class GetBucketAccelerateConfigurationResponse : BaseResponse
5 | {
6 | public bool AccelerateEnabled { get; internal set; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/GetBucketLifecycleConfigurationResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Requests.S3Types;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
4 |
5 | public class GetBucketLifecycleConfigurationResponse : BaseResponse
6 | {
7 | public IList Rules { get; } = new List();
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/GetBucketLockConfigurationResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
5 |
6 | public class GetBucketLockConfigurationResponse : BaseResponse, IHasLock
7 | {
8 | public LockMode LockMode { get; internal set; }
9 | public DateTimeOffset? LockRetainUntil { get; internal set; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/GetBucketPolicyResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class GetBucketPolicyResponse : BaseResponse
4 | {
5 | public string Policy { get; internal set; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/GetBucketTaggingResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class GetBucketTaggingResponse : BaseResponse
4 | {
5 | public IDictionary Tags { get; } = new Dictionary(StringComparer.OrdinalIgnoreCase);
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/GetBucketVersioningResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class GetBucketVersioningResponse : BaseResponse
4 | {
5 | public bool Status { get; internal set; }
6 | public bool MfaDelete { get; internal set; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/HeadBucketResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class HeadBucketResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/ListBucketsResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.S3Types;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
4 |
5 | public class ListBucketsResponse : BaseResponse
6 | {
7 | public ListBucketsResponse()
8 | {
9 | Buckets = new List();
10 | }
11 |
12 | /// The owner of the buckets inside .
13 | public S3Identity Owner { get; internal set; }
14 |
15 | /// The list of buckets
16 | public IList Buckets { get; }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/PutBucketAccelerateConfigurationResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | /// PutBucketAccelerateConfiguration
4 | public class PutBucketAccelerateConfigurationResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/PutBucketLifecycleConfigurationResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | /// PutBucketLifecycleConfigurationResponse
4 | public class PutBucketLifecycleConfigurationResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/PutBucketLockConfigurationResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
4 |
5 | public class PutBucketLockConfigurationResponse : BaseResponse, IHasRequestCharged
6 | {
7 | public bool RequestCharged { get; internal set; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/PutBucketPolicyResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class PutBucketPolicyResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/PutBucketTaggingResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class PutBucketTaggingResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/PutBucketVersioningResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | /// PutBucketVersioningResponse
4 | public class PutBucketVersioningResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Buckets/PutPublicAccessBlockResponse.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Buckets;
2 |
3 | public class PutPublicAccessBlockResponse : BaseResponse;
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/BucketAlreadyExistsError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class BucketAlreadyExistsError : GenericError
8 | {
9 | internal BucketAlreadyExistsError(IDictionary lookup) : base(lookup)
10 | {
11 | BucketName = lookup.GetOptionalValue("BucketName");
12 | }
13 |
14 | public string? BucketName { get; }
15 |
16 | public override string GetErrorDetails() => "BucketName: " + BucketName;
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/BucketNotEmptyError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class BucketNotEmptyError : GenericError
8 | {
9 | internal BucketNotEmptyError(IDictionary lookup) : base(lookup)
10 | {
11 | BucketName = lookup.GetOptionalValue("BucketName");
12 | }
13 |
14 | public string? BucketName { get; }
15 |
16 | public override string GetErrorDetails() => $"BucketName: {BucketName}";
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/HeadersNotSignedError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class HeadersNotSignedError : GenericError
8 | {
9 | internal HeadersNotSignedError(IDictionary lookup) : base(lookup)
10 | {
11 | HeadersNotSigned = lookup.GetOptionalValue("HeadersNotSigned");
12 | }
13 |
14 | public string? HeadersNotSigned { get; }
15 |
16 | public override string GetErrorDetails() => "Headers not signed: " + HeadersNotSigned;
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/InvalidArgumentError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class InvalidArgumentError : GenericError
8 | {
9 | internal InvalidArgumentError(IDictionary lookup) : base(lookup)
10 | {
11 | ArgumentName = lookup.GetOptionalValue("ArgumentName");
12 | ArgumentValue = lookup.GetOptionalValue("ArgumentValue");
13 | }
14 |
15 | public string? ArgumentName { get; }
16 | public string? ArgumentValue { get; }
17 |
18 | public override string GetErrorDetails() => $"Argument: {ArgumentName} - Value: {ArgumentValue}";
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/InvalidBucketNameError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class InvalidBucketNameError : GenericError
8 | {
9 | internal InvalidBucketNameError(IDictionary lookup) : base(lookup)
10 | {
11 | BucketName = lookup.GetOptionalValue("BucketName");
12 | }
13 |
14 | public string? BucketName { get; }
15 |
16 | public override string GetErrorDetails() => "BucketName: " + BucketName;
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/MethodNotAllowedError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class MethodNotAllowedError : GenericError
8 | {
9 | internal MethodNotAllowedError(IDictionary lookup) : base(lookup)
10 | {
11 | Method = lookup.GetOptionalValue("Method");
12 | ResourceType = lookup.GetOptionalValue("ResourceType");
13 | RequestId = lookup.GetOptionalValue("RequestId");
14 | HostId = lookup.GetOptionalValue("HostId");
15 | }
16 |
17 | public string? Method { get; }
18 | public string? ResourceType { get; }
19 | public string? RequestId { get; }
20 | public string? HostId { get; }
21 |
22 | public override string GetErrorDetails() => $"Method: {Method} ResourceType: {ResourceType}";
23 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/NoSuchBucketError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class NoSuchBucketError : GenericError
8 | {
9 | internal NoSuchBucketError(IDictionary lookup) : base(lookup)
10 | {
11 | BucketName = lookup.GetOptionalValue("BucketName");
12 | }
13 |
14 | public string? BucketName { get; }
15 |
16 | public override string GetErrorDetails() => $"BucketName: {BucketName}";
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Errors/PreconditionFailedError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Internals.Extensions;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Errors;
5 |
6 | [PublicAPI]
7 | public class PreconditionFailedError : GenericError
8 | {
9 | internal PreconditionFailedError(IDictionary lookup) : base(lookup)
10 | {
11 | //The condition field is optional since only Amazon S3 returns it
12 | Condition = lookup.GetOptionalValue("Condition");
13 | }
14 |
15 | public string? Condition { get; }
16 |
17 | public override string GetErrorDetails() => "Condition: " + Condition;
18 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasAbort.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasAbort
4 | {
5 | ///
6 | /// If the bucket has a lifecycle rule configured with an action to abort incomplete multipart uploads and the prefix in the lifecycle rule matches the object name in the
7 | /// request, the response includes this header. The header indicates when the initiated multipart upload becomes eligible for an abort operation.
8 | ///
9 | DateTimeOffset? AbortsOn { get; }
10 |
11 | ///
12 | /// This header is returned along with the x-amz-abort-date header. It identifies the applicable lifecycle configuration rule that defines the action to abort incomplete
13 | /// multipart uploads.
14 | ///
15 | string? AbortRuleId { get; }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasCache.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
4 |
5 | [PublicAPI]
6 | public interface IHasCache : IHasETag
7 | {
8 | /// Can be used to specify caching behavior along the request/reply chain.
9 | string? CacheControl { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasContent.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
4 |
5 | [PublicAPI]
6 | public interface IHasContent : IDisposable
7 | {
8 | Stream Content { get; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasDeleteMarker.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasDeleteMarker
4 | {
5 | ///
6 | /// Specifies whether the versioned object that was permanently deleted was (true) or was not (false) a delete marker. In a simple DELETE, this header indicates whether
7 | /// (true) or not (false) a delete marker was created.
8 | ///
9 | bool IsDeleteMarker { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasETag.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasETag
4 | {
5 | /// The entity tag is a hash of the object. The ETag reflects changes only to the contents of an object, not its metadata.
6 | string? ETag { get; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasExpiration.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasExpiration
4 | {
5 | /// The datetime the object expires
6 | DateTimeOffset? LifeCycleExpiresOn { get; }
7 |
8 | /// The rule id used for expiration
9 | string? LifeCycleRuleId { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasExpiresOn.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasExpiresOn
4 | {
5 | /// A date time for when the response has expired and should no longer be cached.
6 | DateTimeOffset? ExpiresOn { get; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasLastModified.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasLastModified
4 | {
5 | DateTimeOffset? LastModified { get; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasLegalHold.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasLegalHold
4 | {
5 | ///
6 | /// Specifies whether a legal hold is in effect for this object. This header is only returned if the requester has the s3:GetObjectLegalHold permission. This header is not
7 | /// returned if the specified version of this object has never had a legal hold applied.
8 | ///
9 | bool LockLegalHold { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasLock.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
5 |
6 | [PublicAPI]
7 | public interface IHasLock
8 | {
9 | /// The Object Lock mode, if any, that's in effect for this object. This header is only returned if the requester has the s3:GetObjectRetention permission.
10 | LockMode LockMode { get; }
11 |
12 | /// The date and time when the Object Lock retention period expires. This header is only returned if the requester has the s3:GetObjectRetention permission.
13 | DateTimeOffset? LockRetainUntil { get; }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasMetadata.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
4 |
5 | [PublicAPI]
6 | public interface IHasMetadata
7 | {
8 | ///
9 | /// Header starting with this prefix are user-defined metadata. Each one is stored and returned as a set of key-value pairs. Amazon S3 doesn't validate or interpret
10 | /// user-defined metadata.
11 | ///
12 | IDictionary? Metadata { get; }
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasRequestCharged.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasRequestCharged
4 | {
5 | /// If present, indicates that the requester was successfully charged for the request.
6 | bool RequestCharged { get; }
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasRestoration.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
4 |
5 | [PublicAPI]
6 | public interface IHasRestoration
7 | {
8 | /// If the object was restored from Amazon Glacier, this value indicates when the object will expire.
9 | DateTimeOffset? RestoreExpiresOn { get; }
10 |
11 | /// If true, indicates that the object is currently being restored from Amazon Glacier.
12 | bool RestoreInProgress { get; }
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasSse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
5 |
6 | [PublicAPI]
7 | public interface IHasSse
8 | {
9 | ///
10 | /// If you specified server-side encryption either with an AWS KMS-managed or Amazon S3-managed encryption key in your PUT request, the response includes this header. It
11 | /// confirms the encryption algorithm that Amazon S3 used to encrypt the object.
12 | ///
13 | SseAlgorithm SseAlgorithm { get; }
14 |
15 | /// If present, specifies the ID of the AWS Key Management Service (KMS) customer master key (CMK) that was used for the object.
16 | string? SseKmsKeyId { get; }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasSseContext.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasSseContext
4 | {
5 | ///
6 | /// If present, specifies the AWS KMS Encryption Context to use for object encryption. The value of this header is a base64-encoded UTF-8 string holding JSON with the
7 | /// encryption context key-value pairs.
8 | ///
9 | string? SseContext { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasSseCustomerKey.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
4 |
5 | public interface IHasSseCustomerKey
6 | {
7 | /// If server-side encryption with a customer-provided encryption key was requested, the response will include this header confirming the encryption algorithm used.
8 | SseCustomerAlgorithm SseCustomerAlgorithm { get; }
9 |
10 | ///
11 | /// If server-side encryption using customer-provided encryption keys was requested, the response returns this header to verify the roundtrip message integrity of the
12 | /// customer-provided encryption key.
13 | ///
14 | byte[]? SseCustomerKeyMd5 { get; }
15 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasStorageClass.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
4 |
5 | public interface IHasStorageClass
6 | {
7 | StorageClass StorageClass { get; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasUploadId.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasUploadId
4 | {
5 | string UploadId { get; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasVersionId.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasVersionId
4 | {
5 | string? VersionId { get; }
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Interfaces/IHasWebsiteRedirect.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | public interface IHasWebsiteRedirect
4 | {
5 | ///
6 | /// f the bucket is configured as a website, redirects requests for this object to another object in the same bucket or to an external URL. Amazon S3 stores the value of this
7 | /// header in the object metadata.
8 | ///
9 | string? WebsiteRedirectLocation { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Multipart/AbortMultipartUploadResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Multipart;
4 |
5 | public class AbortMultipartUploadResponse : BaseResponse, IHasRequestCharged
6 | {
7 | public bool RequestCharged { get; internal set; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/DeleteObjectResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
4 |
5 | public class DeleteObjectResponse : BaseResponse, IHasRequestCharged, IHasVersionId, IHasDeleteMarker
6 | {
7 | public bool IsDeleteMarker { get; internal set; }
8 | public bool RequestCharged { get; internal set; }
9 | public string? VersionId { get; internal set; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/DeleteObjectsResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 | using Genbox.SimpleS3.Core.Network.Responses.S3Types;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
5 |
6 | public class DeleteObjectsResponse : BaseResponse, IHasRequestCharged
7 | {
8 | public IList Deleted { get; } = new List();
9 | public IList Errors { get; } = new List();
10 | public bool RequestCharged { get; internal set; }
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/GetObjectAclResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 | using Genbox.SimpleS3.Core.Network.Responses.S3Types;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
5 |
6 | public class GetObjectAclResponse : BaseResponse, IHasRequestCharged
7 | {
8 | public GetObjectAclResponse()
9 | {
10 | Grants = new List();
11 | }
12 |
13 | public S3Identity Owner { get; internal set; }
14 | public IList Grants { get; }
15 | public bool RequestCharged { get; internal set; }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/GetObjectLegalHoldResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
4 |
5 | public class GetObjectLegalHoldResponse : BaseResponse, IHasRequestCharged
6 | {
7 | public bool LegalHold { get; internal set; }
8 | public bool RequestCharged { get; internal set; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/GetObjectResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
4 |
5 | public class GetObjectResponse : HeadObjectResponse, IHasContent, IHasRequestCharged
6 | {
7 | public Stream Content { get; internal set; } = Stream.Null;
8 |
9 | public void Dispose()
10 | {
11 | Dispose(true);
12 | GC.SuppressFinalize(this);
13 | }
14 |
15 | public bool RequestCharged { get; internal set; }
16 |
17 | protected virtual void Dispose(bool disposing)
18 | {
19 | if (disposing)
20 | Content.Dispose();
21 | }
22 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/PutObjectAclResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
4 |
5 | public class PutObjectAclResponse : BaseResponse, IHasRequestCharged
6 | {
7 | public bool RequestCharged { get; internal set; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/PutObjectLegalHoldResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
4 |
5 | public class PutObjectLegalHoldResponse : BaseResponse, IHasRequestCharged
6 | {
7 | public bool RequestCharged { get; internal set; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/Objects/RestoreObjectResponse.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.Objects;
4 |
5 | public class RestoreObjectResponse : BaseResponse, IHasRequestCharged
6 | {
7 | public string? RestoreOutputPath { get; internal set; }
8 | public bool RequestCharged { get; internal set; }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/S3Types/S3Bucket.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Common.Marshal;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.S3Types;
5 |
6 | [PublicAPI]
7 | public class S3Bucket(string bucketName, DateTimeOffset createdOn) : IHasBucketName
8 | {
9 | /// The date the bucket was created
10 | public DateTimeOffset CreatedOn { get; } = createdOn;
11 |
12 | /// Name of the bucket
13 | public string BucketName { get; } = bucketName;
14 |
15 | public override string ToString() => BucketName;
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/S3Types/S3DeleteError.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Common.Marshal;
3 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
4 |
5 | namespace Genbox.SimpleS3.Core.Network.Responses.S3Types;
6 |
7 | public class S3DeleteError(string objectKey, ErrorCode code, string message, string? versionId) : IHasVersionId, IHasObjectKey
8 | {
9 | public ErrorCode Code { get; } = code;
10 | public string Message { get; } = message;
11 | public string ObjectKey { get; } = objectKey;
12 | public string? VersionId { get; } = versionId;
13 | public override string ToString() => $"Error on {ObjectKey}: {Message}";
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/S3Types/S3DeleteMarker.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Common.Marshal;
2 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Responses.S3Types;
5 |
6 | public class S3DeleteMarker(bool isLatest, string objectKey, DateTimeOffset lastModified, S3Identity owner, string versionId) : IHasObjectKey, IHasVersionId
7 | {
8 | public bool IsLatest { get; } = isLatest;
9 | public DateTimeOffset LastModified { get; } = lastModified;
10 | public S3Identity Owner { get; } = owner;
11 | public string ObjectKey { get; internal set; } = objectKey;
12 | public string VersionId { get; } = versionId;
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/S3Types/S3Grant.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.S3Types;
4 |
5 | public class S3Grant(S3Grantee grantee, S3Permission permission)
6 | {
7 | public S3Grantee Grantee { get; } = grantee;
8 | public S3Permission Permission { get; } = permission;
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/S3Types/S3Grantee.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Enums;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.S3Types;
4 |
5 | public class S3Grantee(GrantType type, string? id, string? displayName, string? uri)
6 | {
7 | public GrantType Type { get; } = type;
8 | public string? Id { get; } = id;
9 | public string? DisplayName { get; } = displayName;
10 | public string? Uri { get; } = uri;
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/S3Types/S3Identity.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.S3Types;
2 |
3 | public class S3Identity(string id, string? name)
4 | {
5 | /// The display name of the identity
6 | public string? Name { get; } = name;
7 |
8 | /// The unique identifier of the identity
9 | public string Id { get; } = id;
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Network/Responses/S3Types/S3Part.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Network.Responses.Interfaces;
2 |
3 | namespace Genbox.SimpleS3.Core.Network.Responses.S3Types;
4 |
5 | public class S3Part(int partNumber, DateTimeOffset lastModified, long size, string? eTag) : IHasETag
6 | {
7 | public int PartNumber { get; } = partNumber;
8 | public DateTimeOffset LastModified { get; } = lastModified;
9 | public long Size { get; } = size;
10 | public string? ETag { get; } = eTag;
11 |
12 | public override string ToString() => $"Part: {PartNumber}";
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Runtime.CompilerServices;
2 |
3 | [assembly: InternalsVisibleTo("Genbox.ProviderTests")]
4 | [assembly: InternalsVisibleTo("Genbox.SimpleS3.Core.Tests")]
5 | [assembly: InternalsVisibleTo("Genbox.SimpleS3.Core.Benchmarks")]
6 | [assembly: InternalsVisibleTo("Genbox.SimpleS3.Extensions.AmazonS3.Tests")]
--------------------------------------------------------------------------------
/Src/SimpleS3.Core/SimpleS3.Core.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Examples.Advanced/ClientSetup.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.AmazonS3;
2 | using Genbox.SimpleS3.Extensions.AmazonS3;
3 |
4 | namespace Genbox.SimpleS3.Examples.Advanced;
5 |
6 | public static class ClientSetup
7 | {
8 | /// Shows how to use a simple client to work with S3
9 | public static void Example()
10 | {
11 | //Not much to it. Give it credentials, a region and you are ready to use S3.
12 | using AmazonS3Client client = new AmazonS3Client("YourKeyId", "YourAccessKey", AmazonS3Region.EuNorth1);
13 | }
14 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Examples.Advanced/SetupDependencyInjection.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.AmazonS3.Extensions;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Microsoft.Extensions.DependencyInjection;
4 |
5 | namespace Genbox.SimpleS3.Examples.Advanced;
6 |
7 | public static class SetupDependencyInjection
8 | {
9 | /// Shows how to use dependency injection to setup a client to AmazonS3
10 | public static void Example()
11 | {
12 | //Create the dependency injection container
13 | ServiceCollection services = new ServiceCollection();
14 |
15 | //Add all the AmazonS3 services
16 | services.AddAmazonS3();
17 |
18 | //Build the service provider
19 | using ServiceProvider serviceProvider = services.BuildServiceProvider();
20 |
21 | //Now we can get the client.
22 | ISimpleClient client = serviceProvider.GetRequiredService();
23 | }
24 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Examples.Advanced/SimpleS3.Examples.Advanced.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | Library
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Examples/SimpleS3.Examples.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/README.md:
--------------------------------------------------------------------------------
1 | Files in this directory comes from the official Amazon test suite. I've removed the tests that are incompatible with S3 and some tests that does not make sense from a clients
2 | perspective.
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-casing/get-query-casing.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /
3 | param1=value1&PARAM2=VALUE2
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-casing/get-query-casing.req.disabled:
--------------------------------------------------------------------------------
1 | GET /?PARAM2=VALUE2¶m1=value1 HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-casing/get-query-casing.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | 49434b13bbd7105e29de1fa7d46391cdce739cb2533d60c8f25f76819526af4b
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-order/get-query-order.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /
3 | Param1=value1&Param2=value2
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-order/get-query-order.req:
--------------------------------------------------------------------------------
1 | GET /?Param2=value2&Param1=value1 HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-order/get-query-order.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | 816cd5b414d056048ba4f7c5386d6e0533120fb1fcfa93762cf0fc39e2cf19e0
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-reserved/get-query-reserved.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /
3 | -._~0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz=-._~0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-reserved/get-query-reserved.req:
--------------------------------------------------------------------------------
1 | GET /?-._~0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz=-._~0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-reserved/get-query-reserved.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | c30d4703d9f799439be92736156d47ccfb2d879ddf56f5befa6d1d6aab979177
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-utf8/get-query-utf8.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /
3 | %E1%88%B4=bar
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-utf8/get-query-utf8.req:
--------------------------------------------------------------------------------
1 | GET /?ሴ=bar HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query-utf8/get-query-utf8.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | eb30c5bed55734080471a834cc727ae56beb50e5f39d1bff6d0d38cb192a7073
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query/get-query.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /
3 | Param1=value1
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query/get-query.req:
--------------------------------------------------------------------------------
1 | GET /?Param1=value1 HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-query/get-query.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | 1e24db194ed7d0eec2de28d7369675a243488e08526e8c1c73571282f7c517ab
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-reserved/get-reserved.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /-._~0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz
3 |
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-reserved/get-reserved.req:
--------------------------------------------------------------------------------
1 | GET /-._~0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-reserved/get-reserved.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | 6a968768eefaa713e2a6b16b589a8ea192661f098f37349f4e2c0082757446f9
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-utf8/get-utf8.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /%E1%88%B4
3 |
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-utf8/get-utf8.req:
--------------------------------------------------------------------------------
1 | GET /ሴ HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get-utf8/get-utf8.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | 2a0a97d02205e45ce2e994789806b19270cfbbb0921b278ccf58f5249ac42102
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get/get.creq:
--------------------------------------------------------------------------------
1 | GET
2 | /
3 |
4 | host:example.amazonaws.com
5 | x-amz-date:20150830T123600Z
6 |
7 | host;x-amz-date
8 | e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get/get.req:
--------------------------------------------------------------------------------
1 | GET / HTTP/1.1
2 | Host:example.amazonaws.com
3 | X-Amz-Date:20150830T123600Z
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/Resources/get/get.sts:
--------------------------------------------------------------------------------
1 | AWS4-HMAC-SHA256
2 | 20150830T123600Z
3 | 20150830/us-east-1/service/aws4_request
4 | bb579772317eb040ac9ed261061d46c1f17a8133879d6129b6e1c25292927e63
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3.Tests/SimpleS3.Extensions.AmazonS3.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Runtime.CompilerServices;
2 |
3 | [assembly: InternalsVisibleTo("Genbox.SimpleS3.Extensions.AmazonS3.Tests")]
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.AmazonS3/SimpleS3.Extensions.AmazonS3.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.BackBlazeB2.Tests/SimpleS3.Extensions.BackBlazeB2.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.BackBlazeB2/BackBlazeB2Region.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.BackBlazeB2;
2 |
3 | public enum BackBlazeB2Region
4 | {
5 | Unknown = 0,
6 | UsWest000,
7 | UsWest001,
8 | UsWest002,
9 | EuCentral003,
10 | UsWest004,
11 | UsEast005
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.BackBlazeB2/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Runtime.CompilerServices;
2 |
3 | [assembly: InternalsVisibleTo("Genbox.SimpleS3.Extensions.BackBlazeB2.Tests")]
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.BackBlazeB2/SimpleS3.Extensions.BackBlazeB2.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.GenericS3.Tests/SimpleS3.Extensions.GenericS3.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.GenericS3/GenericS3Config.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.Core.Abstracts.Authentication;
3 | using Genbox.SimpleS3.Core.Common.Authentication;
4 | using JetBrains.Annotations;
5 |
6 | namespace Genbox.SimpleS3.Extensions.GenericS3;
7 |
8 | [PublicAPI]
9 | public class GenericS3Config() : SimpleS3Config("GenericS3", string.Empty) //Needed for config binding
10 | {
11 | public GenericS3Config(string endpoint) : this()
12 | {
13 | Endpoint = endpoint;
14 | }
15 |
16 | public GenericS3Config(IAccessKey? credentials, string endpoint, string regionCode) : this(endpoint)
17 | {
18 | Credentials = credentials;
19 | RegionCode = regionCode;
20 | }
21 |
22 | public GenericS3Config(string keyId, string secretKey, string endpoint, string regionCode) : this(new StringAccessKey(keyId, secretKey), endpoint, regionCode) {}
23 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.GenericS3/GenericS3RegionData.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Region;
2 |
3 | namespace Genbox.SimpleS3.Extensions.GenericS3;
4 |
5 | public class GenericS3RegionData : IRegionData
6 | {
7 | public static GenericS3RegionData Instance { get; } = new GenericS3RegionData();
8 |
9 | public IEnumerable GetRegions()
10 | {
11 | yield break;
12 | }
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.GenericS3/SimpleS3.Extensions.GenericS3.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.GoogleCloudStorage.Tests/SimpleS3.Extensions.GoogleCloudStorage.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.GoogleCloudStorage/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Runtime.CompilerServices;
2 |
3 | [assembly: InternalsVisibleTo("Genbox.SimpleS3.Extensions.GoogleCloudStorage.Tests")]
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.GoogleCloudStorage/SimpleS3.Extensions.GoogleCloudStorage.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClient/HttpBuilderActions.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.HttpClient;
2 |
3 | public class HttpBuilderActions
4 | {
5 | public IList> HttpClientActions { get; } = new List>();
6 | public IList> HttpHandlerActions { get; } = new List>();
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClient/HttpClientConfig.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Common;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Extensions.HttpClient;
5 |
6 | [PublicAPI]
7 | public class HttpClientConfig
8 | {
9 | /// Set to 'true' if you want the proxy that is defined to be used. Otherwise set it to 'false'. Defaults to 'false'.
10 | public bool UseProxy { get; set; }
11 |
12 | /// Use this to set a proxy to which all requests should be sent through.
13 | public string? Proxy { get; set; }
14 |
15 | public HttpVersion HttpVersion { get; set; }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClient/IHttpClientBuilder.cs:
--------------------------------------------------------------------------------
1 | using Microsoft.Extensions.DependencyInjection;
2 |
3 | namespace Genbox.SimpleS3.Extensions.HttpClient;
4 |
5 | public interface IHttpClientBuilder
6 | {
7 | IServiceCollection Services { get; }
8 |
9 | string Name { get; }
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClient/Internal/CustomHttpClientBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Microsoft.Extensions.DependencyInjection;
3 |
4 | namespace Genbox.SimpleS3.Extensions.HttpClient.Internal;
5 |
6 | internal sealed class CustomHttpClientBuilder(IServiceCollection services, string? name = null) : ServiceBuilderBase(services, name), IHttpClientBuilder;
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClient/README.md:
--------------------------------------------------------------------------------
1 | # SimpleS3.Extensions.HttpClient
2 |
3 | This extension is a network driver that provides basic HTTP communication through the .NET System.Net.Http.HttpClient class. A single HttpClient instance is used for all
4 | connections. It supports web proxies.
5 |
6 | To use it, add a reference to [Genbox.SimpleS3.Core](https://www.nuget.org/packages/Genbox.SimpleS3.Core)
7 | and [Genbox.SimpleS3.Extensions.HttpClient](https://www.nuget.org/packages/Genbox.SimpleS3.Extensions.HttpClient).
8 |
9 | ### Using Microsoft.Extensions.DependencyInjection
10 |
11 | If you are using [Microsoft's dependency injection](https://www.nuget.org/packages/Microsoft.Extensions.DependencyInjection/) (recommended), then you simply add the driver like
12 | this:
13 |
14 | ```csharp
15 | ServiceCollection services = new ServiceCollection();
16 | ICoreBuilder coreBuilder = SimpleS3CoreServices.AddSimpleS3Core(services);
17 | coreBuilder.UseHttpClient();
18 | ```
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClient/SimpleS3.Extensions.HttpClient.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory.Polly/Internal/PollyHttpMessageHandler.cs:
--------------------------------------------------------------------------------
1 | using Polly;
2 |
3 | namespace Genbox.SimpleS3.Extensions.HttpClientFactory.Polly.Internal;
4 |
5 | internal sealed class PollyHttpMessageHandler(IAsyncPolicy policy) : DelegatingHandler
6 | {
7 | private readonly Context _context = new Context();
8 | private readonly IAsyncPolicy _policy = policy ?? throw new ArgumentNullException(nameof(policy));
9 |
10 | protected override async Task SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
11 | {
12 | return await _policy.ExecuteAsync((_, ct) => SendCoreAsync(request, ct), _context, cancellationToken).ConfigureAwait(false);
13 | }
14 |
15 | private Task SendCoreAsync(HttpRequestMessage request, CancellationToken cancellationToken) => base.SendAsync(request, cancellationToken);
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory.Polly/PollyConfig.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Extensions.HttpClientFactory.Polly;
4 |
5 | [PublicAPI]
6 | public class PollyConfig
7 | {
8 | //Default policy:
9 | //- Retries: 3
10 | //-Timeout: 2^attempt seconds (2, 4, 8 seconds) + 0 to 1000 ms jitter
11 |
12 | public int Retries { get; set; } = 3;
13 |
14 | public RetryMode RetryMode { get; set; } = RetryMode.ExponentialBackoffJitter;
15 | public TimeSpan MaxRandomDelay { get; set; } = TimeSpan.FromMilliseconds(1000);
16 | public TimeSpan Timeout { get; set; } = TimeSpan.FromMinutes(10);
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory.Polly/Retry/RetryableBufferingStreamWrapper.cs:
--------------------------------------------------------------------------------
1 | using System.Diagnostics.CodeAnalysis;
2 | using Genbox.SimpleS3.Core.Abstracts.Request;
3 | using Genbox.SimpleS3.Core.Abstracts.Wrappers;
4 |
5 | namespace Genbox.SimpleS3.Extensions.HttpClientFactory.Polly.Retry;
6 |
7 | internal sealed class RetryableBufferingStreamWrapper : IRequestStreamWrapper
8 | {
9 | public bool IsSupported(IRequest request) => true;
10 |
11 | [SuppressMessage("IDisposableAnalyzers.Correctness", "IDISP015:Member should not return created and cached instance")]
12 | public Stream Wrap(Stream input, IRequest request) => input.CanSeek ? input : new RetryableBufferingStream(input);
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory.Polly/RetryMode.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.HttpClientFactory.Polly;
2 |
3 | public enum RetryMode
4 | {
5 | NoDelay = 0,
6 | LinearDelay,
7 | LinearDelayJitter,
8 | ExponentialBackoff,
9 | ExponentialBackoffJitter
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory.Polly/SimpleS3.Extensions.HttpClientFactory.Polly.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory/HttpBuilderActions.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.HttpClientFactory;
2 |
3 | public class HttpBuilderActions
4 | {
5 | public IList> HttpClientActions { get; } = new List>();
6 | public IList> HttpHandlerActions { get; } = new List>();
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory/HttpClientFactoryConfig.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Common;
2 | using JetBrains.Annotations;
3 |
4 | namespace Genbox.SimpleS3.Extensions.HttpClientFactory;
5 |
6 | [PublicAPI]
7 | public class HttpClientFactoryConfig
8 | {
9 | /// Set to 'true' if you want the proxy that is defined to be used. Otherwise set it to 'false'. Defaults to 'false'.
10 | public bool UseProxy { get; set; }
11 |
12 | /// Use this to set a proxy to which all requests should be sent through.
13 | public string? Proxy { get; set; }
14 |
15 | /// Set the HTTP version that the driver should use.
16 | public HttpVersion HttpVersion { get; set; }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory/Internal/CustomHttpClientFactoryBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Microsoft.Extensions.DependencyInjection;
3 |
4 | namespace Genbox.SimpleS3.Extensions.HttpClientFactory.Internal;
5 |
6 | internal sealed class CustomHttpClientFactoryBuilder(IServiceCollection services, string? name = null) : ServiceBuilderBase(services, name), IHttpClientBuilder;
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.HttpClientFactory/SimpleS3.Extensions.HttpClientFactory.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Abstracts/IProfile.cs:
--------------------------------------------------------------------------------
1 | using JetBrains.Annotations;
2 |
3 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
4 |
5 | [PublicAPI]
6 | public interface IProfile
7 | {
8 | string Name { get; set; }
9 | string KeyId { get; set; }
10 | byte[] AccessKey { get; set; }
11 | string RegionCode { get; set; }
12 | string Location { get; set; }
13 | DateTimeOffset CreatedOn { get; set; }
14 | IDictionary? Tags { get; set; }
15 | string? GetTag(string key);
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Abstracts/IProfileManager.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
2 |
3 | public interface IProfileManager
4 | {
5 | IProfile? GetProfile(string name);
6 | string SaveProfile(IProfile profile);
7 | IProfile CreateProfile(string name, string keyId, byte[] accessKey, string region, bool persist = true);
8 | IEnumerable List();
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Abstracts/IProfileManagerBuilder.cs:
--------------------------------------------------------------------------------
1 | using Microsoft.Extensions.DependencyInjection;
2 |
3 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
4 |
5 | public interface IProfileManagerBuilder
6 | {
7 | IServiceCollection Services { get; }
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Abstracts/IProfileSerializer.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
2 |
3 | public interface IProfileSerializer
4 | {
5 | byte[] Serialize(T profile) where T : IProfile;
6 | T Deserialize(byte[] data) where T : IProfile;
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Abstracts/IProfileSetup.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
2 |
3 | public interface IProfileSetup
4 | {
5 | IProfile SetupProfile(string profileName, bool persist = true);
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Abstracts/IStorage.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
2 |
3 | public interface IStorage
4 | {
5 | byte[]? Get(string name);
6 | string Put(string name, byte[] data);
7 | IEnumerable List();
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/DiskStorageOptions.cs:
--------------------------------------------------------------------------------
1 | using System.Runtime.InteropServices;
2 |
3 | namespace Genbox.SimpleS3.Extensions.ProfileManager;
4 |
5 | public class DiskStorageOptions
6 | {
7 | public static string DefaultLocation => RuntimeInformation.IsOSPlatform(OSPlatform.Windows) ? Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "SimpleS3", "Profiles") : Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), ".SimpleS3", "Profiles");
8 |
9 | public string ProfileLocation { get; set; } = DefaultLocation;
10 |
11 | public bool OverwriteExisting { get; set; }
12 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Extensions/ProfileAccessKey.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Authentication;
2 | using Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
3 |
4 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Extensions;
5 |
6 | public class ProfileAccessKey(IProfile profile) : IAccessKey
7 | {
8 | public string KeyId { get; } = profile.KeyId;
9 | public byte[] SecretKey { get; } = profile.AccessKey;
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Extensions/ProfileManagerExtensions.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
2 |
3 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Extensions;
4 |
5 | public static class ProfileManagerExtensions
6 | {
7 | public static IProfile? GetDefaultProfile(this IProfileManager profileManager) => profileManager.GetProfile(ProfileManager.DefaultProfile);
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Extensions/ProfileSetupExtensions.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
2 |
3 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Extensions;
4 |
5 | public static class ProfileSetupExtensions
6 | {
7 | public static IProfile SetupDefaultProfile(this IProfileSetup setup, bool persist = true) => setup.SetupProfile(ProfileManager.DefaultProfile, persist);
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Internal/DataProtection/DataProtectionKeyProtector.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Authentication;
2 | using Microsoft.AspNetCore.DataProtection;
3 |
4 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Internal.DataProtection;
5 |
6 | internal class DataProtectionKeyProtector(IDataProtectionProvider provider) : IAccessKeyProtector
7 | {
8 | private readonly IDataProtector _protector = provider.CreateProtector(nameof(DataProtectionKeyProtector));
9 |
10 | public byte[] ProtectKey(byte[] key) => _protector.Protect(key);
11 |
12 | public byte[] UnprotectKey(byte[] key) => _protector.Unprotect(key);
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/Internal/ProfileManagerBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Extensions.ProfileManager.Abstracts;
2 | using Microsoft.Extensions.DependencyInjection;
3 |
4 | namespace Genbox.SimpleS3.Extensions.ProfileManager.Internal;
5 |
6 | internal class ProfileManagerBuilder(IServiceCollection services) : IProfileManagerBuilder
7 | {
8 | public IServiceCollection Services { get; } = services;
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/ProfileManagerOptions.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Extensions.ProfileManager;
2 |
3 | public class ProfileManagerOptions
4 | {
5 | /// Controls whether the ProfileManager should clear the input key when creating profiles or not. Defaults to true.
6 | public bool ClearInputKey { get; set; } = true;
7 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.ProfileManager/SimpleS3.Extensions.ProfileManager.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.Wasabi.Tests/SimpleS3.Extensions.Wasabi.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.Wasabi/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Runtime.CompilerServices;
2 |
3 | [assembly: InternalsVisibleTo("Genbox.SimpleS3.Extensions.Wasabi.Tests")]
--------------------------------------------------------------------------------
/Src/SimpleS3.Extensions.Wasabi/SimpleS3.Extensions.Wasabi.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.GenericS3.Tests/SimpleS3.GenericS3.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Src/SimpleS3.GenericS3.Tests/StaticCreatorTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Common.Authentication;
2 | using Genbox.SimpleS3.Core.TestBase.Code;
3 | using Genbox.SimpleS3.Extensions.GenericS3;
4 |
5 | namespace Genbox.SimpleS3.GenericS3.Tests;
6 |
7 | public class StaticCreatorTests
8 | {
9 | [Fact]
10 | public async Task StaticClient()
11 | {
12 | NullNetworkDriver driver = new NullNetworkDriver();
13 |
14 | GenericS3Config config = new GenericS3Config(new StringAccessKey("ExampleKeyId00000000", "wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLEKEY"), "https://myendpoint.com", "us-east-1");
15 | using GenericS3Client client = new GenericS3Client(config, driver);
16 |
17 | await client.GetObjectAsync("testbucket", "GetObjectAsync");
18 | Assert.Equal("https://myendpoint.com/GetObjectAsync", driver.LastUrl);
19 | }
20 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.GenericS3/SimpleS3.GenericS3.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/Src/SimpleS3.GoogleCloudStorage.Tests/SimpleS3.GoogleCloudStorage.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Src/SimpleS3.GoogleCloudStorage.Tests/StaticCreatorTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.TestBase.Code;
2 | using Genbox.SimpleS3.Extensions.GoogleCloudStorage;
3 |
4 | namespace Genbox.SimpleS3.GoogleCloudStorage.Tests;
5 |
6 | public class StaticCreatorTests
7 | {
8 | [Fact]
9 | public async Task StaticClient()
10 | {
11 | NullNetworkDriver driver = new NullNetworkDriver();
12 |
13 | GoogleCloudStorageConfig config = new GoogleCloudStorageConfig("GOOGTS7C7FUP3AIRVJTE2BCDKINBTES3HC2GY5CBFJDCQ2SYHV6A6XXVTJFSA", "bGoa+V7g/yqDXvKRqq+JTFn4uQZbPiQJo4pf9RzJ", GoogleCloudStorageRegion.EuropeWest1);
14 | using GoogleCloudStorageClient client = new GoogleCloudStorageClient(config, driver);
15 |
16 | await client.GetObjectAsync("testbucket", "GetObjectAsync");
17 | Assert.Equal("https://testbucket.storage.googleapis.com/GetObjectAsync", driver.LastUrl);
18 | }
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.GoogleCloudStorage/SimpleS3.GoogleCloudStorage.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/Src/SimpleS3.ProviderBase/Abstracts/IClientBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Microsoft.Extensions.DependencyInjection;
3 |
4 | namespace Genbox.SimpleS3.ProviderBase.Abstracts;
5 |
6 | public interface IClientBuilder
7 | {
8 | IServiceCollection Services { get; }
9 |
10 | IHttpClientBuilder HttpBuilder { get; }
11 |
12 | ICoreBuilder CoreBuilder { get; }
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.ProviderBase/ClientBuilder.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts;
2 | using Genbox.SimpleS3.ProviderBase.Abstracts;
3 | using Microsoft.Extensions.DependencyInjection;
4 |
5 | namespace Genbox.SimpleS3.ProviderBase;
6 |
7 | public class ClientBuilder(IServiceCollection services, IHttpClientBuilder httpBuilder, ICoreBuilder coreBuilder, string? name = null) : ServiceBuilderBase(services, name), IClientBuilder
8 | {
9 | public IHttpClientBuilder HttpBuilder { get; } = httpBuilder;
10 | public ICoreBuilder CoreBuilder { get; } = coreBuilder;
11 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.ProviderBase/ErrorMessages.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.ProviderBase;
2 |
3 | public static class ErrorMessages
4 | {
5 | public const string ProviderNotSupported = "The provider does not support this function";
6 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.ProviderBase/NetworkConfig.cs:
--------------------------------------------------------------------------------
1 | using System.Net;
2 | using Genbox.SimpleS3.Extensions.HttpClientFactory.Polly;
3 |
4 | namespace Genbox.SimpleS3.ProviderBase;
5 |
6 | public class NetworkConfig
7 | {
8 | public IWebProxy? Proxy { get; set; }
9 | public int Retries { get; set; } = 3;
10 | public RetryMode RetryMode { get; set; } = RetryMode.ExponentialBackoffJitter;
11 | public TimeSpan MaxRandomDelay { get; set; } = TimeSpan.FromMilliseconds(1000);
12 | public TimeSpan Timeout { get; set; } = TimeSpan.FromMinutes(10);
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.ProviderBase/SimpleS3.ProviderBase.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/Api.txt:
--------------------------------------------------------------------------------
1 | GetBucketAccelerateConfiguration,bucket
2 | GetObject,object
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/Enums/ApiType.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Utility.S3Template.Enums;
2 |
3 | internal enum ApiType
4 | {
5 | Unknown = 0,
6 | Bucket,
7 | Object
8 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/Enums/DataType.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Utility.S3Template.Enums;
2 |
3 | internal enum DataType
4 | {
5 | Unknown = 0,
6 | Request,
7 | RequestMarshal,
8 | Response,
9 | ResponseMarshal
10 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/SimpleS3.Utility.S3Template.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | PreserveNewest
8 |
9 |
10 | PreserveNewest
11 |
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/Templates/RequestMarshalTemplate.txt:
--------------------------------------------------------------------------------
1 | using System.IO;
2 | using Genbox.SimpleS3.Core.Abstracts;
3 | using Genbox.SimpleS3.Core.Abstracts.Marshallers;
4 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
5 | using JetBrains.Annotations;
6 |
7 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Requests.%ApiType%s
8 | {
9 | internal class %ApiName%RequestMarshal : IRequestMarshal<%ApiName%Request>
10 | {
11 | public Stream MarshalRequest(%ApiName%Request request, IS3Config config)
12 | {
13 | return null;
14 | }
15 | }
16 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/Templates/RequestTemplate.txt:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.Abstracts.Enums;
2 | using Genbox.SimpleS3.Core.Network.Requests.Interfaces;
3 |
4 | namespace Genbox.SimpleS3.Core.Network.Requests.%ApiType%s
5 | {
6 | ///
7 | /// %ApiName%
8 | ///
9 | public class %ApiName%Request : BaseRequest, IHas%ApiType%Name
10 | {
11 | public %ApiName%Request(string %ApiTypeLower%Name) : base(HttpMethod.)
12 | {
13 | %ApiType%Name = %ApiTypeLower%Name;
14 | }
15 |
16 | public string %ApiType%Name { get; set; }
17 | }
18 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/Templates/ResponseMarshalTemplate.txt:
--------------------------------------------------------------------------------
1 | using System.Collections.Generic;
2 | using System.IO;
3 | using Genbox.SimpleS3.Core.Abstracts;
4 | using Genbox.SimpleS3.Core.Abstracts.Marshallers;
5 | using Genbox.SimpleS3.Core.Network.Requests.Buckets;
6 | using Genbox.SimpleS3.Core.Network.Responses.Buckets;
7 | using JetBrains.Annotations;
8 |
9 | namespace Genbox.SimpleS3.Core.Internals.Marshallers.Responses.%ApiType%s
10 | {
11 | internal class %ApiName%ResponseMarshal : IResponseMarshal<%ApiName%Request, %ApiName%Response>
12 | {
13 | public void MarshalResponse(IS3Config config, %ApiName%Request request, %ApiName%Response response, IDictionary headers, Stream responseStream)
14 | {
15 | }
16 | }
17 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.S3Template/Templates/ResponseTemplate.txt:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Core.Network.Responses.%ApiType%s
2 | {
3 | ///
4 | /// %ApiName%
5 | ///
6 | public class %ApiName%Response : BaseResponse
7 | {
8 | }
9 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.Shared/S3Provider.cs:
--------------------------------------------------------------------------------
1 | namespace Genbox.SimpleS3.Utility.Shared;
2 |
3 | [Flags]
4 | public enum S3Provider
5 | {
6 | None = 0,
7 | AmazonS3 = 1,
8 | BackBlazeB2 = 2,
9 | GoogleCloudStorage = 4,
10 | Wasabi = 8,
11 |
12 | All = AmazonS3 | BackBlazeB2 | GoogleCloudStorage | Wasabi
13 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.TestCleanup/SimpleS3.Utility.TestCleanup.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | PreserveNewest
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Utility.TestSetup/SimpleS3.Utility.TestSetup.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | PreserveNewest
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Wasabi.Tests/SimpleS3.Wasabi.Tests.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/Src/SimpleS3.Wasabi.Tests/StaticCreatorTests.cs:
--------------------------------------------------------------------------------
1 | using Genbox.SimpleS3.Core.TestBase.Code;
2 | using Genbox.SimpleS3.Extensions.Wasabi;
3 |
4 | namespace Genbox.SimpleS3.Wasabi.Tests;
5 |
6 | public class StaticCreatorTests
7 | {
8 | [Fact]
9 | public async Task StaticClient()
10 | {
11 | NullNetworkDriver driver = new NullNetworkDriver();
12 |
13 | WasabiConfig config = new WasabiConfig("ExampleKeyId00000000", "wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLEKEY", WasabiRegion.EuCentral1);
14 | using WasabiClient client = new WasabiClient(config, driver);
15 |
16 | await client.GetObjectAsync("testbucket", "GetObjectAsync");
17 | Assert.Equal("https://testbucket.s3.eu-central-1.wasabisys.com/GetObjectAsync", driver.LastUrl);
18 | }
19 | }
--------------------------------------------------------------------------------
/Src/SimpleS3.Wasabi/SimpleS3.Wasabi.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------