GlassCloud
GlassCloud
Rokid Bridge 및 GlassBridge용 클라우드 서버 — 기기 연결, MCP 도구 릴레이, 갤러리가 포함된 이미지 저장소, 서버 측 LLM 장면 설명을 처리합니다.
기능
GlassCloud는 Rokid 스마트 글래스 앱을 위한 백엔드입니다. 다음 기능을 제공합니다:
기기 연결 — 웹 콘솔과 Android 앱 간의 QR 코드 또는 토큰 기반 페어링
MCP 도구 릴레이 — WebSocket을 통해 글래스에서 Google API로 Gmail 및 Calendar 도구 호출을 프록시 처리
이미지 갤러리 — 글래스에서 업로드된 장면 이미지를 수신하고 메타데이터와 함께 저장하며 웹 갤러리에 표시
서버 측 LLM — 설명이 없는 이미지가 도착하면 자동으로 Gemini 또는 ChatGPT를 호출하여 설명을 생성한 후, 글래스에 표시할 수 있도록 앱으로 반환
공개 갤러리 링크 — 사용자별 공개 공유 토큰을 통해 로그인 없이 갤러리 조회 가능
┌─────────────────┐ ┌─────────────────┐ ┌─────────────────┐
│ Rokid Glasses │────▶│ GlassCloud │────▶│ Google APIs │
│ + Android App │ WS │ (This Server) │ │ Gmail/Calendar │
└─────────────────┘ └─────────────────┘ └─────────────────┘
│ │
REST API │ │ Server-side LLM
▼ ▼
┌─────────────────┐
│ Web Console │
│ Gallery · LLM │
│ Settings · QR │
└─────────────────┘빠른 시작
# Install dependencies
npm install
# Copy and fill in environment variables
cp .env.example .env
# Edit .env — see Configuration section below
# Development (auto-reload)
npm run dev
# Production build + run
npm run build
npm start**http://localhost:3000/console**에 접속하여 웹 콘솔을 엽니다.
구성
모든 환경 변수는 시작 시 Zod를 통해 검증됩니다. 필수 변수가 누락된 경우 서버는 누락된 필드를 출력하고 종료됩니다.
보안 키 생성
node -e "console.log(require('crypto').randomBytes(32).toString('base64'))"JWT_SECRET용으로 한 번, ENCRYPTION_KEY용으로 한 번, 총 두 번 실행하십시오.
필수 변수
변수 | 설명 |
| 기기 JWT 서명용. 최소 32자. 무작위의 비밀 값이어야 함. |
| 저장된 OAuth 토큰 및 LLM API 키 암호화용 (AES-256-GCM). 최소 32자. |
| Google OAuth 2.0 클라이언트 ID |
| Google OAuth 2.0 클라이언트 비밀 |
| OAuth 리다이렉트 URI — Google Cloud Console에 등록된 것과 일치해야 함 (예: |
선택적 변수
변수 | 기본값 | 설명 | |||||
|
| HTTP 서버 포트 | |||||
|
|
|
|
| |||
|
|
|
|
|
|
|
|
|
| SQLite 데이터베이스 파일 경로 | |||||
|
| 허용된 CORS 오리진의 쉼표로 구분된 목록 | |||||
|
| 속도 제한 윈도우 (밀리초) | |||||
|
| IP당 윈도우별 최대 요청 수 ( | |||||
|
| WebSocket 유지 확인 핑 간격 | |||||
|
| 연결 종료 전 퐁 응답 대기 시간 |
.env 예시
PORT=3000
NODE_ENV=production
LOG_LEVEL=info
DATABASE_PATH=./data/glasscloud.db
JWT_SECRET=<generate with command above>
ENCRYPTION_KEY=<generate with command above>
CORS_ORIGINS=https://yourserver.com
GOOGLE_CLIENT_ID=123456789.apps.googleusercontent.com
GOOGLE_CLIENT_SECRET=GOCSPX-xxxxx
GOOGLE_CALLBACK_URL=https://yourserver.com/auth/google/callbackGoogle OAuth 설정
OAuth 2.0 클라이언트 ID(웹 애플리케이션)를 생성합니다.
승인된 리다이렉트 URI에 콜백 URL을 추가합니다:
https://yourserver.com/auth/google/callback프로젝트에서 Gmail API 및 Google Calendar API를 활성화합니다.
OAuth 동의 화면 → 테스트 사용자에 테스트 사용자를 추가합니다 (앱이 테스트 모드인 동안 필수).
Google 범위(Scopes) 참고: 이 앱은
gmail.readonly및calendar.events를 요청합니다. 100명 이상의 사용자가 있는 공개 배포의 경우, Google은 CASA 보안 평가를 요구합니다. 개인용 또는 테스트용인 경우 앱을 테스트 모드로 유지하십시오.
LLM 설정 (서버 측 장면 설명)
GlassCloud는 설명 없이 업로드된 이미지(예: Rokid 앱이 "Bypass LLM" 모드일 때)에 대해 자동으로 장면 설명을 생성할 수 있습니다. 생성된 설명은 다음과 같이 처리됩니다:
데이터베이스에 저장되고 갤러리에 표시됨
앱이 글래스에 즉시 표시할 수 있도록 업로드 API 응답으로 반환됨
구성
/console에 로그인하고 헤더에서 **LLM Settings →**를 클릭합니다.제공업체(Gemini 또는 ChatGPT)를 선택하고 API 키를 붙여넣습니다.
선택적으로 사용자 지정 프롬프트를 추가하고 하나를 활성 상태로 선택합니다.
기본 프롬프트는 다음과 같습니다: "이 이미지의 장면을 간결하게 설명하세요."
API 키
제공업체 | 획득 방법 |
Gemini | |
ChatGPT |
API 키는 ENCRYPTION_KEY(AES-256-GCM)를 사용하여 저장 시 암호화됩니다. API 키가 구성되지 않은 경우, 서버 측 LLM은 조용히 건너뛰며 설명이 비어 있는 이미지는 그대로 저장됩니다.
웹 콘솔 페이지
URL | 설명 |
| 대시보드: 통계, 기기 연결, MCP 서비스 관리 |
| 기기 페어링을 위한 QR 코드 / 링크 토큰 생성 |
| 이미지 갤러리 (썸네일, 세부 정보, 삭제가 포함된 테이블 뷰) |
| 메타데이터가 포함된 전체 크기 이미지 |
| LLM 제공업체, API 키 및 프롬프트 관리 |
| 공개 갤러리 (로그인 불필요) |
| 공개 사진 세부 정보 |
REST API 엔드포인트
기기 및 인증
엔드포인트 | 메서드 | 인증 | 설명 |
| GET | 없음 | 연결 통계가 포함된 상태 확인 |
| GET | 없음 | Google OAuth 흐름 시작 |
| GET | 없음 | OAuth 콜백 |
| POST | 없음 | 링크 토큰을 기기 JWT로 교환 |
| GET | 기기 JWT | 연결된 기기 목록 |
| DELETE | 세션 | 기기 연결 해제 |
이미지
엔드포인트 | 메서드 | 인증 | 설명 |
| POST | 기기 JWT | 이미지 + 메타데이터 업로드 (multipart/form-data) |
| GET | 기기 JWT | ID별 이미지 메타데이터 가져오기 |
업로드 필드
필드 | 유형 | 필수 | 설명 |
| 파일 | 예 | JPEG, PNG 또는 WebP — 최대 20MB |
| 문자열 | 예 | 장면 설명 (빈 문자열 가능) |
| 문자열 | 예 | 기기 모델명 |
| 문자열 | 예 | 고유 기기 식별자 |
| 문자열 | 아니오 | 이미지가 캡처된 ISO 8601 타임스탬프 |
| 숫자 | 아니오 | 이미지 너비 (픽셀) |
| 숫자 | 아니오 | 이미지 높이 (픽셀) |
| 문자열 | 아니오 | 기기에서 사용된 LLM (예: |
scene_description이 비어 있고 서버 측 LLM이 구성된 경우, 서버는 LLM을 호출하고 응답에 llmDescription을 포함합니다:
{
"imageId": "uuid",
"originalFilename": "uuid.jpg",
"thumbnailFilename": "uuid_thumb.jpg",
"receivedAt": 1714000000000,
"capturedAt": 1714000000000,
"llmDescription": "A person walking through a crowded market..."
}MCP
엔드포인트 | 메서드 | 인증 | 설명 |
| GET | 기기 JWT | 사용 가능한 MCP 서비스 및 도구 목록 |
WebSocket 프로토콜
연결 주소: ws://localhost:3000/ws?deviceId=YOUR_DEVICE_ID
클라이언트 → 서버
// Execute a tool
{ "type": "tool_execute", "requestId": "uuid", "serverId": "gmail",
"toolName": "gmail.get_unread", "arguments": { "maxResults": 10 } }
// Link device to user account
{ "type": "link_device", "requestId": "uuid",
"linkToken": "from-qr-code", "deviceId": "..." }
// Get user account info
{ "type": "get_user_account", "requestId": "uuid", "deviceId": "..." }서버 → 클라이언트
// Immediate progress (for voice feedback while tool runs)
{ "type": "tool_progress", "requestId": "uuid",
"status": "executing", "message": "Checking your emails..." }
// Tool result
{ "type": "tool_result", "requestId": "uuid",
"result": { "success": true, "content": "You have 3 unread emails..." } }
// Error
{ "type": "error", "requestId": "uuid", "error": "Token expired" }사용 가능한 MCP 도구
Gmail
도구 | 설명 |
| 읽지 않은 이메일 수 및 요약 가져오기 |
| 쿼리로 이메일 검색 |
| ID로 전체 이메일 내용 가져오기 |
Calendar
도구 | 설명 |
| 오늘의 일정 가져오기 |
| N일간의 일정 가져오기 |
| 새 일정 생성 |
데이터베이스 스키마
데이터베이스는 WAL 모드의 SQLite입니다. 스키마는 시작 시 생성되며, 새 열은 멱등성 마이그레이션을 통해 추가됩니다.
-- Users (from Google OAuth)
users (
id, google_id, email, display_name, profile_picture_url,
public_gallery_token, -- UUID for public gallery share link
llm_provider, -- 'Gemini' or 'ChatGPT' (default: 'Gemini')
openai_api_key_encrypted, -- AES-256-GCM encrypted
gemini_api_key_encrypted, -- AES-256-GCM encrypted
active_prompt_id, -- FK to llm_prompts.id
created_at, updated_at
)
-- Linked devices
devices (id, user_id, device_name, device_model, last_seen_at, last_heartbeat_at, linked_at, created_at)
-- QR code link tokens (single-use, 5 min expiry)
link_tokens (id, user_id, expires_at, used_at, used_by_device_id, created_at)
-- Encrypted Google OAuth tokens
oauth_tokens (id, user_id, provider, access_token_encrypted, refresh_token_encrypted, ...)
-- Scene images from glasses
glass_images (
id, device_model, device_instance_id,
scene_description, -- May be empty; server-side LLM fills it if blank
original_filename, thumbnail_filename,
captured_at, received_at, created_at,
image_width, image_height, -- Pixels (nullable)
user_id, -- FK to users.id (nullable for legacy rows)
llm_provider -- Which LLM generated the description
)
-- User-defined LLM prompts
llm_prompts (id, user_id, name, text, created_at)
-- Third-party MCP servers registered via console
third_party_mcp_services (id, name, description, owner_user_id, endpoint_url, auth_type, auth_config_encrypted, tools_json, ...)디렉토리 구조
src/
├── index.ts # Entry point — starts HTTP + WebSocket servers
├── config/
│ ├── env.ts # Zod environment validation (exits on invalid config)
│ └── mcp-services.ts # Built-in MCP service definitions
├── server/
│ ├── express.ts # Express app — middleware, route mounting, error handling
│ ├── sessions.ts # In-memory session store for console auth
│ └── websocket.ts # WebSocket server with zombie connection cleanup
├── routes/
│ ├── auth.ts # Google OAuth flow
│ ├── console.ts # Web console dashboard
│ ├── devices.ts # Device management API
│ ├── gallery.ts # Image gallery (authenticated + public)
│ ├── health.ts # Health check
│ ├── images.ts # Image upload + retrieval API
│ ├── link.ts # QR code token generation
│ ├── mcp.ts # MCP services API
│ └── settings.ts # LLM settings page
├── services/
│ ├── auth.service.ts # OAuth + token refresh mutex
│ ├── device.service.ts # Device CRUD
│ ├── image.service.ts # Image save/list/delete + thumbnail generation
│ ├── link.service.ts # QR code token handling
│ ├── llm.service.ts # LLM settings CRUD + callLlm() (Gemini / ChatGPT)
│ ├── mcp-proxy.service.ts # MCP tool execution with input coercion
│ └── mcp-registry.service.ts # Third-party MCP server registry
├── websocket/
│ ├── handler.ts # Message routing with progress feedback
│ ├── protocol.ts # Message type definitions
│ └── connection.ts # Connection tracking
├── db/
│ ├── index.ts # SQLite connection + WAL mode
│ └── schema.ts # CREATE TABLE + ALTER TABLE migrations
├── utils/
│ ├── crypto.ts # AES-256-GCM encrypt/decrypt + token generation
│ ├── logger.ts # Pino structured logging
│ └── cache.ts # LRU cache for MCP tool results
└── types/
├── api.ts # REST API types
├── mcp.ts # MCP types
└── websocket.ts # WebSocket message types데이터 파일은 ./data/에 기록됩니다:
./data/glasscloud.db— SQLite 데이터베이스./data/images/— 원본 업로드 이미지./data/thumbnails/— 400×400 JPEG 썸네일 (Sharp으로 생성)
보안
OAuth 토큰은
ENCRYPTION_KEY를 사용하여 AES-256-GCM으로 저장 시 암호화됨LLM API 키는 동일한 키로 저장 시 암호화됨
기기 JWT는
JWT_SECRET(HS256)으로 서명되며 모든 API 요청 시 검증됨링크 토큰은 SHA-256 해시로만 저장되며, 1회용이고 5분 후 만료됨
모든
/api/*경로에 속도 제한 적용 (환경 변수를 통해 구성 가능)모든 응답에 Helmet 보안 헤더 적용
공개 갤러리 토큰은 무작위 UUID이며, 재생성 시 이전 링크는 즉시 무효화됨
라이선스
MIT
This server cannot be installed
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Related MCP Connectors
The Remote MCP server acts as a standardized bridge between LLM applications (like Claude, ChatGPT, and Cursor) and external services, enabling AI agents to access external tools and resources. Its primary capability is providing a centralized search tool to discover other MCP servers and their respective tools. Unlike local implementations, it runs remotely with OAuth authentication and permission controls for security.
MCP server connecting AI agents to 100+ apps (Gmail, Slack, Notion, GitHub) via one-click OAuth.
Hosted MCP server with managed OAuth for 15+ toolkits: Google Workspace, Fitbit, Oura, Kalshi, etc.
Melaya is a remote MCP server. It gives an assistant hands on your own Android phone and browser: it reads the screen through the accessibility tree, then taps, types and navigates inside the apps and sites you allow-list, with no per-app API. It also builds, schedules and runs agent pipelines across 6k+ connected tools. OAuth 2.1, nothing to install.
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/jerryliu816/glasscloud'
If you have feedback or need assistance with the MCP directory API, please join our Discord server