manage webhooks working

This commit is contained in:
mbecker20
2024-07-05 03:29:23 -07:00
parent 78a63f92bb
commit c21c8f99ae
6 changed files with 143 additions and 12 deletions

View File

@@ -3,7 +3,7 @@ use std::{
sync::OnceLock,
};
use anyhow::{anyhow, Context};
use anyhow::Context;
use async_timing_util::unix_timestamp_ms;
use futures::TryStreamExt;
use monitor_client::{
@@ -318,7 +318,10 @@ impl Resolve<GetBuildWebhookEnabled, User> for State {
user: User,
) -> anyhow::Result<GetBuildWebhookEnabledResponse> {
let Some(github) = github_client() else {
return Err(anyhow!("github_webhook_app is not configured in core config toml"));
return Ok(GetBuildWebhookEnabledResponse {
managed: false,
enabled: false,
});
};
let build = resource::get_check_permissions::<Build>(

View File

@@ -1,4 +1,4 @@
use anyhow::{anyhow, Context};
use anyhow::Context;
use monitor_client::{
api::read::*,
entities::{
@@ -128,7 +128,11 @@ impl Resolve<GetRepoWebhooksEnabled, User> for State {
user: User,
) -> anyhow::Result<GetRepoWebhooksEnabledResponse> {
let Some(github) = github_client() else {
return Err(anyhow!("github_webhook_app is not configured in core config toml"));
return Ok(GetRepoWebhooksEnabledResponse {
managed: false,
clone_enabled: false,
pull_enabled: false,
});
};
let repo = resource::get_check_permissions::<Repo>(

View File

@@ -262,8 +262,6 @@ pub type ListCommonBuildExtraArgsResponse = Vec<String>;
//
/// Get whether a Build's target repo has a webhook for the build configured. Response: [GetBuildWebhookEnabledResponse].
///
/// Note. Will fail with 500 if `github_webhook_app` is not configured in core config.
#[typeshare]
#[derive(
Serialize, Deserialize, Debug, Clone, Request, EmptyTraits,

View File

@@ -114,8 +114,6 @@ pub struct GetReposSummaryResponse {
//
/// Get a target Repo's configured webhooks. Response: [GetRepoWebhooksEnabledResponse].
///
/// Note. Will fail with 500 if `github_webhook_app` is not configured in core config.
#[typeshare]
#[derive(
Serialize, Deserialize, Debug, Clone, Request, EmptyTraits,

View File

@@ -263,7 +263,7 @@ export const BuildConfig = ({
<div
className={text_color_class_by_intention("Good")}
>
enabled
ENABLED
</div>
</div>
<ConfirmButton
@@ -285,7 +285,7 @@ export const BuildConfig = ({
"Critical"
)}
>
disabled
DISABLED
</div>
</div>
<ConfirmButton

View File

@@ -4,16 +4,21 @@ import {
ConfigItem,
SystemCommand,
} from "@components/config/util";
import { useRead, useWrite } from "@lib/hooks";
import { useInvalidate, useRead, useWrite } from "@lib/hooks";
import { Types } from "@monitor/client";
import { useState } from "react";
import { CopyGithubWebhook, ServerSelector } from "../common";
import { useToast } from "@ui/use-toast";
import { text_color_class_by_intention } from "@lib/color";
import { ConfirmButton } from "@components/util";
import { Ban, CirclePlus } from "lucide-react";
export const RepoConfig = ({ id }: { id: string }) => {
const perms = useRead("GetPermissionLevel", {
target: { type: "Repo", id },
}).data;
const config = useRead("GetRepo", { repo: id }).data?.config;
const webhooks = useRead("GetRepoWebhooksEnabled", { repo: id }).data;
const global_disabled =
useRead("GetCoreInfo", {}).data?.ui_write_disabled ?? false;
const [update, set] = useState<Partial<Types.RepoConfig>>({});
@@ -108,7 +113,130 @@ export const RepoConfig = ({ id }: { id: string }) => {
<CopyGithubWebhook path={`/repo/${id}/pull`} />
</ConfigItem>
),
webhook_enabled: true,
webhook_enabled: webhooks !== undefined && !webhooks.managed,
["managed" as any]: () => {
const inv = useInvalidate();
const { toast } = useToast();
const { mutate: createWebhook, isPending: createPending } =
useWrite("CreateRepoWebhook", {
onSuccess: () => {
toast({ title: "Webhook Created" });
inv(["GetRepoWebhooksEnabled", { repo: id }]);
},
});
const { mutate: deleteWebhook, isPending: deletePending } =
useWrite("DeleteRepoWebhook", {
onSuccess: () => {
toast({ title: "Webhook Deleted" });
inv(["GetRepoWebhooksEnabled", { repo: id }]);
},
});
if (!webhooks || !webhooks.managed) return;
return (
<ConfigItem label="Manage Webhook">
{webhooks.clone_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>
and will trigger
<div
className={text_color_class_by_intention("Neutral")}
>
CLONE
</div>
</div>
<ConfirmButton
title="Disable"
icon={<Ban className="w-4 h-4" />}
variant="destructive"
onClick={() =>
deleteWebhook({
repo: id,
action: Types.RepoWebhookAction.Clone,
})
}
loading={deletePending}
disabled={disabled || deletePending}
/>
</div>
)}
{!webhooks.clone_enabled && webhooks.pull_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>
and will trigger
<div
className={text_color_class_by_intention("Neutral")}
>
PULL
</div>
</div>
<ConfirmButton
title="Disable"
icon={<Ban className="w-4 h-4" />}
variant="destructive"
onClick={() =>
deleteWebhook({
repo: id,
action: Types.RepoWebhookAction.Pull,
})
}
loading={deletePending}
disabled={disabled || deletePending}
/>
</div>
)}
{!webhooks.clone_enabled && !webhooks.pull_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 for Clone"
icon={<CirclePlus className="w-4 h-4" />}
onClick={() =>
createWebhook({
repo: id,
action: Types.RepoWebhookAction.Clone,
})
}
loading={createPending}
disabled={disabled || createPending}
/>
<ConfirmButton
title="Enable for Pull"
icon={<CirclePlus className="w-4 h-4" />}
onClick={() =>
createWebhook({
repo: id,
action: Types.RepoWebhookAction.Pull,
})
}
loading={createPending}
disabled={disabled || createPending}
/>
</div>
)}
</ConfigItem>
);
},
},
},
],