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

unify commands #544

Merged
merged 1 commit into from
Jun 4, 2024
Merged
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
24 changes: 11 additions & 13 deletions golem-cli/src/cloud/command.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,33 +13,31 @@
// limitations under the License.

use crate::cloud::command::account::AccountSubcommand;
use crate::cloud::command::api_definition::ApiDefinitionSubcommand;
use crate::cloud::command::api_deployment::ApiDeploymentSubcommand;
use crate::cloud::command::certificate::CertificateSubcommand;
use crate::cloud::command::domain::DomainSubcommand;
use crate::cloud::command::policy::ProjectPolicySubcommand;
use crate::cloud::command::project::ProjectSubcommand;
use crate::cloud::command::token::TokenSubcommand;
use crate::cloud::command::worker::WorkerSubcommand;
use crate::cloud::model::{AccountId, ProjectAction, ProjectPolicyId, ProjectRef};
use crate::cloud::model::{
AccountId, CloudComponentIdOrName, ProjectAction, ProjectPolicyId, ProjectRef,
};
use crate::command::api_definition::ApiDefinitionSubcommand;
use crate::command::api_deployment::ApiDeploymentSubcommand;
use crate::command::component::ComponentSubCommand;
use crate::command::worker::WorkerSubcommand;
use crate::model::Format;
use clap::{Parser, Subcommand};
use clap_verbosity_flag::Verbosity;
use component::ComponentSubCommand;
use golem_examples::model::{ExampleName, GuestLanguage, GuestLanguageTier, PackageName};
use std::path::PathBuf;
use uuid::Uuid;

pub mod account;
pub mod api_definition;
pub mod api_deployment;
pub mod certificate;
pub mod component;
pub mod domain;
pub mod policy;
pub mod project;
pub mod token;
pub mod worker;

#[derive(Subcommand, Debug)]
#[command()]
Expand All @@ -48,14 +46,14 @@ pub enum CloudCommand {
#[command()]
Component {
#[command(subcommand)]
subcommand: ComponentSubCommand,
subcommand: ComponentSubCommand<ProjectRef, CloudComponentIdOrName>,
},

/// Manage Golem workers
#[command()]
Worker {
#[command(subcommand)]
subcommand: WorkerSubcommand,
subcommand: WorkerSubcommand<CloudComponentIdOrName>,
},

/// Manage accounts
Expand Down Expand Up @@ -157,14 +155,14 @@ pub enum CloudCommand {
#[command()]
ApiDefinition {
#[command(subcommand)]
subcommand: ApiDefinitionSubcommand,
subcommand: ApiDefinitionSubcommand<ProjectRef>,
},

/// Manage Golem api deployments
#[command()]
ApiDeployment {
#[command(subcommand)]
subcommand: ApiDeploymentSubcommand,
subcommand: ApiDeploymentSubcommand<ProjectRef>,
},

#[command()]
Expand Down
22 changes: 18 additions & 4 deletions golem-cli/src/cloud/factory.rs
Original file line number Diff line number Diff line change
Expand Up @@ -32,17 +32,18 @@ use crate::cloud::clients::project_grant::{ProjectGrantClient, ProjectGrantClien
use crate::cloud::clients::token::{TokenClient, TokenClientLive};
use crate::cloud::clients::worker::WorkerClientLive;
use crate::cloud::clients::CloudAuthentication;
use crate::cloud::model::ProjectId;
use crate::cloud::model::{ProjectId, ProjectRef};
use crate::cloud::service::account::{AccountService, AccountServiceLive};
use crate::cloud::service::certificate::{CertificateService, CertificateServiceLive};
use crate::cloud::service::domain::{DomainService, DomainServiceLive};
use crate::cloud::service::grant::{GrantService, GrantServiceLive};
use crate::cloud::service::policy::{ProjectPolicyService, ProjectPolicyServiceLive};
use crate::cloud::service::project::{ProjectService, ProjectServiceLive};
use crate::cloud::service::project::{CloudProjectResolver, ProjectService, ProjectServiceLive};
use crate::cloud::service::project_grant::{ProjectGrantService, ProjectGrantServiceLive};
use crate::cloud::service::token::{TokenService, TokenServiceLive};
use crate::factory::{FactoryWithAuth, ServiceFactory};
use crate::model::GolemError;
use crate::service::project::ProjectResolver;
use golem_cloud_client::{Context, Security};
use url::Url;

Expand Down Expand Up @@ -121,7 +122,7 @@ impl CloudServiceFactory {
pub fn project_service(
&self,
auth: &CloudAuthentication,
) -> Result<Box<dyn ProjectService + Send + Sync>, GolemError> {
) -> Result<Box<dyn ProjectService + Send + Sync + 'static>, GolemError> {
Ok(Box::new(ProjectServiceLive {
account_id: auth.account_id(),
client: self.project_client(auth)?,
Expand Down Expand Up @@ -277,18 +278,31 @@ impl CloudServiceFactory {

impl ServiceFactory for CloudServiceFactory {
type SecurityContext = CloudAuthentication;
type ProjectRef = ProjectRef;
type ProjectContext = ProjectId;

fn with_auth(
&self,
auth: &Self::SecurityContext,
) -> FactoryWithAuth<Self::ProjectContext, Self::SecurityContext> {
) -> FactoryWithAuth<Self::ProjectRef, Self::ProjectContext, Self::SecurityContext> {
FactoryWithAuth {
auth: auth.clone(),
factory: Box::new(self.clone()),
}
}

fn project_resolver(
&self,
auth: &Self::SecurityContext,
) -> Result<
Box<dyn ProjectResolver<Self::ProjectRef, Self::ProjectContext> + Send + Sync>,
GolemError,
> {
Ok(Box::new(CloudProjectResolver {
service: self.project_service(auth)?,
}))
}

fn component_client(
&self,
auth: &Self::SecurityContext,
Expand Down
11 changes: 1 addition & 10 deletions golem-cli/src/cloud/model.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@

pub mod text;

use crate::model::{ComponentId, ComponentIdOrName, ComponentName};
use crate::model::{ComponentId, ComponentName};
use clap::{ArgMatches, Error, FromArgMatches};
use derive_more::{Display, FromStr, Into};
use serde::{Deserialize, Serialize};
Expand Down Expand Up @@ -221,15 +221,6 @@ pub enum CloudComponentIdOrName {
Name(ComponentName, ProjectRef),
}

impl CloudComponentIdOrName {
pub fn split(self) -> (ComponentIdOrName, Option<ProjectRef>) {
match self {
CloudComponentIdOrName::Id(id) => (ComponentIdOrName::Id(id), None),
CloudComponentIdOrName::Name(name, p) => (ComponentIdOrName::Name(name), Some(p)),
}
}
}

#[derive(Copy, Clone, PartialEq, Eq, Debug, EnumIter, Serialize, Deserialize)]
pub enum Role {
Admin,
Expand Down
15 changes: 15 additions & 0 deletions golem-cli/src/cloud/service/project.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
use crate::cloud::clients::project::ProjectClient;
use crate::cloud::model::{AccountId, ProjectId, ProjectRef};
use crate::model::{GolemError, GolemResult};
use crate::service::project::ProjectResolver;
use async_trait::async_trait;
use golem_cloud_client::model::Project;
use indoc::formatdoc;
Expand Down Expand Up @@ -117,3 +118,17 @@ impl ProjectService for ProjectServiceLive {
}
}
}

pub struct CloudProjectResolver {
pub service: Box<dyn ProjectService + Send + Sync>,
}

#[async_trait]
impl ProjectResolver<ProjectRef, ProjectId> for CloudProjectResolver {
async fn resolve_id_or_default(
&self,
project_ref: ProjectRef,
) -> Result<ProjectId, GolemError> {
self.service.resolve_id_or_default(project_ref).await
}
}
8 changes: 4 additions & 4 deletions golem-cli/src/cloud_main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ async fn async_main(cmd: GolemCloudCommand) -> Result<(), Box<dyn std::error::Er
subcommand
.handle(
factory.component_service(&auth)?.as_ref(),
factory.project_service(&auth)?.as_ref(),
factory.project_resolver(&auth)?.as_ref(),
)
.await
}
Expand All @@ -104,7 +104,7 @@ async fn async_main(cmd: GolemCloudCommand) -> Result<(), Box<dyn std::error::Er
.handle(
cmd.format,
factory.worker_service(&auth)?.as_ref(),
factory.project_service(&auth)?.as_ref(),
factory.project_resolver(&auth)?.as_ref(),
)
.await
}
Expand Down Expand Up @@ -168,15 +168,15 @@ async fn async_main(cmd: GolemCloudCommand) -> Result<(), Box<dyn std::error::Er
subcommand
.handle(
factory.api_definition_service(&auth)?.as_ref(),
factory.project_service(&auth)?.as_ref(),
factory.project_resolver(&auth)?.as_ref(),
)
.await
}
CloudCommand::ApiDeployment { subcommand } => {
subcommand
.handle(
factory.api_deployment_service(&auth)?.as_ref(),
factory.project_service(&auth)?.as_ref(),
factory.project_resolver(&auth)?.as_ref(),
)
.await
}
Expand Down
41 changes: 41 additions & 0 deletions golem-cli/src/command.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
// Copyright 2024 Golem Cloud
//
// 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 crate::cloud::model::{CloudComponentIdOrName, ProjectRef};
use crate::model::ComponentIdOrName;
use crate::oss::model::OssContext;

pub mod api_definition;
pub mod api_deployment;
pub mod component;
pub mod worker;

pub trait ComponentRefSplit<ProjectRef> {
fn split(self) -> (ComponentIdOrName, Option<ProjectRef>);
}

impl ComponentRefSplit<OssContext> for ComponentIdOrName {
fn split(self) -> (ComponentIdOrName, Option<OssContext>) {
(self, None)
}
}

impl ComponentRefSplit<ProjectRef> for CloudComponentIdOrName {
fn split(self) -> (ComponentIdOrName, Option<ProjectRef>) {
match self {
CloudComponentIdOrName::Id(id) => (ComponentIdOrName::Id(id), None),
CloudComponentIdOrName::Name(name, p) => (ComponentIdOrName::Name(name), Some(p)),
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,17 +12,16 @@
// See the License for the specific language governing permissions and
// limitations under the License.

use crate::cloud::model::{ProjectId, ProjectRef};
use crate::cloud::service::project::ProjectService;
use crate::model::{
ApiDefinitionId, ApiDefinitionVersion, GolemError, GolemResult, PathBufOrStdin,
};
use crate::service::api_definition::ApiDefinitionService;
use crate::service::project::ProjectResolver;
use clap::Subcommand;

#[derive(Subcommand, Debug)]
#[command()]
pub enum ApiDefinitionSubcommand {
pub enum ApiDefinitionSubcommand<ProjectRef: clap::Args> {
/// Lists all api definitions
#[command()]
List {
Expand Down Expand Up @@ -110,11 +109,11 @@ pub enum ApiDefinitionSubcommand {
},
}

impl ApiDefinitionSubcommand {
pub async fn handle(
impl<ProjectRef: clap::Args + Send + Sync + 'static> ApiDefinitionSubcommand<ProjectRef> {
pub async fn handle<ProjectContext>(
self,
service: &(dyn ApiDefinitionService<ProjectContext = ProjectId> + Send + Sync),
projects: &(dyn ProjectService + Send + Sync),
service: &(dyn ApiDefinitionService<ProjectContext = ProjectContext> + Send + Sync),
projects: &(dyn ProjectResolver<ProjectRef, ProjectContext> + Send + Sync),
) -> Result<GolemResult, GolemError> {
match self {
ApiDefinitionSubcommand::Get {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,15 +12,14 @@
// See the License for the specific language governing permissions and
// limitations under the License.

use crate::cloud::model::{ProjectId, ProjectRef};
use crate::cloud::service::project::ProjectService;
use crate::model::{ApiDefinitionId, ApiDefinitionVersion, GolemError, GolemResult};
use crate::service::api_deployment::ApiDeploymentService;
use crate::service::project::ProjectResolver;
use clap::Subcommand;

#[derive(Subcommand, Debug)]
#[command()]
pub enum ApiDeploymentSubcommand {
pub enum ApiDeploymentSubcommand<ProjectRef: clap::Args> {
/// Create or update deployment
#[command()]
Deploy {
Expand All @@ -40,7 +39,7 @@ pub enum ApiDeploymentSubcommand {
host: String,

#[arg(short, long)]
subdomain: String, // TODO: unify cloud with OSS
subdomain: Option<String>,
},

/// Get api deployment
Expand Down Expand Up @@ -72,11 +71,11 @@ pub enum ApiDeploymentSubcommand {
},
}

impl ApiDeploymentSubcommand {
pub async fn handle(
impl<ProjectRef: clap::Args + Send + Sync + 'static> ApiDeploymentSubcommand<ProjectRef> {
pub async fn handle<ProjectContext>(
self,
service: &(dyn ApiDeploymentService<ProjectContext = ProjectId> + Send + Sync),
projects: &(dyn ProjectService + Send + Sync),
service: &(dyn ApiDeploymentService<ProjectContext = ProjectContext> + Send + Sync),
projects: &(dyn ProjectResolver<ProjectRef, ProjectContext> + Send + Sync),
) -> Result<GolemResult, GolemError> {
match self {
ApiDeploymentSubcommand::Deploy {
Expand All @@ -88,7 +87,7 @@ impl ApiDeploymentSubcommand {
} => {
let project_id = projects.resolve_id_or_default(project_ref).await?;
service
.deploy(id, version, host, Some(subdomain), &project_id)
.deploy(id, version, host, subdomain, &project_id)
.await
}
ApiDeploymentSubcommand::Get { site } => service.get(site).await,
Expand Down
Loading
Loading