Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package ca.bc.gov.educ.studentdatacollection.api.constants.v1;

import lombok.Getter;

import java.util.Arrays;
import java.util.Optional;

@Getter
public enum MinistryReportTypeCode {
SCHOOL_ENROLLMENT_HEADCOUNTS("school-enrollment-headcounts");

private final String code;
MinistryReportTypeCode(String code) { this.code = code; }

public static Optional<MinistryReportTypeCode> findByValue(String value) {
return Arrays.stream(values()).filter(e -> Arrays.asList(e.code).contains(value)).findFirst();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ private URL(){
public static final String BASE_URL_COLLECTION="/api/v1/student-data-collection/collection";
public static final String BASE_URL_DISTRICT_COLLECTION="/api/v1/student-data-collection/sdcDistrictCollection";
public static final String BASE_DISTRICT_HEADCOUNTS = "/api/v1/student-data-collection/headcounts";
public static final String BASE_MINISTRY_HEADCOUNTS = "/api/v1/student-data-collection/ministryHeadcounts";
public static final String BASE_URL_SCHOOL_COLLECTION="/api/v1/student-data-collection/sdcSchoolCollection";
public static final String BASE_URL_SCHOOL_COLLECTION_STUDENT="/api/v1/student-data-collection/sdcSchoolCollectionStudent";
public static final String BASE_URL_REPORT_GENERATION="/api/v1/student-data-collection/reportGeneration";
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
package ca.bc.gov.educ.studentdatacollection.api.constants.v1.ministryreports;

import lombok.Getter;

@Getter
public enum SchoolEnrolmentHeader {

SCHOOL_ENROLMENT_COLLECTION("School Enrolment Collection"),
SCHOOL_YEAR("School Year"),
DISTRICT_NUMBER("District Number"),
SCHOOL_NUMBER("School Number"),
SCHOOL_NAME("School Name"),
FACILITY_TYPE("Facility Type"),
SCHOOL_CATEGORY("School Category"),
GRADE_RANGE("Grade Range"),
REPORT_DATE("Report Date"),
KIND_HT_COUNT("Kind(H/T) Count"),
KIND_FT_COUNT("Kind(F/T) Count"),
GRADE_01_COUNT("Grade 1 Count"),
GRADE_02_COUNT("Grade 2 Count"),
GRADE_03_COUNT("Grade 3 Count"),
GRADE_04_COUNT("Grade 4 Count"),
GRADE_05_COUNT("Grade 5 Count"),
GRADE_06_COUNT("Grade 6 Count"),
GRADE_07_COUNT("Grade 7 Count"),
GRADE_08_COUNT("Grade 8 Count"),
GRADE_09_COUNT("Grade 9 Count"),
GRADE_10_COUNT("Grade 10 Count"),
GRADE_11_COUNT("Grade 11 Count"),
GRADE_12_COUNT("Grade 12 Count");

private final String code;
SchoolEnrolmentHeader(String code) { this.code = code; }
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
package ca.bc.gov.educ.studentdatacollection.api.controller.v1;

import ca.bc.gov.educ.studentdatacollection.api.constants.v1.MinistryReportTypeCode;
import ca.bc.gov.educ.studentdatacollection.api.endpoint.v1.MinistryHeadcountReports;
import ca.bc.gov.educ.studentdatacollection.api.exception.InvalidPayloadException;
import ca.bc.gov.educ.studentdatacollection.api.exception.errors.ApiError;
import ca.bc.gov.educ.studentdatacollection.api.service.v1.MinistryHeadcountService;
import ca.bc.gov.educ.studentdatacollection.api.struct.v1.headcounts.HeadcountResultsTable;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RestController;

import java.time.LocalDateTime;
import java.util.Optional;
import java.util.UUID;

import static org.springframework.http.HttpStatus.BAD_REQUEST;

@RestController
@Slf4j
@RequiredArgsConstructor
public class MinistryHeadcountReportsController implements MinistryHeadcountReports {

private final MinistryHeadcountService ministryHeadcountService;

@Override
public HeadcountResultsTable getMinistryHeadcounts(UUID collectionID, String type) {
Optional<MinistryReportTypeCode> code = MinistryReportTypeCode.findByValue(type);

if(code.isEmpty()){
ApiError error = ApiError.builder().timestamp(LocalDateTime.now()).message("Payload contains invalid report type code.").status(BAD_REQUEST).build();
throw new InvalidPayloadException(error);
}

return switch(code.get()) {
case SCHOOL_ENROLLMENT_HEADCOUNTS -> ministryHeadcountService.getAllSchoolEnrollmentHeadcounts(collectionID);
default -> new HeadcountResultsTable();
};
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package ca.bc.gov.educ.studentdatacollection.api.endpoint.v1;

import ca.bc.gov.educ.studentdatacollection.api.constants.v1.URL;
import ca.bc.gov.educ.studentdatacollection.api.struct.v1.headcounts.HeadcountResultsTable;
import io.swagger.v3.oas.annotations.responses.ApiResponse;
import io.swagger.v3.oas.annotations.responses.ApiResponses;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;

import java.util.UUID;

@RequestMapping(URL.BASE_MINISTRY_HEADCOUNTS)
public interface MinistryHeadcountReports {

@GetMapping("/{collectionID}/{type}")
@PreAuthorize("hasAuthority('SCOPE_READ_SDC_MINISTRY_REPORTS')")
@Transactional(readOnly = true)
@ApiResponses(value = {@ApiResponse(responseCode = "200", description = "OK"), @ApiResponse(responseCode = "400", description = "BAD REQUEST")})
HeadcountResultsTable getMinistryHeadcounts(@PathVariable UUID collectionID, @PathVariable(name = "type") String type);
}
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,28 @@ HAVING COUNT(assignedStudentId) > 1)

long countBySdcSchoolCollection_SdcSchoolCollectionIDAndSdcSchoolCollectionStudentStatusCode(UUID sdcSchoolCollectionID, String sdcSchoolCollectionStatusCode);

@Query("SELECT " +
" sscs.sdcSchoolCollection.schoolID as schoolID, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = 'KH' THEN 1 END) as kindHCount, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = 'KF' THEN 1 END) as kindFCount, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '01' THEN 1 END) as grade1Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '02' THEN 1 END) as grade2Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '03' THEN 1 END) as grade3Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '04' THEN 1 END) as grade4Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '05' THEN 1 END) as grade5Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '06' THEN 1 END) as grade6Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '07' THEN 1 END) as grade7Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '08' THEN 1 END) as grade8Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '09' THEN 1 END) as grade9Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '10' THEN 1 END) as grade10Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '11' THEN 1 END) as grade11Count, " +
" COUNT(CASE WHEN sscs.enrolledGradeCode = '12' THEN 1 END) as grade12Count " +
" FROM SdcSchoolCollectionStudentEntity sscs " +
" WHERE sscs.sdcSchoolCollectionStudentStatusCode NOT IN ('ERROR', 'DELETED') " +
" AND sscs.sdcSchoolCollection.collectionEntity.collectionID = :collectionID " +
" GROUP BY sscs.sdcSchoolCollection.sdcSchoolCollectionID ")
List<SchoolHeadcountResult> getAllEnrollmentHeadcountsByCollectionId(@Param("collectionID") UUID collectionID);

@Query(value = """
SELECT stud
FROM SdcSchoolCollectionStudentLightEntity stud, SdcSchoolCollectionEntity school, SdcDistrictCollectionEntity dist
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
package ca.bc.gov.educ.studentdatacollection.api.service.v1;

import ca.bc.gov.educ.studentdatacollection.api.constants.v1.CollectionTypeCodes;
import ca.bc.gov.educ.studentdatacollection.api.constants.v1.ministryreports.SchoolEnrolmentHeader;
import ca.bc.gov.educ.studentdatacollection.api.exception.EntityNotFoundException;
import ca.bc.gov.educ.studentdatacollection.api.model.v1.CollectionEntity;
import ca.bc.gov.educ.studentdatacollection.api.repository.v1.CollectionRepository;
import ca.bc.gov.educ.studentdatacollection.api.repository.v1.SdcSchoolCollectionStudentRepository;
import ca.bc.gov.educ.studentdatacollection.api.rest.RestUtils;
import ca.bc.gov.educ.studentdatacollection.api.struct.v1.Collection;
import ca.bc.gov.educ.studentdatacollection.api.struct.v1.headcounts.HeadcountHeaderColumn;
import ca.bc.gov.educ.studentdatacollection.api.struct.v1.headcounts.HeadcountResultsTable;
import ca.bc.gov.educ.studentdatacollection.api.struct.v1.headcounts.SchoolHeadcountResult;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.util.*;

import static ca.bc.gov.educ.studentdatacollection.api.constants.v1.ministryreports.SchoolEnrolmentHeader.*;


@Service
@Slf4j
@RequiredArgsConstructor
public class MinistryHeadcountService {
private final CollectionRepository collectionRepository;
private final SdcSchoolCollectionStudentRepository sdcSchoolCollectionStudentRepository;
private final RestUtils restUtils;
private static final String COLLECTION_ID = "collectionID";

public HeadcountResultsTable getAllSchoolEnrollmentHeadcounts(UUID collectionID) {
List<SchoolHeadcountResult> collectionRawData = sdcSchoolCollectionStudentRepository.getAllEnrollmentHeadcountsByCollectionId(collectionID);
var collectionOpt = collectionRepository.findById(collectionID);
if(collectionOpt.isEmpty()){
throw new EntityNotFoundException(Collection.class, COLLECTION_ID, collectionID.toString());
}
var collection = collectionOpt.get();

HeadcountResultsTable resultsTable = new HeadcountResultsTable();
var headerList = new ArrayList<String>();
for (SchoolEnrolmentHeader header : SchoolEnrolmentHeader.values()) {
headerList.add(header.getCode());
}
resultsTable.setHeaders(headerList);
var rows = new ArrayList<Map<String, HeadcountHeaderColumn>>();
collectionRawData.stream().forEach(schoolHeadcountResult -> {
var school = restUtils.getSchoolBySchoolID(schoolHeadcountResult.getSchoolID()).get();

var rowMap = new HashMap<String, HeadcountHeaderColumn>();
rowMap.put(SCHOOL_YEAR.getCode(), getHeadcountColumn(getSchoolYearString(collection)));
rowMap.put(DISTRICT_NUMBER.getCode(), getHeadcountColumn(school.getMincode().substring(0,3)));
rowMap.put(SCHOOL_NUMBER.getCode(), getHeadcountColumn(school.getSchoolNumber()));
rowMap.put(SCHOOL_NAME.getCode(), getHeadcountColumn(school.getDisplayName()));
rowMap.put(FACILITY_TYPE.getCode(), getHeadcountColumn(school.getFacilityTypeCode()));
rowMap.put(SCHOOL_CATEGORY.getCode(), getHeadcountColumn(school.getSchoolCategoryCode()));
rowMap.put(REPORT_DATE.getCode(), getHeadcountColumn(collection.getSnapshotDate().toString()));
rowMap.put(KIND_HT_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getKindHCount()));
rowMap.put(KIND_FT_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getKindFCount()));
rowMap.put(GRADE_01_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade1Count()));
rowMap.put(GRADE_02_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade2Count()));
rowMap.put(GRADE_03_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade3Count()));
rowMap.put(GRADE_04_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade4Count()));
rowMap.put(GRADE_05_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade5Count()));
rowMap.put(GRADE_06_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade6Count()));
rowMap.put(GRADE_07_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade7Count()));
rowMap.put(GRADE_08_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade8Count()));
rowMap.put(GRADE_09_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade9Count()));
rowMap.put(GRADE_10_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade10Count()));
rowMap.put(GRADE_11_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade11Count()));
rowMap.put(GRADE_12_COUNT.getCode(), getHeadcountColumn(schoolHeadcountResult.getGrade12Count()));
rows.add(rowMap);
});
resultsTable.setRows(rows);
return resultsTable;
}

private HeadcountHeaderColumn getHeadcountColumn(String value){
HeadcountHeaderColumn column = new HeadcountHeaderColumn();
column.setCurrentValue(value);
return column;
}

private String getSchoolYearString(CollectionEntity collection){
var snapshotDateString = collection.getSnapshotDate();
if(!collection.getCollectionTypeCode().equals(CollectionTypeCodes.SEPTEMBER.getTypeCode())){
return snapshotDateString.minusYears(1).getYear() + "/" + snapshotDateString.getYear() + "SY";
}else{
return snapshotDateString.getYear() + "/" + snapshotDateString.plusYears(1).getYear() + "SY";
}
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package ca.bc.gov.educ.studentdatacollection.api.struct.v1.headcounts;

public interface SchoolHeadcountResult extends HeadcountResult{
String getKindHCount();
String getKindFCount();
String getGrade1Count();
String getGrade2Count();
String getGrade3Count();
String getGrade4Count();
String getGrade5Count();
String getGrade6Count();
String getGrade7Count();
String getGrade8Count();
String getGrade9Count();
String getGrade10Count();
String getGrade11Count();
String getGrade12Count();
}
Loading
Loading