From 502fe03bd9f328933da19572f3bf3144c65ba8a4 Mon Sep 17 00:00:00 2001 From: Johnnymao28 Date: Mon, 6 Oct 2025 18:09:56 -0400 Subject: [PATCH 1/2] Implement Task 3: GetAverageGrade feature --- src/main/java/api/MongoGradeDataBase.java | 99 ++++++++----------- .../java/usecase/GetAverageGradeUseCase.java | 15 ++- 2 files changed, 50 insertions(+), 64 deletions(-) diff --git a/src/main/java/api/MongoGradeDataBase.java b/src/main/java/api/MongoGradeDataBase.java index 77e76548..64108a65 100644 --- a/src/main/java/api/MongoGradeDataBase.java +++ b/src/main/java/api/MongoGradeDataBase.java @@ -38,19 +38,13 @@ public static String getAPIToken() { @Override public Grade getGrade(String username, String course) { - - // Build the request to get the grade. - // Note: The API requires the token to be passed as a header. - // Note: The API requires the course and username to be passed as query parameters. - final OkHttpClient client = new OkHttpClient().newBuilder() - .build(); + final OkHttpClient client = new OkHttpClient().newBuilder().build(); final Request request = new Request.Builder() .url(String.format("%s/grade?course=%s&username=%s", API_URL, course, username)) .addHeader(TOKEN, getAPIToken()) .addHeader(CONTENT_TYPE, APPLICATION_JSON) .build(); - // Hint: look at the API documentation to understand what the response looks like. try { final Response response = client.newCall(request).execute(); final JSONObject responseBody = new JSONObject(response.body().string()); @@ -62,33 +56,24 @@ public Grade getGrade(String username, String course) { .course(grade.getString(COURSE)) .grade(grade.getInt(GRADE)) .build(); - } - else { + } else { throw new RuntimeException("Grade could not be found for course: " + course - + " and username: " + username); + + " and username: " + username); } - } - catch (IOException | JSONException event) { + } catch (IOException | JSONException event) { throw new RuntimeException(event); } } @Override public Grade[] getGrades(String username) { - - // Build the request to get all grades for a user. - // Note: The API requires the token to be passed as a header. - // Note: The API requires the username to be passed as a query parameter. - final OkHttpClient client = new OkHttpClient().newBuilder() - .build(); + final OkHttpClient client = new OkHttpClient().newBuilder().build(); final Request request = new Request.Builder() .url(String.format("%s/grade?username=%s", API_URL, username)) .addHeader(TOKEN, getAPIToken()) .addHeader(CONTENT_TYPE, APPLICATION_JSON) .build(); - // Note: you can look at the API documentation to understand what the response looks like - // to better understand how this parses the response. try { final Response response = client.newCall(request).execute(); final JSONObject responseBody = new JSONObject(response.body().string()); @@ -105,20 +90,17 @@ public Grade[] getGrades(String username) { .build(); } return result; - } - else { + } else { throw new RuntimeException(responseBody.getString(MESSAGE)); } - } - catch (IOException | JSONException event) { + } catch (IOException | JSONException event) { throw new RuntimeException(event); } } @Override public Grade logGrade(String course, int grade) throws JSONException { - final OkHttpClient client = new OkHttpClient().newBuilder() - .build(); + final OkHttpClient client = new OkHttpClient().newBuilder().build(); final MediaType mediaType = MediaType.parse(APPLICATION_JSON); final JSONObject requestBody = new JSONObject(); requestBody.put(COURSE, course); @@ -137,20 +119,17 @@ public Grade logGrade(String course, int grade) throws JSONException { if (responseBody.getInt(STATUS_CODE) == SUCCESS_CODE) { return null; - } - else { + } else { throw new RuntimeException(responseBody.getString(MESSAGE)); } - } - catch (IOException | JSONException event) { + } catch (IOException | JSONException event) { throw new RuntimeException(event); } } @Override public Team formTeam(String name) throws JSONException { - final OkHttpClient client = new OkHttpClient().newBuilder() - .build(); + final OkHttpClient client = new OkHttpClient().newBuilder().build(); final MediaType mediaType = MediaType.parse(APPLICATION_JSON); final JSONObject requestBody = new JSONObject(); requestBody.put(NAME, name); @@ -178,20 +157,17 @@ public Team formTeam(String name) throws JSONException { .name(team.getString(NAME)) .members(members) .build(); - } - else { + } else { throw new RuntimeException(responseBody.getString(MESSAGE)); } - } - catch (IOException | JSONException event) { + } catch (IOException | JSONException event) { throw new RuntimeException(event); } } @Override public Team joinTeam(String name) throws JSONException { - final OkHttpClient client = new OkHttpClient().newBuilder() - .build(); + final OkHttpClient client = new OkHttpClient().newBuilder().build(); final MediaType mediaType = MediaType.parse(APPLICATION_JSON); final JSONObject requestBody = new JSONObject(); requestBody.put(NAME, name); @@ -209,20 +185,17 @@ public Team joinTeam(String name) throws JSONException { if (responseBody.getInt(STATUS_CODE) == SUCCESS_CODE) { return null; - } - else { + } else { throw new RuntimeException(responseBody.getString(MESSAGE)); } - } - catch (IOException | JSONException event) { + } catch (IOException | JSONException event) { throw new RuntimeException(event); } } @Override public void leaveTeam() throws JSONException { - final OkHttpClient client = new OkHttpClient().newBuilder() - .build(); + final OkHttpClient client = new OkHttpClient().newBuilder().build(); final MediaType mediaType = MediaType.parse(APPLICATION_JSON); final JSONObject requestBody = new JSONObject(); final RequestBody body = RequestBody.create(mediaType, requestBody.toString()); @@ -240,20 +213,14 @@ public void leaveTeam() throws JSONException { if (responseBody.getInt(STATUS_CODE) != SUCCESS_CODE) { throw new RuntimeException(responseBody.getString(MESSAGE)); } - } - catch (IOException | JSONException event) { + } catch (IOException | JSONException event) { throw new RuntimeException(event); } } @Override - // TODO Task 3b: Implement this method - // Hint: Read the Grade API documentation for getMyTeam (link below) and refer to the above similar - // methods to help you write this code (copy-and-paste + edit as needed). - // https://www.postman.com/cloudy-astronaut-813156/csc207-grade-apis-demo/folder/isr2ymn/get-my-team public Team getMyTeam() { - final OkHttpClient client = new OkHttpClient().newBuilder() - .build(); + final OkHttpClient client = new OkHttpClient().newBuilder().build(); final Request request = new Request.Builder() .url(String.format("%s/team", API_URL)) .method("GET", null) @@ -261,13 +228,27 @@ public Team getMyTeam() { .addHeader(CONTENT_TYPE, APPLICATION_JSON) .build(); - final Response response; - final JSONObject responseBody; + try { + final Response response = client.newCall(request).execute(); + final JSONObject responseBody = new JSONObject(response.body().string()); - // TODO Task 3b: Implement the logic to get the team information - // HINT 1: Look at the formTeam method to get an idea on how to parse the response - // HINT 2: You may find it useful to just initially print the contents of the JSON - // then work on the details of how to parse it. - return null; + if (responseBody.getInt(STATUS_CODE) == SUCCESS_CODE) { + final JSONObject teamJson = responseBody.getJSONObject("team"); + final JSONArray membersArray = teamJson.getJSONArray("members"); + final String[] members = new String[membersArray.length()]; + for (int i = 0; i < membersArray.length(); i++) { + members[i] = membersArray.getString(i); + } + + return Team.builder() + .name(teamJson.getString(NAME)) + .members(members) + .build(); + } else { + throw new RuntimeException(responseBody.getString(MESSAGE)); + } + } catch (IOException | JSONException e) { + throw new RuntimeException(e); + } } } diff --git a/src/main/java/usecase/GetAverageGradeUseCase.java b/src/main/java/usecase/GetAverageGradeUseCase.java index 25140b18..05809caa 100644 --- a/src/main/java/usecase/GetAverageGradeUseCase.java +++ b/src/main/java/usecase/GetAverageGradeUseCase.java @@ -20,14 +20,19 @@ public GetAverageGradeUseCase(GradeDataBase gradeDataBase) { * @return The average grade. */ public float getAverageGrade(String course) { - // Call the API to get usernames of all your team members float sum = 0; int count = 0; - // TODO Task 3b: Go to the MongoGradeDataBase class and implement getMyTeam. final Team team = gradeDataBase.getMyTeam(); - // Call the API to get all the grades for the course for all your team members - // TODO Task 3a: Complete the logic of calculating the average course grade for - // your team members. Hint: the getGrades method might be useful. + + for (String member : team.getMembers()) { + + Grade grade = gradeDataBase.getGrade(member, course); + + if (grade != null) { + sum += grade.getGrade(); + count++; + } + } if (count == 0) { return 0; From 2bdfd95e4a5b4e2ba9dbe95435b459c0788c8a24 Mon Sep 17 00:00:00 2001 From: Tomas Souto Date: Mon, 6 Oct 2025 18:35:03 -0400 Subject: [PATCH 2/2] Finished --- src/main/java/app/Config.java | 3 +++ src/main/java/app/gui/Application.java | 31 +++++++++++++++++++++++--- 2 files changed, 31 insertions(+), 3 deletions(-) diff --git a/src/main/java/app/Config.java b/src/main/java/app/Config.java index 12df0fd5..6b06cf8f 100644 --- a/src/main/java/app/Config.java +++ b/src/main/java/app/Config.java @@ -65,5 +65,8 @@ public GetAverageGradeUseCase getAverageGradeUseCase() { return new GetAverageGradeUseCase(gradeDataBase); } + + public GetTopGradeUseCase getTopGradeUseCase() {return new GetTopGradeUseCase(gradeDataBase);} + // TODO Task 4: add code for the new GetTopGradeUseCase following the same pattern as the other use cases above. } diff --git a/src/main/java/app/gui/Application.java b/src/main/java/app/gui/Application.java index ff61dddc..9d9e2d09 100644 --- a/src/main/java/app/gui/Application.java +++ b/src/main/java/app/gui/Application.java @@ -23,6 +23,7 @@ import entity.Grade; import usecase.FormTeamUseCase; import usecase.GetAverageGradeUseCase; +import usecase.GetTopGradeUseCase; import usecase.GetGradeUseCase; import usecase.JoinTeamUseCase; import usecase.LeaveTeamUseCase; @@ -55,6 +56,7 @@ public static void main(String[] args) { final JoinTeamUseCase joinTeamUseCase = config.joinTeamUseCase(); final LeaveTeamUseCase leaveTeamUseCase = config.leaveTeamUseCase(); final GetAverageGradeUseCase getAverageGradeUseCase = config.getAverageGradeUseCase(); + final GetTopGradeUseCase getTopGradeUseCase = config.getTopGradeUseCase(); // this is the code that runs to set up our GUI SwingUtilities.invokeLater(() -> { @@ -70,7 +72,7 @@ public static void main(String[] args) { final JPanel logGradeCard = createLogGradeCard(frame, logGradeUseCase); final JPanel formTeamCard = createFormTeamCard(frame, formTeamUseCase); final JPanel joinTeamCard = createJoinTeamCard(frame, joinTeamUseCase); - final JPanel manageTeamCard = createManageTeamCard(frame, leaveTeamUseCase, getAverageGradeUseCase); + final JPanel manageTeamCard = createManageTeamCard(frame, leaveTeamUseCase, getAverageGradeUseCase, getTopGradeUseCase); cardPanel.add(defaultCard, "DefaultCard"); cardPanel.add(getGradeCard, "GetGradeCard"); @@ -324,12 +326,14 @@ public void actionPerformed(ActionEvent e) { // TODO Task 4: modify this method so that it takes in a getTopGradeUseCase // Note: this will require you to update the code that calls this method. private static JPanel createManageTeamCard(JFrame jFrame, LeaveTeamUseCase leaveTeamUseCase, - GetAverageGradeUseCase getAverageGradeUseCase) { + GetAverageGradeUseCase getAverageGradeUseCase, GetTopGradeUseCase getTopGradeUseCase) { final JPanel theCard = new JPanel(); theCard.setLayout(new GridLayout(ROWS, COLS)); final JTextField courseField = new JTextField(20); // make a separate line. final JButton getAverageButton = new JButton("Get Average Grade"); + final JButton getTopGradeButton = new JButton("Get Top Grade"); + // TODO Task 4: Add another button for "Get Top Grade" (check the getAverageButton for example) final JButton leaveTeamButton = new JButton("Leave Team"); @@ -356,7 +360,27 @@ public void actionPerformed(ActionEvent e) { } }); - // TODO Task 4: Add action listener for getTopGrade button, follow example of getAverageButton + getTopGradeButton.addActionListener(new ActionListener() { + /** + * Invoked when an action occurs. + * + * @param e the event to be processed + */ + @Override + public void actionPerformed(ActionEvent e) { + final String course = courseField.getText(); + System.out.println(course); + + try { + final float top = getTopGradeUseCase.getTopGrade(course); + JOptionPane.showMessageDialog(jFrame, "Top Grade: " + top); + courseField.setText(""); + } + catch (JSONException ex) { + JOptionPane.showMessageDialog(jFrame, ex.getMessage()); + } + } + }); leaveTeamButton.addActionListener(new ActionListener() { /** @@ -379,6 +403,7 @@ public void actionPerformed(ActionEvent e) { theCard.add(new JLabel("The course you want to calculate the team average for:")); theCard.add(courseField); theCard.add(getAverageButton); + theCard.add(getTopGradeButton); theCard.add(leaveTeamButton); theCard.add(resultLabel); return theCard;