Skip to content

Commit e544e5c

Browse files
committed
chore: improve issue created webhook
1 parent 5605536 commit e544e5c

File tree

3 files changed

+140
-47
lines changed

3 files changed

+140
-47
lines changed

apps/api/src/controllers/ticket.ts

Lines changed: 17 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -9,10 +9,11 @@ import { sendAssignedEmail } from "../lib/nodemailer/ticket/assigned";
99
import { sendComment } from "../lib/nodemailer/ticket/comment";
1010
import { sendTicketCreate } from "../lib/nodemailer/ticket/create";
1111
import { sendTicketStatus } from "../lib/nodemailer/ticket/status";
12-
import { checkSession } from "../lib/session";
13-
import { prisma } from "../prisma";
1412
import { assignedNotification } from "../lib/notifications/issue/assigned";
1513
import { commentNotification } from "../lib/notifications/issue/comment";
14+
import { sendWebhookNotification } from "../lib/notifications/webhook";
15+
import { checkSession } from "../lib/session";
16+
import { prisma } from "../prisma";
1617

1718
const validateEmail = (email: string) => {
1819
return String(email)
@@ -97,33 +98,20 @@ export function ticketRoutes(fastify: FastifyInstance) {
9798

9899
for (let i = 0; i < webhook.length; i++) {
99100
if (webhook[i].active === true) {
100-
const url = webhook[i].url;
101-
if (url.includes("discord.com")) {
102-
const message = {
103-
content: `Ticket ${ticket.id} created by ${ticket.name} -> ${ticket.email}. Priority -> ${ticket.priority}`,
104-
avatar_url:
105-
"https://avatars.githubusercontent.com/u/76014454?s=200&v=4",
106-
username: "Peppermint.sh",
107-
};
108-
axios
109-
.post(url, message)
110-
.then((response) => {
111-
console.log("Message sent successfully!");
112-
console.log("Discord API response:", response.data);
113-
})
114-
.catch((error) => {
115-
console.error("Error sending message:", error);
116-
});
117-
} else {
118-
await axios.post(`${webhook[i].url}`, {
119-
headers: {
120-
"Content-Type": "application/json",
121-
},
122-
body: JSON.stringify({
123-
data: `Ticket ${ticket.id} created by ${ticket.name} -> ${ticket.email}. Priority -> ${ticket.priority}`,
124-
}),
125-
});
126-
}
101+
const message = {
102+
event: "ticket_created",
103+
id: ticket.id,
104+
title: ticket.title,
105+
priority: ticket.priority,
106+
email: ticket.email,
107+
name: ticket.name,
108+
type: ticket.type,
109+
createdBy: ticket.createdBy,
110+
assignedTo: ticket.assignedTo,
111+
client: ticket.client,
112+
};
113+
114+
await sendWebhookNotification(webhook[i], message);
127115
}
128116
}
129117

Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
import axios from "axios";
2+
3+
function getPriorityColor(priority: string): number {
4+
switch (priority.toLowerCase()) {
5+
case "high":
6+
return 16711680; // Red
7+
case "medium":
8+
return 16753920; // Orange
9+
case "low":
10+
return 65280; // Green
11+
default:
12+
return 8421504; // Grey
13+
}
14+
}
15+
16+
export async function sendWebhookNotification(webhook: any, message: any) {
17+
if (!webhook.active) return;
18+
19+
const url = webhook.url;
20+
21+
if (url.includes("discord.com")) {
22+
const discordMessage = {
23+
embeds: [
24+
{
25+
title: "Issue Created",
26+
description: "A new issue has been created",
27+
color: getPriorityColor(message.priority), // Use the priority color function
28+
footer: {
29+
text: "Issue ID: " + message.id,
30+
},
31+
author: {
32+
name: "peppermint.sh",
33+
icon_url:
34+
"https://avatars.githubusercontent.com/u/76014454?s=200&v=4",
35+
url: "https://peppermint.sh/",
36+
},
37+
fields: [
38+
{
39+
name: "Title",
40+
value: message.title,
41+
inline: false,
42+
},
43+
{
44+
name: "Priority Level",
45+
value: message.priority,
46+
inline: false,
47+
},
48+
{
49+
name: "Contact Email",
50+
value: message.email ? message.email : "No email provided",
51+
inline: false,
52+
},
53+
{
54+
name: "Created By",
55+
value: message.createdBy.name,
56+
inline: false,
57+
},
58+
{
59+
name: "Assigned To",
60+
value: message.assignedTo
61+
? message.assignedTo.name
62+
: "Unassigned",
63+
inline: false,
64+
},
65+
{
66+
name: "Client",
67+
value: message.client
68+
? message.client.name
69+
: "No client assigned",
70+
inline: false,
71+
},
72+
{
73+
name: "Type",
74+
value: message.type,
75+
inline: false,
76+
},
77+
],
78+
},
79+
],
80+
content: "",
81+
};
82+
83+
try {
84+
await axios.post(url, discordMessage);
85+
console.log("Discord webhook message sent successfully!");
86+
} catch (error: any) {
87+
if (error.response) {
88+
console.error("Discord API response error:", error.response.data);
89+
} else {
90+
console.error("Error sending Discord webhook:", error.message);
91+
}
92+
throw error;
93+
}
94+
} else {
95+
try {
96+
await axios.post(url, {
97+
data: message,
98+
});
99+
} catch (error) {
100+
console.error("Error sending webhook:", error);
101+
}
102+
}
103+
}

apps/client/pages/issues/index.tsx

Lines changed: 20 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,37 @@
11
import useTranslation from "next-translate/useTranslation";
22
import { useRouter } from "next/router";
3+
import { useEffect, useMemo, useState } from "react";
34
import Loader from "react-spinners/ClipLoader";
4-
import { useState, useMemo, useEffect } from "react";
55

6+
import { toast } from "@/shadcn/hooks/use-toast";
7+
import { cn } from "@/shadcn/lib/utils";
8+
import { Button } from "@/shadcn/ui/button";
9+
import {
10+
Command,
11+
CommandEmpty,
12+
CommandGroup,
13+
CommandInput,
14+
CommandItem,
15+
CommandList,
16+
CommandSeparator,
17+
} from "@/shadcn/ui/command";
618
import {
719
ContextMenu,
820
ContextMenuContent,
921
ContextMenuItem,
1022
ContextMenuSeparator,
11-
ContextMenuTrigger,
1223
ContextMenuSub,
13-
ContextMenuSubTrigger,
1424
ContextMenuSubContent,
25+
ContextMenuSubTrigger,
26+
ContextMenuTrigger,
1527
} from "@/shadcn/ui/context-menu";
28+
import { Popover, PopoverContent, PopoverTrigger } from "@/shadcn/ui/popover";
1629
import { getCookie } from "cookies-next";
30+
import { CheckIcon, Filter, X } from "lucide-react";
1731
import moment from "moment";
1832
import Link from "next/link";
1933
import { useQuery } from "react-query";
2034
import { useUser } from "../../store/session";
21-
import { Popover, PopoverContent, PopoverTrigger } from "@/shadcn/ui/popover";
22-
import { CheckIcon, Filter, X } from "lucide-react";
23-
import { Button } from "@/shadcn/ui/button";
24-
import {
25-
Command,
26-
CommandEmpty,
27-
CommandGroup,
28-
CommandInput,
29-
CommandItem,
30-
CommandList,
31-
CommandSeparator,
32-
} from "@/shadcn/ui/command";
33-
import { cn } from "@/shadcn/lib/utils";
34-
import { toast } from "@/shadcn/hooks/use-toast";
3535

3636
async function getUserTickets(token: any) {
3737
const res = await fetch(`/api/v1/tickets/all`, {
@@ -712,6 +712,8 @@ export default function Tickets() {
712712
"Content-Type": "application/json",
713713
},
714714
body: JSON.stringify({ id: ticket.id }),
715+
}).then(() => {
716+
refetch();
715717
});
716718
}
717719
}}
@@ -728,7 +730,7 @@ export default function Tickets() {
728730
type="button"
729731
className="relative block w-[400px] rounded-lg border-2 border-dashed border-gray-300 p-12 text-center hover:border-gray-400 focus:outline-none focus:ring-2 focus:ring-indigo-500 focus:ring-offset-2"
730732
onClick={() => {
731-
const event = new KeyboardEvent('keydown', { key: 'c' });
733+
const event = new KeyboardEvent("keydown", { key: "c" });
732734
document.dispatchEvent(event);
733735
}}
734736
>

0 commit comments

Comments
 (0)