> ## Documentation Index
> Fetch the complete documentation index at: https://docs.kralis.app/llms.txt
> Use this file to discover all available pages before exploring further.

# CDE result API

> Read-only results for the Catholic Diocese of Enugu Education Board.

CDE means the **Catholic Diocese of Enugu Education Board**. Kralis exposes a read-only result feed for CDE consumers.

The CDE feed is currently public at the API layer as a temporary arrangement. The endpoint includes school-scoped data selected by the school acronym, so treat school acronyms and returned result data as sensitive integration inputs. This public access is expected to be tightened when the CDE integration contract is formalized.

## Integration directory

The shared public integration directory is available at:

```text theme={null}
GET /integrations/
```

It advertises the CDE and Klapp API entry points:

```json theme={null}
{
  "integrations": [
    {
      "name": "cde",
      "about": "Catholic Diocese of Enugu Education Board",
      "api": "https://api.kralis.app/integrations/cde/",
      "docs": "https://docs.kralis.app/integrations/cde"
    },
    {
      "name": "klapp",
      "about": "https://en.klapp.pro/",
      "api": "https://api.kralis.app/integrations/klapp/",
      "docs": "https://docs.kralis.app/integrations/klapp"
    }
  ]
}
```

## Integration index

```text theme={null}
GET /integrations/cde/
```

The public index returns the CDE integration identifier, the school-scoped result path template, and an example path:

```json theme={null}
{
  "integration": "cde",
  "base_path": "https://api.kralis.app/integrations/cde/",
  "school_scoped_base_path_template": "https://api.kralis.app/integrations/cde/{school_acronym}/results/",
  "example_results_path": "https://api.kralis.app/integrations/cde/demo/results/"
}
```

## Route overview

| Route                                         | Authentication | Purpose                                                        |
| --------------------------------------------- | -------------- | -------------------------------------------------------------- |
| `/integrations/cde/`                          | Public         | Returns integration metadata and route templates               |
| `/integrations/cde/<school_acronym>/results/` | Public         | Returns results for one school, class, term, and academic year |

```text theme={null}
GET /integrations/cde/<school_acronym>/results/
```

Required query parameters:

```text theme={null}
class=js1
term=1
year=2024/2025
```

Example:

```text theme={null}
/integrations/cde/demo/results/?class=js1&term=1&year=2024/2025
```

The response includes the selected school context, students, subjects, scores, totals, averages, and result metadata. Class aliases such as `jss1`, term aliases such as `first`, and the full academic year name are supported by the endpoint.

## Response shape

```json theme={null}
{
  "metadata": {
    "school": "Demo School",
    "year": "2024/2025",
    "term": "First Term",
    "student_count": 1,
    "class": "js1",
    "class_full_name": "Junior Secondary School 1"
  },
  "subjects": ["English Language"],
  "students": [
    {
      "student_name": "Example Student",
      "student_id": "school-username",
      "term": "First Term",
      "year": "2024/2025",
      "scores": [
        { "subject": "English Language", "test": 18, "exam": 52, "total": 70 }
      ],
      "total": 70,
      "subject_count": 1,
      "average": 70.0
    }
  ]
}
```

Each student’s `scores` contains the subject name and the CDE-compatible `test`, `exam`, and `total` values. `student_id` is the Kralis username, not a Ministry identifier. The `metadata.class` value is the normalized Kralis class code; `class_full_name` is the display name.

## Query rules and behavior

* `class` is required; `classe` is accepted as an alias.
* `class` is normalized by removing spaces and punctuation and converting to lowercase. `primary1` and `basic1` resolve to `p1`; `jss1` and `sss2` resolve to `js1` and `ss2`.
* `term` is required and accepts `1`, `2`, `3`, ordinal forms, names such as `first`, and forms with an optional `term` prefix or suffix such as `term 1` and `1st term`.
* `year` is required. The endpoint first tries a case-insensitive exact match against `Year.year_name`, then accepts a unique case-insensitive prefix. If a prefix matches more than one year, the response is a validation error and the full year name is required. The resolved year scopes the returned results.
* The class and year must belong to the school resolved from `school_acronym`.
* The term must exist for the selected school and is resolved to `First Term`, `Second Term`, or `Third Term`.
* Only existing Kralis results are returned; this endpoint does not create or update results.
* Results are ordered by student surname and first name.
* `student_id` is the student’s Kralis username. It is not a CDE- or school-issued identifier.
* `subject_count` is the number of score rows returned for that student. If no score rows are available, `average` is returned as `0`.
* The response is cached for one hour, so a just-updated score may not appear immediately.

The legacy `/srms/<school_acronym>/` result alias remains available for compatible consumers but is not the preferred contract.

Use `metadata` to confirm that the response belongs to the requested school, class, academic year, and term before displaying or importing it. Because responses are cached for one hour, clients should allow for a delay after a result is updated in Kralis before requesting it again.
