From 3c29f7ae00dcab8ed7431c8b830a6064d2255cf9 Mon Sep 17 00:00:00 2001 From: Eguo Wang Date: Thu, 18 Jan 2024 23:00:51 +0800 Subject: [PATCH] feat: New folders handler and service --- src/handlers/folder.rs | 173 +++++++++++++++++++++++++++++++++++++++++ src/handlers/mod.rs | 1 + src/routes.rs | 9 ++- src/services/folder.rs | 57 ++++++++++++++ src/services/mod.rs | 3 + src/swagger.rs | 6 ++ 6 files changed, 248 insertions(+), 1 deletion(-) create mode 100644 src/handlers/folder.rs create mode 100644 src/services/folder.rs diff --git a/src/handlers/folder.rs b/src/handlers/folder.rs new file mode 100644 index 0000000..dd3104d --- /dev/null +++ b/src/handlers/folder.rs @@ -0,0 +1,173 @@ +// Copyright (c) The Amphitheatre Authors. All rights reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +use std::sync::Arc; + +use axum::extract::{Path, State}; +use axum::http::StatusCode; +use axum::response::IntoResponse; +use axum::Json; +use uuid::Uuid; + +use crate::context::Context; +use crate::errors::Result; +use crate::requests::file::DestinationRequest; +use crate::services::FolderService; + +// The Folders Service Handlers. + +/// Returns a folder's tree. +#[utoipa::path( + get, path = "/v1/playbooks/{id}/folders/{reference}/{path}", + params( + ("id" = Uuid, description = "The id of playbook"), + ("reference" = String, description = "The name of the commit/branch/tag."), + ("path" = String, description = "The file path relative to the root of the repository."), + ), + responses( + (status = 200, description = "The folder tree", body = Tree), + (status = 404, description = "Playbook not found"), + (status = 404, description = "Folder not found"), + (status = 500, description = "Internal Server Error"), + ), + tag = "Folders" +)] +pub async fn get( + State(ctx): State>, + + Path(id): Path, + Path(reference): Path, + Path(path): Path, +) -> Result { + Ok(Json(FolderService::get(ctx, id, reference, path).await?)) +} + +/// Create a folder +#[utoipa::path( + post, path = "/v1/playbooks/{id}/folders/{reference}/{path}", + params( + ("id" = Uuid, description = "The id of playbook"), + ("reference" = String, description = "The name of the commit/branch/tag."), + ("path" = String, description = "The file path relative to the root of the repository."), + ), + responses( + (status = 201, description = "The folder created successfully", body = Tree), + (status = 404, description = "Playbook not found"), + (status = 500, description = "Internal Server Error"), + ), + tag = "Folders" +)] +pub async fn create( + State(ctx): State>, + + Path(id): Path, + Path(reference): Path, + Path(path): Path, +) -> Result { + Ok((StatusCode::CREATED, Json(FolderService::create(ctx, id, reference, path).await?))) +} + +/// Delete a folder +#[utoipa::path( + delete, path = "/v1/playbooks/{id}/folders/{reference}/{path}", + params( + ("id" = Uuid, description = "The id of playbook"), + ("reference" = String, description = "The name of the commit/branch/tag."), + ("path" = String, description = "The file path relative to the root of the repository."), + ), + responses( + (status = 204, description = "The folder deleted successfully"), + (status = 404, description = "Playbook not found"), + (status = 404, description = "Folder not found"), + (status = 500, description = "Internal Server Error"), + ), + tag = "Folders" +)] +pub async fn delete( + State(ctx): State>, + + Path(id): Path, + Path(reference): Path, + Path(path): Path, +) -> Result { + FolderService::delete(ctx, id, reference, path).await?; + + Ok(StatusCode::NO_CONTENT) +} + +/// Copy a folder +#[utoipa::path( + post, path = "/v1/playbooks/{id}/folders/{reference}/{path}/actions/copy", + params( + ("id" = Uuid, description = "The id of playbook"), + ("reference" = String, description = "The name of the commit/branch/tag. Default: default branch."), + ("path" = String, description = "The file path relative to the root of the repository."), + ), + request_body( + content = inline(DestinationRequest), + description = "The destination request", + content_type = "application/json" + ), + responses( + (status = 200, description = "The folder copied successfully", body = Content), + (status = 404, description = "Playbook not found"), + (status = 404, description = "Folder not found"), + (status = 500, description = "Internal Server Error"), + ), + tag = "Folders" +)] +pub async fn copy( + State(ctx): State>, + + Path(id): Path, + Path(reference): Path, + Path(path): Path, + + Json(req): Json, +) -> Result { + Ok(Json(FolderService::copy(ctx, id, reference, path, req.destination).await?)) +} + +/// Move a folder +#[utoipa::path( + post, path = "/v1/playbooks/{id}/folders/{reference}/{path}/actions/move", + params( + ("id" = Uuid, description = "The id of playbook"), + ("reference" = String, description = "The name of the commit/branch/tag. Default: default branch."), + ("path" = String, description = "The file path relative to the root of the repository."), + ), + request_body( + content = inline(DestinationRequest), + description = "The destination request", + content_type = "application/json" + ), + responses( + (status = 200, description = "The folder moved successfully", body = Content), + (status = 404, description = "Playbook not found"), + (status = 404, description = "Folder not found"), + (status = 500, description = "Internal Server Error"), + ), + tag = "Folders" +)] +pub async fn rename( + State(ctx): State>, + + Path(id): Path, + Path(reference): Path, + Path(path): Path, + + Json(req): Json, +) -> Result { + Ok(Json(FolderService::rename(ctx, id, reference, path, req.destination).await?)) +} diff --git a/src/handlers/mod.rs b/src/handlers/mod.rs index 4b9e820..7989e09 100644 --- a/src/handlers/mod.rs +++ b/src/handlers/mod.rs @@ -13,5 +13,6 @@ // limitations under the License. pub mod file; +pub mod folder; pub mod logger; pub mod playbook; diff --git a/src/routes.rs b/src/routes.rs index 0fda94d..ca84cbc 100644 --- a/src/routes.rs +++ b/src/routes.rs @@ -18,7 +18,7 @@ use axum::routing::{delete, get, post, put}; use axum::Router; use crate::context::Context; -use crate::handlers::{file, logger, playbook}; +use crate::handlers::{file, folder, logger, playbook}; pub fn build() -> Router> { Router::new() @@ -37,4 +37,11 @@ pub fn build() -> Router> { .route("/v1/playbooks/:id/files/:reference/:path", delete(file::delete)) .route("/v1/playbooks/:id/files/:reference/:path/actions/copy", post(file::copy)) .route("/v1/playbooks/:id/files/:reference/:path/actions/move", post(file::rename)) + // + // folders + .route("/v1/playbooks/:id/folders/:reference/:path", get(folder::get)) + .route("/v1/playbooks/:id/folders/:reference/:path", post(folder::create)) + .route("/v1/playbooks/:id/folders/:reference/:path", delete(folder::delete)) + .route("/v1/playbooks/:id/folders/:reference/:path/actions/copy", post(folder::copy)) + .route("/v1/playbooks/:id/folders/:reference/:path/actions/move", post(folder::rename)) } diff --git a/src/services/folder.rs b/src/services/folder.rs new file mode 100644 index 0000000..b09b723 --- /dev/null +++ b/src/services/folder.rs @@ -0,0 +1,57 @@ +// Copyright (c) The Amphitheatre Authors. All rights reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +use std::sync::Arc; +use uuid::Uuid; + +use amp_common::scm::content::Content; + +use crate::context::Context; +use crate::errors::Result; + +pub struct FolderService; + +impl FolderService { + pub async fn get(_ctx: Arc, _id: Uuid, _reference: String, _path: String) -> Result { + todo!() + } + + pub async fn create(_ctx: Arc, _id: Uuid, _reference: String, _path: String) -> Result { + todo!() + } + + pub async fn delete(_ctx: Arc, _id: Uuid, _reference: String, _path: String) -> Result<()> { + todo!() + } + + pub async fn copy( + _ctx: Arc, + _id: Uuid, + _reference: String, + _path: String, + _destination: String, + ) -> Result { + todo!() + } + + pub async fn rename( + _ctx: Arc, + _id: Uuid, + _reference: String, + _path: String, + _destination: String, + ) -> Result { + todo!() + } +} diff --git a/src/services/mod.rs b/src/services/mod.rs index cf6e61b..12115fa 100644 --- a/src/services/mod.rs +++ b/src/services/mod.rs @@ -15,6 +15,9 @@ mod file; pub use file::FileService; +mod folder; +pub use folder::FolderService; + mod logger; pub use logger::LoggerService; diff --git a/src/swagger.rs b/src/swagger.rs index ba479a1..b82d8ec 100644 --- a/src/swagger.rs +++ b/src/swagger.rs @@ -32,6 +32,12 @@ use crate::{handlers, requests}; handlers::file::delete, handlers::file::copy, handlers::file::rename, + + handlers::folder::get, + handlers::folder::create, + handlers::folder::delete, + handlers::folder::copy, + handlers::folder::rename, ), components( schemas(