Mirobody
The canonical registry of human health — roughly two thousand standardized indicators, clinical and lifestyle, resolved into one language.
翻訳待ち
No updates detected yet. GitHub releases will appear here.
The maker's introduction consists of the line above. Read the repository README for more details. Repository README ↗
Loading the full README.
Read the full README ↗시니어(60대 이상)를 위한 AI 복약 관리 시스템
처방전 사진 한 장으로 복약 알림을 자동 등록하고, 브라우저를 닫아도 환자·보호자에게 텔레그램 알림이 발송되는 서비스입니다.
| 기능 | 설명 |
|---|---|
| 📸 처방전 OCR | Gemini Vision API로 처방전 자동 인식 및 약품 정보 추출 |
| 💊 복약 카드 | 어르신이 이해하기 쉬운 언어 + 약 색상/모양 시각화 |
| 🔊 음성 안내 | Web Speech API 기반 복약 정보 읽기 |
| 📲 텔레그램 즉시 알림 | 분석 완료 즉시 환자에게 복약 등록 알림 발송 |
| ⏰ 서버 사이드 스케줄 알림 | QStash cron으로 매일 복약 시각에 자동 알림 (브라우저 종료 무관) |
| 👤 보호자 알림 | 보호자 Chat ID 등록 시 환자와 동시에 텔레그램 발송 |
| 🔍 약품 검증 | 식약처 공공 API로 약품 정보 교차 확인 |
| 분류 | 기술 |
|---|---|
| Frontend | Next.js 16 (App Router), TypeScript, Tailwind CSS v4 |
| AI | Google Gemini 2.5 Flash (Vision) |
| 알림 | Telegram Bot API |
| 스케줄링 | Upstash QStash (서버 사이드 cron) |
| 저장소 | Upstash Redis (보호자 정보 저장) |
| 약품 검증 | 식품의약품안전처 공공 API |
[홈 화면]
보호자 모드 ON → Chat ID 입력
→ POST /api/guardian → Upstash Redis 저장 (30일 TTL)
[처방전 분석]
→ POST /api/analyze
→ Gemini OCR 분석
→ 텔레그램 즉시 알림 발송
→ 약별 복약 시간마다 QStash cron 등록
[매일 복약 시각 — 브라우저 없어도 동작]
QStash → POST /api/notify
→ 환자 텔레그램 발송
→ 보호자 텔레그램 발송 (등록된 경우)
promise/
├── .env.local # 환경 변수 (git 제외)
├── .env.example # 환경 변수 템플릿
├── src/
│ ├── app/
│ │ ├── page.tsx # 홈 (처방전 업로드)
│ │ ├── result/
│ │ │ └── page.tsx # 분석 결과 화면
│ │ └── api/
│ │ ├── analyze/
│ │ │ └── route.ts # Gemini OCR + QStash 스케줄 등록
│ │ ├── notify/
│ │ │ └── route.ts # QStash가 호출하는 알림 발송 엔드포인트
│ │ └── guardian/
│ │ └── route.ts # 보호자 Chat ID 저장/조회
│ ├── lib/
│ │ ├── redis.ts # Upstash Redis 클라이언트
│ │ ├── qstash.ts # QStash 스케줄 등록 헬퍼
│ │ └── historyStorage.ts # 로컬 히스토리 저장
│ ├── components/
│ │ ├── UploadZone.tsx # 사진 업로드 UI
│ │ └── MedicationCard.tsx # 약품 결과 카드
│ ├── hooks/
│ │ └── useVoiceGuide.ts # 음성 안내 훅
│ └── types/
│ └── prescription.ts # 공통 타입 정의
└── public/
└── sw.js # Service Worker (PWA)
# Google Gemini AI
GOOGLE_API_KEY=
# 식약처 공공 API
MFDS_API_KEY=
# n8n 웹훅 (선택)
N8N_WEBHOOK_URL=
# 텔레그램 봇
TELEGRAM_BOT_TOKEN=
TELEGRAM_CHAT_ID=
# Upstash Redis
UPSTASH_REDIS_REST_URL=
UPSTASH_REDIS_REST_TOKEN=
# Upstash QStash
QSTASH_URL=
QSTASH_TOKEN=
QSTASH_CURRENT_SIGNING_KEY=
QSTASH_NEXT_SIGNING_KEY=
# 배포 URL (QStash가 호출할 엔드포인트 기준)
NEXT_PUBLIC_BASE_URL=http://localhost:3000
.env.local에 GOOGLE_API_KEY 입력.env.local에 MFDS_API_KEY 입력@BotFather → /newbot → 토큰 발급@userinfobot 에서 본인 Chat ID 확인.env.local에 TELEGRAM_BOT_TOKEN, TELEGRAM_CHAT_ID 입력.env.local에 각각 입력# 패키지 설치
npm install
# 개발 서버 실행
npm run dev
# → http://localhost:3000
# 프로덕션 빌드
npm run build && npm start
POST /api/analyze처방전 이미지를 분석하고 QStash 스케줄을 등록합니다.
Request — multipart/form-data
| 필드 | 타입 | 필수 | 설명 |
|---|---|---|---|
image | File | ✅ | 처방전 이미지 (최대 10MB) |
phone_number | string | - | 환자 전화번호 |
Response
{
"status": "success",
"data": { /* PrescriptionResult */ },
"message": "처방전 분석이 완료됐어요!",
"alerts_registered": true
}
POST /api/notifyQStash가 매일 복약 시각에 호출하는 텔레그램 발송 엔드포인트. QStash 서명 검증 후 환자·보호자에게 메시지 발송.
Request Header
upstash-signature: <QStash 서명값>
Request Body
{
"patientChatId": "8773271434",
"guardianChatId": "optional",
"drugName": "혈당 조절약",
"dose": "1정",
"scheduleTime": "07:30"
}
POST /api/guardian보호자 Chat ID를 Redis에 저장합니다 (30일 TTL).
Request Body
{
"patientChatId": "8773271434",
"guardianChatId": "보호자_chat_id",
"alerts": ["07:30", "18:30"]
}
GET /api/guardian?patientChatId=xxx저장된 보호자 정보를 조회합니다.
Response
{
"data": {
"guardianChatId": "보호자_chat_id",
"alerts": ["07:30", "18:30"]
}
}
QStash는 외부 URL만 호출 가능하므로, 로컬에서는 /api/notify에 직접 POST 요청으로 확인합니다.
curl -X POST http://localhost:3000/api/notify \
-H "Content-Type: application/json" \
-d '{
"patientChatId": "본인_TELEGRAM_CHAT_ID",
"drugName": "혈당 조절약",
"dose": "1정",
"scheduleTime": "07:30"
}'
로컬 테스트 시 서명 검증이 실패하므로,
src/app/api/notify/route.ts의isValid체크를 임시로 우회하거나 Vercel에 배포 후 테스트하세요.
.env.local 내용 전부 입력NEXT_PUBLIC_BASE_URL을 실제 배포 URL로 변경
NEXT_PUBLIC_BASE_URL=https://your-app.vercel.app
aria-label 추가MIT License — Cursor Bootcamp Project