diff --git a/joj3_config_generator/generator.py b/joj3_config_generator/generator.py
index 2b6f471..2edc98a 100644
--- a/joj3_config_generator/generator.py
+++ b/joj3_config_generator/generator.py
@@ -29,19 +29,25 @@ def convert_joj3_conf(repo_conf: repo.Config, task_conf: task.Config) -> result.
         expire_unix_timestamp=int(task_conf.release.end_time.timestamp()),
         effective_unix_timestamp=int(task_conf.release.begin_time.timestamp()),
         actor_csv_path=str(ACTOR_CSV_PATH),  # students.csv position
-        max_total_score=repo_conf.max_total_score,
+        max_total_score=(
+            repo_conf.max_total_score
+            if not task_conf.max_total_score
+            else task_conf.max_total_score
+        ),
         stage=result.Stage(sandbox_token=repo_conf.sandbox_token),
     )
 
     current_test = os.environ.get("PYTEST_CURRENT_TEST") is not None
     # Construct health check stage
     if not repo_conf.force_skip_health_check_on_test or not current_test:
-        result_conf.stage.stages.append(get_health_check_stage(repo_conf))
+        result_conf.stage.stages.append(get_health_check_stage(repo_conf, task_conf))
     cached: Dict[str, None] = {}
     # Convert each stage in the task configuration
     for task_stage in task_conf.stages:
         result_conf.stage.stages.append(get_conf_stage(task_conf, task_stage, cached))
     if not repo_conf.force_skip_teapot_on_test or not current_test:
-        result_conf.stage.post_stages.append(get_teapot_post_stage(repo_conf))
+        result_conf.stage.post_stages.append(
+            get_teapot_post_stage(repo_conf, task_conf)
+        )
 
     return result_conf
diff --git a/joj3_config_generator/models/task.py b/joj3_config_generator/models/task.py
index 60aaad7..3111e65 100644
--- a/joj3_config_generator/models/task.py
+++ b/joj3_config_generator/models/task.py
@@ -20,6 +20,7 @@ from joj3_config_generator.models.const import (
     DEFAULT_MEMORY_LIMIT,
     DEFAULT_PROC_LIMIT,
 )
+from joj3_config_generator.models.repo import Groups
 
 
 class ParserResultDetail(BaseModel):
@@ -204,3 +205,7 @@ class Config(BaseModel):
     task: Task = Task()  # Task name (e.g., hw3 ex5)
     release: Release = Release()  # Release configuration
     stages: List[Stage] = []  # list of stage configurations
+    groups: Groups = Groups()
+    max_total_score: int = Field(
+        100, validation_alias=AliasChoices("max-total-score", "max_total_score")
+    )
diff --git a/joj3_config_generator/transformers/repo.py b/joj3_config_generator/transformers/repo.py
index 05eaf76..d5d3718 100644
--- a/joj3_config_generator/transformers/repo.py
+++ b/joj3_config_generator/transformers/repo.py
@@ -2,11 +2,13 @@ import hashlib
 from pathlib import Path
 from typing import List
 
-from joj3_config_generator.models import common, repo, result
+from joj3_config_generator.models import common, repo, result, task
 from joj3_config_generator.models.const import TEAPOT_CONFIG_ROOT, TEAPOT_LOG_PATH
 
 
-def get_teapot_post_stage(repo_conf: repo.Config) -> result.StageDetail:
+def get_teapot_post_stage(
+    repo_conf: repo.Config, task_conf: task.Config
+) -> result.StageDetail:
     args = [
         "/usr/local/bin/joint-teapot",
         "joj3-all-env",
@@ -14,7 +16,11 @@ def get_teapot_post_stage(repo_conf: repo.Config) -> result.StageDetail:
         "--grading-repo-name",
         repo_conf.grading_repo_name,
         "--max-total-score",
-        str(repo_conf.max_total_score),
+        (
+            str(repo_conf.max_total_score)
+            if not task_conf.max_total_score
+            else str(task_conf.max_total_score)
+        ),
     ]
     if not repo_conf.submitter_in_issue_title:
         args.append("--no-submitter-in-issue-title")
@@ -52,7 +58,7 @@ def get_health_check_args(repo_conf: repo.Config) -> List[str]:
     ]
 
 
-def get_teapot_check_args(repo_conf: repo.Config) -> List[str]:
+def get_teapot_check_args(repo_conf: repo.Config, task_conf: task.Config) -> List[str]:
     res = [
         "/usr/local/bin/joint-teapot",
         "joj3-check-env",
@@ -69,11 +75,24 @@ def get_teapot_check_args(repo_conf: repo.Config) -> List[str]:
                 repo_conf.groups.time_period_hour,
             )
         )
-        res.extend(["--group-config", group_config_str])
+        if task_conf.groups.name:
+            overwrite_group_config_str = ",".join(
+                f"{name}={max_count}:{time_period}"
+                for name, max_count, time_period in zip(
+                    task_conf.groups.name,
+                    task_conf.groups.max_count,
+                    task_conf.groups.time_period_hour,
+                )
+            )
+            res.extend(["--group-config", overwrite_group_config_str])
+        else:
+            res.extend(["--group-config", group_config_str])
     return res
 
 
-def get_health_check_stage(repo_conf: repo.Config) -> result.StageDetail:
+def get_health_check_stage(
+    repo_conf: repo.Config, task_conf: task.Config
+) -> result.StageDetail:
     health_check_stage = result.StageDetail(
         name="Health Check",
         group="",
@@ -88,7 +107,7 @@ def get_health_check_stage(repo_conf: repo.Config) -> result.StageDetail:
                         args=get_health_check_args(repo_conf),
                     ),
                     result.OptionalCmd(
-                        args=get_teapot_check_args(repo_conf),
+                        args=get_teapot_check_args(repo_conf, task_conf),
                         env=[f"LOG_FILE_PATH={TEAPOT_LOG_PATH}"],
                     ),
                 ],
diff --git a/tests/convert/basic/repo.toml b/tests/convert/basic/repo.toml
index 8c97ca2..a6e7035 100644
--- a/tests/convert/basic/repo.toml
+++ b/tests/convert/basic/repo.toml
@@ -2,7 +2,7 @@ grading-repo-name = "ece280-joj"
 
 sandbox-token = "test"
 # reconfigure later
-max-total-score = 100
+max-total-score = 1000
 max-size = 50.5
 
 # for tests
diff --git a/tests/convert/basic/task.json b/tests/convert/basic/task.json
index c4b9b83..784d1b7 100644
--- a/tests/convert/basic/task.json
+++ b/tests/convert/basic/task.json
@@ -4,7 +4,7 @@
     "expireUnixTimestamp": 1735574399,
     "effectiveUnixTimestamp": 1735487999,
     "actorCsvPath": "/home/tt/.config/joj/students.csv",
-    "maxTotalScore": 100,
+    "maxTotalScore": 10245871,
     "stage": {
         "sandboxExecServer": "172.17.0.1:5051",
         "sandboxToken": "test",
@@ -76,7 +76,7 @@
                                     "--grading-repo-name",
                                     "ece280-joj",
                                     "--group-config",
-                                    "joj=1000:24,run=1000:24"
+                                    "Manuel=500:24,Boming=501:48,Nuvole=502:72"
                                 ],
                                 "env": [
                                     "LOG_FILE_PATH=/home/tt/.cache/joint-teapot-debug.log"
@@ -798,7 +798,7 @@
                                 "--grading-repo-name",
                                 "ece280-joj",
                                 "--max-total-score",
-                                "100"
+                                "10245871"
                             ],
                             "env": [
                                 "LOG_FILE_PATH=/home/tt/.cache/joint-teapot-debug.log"
diff --git a/tests/convert/basic/task.toml b/tests/convert/basic/task.toml
index c76bcf6..edc67e3 100644
--- a/tests/convert/basic/task.toml
+++ b/tests/convert/basic/task.toml
@@ -1,9 +1,15 @@
 # general task configuration
 task.name = "hw7 ex2" # task name
 
+max-total-score = 10245871
 release.end-time = 2024-12-30 23:59:59+08:00
 release.begin-time = 2024-12-29 23:59:59+08:00
 
+[groups]
+name = ["Manuel", "Boming", "Nuvole"]
+max-count = [500, 501, 502]
+time-period-hour = [24, 48, 72]
+
 [[stages]]
 name = "Compilation"
 env = [ "CC=clang", "CXX=clang++" ]