api/routes/modules/assignments/config/
post.rs1use db::models::assignment_file::{FileType, Model as AssignmentFile};
2use axum::{
3 extract::{State, Json, Path},
4 http::StatusCode,
5 response::IntoResponse,
6};
7use sea_orm::{EntityTrait, ColumnTrait, QueryFilter};
8use serde_json::Value;
9use crate::response::ApiResponse;
10use db::models::assignment::{Column as AssignmentColumn, Entity as AssignmentEntity};
11use util::{execution_config::ExecutionConfig, state::AppState};
12
13
14pub async fn set_assignment_config(
61 State(app_state): State<AppState>,
62 Path((module_id, assignment_id)): Path<(i64, i64)>,
63 Json(config_json): Json<Value>,
64) -> impl IntoResponse {
65 let db = app_state.db();
66
67 if !config_json.is_object() {
68 return (
69 StatusCode::BAD_REQUEST,
70 Json(ApiResponse::<()>::error("Configuration must be a JSON object")),
71 );
72 }
73
74 let config: ExecutionConfig = match serde_json::from_value(config_json) {
75 Ok(cfg) => cfg,
76 Err(e) => {
77 return (
78 StatusCode::BAD_REQUEST,
79 Json(ApiResponse::<()>::error(format!("Invalid config format: {}", e))),
80 );
81 }
82 };
83
84 let assignment = match AssignmentEntity::find()
86 .filter(AssignmentColumn::Id.eq(assignment_id as i32))
87 .filter(AssignmentColumn::ModuleId.eq(module_id as i32))
88 .one(db)
89 .await
90 {
91 Ok(Some(a)) => a,
92 Ok(None) => {
93 return (
94 StatusCode::NOT_FOUND,
95 Json(ApiResponse::<()>::error("Assignment or module not found")),
96 );
97 }
98 Err(e) => {
99 eprintln!("DB error: {:?}", e);
100 return (
101 StatusCode::INTERNAL_SERVER_ERROR,
102 Json(ApiResponse::<()>::error("Database error")),
103 );
104 }
105 };
106
107 let bytes = match serde_json::to_vec_pretty(&config) {
109 Ok(b) => b,
110 Err(e) => {
111 eprintln!("Serialization error: {:?}", e);
112 return (
113 StatusCode::INTERNAL_SERVER_ERROR,
114 Json(ApiResponse::<()>::error("Failed to serialize config")),
115 );
116 }
117 };
118
119 match AssignmentFile::save_file(
120 &db,
121 assignment.id.into(),
122 module_id,
123 FileType::Config,
124 "config.json",
125 &bytes,
126 )
127 .await
128 {
129 Ok(_) => (
130 StatusCode::OK,
131 Json(ApiResponse::success((), "Assignment configuration saved")),
132 ),
133 Err(e) => {
134 eprintln!("File save error: {:?}", e);
135 (
136 StatusCode::INTERNAL_SERVER_ERROR,
137 Json(ApiResponse::<()>::error("Failed to save config as assignment file")),
138 )
139 }
140 }
141}
142
143
144pub async fn reset_assignment_config(
158 State(app_state): State<AppState>,
159 Path((module_id, assignment_id)): Path<(i64, i64)>,
160) -> impl IntoResponse {
161 let db = app_state.db();
162
163 let assignment = match AssignmentEntity::find()
165 .filter(AssignmentColumn::Id.eq(assignment_id as i32))
166 .filter(AssignmentColumn::ModuleId.eq(module_id as i32))
167 .one(db)
168 .await
169 {
170 Ok(Some(a)) => a,
171 Ok(None) => {
172 return (
173 StatusCode::NOT_FOUND,
174 Json(ApiResponse::<ExecutionConfig>::error("Assignment or module not found")),
175 );
176 }
177 Err(e) => {
178 eprintln!("DB error: {:?}", e);
179 return (
180 StatusCode::INTERNAL_SERVER_ERROR,
181 Json(ApiResponse::<ExecutionConfig>::error("Database error")),
182 );
183 }
184 };
185
186 let default_cfg = ExecutionConfig::default_config();
188
189 let bytes = match serde_json::to_vec_pretty(&default_cfg) {
191 Ok(b) => b,
192 Err(e) => {
193 eprintln!("Serialization error: {:?}", e);
194 return (
195 StatusCode::INTERNAL_SERVER_ERROR,
196 Json(ApiResponse::<ExecutionConfig>::error("Failed to serialize default config")),
197 );
198 }
199 };
200
201 match AssignmentFile::save_file(
202 &db,
203 assignment.id.into(),
204 module_id,
205 FileType::Config,
206 "config.json",
207 &bytes,
208 )
209 .await
210 {
211 Ok(_) => (
212 StatusCode::OK,
213 Json(ApiResponse::<ExecutionConfig>::success(
214 default_cfg,
215 "Assignment configuration reset to defaults",
216 )),
217 ),
218 Err(e) => {
219 eprintln!("File save error: {:?}", e);
220 (
221 StatusCode::INTERNAL_SERVER_ERROR,
222 Json(ApiResponse::<ExecutionConfig>::error(
223 "Failed to save default config as assignment file",
224 )),
225 )
226 }
227 }
228}