Corvus Integration API
User provisioning, de-provisioning, and student progress export for SIS/CRM integration.
Authentication
All Integration API endpoints require the following authentication:
- Pass the API key in the HTTP header
X-Corvus-API-Key - Pass the API secret in the HTTP header
X-Corvus-API-Secret
API credentials can be managed under Admin → Integrations → Integration API Keys (requires Application Admin role).
| Header | Description |
|---|---|
| X-Corvus-API-Key | Tenant API key (identifies the tenant) |
| X-Corvus-API-Secret | API secret (authenticates the request) |
CreateUpdateUser
Creates a new user or updates an existing user. Idempotent — sending the same logical user multiple times results in the same outcome. Use for nightly sync or delta updates from your SIS.
Web Service: POST https://dm.corvussg.com/api/v1/integration/users
Input
| Name | Type | Required | Description |
|---|---|---|---|
| string | Yes | Primary email. Used for matching if no external ID. | |
| firstName | string | Yes | First name |
| lastName | string | Yes | Last name |
| accountType | string | Yes | "Student" | "Faculty" | "Staff" — determines 950 vs 951 ID |
| accountStatus | string | No | "active" | "inactive". Default: "active" |
| externalId | string | No | Your SIS/CRM user ID. Stored as legacyNumber if not 950/951. |
| schoolProgram | string | No | Program (e.g. Doctoral Studies, MBA) |
| degree | string | No | Degree (e.g. PhD, EdD) |
| monthOfEntry | number | No | 1-12 |
| yearOfEntry | number | No | 4-digit year |
| monthOfGraduation | number | No | 1-12 |
| yearOfGraduation | number | No | 4-digit year |
| domain | string | No | Email domain. Default: "corvus.edu" |
| userTags | string[] | No | Tags for categorization |
| role | string | No | student | faculty | chair | application_admin | etc. Default derived from accountType |
| programId | string | No | Program ID (links to Programs) |
| name | string | No | Display name override. Default: firstName + lastName |
| middleInitial | string | No | Middle initial (used to build name: "FirstName M. LastName") |
| isAffiliatedWithUniversity | boolean | No | University affiliation. Default: true |
| genderPronoun | string | No | e.g. They/Them, He/Him, She/Her |
| nationalities | string[] | No | Nationalities |
| hideProfilePage | boolean | No | Hide profile from directory |
| unsubscribeAllGroupEmails | boolean | No | Opt out of group emails |
| careerInterests | string[] | No | Career interest tags |
| customFields | object | No | Key-value extensibility |
| languages | string[] | No | Languages spoken |
| facultyProfile | object | No | Faculty profile (when accountType is Faculty). See table below. |
facultyProfile (optional, for Faculty/Chair)
| Field | Type | Description |
|---|---|---|
| highestDegree | string | e.g. PhD, EdD |
| degreeField | string | e.g. Education, Business |
| facultyRank | string | e.g. Associate Professor |
| contentExpertiseTags | string[] | e.g. ["Leadership", "Organizational Behavior"] |
| methodsExpertise | string[] | e.g. ["quantitative", "qualitative", "mixed methods"] |
| technicalExpertiseTags | string[] | Technical expertise areas |
| tools | string[] | e.g. ["SPSS", "R", "NVivo"] |
| expertiseNotes | string | Free-text notes |
| eligibleProgramIds | string[] | Program IDs this faculty can serve |
| committeeRolesSupported | string[] | chair | content_expert | methodologist_technical_expert | member |
| availabilityStatus | string | available | limited | unavailable |
| maxConcurrentCommittees | number | Max committee assignments (default 10) |
| graduateFacultyStatus | boolean | Graduate faculty certification |
| canServeAsChair | boolean | Can serve as committee chair (default from role if chair) |
| isExternal | boolean | External/affiliate faculty |
| externalOrganization | string | Org name if external |
| leaveUntil | string | ISO date (e.g. 2025-12-31) — on leave until |
| isCommitteeEligible | boolean | Eligible for committee assignment |
Response
| Name | Type | Description |
|---|---|---|
| success | boolean | true if successful |
| data.id | string | Corvus 950/951 user ID |
| data.email | string | User email |
| data.firstName | string | First name |
| data.lastName | string | Last name |
| data.accountType | string | Student | Faculty | Staff |
| data.accountStatus | string | active | inactive |
| data.legacyNumber | string | externalId if not 950/951 |
| message | string | "DATA INSERTED" or "DATA UPDATED" |
Example
curl -X POST "https://dm.corvussg.com/api/v1/integration/users" \
-H "Content-Type: application/json" \
-H "X-Corvus-API-Key: your-api-key" \
-H "X-Corvus-API-Secret: your-api-secret" \
-d '{"email":"jane.doe@uni.edu","firstName":"Jane","lastName":"Doe","accountType":"Student","externalId":"SIS-12345"}'With faculty profile (Faculty/Chair):
curl -X POST "https://dm.corvussg.com/api/v1/integration/users" \
-H "Content-Type: application/json" \
-H "X-Corvus-API-Key: your-api-key" \
-H "X-Corvus-API-Secret: your-api-secret" \
-d '{"email":"dr.smith@uni.edu","firstName":"Jane","lastName":"Smith","accountType":"Faculty","role":"chair","facultyProfile":{"highestDegree":"PhD","degreeField":"Education","facultyRank":"Professor","contentExpertiseTags":["Leadership"],"methodsExpertise":["qualitative"],"committeeRolesSupported":["chair","content_expert"],"availabilityStatus":"available"}}'Matching logic: externalId (950/951) → legacyNumber → email. If no match, a new user is created.
De-Provision / Restore User
Soft de-provisions or restores a user. De-provisioning sets accountStatus: "inactive" — user cannot log in, but data is preserved.
Web Service: PATCH https://dm.corvussg.com/api/v1/integration/users/:id
Path Parameters
| Param | Description |
|---|---|
| id | Corvus 950/951 ID or externalId (legacyNumber) |
Request Body (optional)
| Field | Default | Description |
|---|---|---|
| accountStatus | inactive | "active" | "inactive" |
Example (De-provision)
curl -X PATCH "https://dm.corvussg.com/api/v1/integration/users/9509922064" \
-H "Content-Type: application/json" \
-H "X-Corvus-API-Key: your-api-key" \
-H "X-Corvus-API-Secret: your-api-secret" \
-d '{"accountStatus":"inactive"}'Student Progress Export
Returns student progress data for export to SIS/CRM. Use for nightly sync or on-demand reporting. Includes dissertation versions, milestones, pacing status, and committee formation.
Web Service: GET https://dm.corvussg.com/api/v1/integration/progress
Query Parameters
| Param | Type | Default | Description |
|---|---|---|---|
| studentId | string | — | Optional. Single ID or comma-separated list. |
| since | string | — | Optional. ISO 8601 date. Delta sync filter. |
| limit | number | 1000 | Max records (1–5000) |
Example
curl -s "https://dm.corvussg.com/api/v1/integration/progress?studentId=9509922064" \ -H "X-Corvus-API-Key: your-api-key" \ -H "X-Corvus-API-Secret: your-api-secret"
Forms Sync Scaffold (No External Side Effects)
These endpoints provide a connector-ready queue and payload preview for future SIS/CRM/LMS integrations. They are safe by design: they only read/update internal Corvus queue metadata and do not call external systems.
Primary future targets include PeopleSoft (SIS), Salesforce (CRM), and Canvas (LMS). Connector code is intentionally not enabled in this scaffold.
1) List Queue
Web Service: GET https://dm.corvussg.com/api/v1/integration/sync/queue
| Query Param | Type | Default | Description |
|---|---|---|---|
| status | string | all | all | not_queued | queued | processing | sent | failed |
| limit | number | 100 | Maximum records, capped at 500 |
curl -s "https://dm.corvussg.com/api/v1/integration/sync/queue?status=queued&limit=50" \ -H "X-Corvus-API-Key: your-api-key" \ -H "X-Corvus-API-Secret: your-api-secret"
2) Payload Preview
Web Service: GET https://dm.corvussg.com/api/v1/integration/sync/payload/:submissionId
Returns the outbound envelope that a future connector would send. This is preview-only and does not transmit data externally.
curl -s "https://dm.corvussg.com/api/v1/integration/sync/payload/<submission-id>" \ -H "X-Corvus-API-Key: your-api-key" \ -H "X-Corvus-API-Secret: your-api-secret"
3) Replay Control
Web Service: POST https://dm.corvussg.com/api/v1/integration/sync/replay
Re-queues a submission for a future connector run by setting internal queue status to queued. No external API is called.
curl -X POST "https://dm.corvussg.com/api/v1/integration/sync/replay" \
-H "Content-Type: application/json" \
-H "X-Corvus-API-Key: your-api-key" \
-H "X-Corvus-API-Secret: your-api-secret" \
-d '{"submissionId":"<submission-id>","targetSystem":"peoplesoft"}'4) Connector Ack Stub
Web Service: POST https://dm.corvussg.com/api/v1/integration/sync/ack
Updates internal queue state as if an external connector responded. Accepted statuses:processing,sent,failed.
curl -X POST "https://dm.corvussg.com/api/v1/integration/sync/ack" \
-H "Content-Type: application/json" \
-H "X-Corvus-API-Key: your-api-key" \
-H "X-Corvus-API-Secret: your-api-secret" \
-d '{"submissionId":"<submission-id>","status":"failed","targetSystem":"salesforce","lastError":"Validation mismatch"}'Contract Files
- OpenAPI:
apiDocs/openapi.sync-scaffold.yaml - Queue item schema:
apiDocs/schemas/forms-sync-queue-item.schema.json - Envelope schema:
apiDocs/schemas/forms-sync-envelope.schema.json
Automatic Queue Trigger
When a form submission is moved to approved or closed in review workflows, Corvus auto-queues sync metadata internally. This still performs no outbound connector call.
Idempotency guard: if an item is already queued or processing, repeated status updates do not re-queue it. Use replay controls for intentional re-queue.
Discrepancy-safe gating: if unresolved mapped-field discrepancies exist, queue attempts are blocked internally and the sync state is marked failed until discrepancies are reviewed.
Root Endpoint
Health check / connectivity test. Returns 200 if credentials are valid.
Web Service: GET https://dm.corvussg.com/api/v1/integration
Example Response
{
"success": true,
"message": "Integration API",
"tenantId": "default"
}For more details, see the apiDocs/ folder in the Corvus codebase. Contact your administrator for API credentials.