From 130eef8987ccc9fe08b32f7a1d87ea28c53b4b09 Mon Sep 17 00:00:00 2001 From: Nancy Huang <205217630+naanci@users.noreply.github.com> Date: Sun, 27 Sep 2026 17:37:36 -0400 Subject: [PATCH 1/3] TAN-987-fix: remove check/contraints for null for updates --- .../V0081__Drop_createdAt_not_null_constraints.SQL | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 db/migration/V0081__Drop_createdAt_not_null_constraints.SQL diff --git a/db/migration/V0081__Drop_createdAt_not_null_constraints.SQL b/db/migration/V0081__Drop_createdAt_not_null_constraints.SQL new file mode 100644 index 000000000..66c63100e --- /dev/null +++ b/db/migration/V0081__Drop_createdAt_not_null_constraints.SQL @@ -0,0 +1,7 @@ +SET LOCAL lock_timeout = '5s'; + +ALTER TABLE "User" +DROP CONSTRAINT "ck_user_createdAt_not_null"; + +ALTER TABLE "Session" +DROP CONSTRAINT "ck_session_createdAt_not_null"; From 090a5edd8682f9891286f94e9d93e7688abb9d6c Mon Sep 17 00:00:00 2001 From: Nancy Huang <205217630+naanci@users.noreply.github.com> Date: Mon, 28 Sep 2026 11:25:37 -0400 Subject: [PATCH 2/3] TAN-987-fix: remove unneeded timeout --- db/migration/V0081__Drop_createdAt_not_null_constraints.SQL | 2 -- 1 file changed, 2 deletions(-) diff --git a/db/migration/V0081__Drop_createdAt_not_null_constraints.SQL b/db/migration/V0081__Drop_createdAt_not_null_constraints.SQL index 66c63100e..1a5dee5d5 100644 --- a/db/migration/V0081__Drop_createdAt_not_null_constraints.SQL +++ b/db/migration/V0081__Drop_createdAt_not_null_constraints.SQL @@ -1,5 +1,3 @@ -SET LOCAL lock_timeout = '5s'; - ALTER TABLE "User" DROP CONSTRAINT "ck_user_createdAt_not_null"; From 4b4535564a85738f3682787de20ce7491d37b8f1 Mon Sep 17 00:00:00 2001 From: Nancy Huang <205217630+naanci@users.noreply.github.com> Date: Sun, 4 Oct 2026 20:19:37 -0400 Subject: [PATCH 3/3] TAN-989: migrate updated leetcode question in prod database, improve logging by adding question ID and slug --- .../V0082__Correct_renamed_question_596.SQL | 18 +++++++++++ .../AttachTagsToExistingQuestion.java | 13 ++++++-- .../AttachTagsToExistingQuestionTest.java | 32 ++++++++++++++++++- 3 files changed, 60 insertions(+), 3 deletions(-) create mode 100644 db/migration/V0082__Correct_renamed_question_596.SQL diff --git a/db/migration/V0082__Correct_renamed_question_596.SQL b/db/migration/V0082__Correct_renamed_question_596.SQL new file mode 100644 index 000000000..826037a08 --- /dev/null +++ b/db/migration/V0082__Correct_renamed_question_596.SQL @@ -0,0 +1,18 @@ +DO $$ +BEGIN + CASE current_database() + WHEN 'codebloom-prod' THEN + UPDATE + "Question" + SET + "questionTitle" = 'Classes With at Least 5 Students', + "questionSlug" = 'classes-with-at-least-5-students', + "questionLink" = 'https://leetcode.com/problems/classes-with-at-least-5-students' + WHERE + id = '7ea283ec-2e03-4753-b8f8-406b3a68cbe1' + AND "questionNumber" = 596 + AND "questionSlug" = 'classes-more-than-5-students'; + ELSE + RAISE NOTICE 'Skipping prod only migration: Current database is %', current_database(); + END CASE; +END $$; diff --git a/src/main/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestion.java b/src/main/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestion.java index 8ac7d4eae..ed1053836 100644 --- a/src/main/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestion.java +++ b/src/main/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestion.java @@ -44,12 +44,16 @@ void attachTagsToExistingQuestions() { } for (var question : questions) { - log.info("Updating question with id of {}", question.getId()); + log.info("Updating question with id of {} and slug {}", question.getId(), question.getQuestionSlug()); LeetcodeQuestion leetcodeQuestion; try { leetcodeQuestion = leetcodeClient.findQuestionBySlug(question.getQuestionSlug()); } catch (Exception e) { - log.error("LeetcodeClient threw an exception", e); + log.error( + "LeetcodeClient threw an exception for question id {} and slug {}", + question.getId(), + question.getQuestionSlug(), + e); continue; } @@ -64,6 +68,11 @@ void attachTagsToExistingQuestions() { questionTopicRepository.createQuestionTopic(newQuestionTopic); } + log.info( + "Attached {} topics to question id {} and slug {}", + leetcodeQuestion.getTopics().size(), + question.getId(), + question.getQuestionSlug()); } log.info("This task is complete."); diff --git a/src/test/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestionTest.java b/src/test/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestionTest.java index ad5d385d9..623e12602 100644 --- a/src/test/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestionTest.java +++ b/src/test/java/org/patinanetwork/codebloom/scheduled/leetcode/AttachTagsToExistingQuestionTest.java @@ -68,8 +68,38 @@ function hello() { .thenThrow(new RuntimeException("Expected!")); attachTagsToExistingQuestion.attachTagsToExistingQuestions(); + verifyNoInteractions(questionTopicRepository); assertTrue(logWatcher.list.stream() .anyMatch(log -> log.getLevel().equals(Level.ERROR) - && log.getFormattedMessage().contains("LeetcodeClient threw an exception"))); + && log.getFormattedMessage().contains("LeetcodeClient threw an exception") + && log.getFormattedMessage().contains(mockQuestion.getId()) + && log.getFormattedMessage().contains(mockQuestion.getQuestionSlug()))); + } + + @Test + void correctedSlugAttachesTopicsAndContinuesPastFailedQuestion() { + var failed = Question.builder().id("failed").questionSlug("old-slug").build(); + var corrected = Question.builder() + .id("corrected") + .questionSlug("classes-with-at-least-5-students") + .build(); + when(questionRepository.getAllQuestionsWithNoTopics()).thenReturn(List.of(failed, corrected)); + when(leetcodeClient.findQuestionBySlug("old-slug")).thenThrow(new RuntimeException("Missing")); + when(leetcodeClient.findQuestionBySlug(corrected.getQuestionSlug())) + .thenReturn(org.patinanetwork.codebloom.common.leetcode.models.LeetcodeQuestion.builder() + .topics(List.of(org.patinanetwork.codebloom.common.leetcode.models.LeetcodeTopicTag.builder() + .name("Database") + .slug("database") + .build())) + .build()); + + attachTagsToExistingQuestion.attachTagsToExistingQuestions(); + + verify(questionTopicRepository) + .createQuestionTopic( + argThat(topic -> topic.getQuestionId().orElseThrow().equals("corrected") + && topic.getTopicSlug().equals("database"))); + assertTrue(logWatcher.list.stream().anyMatch(log -> log.getFormattedMessage() + .contains("Attached 1 topics to question id corrected and slug classes-with-at-least-5-students"))); } }