Skip to content
New issue

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

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

Already on GitHub? Sign in to your account

upgrade to .net8 with minimal api #4

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .github/workflows/dotnet.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ on:

env:
APP_NAME: 'OneCloud.S3.API'
DOTNET_VERSION: '7.0.x'
DOTNET_VERSION: '8.0.x'

jobs:
build-and-publish:
Expand Down Expand Up @@ -52,7 +52,7 @@ jobs:

- name: Build Container Image
working-directory: ./${{env.APP_NAME}}/
run: dotnet publish -p:PublishProfile=DefaultContainer -p:ContainerImageName=ghcr.io/${{ github.repository }} -c Release
run: dotnet publish --os linux --arch x64 --self-contained true -c Release -p:PublishProfile=DefaultContainer -p:PublishSingleFile=true -p:ContainerImageName=ghcr.io/${{ github.repository }}

- name: Push Image to Container Registry
run: docker push ghcr.io/${{ github.repository }} --all-tags
20 changes: 10 additions & 10 deletions Directory.Packages.props
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
<Project>
<PropertyGroup>
<ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>
</PropertyGroup>
<ItemGroup>
<PackageVersion Include="AWSSDK.S3" Version="3.7.107.5" />
<PackageVersion Include="Microsoft.AspNetCore.OpenApi" Version="7.0.8" />
<PackageVersion Include="Microsoft.NET.Build.Containers" Version="7.0.305" />
<PackageVersion Include="Swashbuckle.AspNetCore" Version="6.5.0" />
</ItemGroup>
</Project>
<PropertyGroup>
<ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>
</PropertyGroup>
<ItemGroup>
<PackageVersion Include="AWSSDK.S3" Version="3.7.305.10" />
<PackageVersion Include="Microsoft.AspNetCore.OpenApi" Version="8.0.1" />
<PackageVersion Include="Microsoft.NET.Build.Containers" Version="8.0.101" />
<PackageVersion Include="Swashbuckle.AspNetCore" Version="6.5.0" />
</ItemGroup>
</Project>
87 changes: 0 additions & 87 deletions OneCloud.S3.API/Controllers/BucketsController.cs

This file was deleted.

119 changes: 0 additions & 119 deletions OneCloud.S3.API/Controllers/ObjectsController.cs

This file was deleted.

59 changes: 59 additions & 0 deletions OneCloud.S3.API/EndPoints/BucketsEndPoints.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
using Amazon.S3;
using Amazon.S3.Model;
using Microsoft.AspNetCore.Http.HttpResults;
using OneCloud.S3.API.Models;
using System.Net;

namespace OneCloud.S3.API.EndPoints;

public static class BucketsEndPoints
{
public static IEndpointRouteBuilder UseBucketsEndpoints(this IEndpointRouteBuilder builder)
{
var buckets = builder
.MapGroup("storage/buckets")
.WithTags("Buckets");

buckets.MapGet("", async (AmazonS3Client client, CancellationToken cancellationToken) =>
await client.ListBucketsAsync(cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK } response
? TypedResults.Ok(response.Buckets.Select(s => new BucketDto(s.BucketName, s.CreationDate)))
: Results.NotFound())
.Produces<IEnumerable<BucketDto>>()
.Produces(StatusCodes.Status404NotFound)
.WithName("GetBuckets")
.WithSummary("Buckets list");

buckets.MapGet("{bucketName}", async (AmazonS3Client client, string bucketName, CancellationToken cancellationToken) =>
await client.ListObjectsAsync(new ListObjectsRequest { BucketName = bucketName }, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK } response
? TypedResults.Ok(response.S3Objects.Select(s => new ObjectDto(s.BucketName, s.Key, s.ETag, s.LastModified, s.Size)))
: Results.NotFound())
.Produces<IEnumerable<ObjectDto>>()
.Produces(StatusCodes.Status404NotFound)
.WithName("GetBucketContent")
.WithSummary("Bucket content");

buckets.MapPost("{bucketName}", async (AmazonS3Client client, string bucketName, CancellationToken cancellationToken) =>
await client.PutBucketAsync(bucketName, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK }
? TypedResults.CreatedAtRoute("GetBucketContent", new { bucketName })
: Results.BadRequest())
.Produces<CreatedAtRoute>(StatusCodes.Status201Created)
.Produces(StatusCodes.Status403Forbidden)
.WithName("CreateBucket")
.WithSummary("Create bucket");

buckets.MapDelete("{bucketName}", async (AmazonS3Client client, string bucketName, CancellationToken cancellationToken) =>
await client.DeleteBucketAsync(bucketName, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK }
? TypedResults.NoContent()
: Results.NotFound())
.Produces<NoContent>()
.Produces(StatusCodes.Status404NotFound)
.WithName("DeleteBucket")
.WithSummary("Delete bucket");

return builder;
}
}
83 changes: 83 additions & 0 deletions OneCloud.S3.API/EndPoints/ObjectsEndPoints.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
using Amazon.S3;
using Amazon.S3.Model;
using Microsoft.AspNetCore.Http.HttpResults;
using Microsoft.Net.Http.Headers;
using OneCloud.S3.API.Models;
using System.Net;

namespace OneCloud.S3.API.EndPoints;

public static class ObjectsEndPoints
{
public static IEndpointRouteBuilder UseObjectsEndpoints(this IEndpointRouteBuilder builder)
{
var objects = builder
.MapGroup("storage/objects")
.WithTags("Objects");

objects.MapGet("{bucketName}", async (AmazonS3Client client, string bucketName, string filePath, CancellationToken cancellationToken) =>
await client.GetObjectAsync(new GetObjectRequest { BucketName = bucketName, Key = filePath }, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK } response
? TypedResults.Stream(response.ResponseStream, response.Headers.ContentType, response.Key, response.LastModified, EntityTagHeaderValue.Parse(response.ETag), true)
: Results.NotFound())
.Produces<FileStreamHttpResult>()
.Produces(StatusCodes.Status404NotFound)
.WithName("GetObject")
.WithSummary("Get object");

objects.MapGet("{bucketName}/url", (AmazonS3Client client, string bucketName, string filePath, DateTime expires) =>
client.GetPreSignedURL(new GetPreSignedUrlRequest { BucketName = bucketName, Key = filePath, Expires = expires, Protocol = Protocol.HTTPS })
is { } url
? TypedResults.Created(url, new ObjectUrlDto(url, expires))
: Results.NotFound())
.Produces<ObjectUrlDto>()
.Produces(StatusCodes.Status404NotFound)
.WithName("GetObjectUrl")
.WithSummary("Temporary public URL to object");

objects.MapPost("{bucketName}", async (AmazonS3Client client, string bucketName, string filePath, IFormFile file, CancellationToken cancellationToken) =>
{
await using var stream = file.OpenReadStream();
return await client.PutObjectAsync(new PutObjectRequest { BucketName = bucketName, Key = filePath, ContentType = file.ContentType, InputStream = stream, AutoCloseStream = true, UseChunkEncoding = false }, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK }
? TypedResults.CreatedAtRoute("GetObject", new { bucketName, filePath, file.ContentType })
: Results.BadRequest();
})
.Produces<PutObjectResponse>(StatusCodes.Status201Created)
.Produces(StatusCodes.Status403Forbidden)
.WithName("CreateObject")
.WithSummary("Create object");

objects.MapPut("{bucketName}/permission", async (AmazonS3Client client, string bucketName, string filePath, bool isPublicRead, CancellationToken cancellationToken) =>
await client.PutACLAsync(new PutACLRequest { BucketName = bucketName, Key = filePath, CannedACL = isPublicRead ? S3CannedACL.PublicRead : S3CannedACL.Private }, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK }
? TypedResults.NoContent()
: Results.NotFound())
.Produces<NoContent>()
.Produces(StatusCodes.Status404NotFound)
.WithName("ChangeObjectPermissions")
.WithSummary("Change object permissions");

objects.MapPut("{bucketName}/copy", async (AmazonS3Client client, string bucketName, string filePath, string destBucket, string destFilePath, CancellationToken cancellationToken) =>
await client.CopyObjectAsync(new CopyObjectRequest { SourceBucket = bucketName, SourceKey = filePath, DestinationBucket = destBucket, DestinationKey = destFilePath }, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK }
? TypedResults.NoContent()
: Results.NotFound())
.Produces<NoContent>()
.Produces(StatusCodes.Status404NotFound)
.WithName("CopyObject")
.WithSummary("Copy object");

objects.MapDelete("{bucketName}", async (AmazonS3Client client, string bucketName, string filePath, CancellationToken cancellationToken) =>
await client.DeleteObjectAsync(new DeleteObjectRequest { BucketName = bucketName, Key = filePath }, cancellationToken)
is { HttpStatusCode: HttpStatusCode.OK }
? TypedResults.NoContent()
: Results.NotFound())
.Produces<NoContent>()
.Produces(StatusCodes.Status404NotFound)
.WithName("DeleteObject")
.WithSummary("Delete object");

return builder;
}
}
Loading
Loading