fix: slow responses query slowing down database (#5846)

This commit is contained in:
Matti Nannt
2025-05-21 06:13:31 +02:00
committed by GitHub
parent 9478946c7a
commit 12aa959f50
6 changed files with 37 additions and 20 deletions
+1 -1
View File
@@ -82,7 +82,7 @@
"please_click_the_link_in_the_email_to_activate_your_account": "Please click the link in the email to activate your account.",
"please_confirm_your_email_address": "Please confirm your email address",
"resend_verification_email": "Resend verification email",
"verification_email_successfully_sent": "Verification email successfully sent. Please check your inbox.",
"verification_email_successfully_sent": "Verification email sent to {email}. Please verify to complete the update.",
"we_sent_an_email_to": "We sent an email to {email}. ",
"you_didnt_receive_an_email_or_your_link_expired": "You didn't receive an email or your link expired?"
},
+1 -1
View File
@@ -82,7 +82,7 @@
"please_click_the_link_in_the_email_to_activate_your_account": "Por favor, clique no link no email para ativar a sua conta.",
"please_confirm_your_email_address": "Por favor, confirme o seu endereço de email",
"resend_verification_email": "Reenviar email de verificação",
"verification_email_successfully_sent": "Email de verificação enviado com sucesso. Por favor, verifique a sua caixa de entrada.",
"verification_email_successfully_sent": "Email de verificação enviado para {email}. Por favor, verifique para completar a atualização.",
"we_sent_an_email_to": "Enviámos um email para {email}. ",
"you_didnt_receive_an_email_or_your_link_expired": "Não recebeu um email ou o seu link expirou?"
},
@@ -135,14 +135,11 @@ export const getResponses = async (
): Promise<Result<ApiResponseWithMeta<Response[]>, ApiErrorResponseV2>> => {
try {
const query = getResponsesQuery(environmentIds, params);
const whereClause = query.where;
const [responses, count] = await prisma.$transaction([
prisma.response.findMany({
...query,
}),
prisma.response.count({
where: query.where,
}),
const [responses, totalCount] = await Promise.all([
prisma.response.findMany(query),
prisma.response.count({ where: whereClause }),
]);
if (!responses) {
@@ -152,7 +149,7 @@ export const getResponses = async (
return ok({
data: responses,
meta: {
total: count,
total: totalCount,
limit: params.limit,
offset: params.skip,
},
@@ -214,17 +214,18 @@ describe("Response Lib", () => {
describe("getResponses", () => {
test("return responses with meta information", async () => {
const responses = [response];
prisma.$transaction = vi.fn().mockResolvedValue([responses, responses.length]);
(prisma.response.findMany as any).mockResolvedValue([response]);
(prisma.response.count as any).mockResolvedValue(1);
const result = await getResponses(environmentId, responseFilter);
expect(prisma.$transaction).toHaveBeenCalled();
const result = await getResponses([environmentId], responseFilter);
expect(prisma.response.findMany).toHaveBeenCalled();
expect(prisma.response.count).toHaveBeenCalled();
expect(result.ok).toBe(true);
if (result.ok) {
expect(result.data).toEqual({
data: [response],
meta: {
total: responses.length,
total: 1,
limit: responseFilter.limit,
offset: responseFilter.skip,
},
@@ -233,9 +234,10 @@ describe("Response Lib", () => {
});
test("return a not_found error if responses are not found", async () => {
prisma.$transaction = vi.fn().mockResolvedValue([null, 0]);
(prisma.response.findMany as any).mockResolvedValue(null);
(prisma.response.count as any).mockResolvedValue(0);
const result = await getResponses(environmentId, responseFilter);
const result = await getResponses([environmentId], responseFilter);
expect(result.ok).toBe(false);
if (!result.ok) {
expect(result.error).toEqual({
@@ -245,10 +247,25 @@ describe("Response Lib", () => {
}
});
test("return an internal_server_error error if prisma transaction fails", async () => {
prisma.$transaction = vi.fn().mockRejectedValue(new Error("Internal server error"));
test("return an internal_server_error error if prisma findMany fails", async () => {
(prisma.response.findMany as any).mockRejectedValue(new Error("Internal server error"));
(prisma.response.count as any).mockResolvedValue(0);
const result = await getResponses(environmentId, responseFilter);
const result = await getResponses([environmentId], responseFilter);
expect(result.ok).toBe(false);
if (!result.ok) {
expect(result.error).toEqual({
type: "internal_server_error",
details: [{ field: "responses", issue: "Internal server error" }],
});
}
});
test("return an internal_server_error error if prisma count fails", async () => {
(prisma.response.findMany as any).mockResolvedValue([response]);
(prisma.response.count as any).mockRejectedValue(new Error("Internal server error"));
const result = await getResponses([environmentId], responseFilter);
expect(result.ok).toBe(false);
if (!result.ok) {
expect(result.error).toEqual({
@@ -0,0 +1,2 @@
-- CreateIndex
CREATE INDEX "Response_created_at_idx" ON "Response"("created_at");
+1
View File
@@ -172,6 +172,7 @@ model Response {
display Display? @relation(fields: [displayId], references: [id])
@@unique([surveyId, singleUseId])
@@index([createdAt])
@@index([surveyId, createdAt]) // to determine monthly response count
@@index([contactId, createdAt]) // to determine monthly identified users (persons)
@@index([surveyId])