Skip to content
Merged
Show file tree
Hide file tree
Changes from 11 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
19 changes: 18 additions & 1 deletion components/dashboard/src/data/prebuilds/prebuild-queries.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,11 @@
*/

import { useMutation, useQuery } from "@tanstack/react-query";
import { prebuildClient, stream } from "../../service/public-api";
import { configurationClient, prebuildClient, stream } from "../../service/public-api";
import { Prebuild, PrebuildPhase_Phase } from "@gitpod/public-api/lib/gitpod/v1/prebuild_pb";
import { ApplicationError, ErrorCodes } from "@gitpod/gitpod-protocol/lib/messaging/error";
import { PlainMessage, toPlainMessage } from "@bufbuild/protobuf";
import { GetConfigurationWebhookActivityStatusResponse } from "@gitpod/public-api/lib/gitpod/v1/configuration_pb";

export function usePrebuildQuery(prebuildId: string) {
return useQuery<Prebuild, Error>(
Expand Down Expand Up @@ -75,3 +77,18 @@ export function useTriggerPrebuildMutation(configurationId?: string, gitRef?: st
},
});
}

export function useWebhookActivityStatusQuery(configurationId: string) {
return useQuery<PlainMessage<GetConfigurationWebhookActivityStatusResponse>, Error>(
["webhookActivityStatus", configurationId],
async () => {
const resp = await configurationClient.getConfigurationWebhookActivityStatus({ configurationId });
return toPlainMessage(resp);
},
{
retry: false,
staleTime: 1000 * 60, // 1 minute
cacheTime: 1000 * 60 * 15, // 15 minutes
},
);
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
*/

import { FC, useCallback, useState } from "react";
import { Configuration } from "@gitpod/public-api/lib/gitpod/v1/configuration_pb";
import { Configuration, PrebuildTriggerStrategy } from "@gitpod/public-api/lib/gitpod/v1/configuration_pb";
import { ConfigurationSettingsField } from "./ConfigurationSettingsField";
import { Heading3, Subheading } from "@podkit/typography/Headings";
import { SwitchInputField } from "@podkit/switch/Switch";
Expand All @@ -15,6 +15,9 @@ import { LoadingState } from "@podkit/loading/LoadingState";
import { EnablePrebuildsError } from "./prebuilds/EnablePrebuildsError";
import { TextMuted } from "@podkit/typography/TextMuted";
import { Link } from "react-router-dom";
import { useWebhookActivityStatusQuery } from "../../data/prebuilds/prebuild-queries";
import Alert from "../../components/Alert";
import { useToast } from "../../components/toasts/Toasts";

type Props = {
configuration: Configuration;
Expand Down Expand Up @@ -59,6 +62,10 @@ export const ConfigurationDetailPrebuilds: FC<Props> = ({ configuration }) => {
<ConfigurationSettingsField>
<Heading3>Prebuilds</Heading3>
<Subheading className="max-w-lg">Prebuilds reduce wait time for new workspaces.</Subheading>
{configuration.prebuildSettings?.enabled &&
configuration.prebuildSettings.triggerStrategy !== PrebuildTriggerStrategy.ACTIVITY_BASED && (
<WebhookTriggerMessage configurationId={configuration.id} />
)}

<SwitchInputField
className="mt-6"
Expand Down Expand Up @@ -95,3 +102,37 @@ export const ConfigurationDetailPrebuilds: FC<Props> = ({ configuration }) => {
</>
);
};

export const WebhookTriggerMessage = ({ configurationId }: { configurationId: string }) => {
const integrationStatus = useWebhookActivityStatusQuery(configurationId);
const { toast } = useToast();

if (integrationStatus.isError) {
toast("Failed to load webhook activity status");
return null;
}
if (!integrationStatus?.data?.isWebhookActive) {
return null;
}

return (
<Alert type="warning">
<div className="flex flex-row gap-2 items-center">
<span>
We have gotten webhook activity for your most recent commit. You should consider removing webhooks
from the repository in favor of activity-based prebuilds.
</span>
<div>
<a
href="https://www.gitpod.io/changelog/activity-based-prebuilds"
className="gp-link"
target="_blank"
rel="noreferrer"
>
Learn more
</a>
</div>
</div>
</Alert>
);
};
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ export const EnablePrebuildsError: FC<Props> = ({ error, onReconnect }) => {
// We need to authorize with the provider to acquire the correct scopes to install webhooks
if (error instanceof ApplicationError && error.code === ErrorCodes.NOT_AUTHENTICATED) {
return (
<RepositoryUnauthroizedErrorMessage
<RepositoryUnauthorizedErrorMessage
error={error.data as RepositoryUnauthorizedError}
onReconnect={onReconnect}
/>
Expand Down Expand Up @@ -63,11 +63,11 @@ const GenericErrorMessage: FC<GenericErrorMessageProps> = ({ message }) => {
);
};

type RepositoryUnauthroizedErrorMessageProps = {
type RepositoryUnauthorizedErrorMessageProps = {
error: RepositoryUnauthorizedError;
onReconnect: () => void;
};
const RepositoryUnauthroizedErrorMessage: FC<RepositoryUnauthroizedErrorMessageProps> = ({ error, onReconnect }) => {
const RepositoryUnauthorizedErrorMessage: FC<RepositoryUnauthorizedErrorMessageProps> = ({ error, onReconnect }) => {
const { toast } = useToast();

const authorizeWithProvider = useCallback(async () => {
Expand Down Expand Up @@ -106,7 +106,7 @@ const RepositoryUnauthroizedErrorMessage: FC<RepositoryUnauthroizedErrorMessageP
</span>
) : (
<span>
Unable to enable prebuilds. This could be because you don’t have admin/write premissions for
Unable to enable prebuilds. This could be because you don’t have admin/write permissions for
this repo or it could be an invalid token. Please try to reconnect. If the problem persists, you
can contact support.
</span>
Expand Down
20 changes: 20 additions & 0 deletions components/public-api/gitpod/v1/configuration.proto
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,9 @@ service ConfigurationService {

// Deletes a configuration.
rpc DeleteConfiguration(DeleteConfigurationRequest) returns (DeleteConfigurationResponse) {}

// GetConfigurationWebhookActivityStatus returns the observed status of installed prebuild webhooks on the configuration
rpc GetConfigurationWebhookActivityStatus(GetConfigurationWebhookActivityStatusRequest) returns (GetConfigurationWebhookActivityStatusResponse) {}
}

message CreateConfigurationRequest {
Expand Down Expand Up @@ -147,3 +150,20 @@ message DeleteConfigurationRequest {
}

message DeleteConfigurationResponse {}

message GetConfigurationWebhookActivityStatusRequest {
string configuration_id = 1;
}

message GetConfigurationWebhookActivityStatusResponse {
message WebhookEvent {
string commit = 1;
google.protobuf.Timestamp creation_time = 2;
}

// is_webhook_active determines whether the webhook is active or not for the configuration.
bool is_webhook_active = 1;

// latest_webhook_event is the latest event that was observed by the webhook. Only set if is_webhook_active is true.
WebhookEvent latest_webhook_event = 2;
}
Loading
Loading