Explorar el Código

Add link to job run in notifications (#4027)

Feroze Mohideen hace 2 años
padre
commit
bed3788f4e

+ 1 - 0
api/server/handlers/porter_app/create_and_update_events.go

@@ -653,6 +653,7 @@ func (p *CreateUpdatePorterAppEventHandler) handleNotification(ctx context.Conte
 		PorterAgentEventId: int64(agentEventMetadata.AgentEventID),
 		RawSummary:         agentEventMetadata.Summary,
 		RawDetail:          agentEventMetadata.Detail,
+		JobRunId:           agentEventMetadata.JobRunID,
 	})
 
 	_, err = p.Config().ClusterControlPlaneClient.CreateNotification(ctx, createNotificationRequest)

+ 1 - 0
dashboard/src/main/home/app-dashboard/app-view/tabs/activity-feed/events/types.ts

@@ -79,6 +79,7 @@ const serviceNoticationValidator = z.object({
         status: z.literal("UNKNOWN"),
       }),
     ]),
+    job_run_id: z.string(),
   }),
 });
 const revisionNotificationValidator = z.object({

+ 3 - 3
dashboard/src/main/home/app-dashboard/app-view/tabs/notifications/NotificationFeed.tsx

@@ -2,7 +2,6 @@ import React, { useEffect, useState } from "react";
 import { useHistory, useLocation } from "react-router";
 import styled from "styled-components";
 
-import Container from "components/porter/Container";
 import Fieldset from "components/porter/Fieldset";
 import Link from "components/porter/Link";
 import Spacer from "components/porter/Spacer";
@@ -68,7 +67,7 @@ const NotificationFeed: React.FC<Props> = ({
   return (
     <StyledNotificationFeed>
       {selectedNotification ? (
-        <Container>
+        <>
           <Link to={`/apps/${appName}/notifications`}>
             <BackButton>
               <i className="material-icons">keyboard_backspace</i>
@@ -84,7 +83,7 @@ const NotificationFeed: React.FC<Props> = ({
             deploymentTargetId={deploymentTargetId}
             appId={appId}
           />
-        </Container>
+        </>
       ) : (
         <NotificationList
           notifications={notifications}
@@ -103,6 +102,7 @@ export default NotificationFeed;
 
 const StyledNotificationFeed = styled.div`
   display: flex;
+  flex-direction: column;
   margin-bottom: -50px;
   width: 100%;
   animation: fadeIn 0.3s 0s;

+ 8 - 15
dashboard/src/main/home/app-dashboard/app-view/tabs/notifications/NotificationTile.tsx

@@ -4,6 +4,7 @@ import { match } from "ts-pattern";
 
 import Container from "components/porter/Container";
 import Spacer from "components/porter/Spacer";
+import Tag from "components/porter/Tag";
 import Text from "components/porter/Text";
 import {
   isClientServiceNotification,
@@ -29,6 +30,8 @@ const NotificationTile: React.FC<Props> = ({ notification, onClick }) => {
       .with({ scope: "SERVICE" }, (n) => {
         return n.isDeployRelated
           ? "A service failed to deploy"
+          : ["job", "predeploy"].includes(n.service.config.type)
+          ? "A job run encountered issues"
           : "A service is unhealthy";
       })
       .with({ scope: "APPLICATION" }, () => {
@@ -52,7 +55,7 @@ const NotificationTile: React.FC<Props> = ({ notification, onClick }) => {
         <Spacer inline x={0.5} />
         {isClientServiceNotification(notification) && (
           <Container row style={{ width: "200px" }}>
-            <ServiceNameTag>
+            <Tag>
               {match(notification.service.config.type)
                 .with("web", () => <ServiceTypeIcon src={web} />)
                 .with("worker", () => <ServiceTypeIcon src={worker} />)
@@ -60,8 +63,8 @@ const NotificationTile: React.FC<Props> = ({ notification, onClick }) => {
                 .with("predeploy", () => <ServiceTypeIcon src={job} />)
                 .exhaustive()}
               <Spacer inline x={0.5} />
-              {notification.service.name.value}
-            </ServiceNameTag>
+              <Text>{notification.service.name.value}</Text>
+            </Tag>
           </Container>
         )}
       </Container>
@@ -103,19 +106,9 @@ const NotificationSummary = styled.div`
   font-weight: 500;
 `;
 
-const ServiceNameTag = styled.div`
-  display: flex;
-  justify-content: center;
-  padding: 3px 5px;
-  border-radius: 5px;
-  background: #ffffff22;
-  user-select: text;
-  font-size: 13px;
-`;
-
 const ServiceTypeIcon = styled.img`
-  height: 12px;
-  margin-top: 2px;
+  height: 13px;
+  margin-top: 4px;
 `;
 
 const StatusDot = styled.div<{ color: string }>`

+ 1 - 0
dashboard/src/main/home/app-dashboard/app-view/tabs/notifications/expanded-views/NotificationExpandedView.tsx

@@ -50,6 +50,7 @@ export default NotificationExpandedView;
 
 export const StyledNotificationExpandedView = styled.div`
   height: 100%;
+  width: 100%;
   display: flex;
   justify-content: space-between;
   flex-direction: column;

+ 0 - 1
dashboard/src/main/home/app-dashboard/app-view/tabs/notifications/expanded-views/ServiceNotificationExpandedView.tsx

@@ -55,7 +55,6 @@ const ServiceNotificationExpandedView: React.FC<Props> = ({
               {notification.service.name.value}
             </ServiceNameTag>
             <Spacer inline x={0.5} />
-
             <Text size={16} color={"#FFBF00"}>
               {notification.isDeployRelated
                 ? "failed to deploy"

+ 22 - 3
dashboard/src/main/home/app-dashboard/app-view/tabs/notifications/expanded-views/messages/ServiceMessage.tsx

@@ -61,12 +61,12 @@ const ServiceMessage: React.FC<Props> = ({
           <Container row>
             <img
               src={document}
-              style={{ width: "15px", marginRight: "15px" }}
+              style={{ width: "15px", marginRight: "10px" }}
             />
             {message.error.summary}
           </Container>
           <Container row>
-            <img src={time} style={{ width: "15px", marginRight: "15px" }} />
+            <img src={time} style={{ width: "15px", marginRight: "10px" }} />
             <Text>{feedDate(message.timestamp)}</Text>
           </Container>
         </Container>
@@ -121,7 +121,26 @@ const ServiceMessage: React.FC<Props> = ({
             </ul>
           </>
         )}
-
+        {service.config.type === "job" && message.metadata.job_run_id && (
+          <Container row>
+            <Tag>
+              <Link
+                to={`/apps/${appName}/job-history?job_run_id=${message.metadata.job_run_id}&service=${service.name.value}`}
+              >
+                <Text size={16}>Job run</Text>
+                <i
+                  className="material-icons"
+                  style={{
+                    fontSize: "16px",
+                    marginLeft: "5px",
+                  }}
+                >
+                  open_in_new
+                </i>
+              </Link>
+            </Tag>
+          </Container>
+        )}
         {service.config.type !== "job" && message.error.should_view_logs && (
           <>
             <Container row>

+ 1 - 1
go.mod

@@ -83,7 +83,7 @@ require (
 	github.com/matryer/is v1.4.0
 	github.com/nats-io/nats.go v1.24.0
 	github.com/open-policy-agent/opa v0.44.0
-	github.com/porter-dev/api-contracts v0.2.55
+	github.com/porter-dev/api-contracts v0.2.56
 	github.com/riandyrn/otelchi v0.5.1
 	github.com/santhosh-tekuri/jsonschema/v5 v5.0.1
 	github.com/stefanmcshane/helm v0.0.0-20221213002717-88a4a2c6e77d

+ 2 - 0
go.sum

@@ -1522,6 +1522,8 @@ github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZN
 github.com/polyfloyd/go-errorlint v0.0.0-20210722154253-910bb7978349/go.mod h1:wi9BfjxjF/bwiZ701TzmfKu6UKC357IOAtNr0Td0Lvw=
 github.com/porter-dev/api-contracts v0.2.55 h1:H8RvD004mX4uWrlRVcL8kzo7ZtFQyZDN+X9j+2bW7fc=
 github.com/porter-dev/api-contracts v0.2.55/go.mod h1:fX6JmP5QuzxDLvqP3evFOTXjI4dHxsG0+VKNTjImZU8=
+github.com/porter-dev/api-contracts v0.2.56 h1:zym8eomipCj7BVQVlnCY4RjNv1tkduY68gsmwVJIfaQ=
+github.com/porter-dev/api-contracts v0.2.56/go.mod h1:fX6JmP5QuzxDLvqP3evFOTXjI4dHxsG0+VKNTjImZU8=
 github.com/porter-dev/switchboard v0.0.3 h1:dBuYkiVLa5Ce7059d6qTe9a1C2XEORFEanhbtV92R+M=
 github.com/porter-dev/switchboard v0.0.3/go.mod h1:xSPzqSFMQ6OSbp42fhCi4AbGbQbsm6nRvOkrblFeXU4=
 github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI=

+ 2 - 0
internal/porter_app/notifications/app_event.go

@@ -28,6 +28,8 @@ type AppEventMetadata struct {
 	AppName string `json:"app_name"`
 	// Detail is the detail of the app event
 	Detail string `json:"detail"`
+	// JobRunID is the ID of the job run that this event refers to, if applicable
+	JobRunID string `json:"job_run_id"`
 }
 
 // ParseAgentEventMetadata parses raw app event metadata to a AppEventMetadata struct

+ 3 - 3
internal/porter_app/notifications/notification.go

@@ -29,11 +29,11 @@ type Notification struct {
 // Metadata is the metadata of the notification
 type Metadata struct {
 	// Deployment is the deployment metadata, used to determine if the notification occurred during deployment or after
-	Deployment Deployment `json:"deployment,omitempty"`
+	Deployment Deployment `json:"deployment"`
 	// ServiceName is the name of the service
-	ServiceName string `json:"service_name,omitempty"`
+	ServiceName string `json:"service_name"`
 	// JobRunID is the id of the job run, if the service is a job
-	JobRunID string `json:"job_run_id,omitempty"`
+	JobRunID string `json:"job_run_id"`
 }
 
 // Scope is the scope of the notification