A lightweight FastAPI application that simulates integrating user data between an HR system, an Identity Provider (Okta), and optionally a Device Management platform (Jamf).
It demonstrates how structured data from different sources can be combined and served via a REST API.
- Accepts incoming HR user data via a simulated webhook (
POST /hr/webhook
) - Reads mock Okta data from a local JSON file
- Optionally includes mock Jamf device data (personalization)
- Merges and normalizes data into a single enriched user object
- Serves enriched data via API endpoint (
GET /user/{employee_id}
) - Includes a health check endpoint (
GET /health
) - Inline logging for clear visibility into each process step
app/
├── main.py # FastAPI application
└── data/
├── hr_user.json # Mock HR data
├── okta_user_data.json# Mock Okta user data
└── jamf_device_data.json # Optional Jamf mock data
requirements.txt
README.md
1️⃣ Clone the repository
git clone hhttps://github.com/ehanda/code_challenge
2️⃣ Change into the project directory
cd code_challenge
3️⃣ (Optional but recommended) — Create and activate a virtual environment
python3 -m venv venv
source venv/bin/activate # On macOS/Linux
pip3 install -r requirements.txt
uvicorn app.main:app --reload
You should see:
INFO: Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit)
Tip: Once the server is running, keep that terminal window open —
it’s hosting your API.If you want to send
curl
commands or other requests, open a second terminal window or tab so that Uvicorn can keep running in the first one.
Option 1 — FastAPI Docs
- Open your browser at http://127.0.0.1:8000/docs
- Click POST /hr/webhook → Try it out
- Paste the contents of
app/data/hr_user.json
- Click Execute to see the enriched data
Option 2 — Curl (in a separate terminal window)
# POST HR data
curl -X POST "http://127.0.0.1:8000/hr/webhook" -H "Content-Type: application/json" -d @app/data/hr_user.json
# Retrieve enriched user
curl "http://127.0.0.1:8000/user/12345"
# Health check
curl "http://127.0.0.1:8000/health"
You’ll see logs in the first terminal showing each step (HR → Okta → Jamf enrichment).
Python
- Chosen for readability, reliability, and strong ecosystem support for REST APIs and automation.
FastAPI
- Lightweight, asynchronous web framework with automatic interactive documentation (
/docs
). - Excellent for quick API prototyping and clear schema validation.
Pydantic
- Provides strong data validation for incoming HR JSON payloads.
- Automatically converts and checks field types, reducing boilerplate code.
JSON Files
- Used as mock data sources (HR, Okta, Jamf).
- Keeps everything self-contained and runnable without external dependencies or API keys.
In-Memory Dictionary
- Used as a temporary “database.”
- Simple, fast, and resets cleanly on each run — ideal for interview/demo purposes.
No Database
- Skipped persistent storage (like SQLite or Postgres) to keep setup minimal.
- Trade-off: data doesn’t persist across runs — but perfect for a demo environment.
Mock Data Instead of Real APIs
- Local JSON files simulate responses from Okta and Jamf.
- Trade-off: avoids authentication and latency but doesn’t demonstrate live API calls.
Single-File Design
- All logic in
main.py
for simplicity and clarity. - Trade-off: less modular than a real-world production structure.
No Authentication
- Skipped API keys or OAuth to keep testing friction-free.
- In production, requests should be authenticated to prevent unauthorized access.
- Replace JSON mocks with real API calls to Okta and Jamf using
requests
orhttpx
- Add SQLite or Postgres for persistent storage
- Implement API key or OAuth authentication
- Add unit tests using
pytest
- Containerize the app with Docker for deployment
- Add async Okta/Jamf calls for performance
- Integrate with CI/CD for testing and deployment
“I added a mock Jamf device data file to demonstrate how this same integration pattern could extend to device management — for example, associating an employee with their assigned MacBook or pushing configuration updates in Jamf or Kandji.
This ties directly into the kind of automation and API integration work I’ve done in IT engineering.”
{
"id": "12345",
"name": "Jane Doe",
"email": "jane.doe@example.com",
"title": "Software Engineer",
"department": "Engineering",
"startDate": "2024-01-15",
"groups": ["Everyone", "Engineering", "Full-Time Employees"],
"applications": ["Google Workspace", "Slack", "Jira"],
"onboarded": true,
"device": {
"device_name": "Jane’s MacBook Pro",
"os_version": "macOS 14.2",
"status": "Enrolled"
}
}