build repo webhook management

This commit is contained in:
mbecker20
2024-07-05 03:17:29 -07:00
parent ce67655021
commit 78a63f92bb
3 changed files with 120 additions and 34 deletions
+27 -4
View File
@@ -2,8 +2,11 @@ use anyhow::{anyhow, Context};
use monitor_client::{
api::write::*,
entities::{
build::Build, config::core::CoreConfig,
permission::PermissionLevel, user::User, NoData,
build::{Build, PartialBuildConfig},
config::core::CoreConfig,
permission::PermissionLevel,
user::User,
NoData,
},
};
use octorust::types::{
@@ -76,7 +79,9 @@ impl Resolve<CreateBuildWebhook, User> for State {
user: User,
) -> anyhow::Result<CreateBuildWebhookResponse> {
let Some(github) = github_client() else {
return Err(anyhow!("github_webhook_app is not configured in core config toml"));
return Err(anyhow!(
"github_webhook_app is not configured in core config toml"
));
};
let build = resource::get_check_permissions::<Build>(
@@ -149,6 +154,22 @@ impl Resolve<CreateBuildWebhook, User> for State {
.await
.context("failed to create webhook")?;
if !build.config.webhook_enabled {
self
.resolve(
UpdateBuild {
id: build.id,
config: PartialBuildConfig {
webhook_enabled: Some(true),
..Default::default()
},
},
user,
)
.await
.context("failed to update build to enable webhook")?;
}
Ok(NoData {})
}
}
@@ -161,7 +182,9 @@ impl Resolve<DeleteBuildWebhook, User> for State {
user: User,
) -> anyhow::Result<DeleteBuildWebhookResponse> {
let Some(github) = github_client() else {
return Err(anyhow!("github_webhook_app is not configured in core config toml"));
return Err(anyhow!(
"github_webhook_app is not configured in core config toml"
));
};
let build = resource::get_check_permissions::<Build>(
+21 -2
View File
@@ -2,8 +2,11 @@ use anyhow::{anyhow, Context};
use monitor_client::{
api::write::*,
entities::{
config::core::CoreConfig, permission::PermissionLevel,
repo::Repo, user::User, NoData,
config::core::CoreConfig,
permission::PermissionLevel,
repo::{PartialRepoConfig, Repo},
user::User,
NoData,
},
};
use octorust::types::{
@@ -158,6 +161,22 @@ impl Resolve<CreateRepoWebhook, User> for State {
.await
.context("failed to create webhook")?;
if !repo.config.webhook_enabled {
self
.resolve(
UpdateRepo {
id: repo.id,
config: PartialRepoConfig {
webhook_enabled: Some(true),
..Default::default()
},
},
user,
)
.await
.context("failed to update repo to enable webhook")?;
}
Ok(NoData {})
}
}
@@ -8,14 +8,17 @@ import {
SecretSelector,
SystemCommand,
} from "@components/config/util";
import { useRead, useWrite } from "@lib/hooks";
import { useInvalidate, useRead, useWrite } from "@lib/hooks";
import { env_to_text } from "@lib/utils";
import { Types } from "@monitor/client";
import { Button } from "@ui/button";
import { Textarea } from "@ui/textarea";
import { PlusCircle } from "lucide-react";
import { Ban, CirclePlus, PlusCircle } from "lucide-react";
import { ReactNode, RefObject, createRef, useState } from "react";
import { CopyGithubWebhook, LabelsConfig, ResourceSelector } from "../common";
import { useToast } from "@ui/use-toast";
import { text_color_class_by_intention } from "@lib/color";
import { ConfirmButton } from "@components/util";
export const BuildConfig = ({
id,
@@ -28,9 +31,9 @@ export const BuildConfig = ({
target: { type: "Build", id },
}).data;
const config = useRead("GetBuild", { build: id }).data?.config;
const webhook = useRead("GetBuildWebhookEnabled", { build: id }).data;
const global_disabled =
useRead("GetCoreInfo", {}).data?.ui_write_disabled ?? false;
// const docker_organizations = useRead("ListDockerOrganizations", {}).data;
const [update, set] = useState<Partial<Types.BuildConfig>>({});
const { mutateAsync } = useWrite("UpdateBuild");
@@ -145,29 +148,6 @@ export const BuildConfig = ({
},
build_path: true,
dockerfile_path: true,
// docker_account: (account, set) =>
// (update.builder_id ?? config.builder_id ? true : false) && (
// <AccountSelector
// id={update.builder_id ?? config.builder_id ?? undefined}
// type="Builder"
// account_type="docker"
// selected={account}
// onSelect={(docker_account) => set({ docker_account })}
// disabled={disabled}
// placeholder="None"
// />
// ),
// docker_organization:
// docker_organizations === undefined ||
// docker_organizations.length === 0
// ? undefined
// : (value, set) => (
// <DockerOrganizations
// value={value}
// set={set}
// disabled={disabled}
// />
// ),
use_buildx: true,
},
},
@@ -251,11 +231,75 @@ export const BuildConfig = ({
label: "Github Webhook",
components: {
["build" as any]: () => (
<ConfigItem label="Build">
<ConfigItem label="Webhook Url">
<CopyGithubWebhook path={`/build/${id}`} />
</ConfigItem>
),
webhook_enabled: true,
webhook_enabled: webhook !== undefined && !webhook.managed,
["managed" as any]: () => {
const inv = useInvalidate();
const { toast } = useToast();
const { mutate: createWebhook, isPending: createPending } =
useWrite("CreateBuildWebhook", {
onSuccess: () => {
toast({ title: "Webhook Created" });
inv(["GetBuildWebhookEnabled", { build: id }]);
},
});
const { mutate: deleteWebhook, isPending: deletePending } =
useWrite("DeleteBuildWebhook", {
onSuccess: () => {
toast({ title: "Webhook Deleted" });
inv(["GetBuildWebhookEnabled", { build: id }]);
},
});
if (!webhook || !webhook.managed) return;
return (
<ConfigItem label="Manage Webhook">
{webhook.enabled && (
<div className="flex items-center gap-4 flex-wrap">
<div className="flex items-center gap-2">
Incoming webhook is{" "}
<div
className={text_color_class_by_intention("Good")}
>
enabled
</div>
</div>
<ConfirmButton
title="Disable"
icon={<Ban className="w-4 h-4" />}
variant="destructive"
onClick={() => deleteWebhook({ build: id })}
loading={deletePending}
disabled={disabled || deletePending}
/>
</div>
)}
{!webhook.enabled && (
<div className="flex items-center gap-4 flex-wrap">
<div className="flex items-center gap-2">
Incoming webhook is{" "}
<div
className={text_color_class_by_intention(
"Critical"
)}
>
disabled
</div>
</div>
<ConfirmButton
title="Enable"
icon={<CirclePlus className="w-4 h-4" />}
onClick={() => createWebhook({ build: id })}
loading={createPending}
disabled={disabled || createPending}
/>
</div>
)}
</ConfigItem>
);
},
},
},
],