nerve MCP server
2026년 10월 27일 커밋스크린샷 캡처, UI 요소 검사, 탭, 스와이프 및 앱 관리 도구를 통해 AI 에이전트가 Android 및 iOS 기기를 제어할 수 있도록 합니다.
다른 이름 LincForge/nerve
- 스타
- 1
- Tools
- 49
- 다운로드, 30일
- —
- 최신 버전
- —
- 마지막 커밋
- 2026년 10월 27일
- 라이선스
- Apache-2.0
nerve MCP란?
nerve은(는) MCP server입니다. 스크린샷 캡처, UI 요소 검사, 탭, 스와이프 및 앱 관리 도구를 통해 AI 에이전트가 Android 및 iOS 기기를 제어할 수 있도록 합니다. 49개 도구를 제공합니다. 예: nerve_capabilities, nerve_discover, nerve_pool.
프로젝트 README에서 생성된 요약
nerve MCP server 정보
nerve는 AI 에이전트를 통해 Android 및 iOS 기기를 제어할 수 있게 해줍니다. 이 MCP server는 에이전트가 스크샷 찍기, UI 요소 트리 검사, 탭, 스와이프, 타이핑 및 애플리케이션 관리와 같은 작업을 수행할 수 있도록 49개의 도구를 제공합니다. AI 코딩 에이전트를 사용하는 개발자를 위해 설계되었으며, Claude Code와 같은 MCP 클라이언트에서 물리적 기기 또는 에뮬레이터와 직접 상호작용할 수 있는 방법을 제공합니다.
사용자는 Python 3.13+ 및 uv 패키지 관리자를 사용하여 로컬에 서버를 설정할 수 있습니다. Android의 경우 adb를 활용하며 추가 설정 없이 에뮬레이터에서 실행할 수 있습니다. iOS 지원은 macOS에서 WebDriverAgent를 통해 가능합니다. 이 서버에는 응답하지 않는 adb 서버나 누수된 UiAutomation 세션과 같은 일반적인 하드웨어 문제를 처리하기 위한 특화된 로직이 포함되어 있습니다. 토큰 사용량을 관리하기 위해 에이전트에 전송되는 스크린샷은 자동으로 약 300k 픽셀로 크기가 조정됩니다. 고급 시각적 그라운딩(visual grounding)을 위해 사용자는 Meta AI API 키를 제공하여 Meta의 SAM 3.1 모델을 선택적으로 사용할 수 있습니다.
활용 사례
- 1모바일 UI 구조 검사에이전트가 현재 포그라운드 애플리케이션과 UI 요소 전체 목록을 가져와 화면 레이아웃을 파악할 수 있습니다.
- 2레이블이 없는 인터페이스 요소 식별표준 UI 트리로 버튼을 식별할 수 없는 경우, 에이전트는 시각적 그라운딩을 사용하여 커스텀 캔버스 상의 컨트롤을 찾을 수 있습니다.
- 3기기 연결 문제 디버깅서버가 호스트와 모바일 기기 간의 연결 상태를 진단할 수 있습니다.
프로젝트의 README를 바탕으로 작성되었습니다. 모든 활용 사례는 해당 내용의 인용문과 대조하여 확인합니다.
nerve MCP 도구 49
README에서 감지됨nerve_capabilitiesnerve_discovernerve_poolnerve_screenshotnerve_stream_screenshotnerve_stream_startnerve_stream_statusnerve_stream_stopnerve_diffnerve_elementsnerve_groundnerve_state
| nerve_capabilities | — | |
| nerve_discover | — | |
| nerve_pool | — | |
| nerve_screenshot | — | |
| nerve_stream_screenshot | — | |
| nerve_stream_start | — | |
| nerve_stream_status | — | |
| nerve_stream_stop | — | |
| nerve_diff | — | |
| nerve_elements | — | |
| nerve_ground | — | |
| nerve_state | — |
도구 49개 모두 보기도구 수 줄이기
nerve_navigatenerve_navigate_screenshotnerve_densitynerve_keynerve_long_pressnerve_swipenerve_tapnerve_typenerve_appsnerve_clear_app_datanerve_grant_permissionnerve_installnerve_killnerve_launchnerve_uninstallnerve_emulator_listnerve_emulator_startnerve_emulator_stopnerve_inject_sensornerve_extract_framesnerve_record_fixednerve_record_startnerve_record_stopnerve_actionlog_startnerve_actionlog_stopnerve_replaynerve_ensure_readynerve_networknerve_inspectnerve_logcatnerve_metricsnerve_session_statsnerve_stream_logsnerve_usage_statsnerve_releasenerve_reservenerve_device_state
| nerve_navigate | — | |
| nerve_navigate_screenshot | — | |
| nerve_density | — | |
| nerve_key | — | |
| nerve_long_press | — | |
| nerve_swipe | — | |
| nerve_tap | — | |
| nerve_type | — | |
| nerve_apps | — | |
| nerve_clear_app_data | — | |
| nerve_grant_permission | — | |
| nerve_install | — | |
| nerve_kill | — | |
| nerve_launch | — | |
| nerve_uninstall | — | |
| nerve_emulator_list | — | |
| nerve_emulator_start | — | |
| nerve_emulator_stop | — | |
| nerve_inject_sensor | — | |
| nerve_extract_frames | — | |
| nerve_record_fixed | — | |
| nerve_record_start | — | |
| nerve_record_stop | — | |
| nerve_actionlog_start | — | |
| nerve_actionlog_stop | — | |
| nerve_replay | — | |
| nerve_ensure_ready | — | |
| nerve_network | — | |
| nerve_inspect | — | |
| nerve_logcat | — | |
| nerve_metrics | — | |
| nerve_session_stats | — | |
| nerve_stream_logs | — | |
| nerve_usage_stats | — | |
| nerve_release | — | |
| nerve_reserve | — | |
| nerve_device_state | — |
구성
META_AI_API_KEYNERVE_GROUNDINGWDA_PROJECT_DIRWDA_TEAM_ID
| 이름 | 설명 | 유형 |
|---|---|---|
| META_AI_API_KEY | — | |
| NERVE_GROUNDING | — | |
| WDA_PROJECT_DIR | — | |
| WDA_TEAM_ID | — |
자동 검사
2026년 11월 14일에 실행됨전체 보고서 →아직 인증되지 않았습니다. 서버는 80점 이상의 점수, 심각한 결함 없음, 그리고 검사에 충분한 데이터를 갖추어야 합니다. 검사 방식 · 점수를 높이기 위해 수정할 항목
- 소스 저장소 연결 및 접근 가능lincforge/nerve is public and reachablegithub.com/lincforge/nerve ↗통과
- 패키지가 이 저장소를 소스로 명시검사되지 않음
- 빌드 출처(Sigstore 증명)검사되지 않음
- 오픈 소스 라이선스 (OSI)Apache-2.0spdx.org/licenses/Apache-2.0.html ↗통과
- 최근 1년 내 커밋 또는 릴리스Last commit or release 2026-10-27github.com/lincforge/nerve ↗통과
- OpenSSF Scorecard검사되지 않음
- 패키지 이름이 인기 패키지와 유사하지 않음검사되지 않음
- 패키지 및 해당 종속성에 중요한 보안 권고 없음검사되지 않음
- 모델에 대한 숨겨진 지침 없음49 tool descriptions and the README read; no override phrases, credential paths or hidden characters통과
- 파괴적인 도구에 라벨 표시됨No tool named like delete, drop or exec통과
- 원격 엔드포인트가 MCP 핸드셰이크에 응답검사되지 않음
README
GitHub에서 보기linc-nerve
Field-tested device control for AI coding agents — the self-healing tricks we learned keeping a physical Android/iOS bench alive, as an MCP server and a plain CLI.
nerve exposes 49 tools — screenshots, the UI
element tree, tap/swipe/type, app install/launch, logs, recording — to any MCP client, and the same
tools as nerve <tool> commands that print JSON.
Field notes
A device bench fails in ways a single emulator never shows you. Each of these is a behaviour you can read in the code:
- adb can wedge while looking alive. After a wireless device drops, the adb server can sit in a
busy-spin: every
adbcall hangs, andadb kill-serverhangs too because it talks to the same wedged socket. A watchdog treats "unresponsive and server at ≥ 80% CPU" as the wedge signature and recovers by killing the server's PID, never byadb kill-server; an unresponsive server with an idle CPU is left alone. →src/linc_nerve/core/adb_health.py - A leaked UiAutomation session silently breaks the element tree.
uiautomator dumpis killed while another process (a leaked test driver) holds the device's single UiAutomation connection. Recovery is evidence-gated and escalates in tiers under one 45 s deadline, force-stopping only a known allowlist of test drivers — the Pixel Watch companion app, whose package name looks similar, is never touched. An empty element list therefore always means an empty screen, never a failed dump. →src/linc_nerve/core/android_ui.py - Readiness checks fail toward "unknown", not "ready". Wake/lock state is parsed from
dumpsys, whose format varies by OEM and Android version; an unrecognised format reads asunknown, so a caller skips rather than tapping a locked screen. →src/linc_nerve/core/device_state.py - Screenshots handed to an agent are budgeted. Inline images for MCP agents are rescaled to
about 300k pixels (≈ 400 vision tokens); the full-resolution file on disk is left untouched for
everything else. →
src/linc_nerve/mcp/_core.py
Quickstart
Android emulator first — no physical device, Xcode or WebDriverAgent needed.
Prerequisites: Python 3.13+ (uv fetches it for you; with plain pip you need it installed),
uv, the Android SDK command-line tools, and platform-tools and
emulator on your PATH (adb and emulator; with Homebrew's android-commandlinetools add
$(brew --prefix)/share/android-commandlinetools/emulator to PATH). Then create an emulator.
On Apple silicon, replace x86_64 with arm64-v8a in the first two lines below.
avdmanager asks whether to create a custom hardware profile; answer no.
sdkmanager "platform-tools" "emulator" "system-images;android-35;google_apis;x86_64"
avdmanager create avd -n nerve -k "system-images;android-35;google_apis;x86_64"
emulator -avd nerve -no-window &
adb wait-for-device
adb wait-for-device returns before Android has finished booting. Wait until
adb shell getprop sys.boot_completed prints 1 (usually a minute or so on first boot) before
step 1, or the first state call can hit a half-booted device.
Install: pipx install --python python3.13 linc-nerve (or python3.13 -m pip install linc-nerve inside a venv),
after which the same commands run as nerve doctor, nerve discover and
nerve state --device <serial>; and for Claude Code claude mcp add nerve -- nerve bellows.
1. Check the environment. The daemon, WebDriverAgent and $LINC_HOME (default ~/.linc) are
optional, so on a fresh Android-only machine nothing fails (exit code 0); missing optional pieces
show as ! warnings with an indented hint: line. The exact set of lines depends on your machine
(macOS runs the xcode-clt check, a running daemon shows ✓). Sample from a fresh Linux machine,
trimmed:
uvx linc-nerve doctor
✓ adb: adb responsive (/usr/local/bin/adb)
✓ device-auth: no unauthorized devices
✓ scrcpy-server: …/linc_nerve/vendor/scrcpy-server-v3.3.4
! wda-project: WDA_PROJECT_DIR not set — iOS tap/swipe/elements unavailable (Android works without it)
hint: git clone https://github.com/appium/WebDriverAgent.git ~/.linc/wda/src && export WDA_PROJECT_DIR=~/.linc/wda/src
! wda-team-id: WDA_TEAM_ID not set — physical-iOS WDA signing will fail
hint: …
- xcode-clt: skipped — not macOS
! daemon: no nerve daemon on 127.0.0.1:8111 — CLI calls run in-process (the daemon is optional)
hint: …
! linc-layout: missing directories: /home/you/.linc, /home/you/.linc/nerve/recordings — nerve creates them on first use
hint: …
8 checks: 0 failed, 4 warned
2. Find the emulator.
uvx linc-nerve discover
{"devices": [{"serial": "emulator-5554", "platform": "android", "device_type": "emulator", …, "state": "online"}], "count": 1, "android": 1, "ios": 0}
With several devices attached, devices lists all of them; pass the emulator's serial to the
later commands.
3. Read the screen — foreground app, element tree and a screenshot path in one call. Your
launcher package and element count depend on the system image, and the screenshot lands in your
temp directory ($TMPDIR on macOS, not /tmp):
uvx linc-nerve state --device emulator-5554
{"device": "emulator-5554", "platform": "android", "foreground": {"package": "com.google.android.apps.nexuslauncher", …}, "element_count": 31, "elements": [ … ], "screenshot": "<temp dir>/nerve-output/…png", …}
4. Give it to your agent. For Claude Code:
claude mcp add nerve -- uvx linc-nerve bellows
Run claude mcp list and check that nerve shows as connected, then paste a first prompt:
Take a screenshot of the emulator and tell me what app is in the foreground.
Every MCP tool is also a CLI command: the tool name minus nerve_, with _ → -
(nerve_clear_app_data → nerve clear-app-data). Output is JSON on stdout; for text, put --human
before the command (nerve --human discover, not nerve discover --human). Exit 0 success, 1
tool error, 2 usage error. nerve schema --json prints the full command tree.
iOS (experimental)
iOS simulators and physical devices work through WebDriverAgent
(WDA), which you build once. nerve doctor prints the same steps as hints:
git clone https://github.com/appium/WebDriverAgent.git ~/.linc/wda/src
export WDA_PROJECT_DIR=~/.linc/wda/src
export WDA_TEAM_ID=<Apple Developer Team ID> # physical devices only; simulators don't need it
Needs macOS with Xcode. Expect rough edges: WDA always binds port 8100, first start takes ~4 s on a simulator and 15–30 s on a physical device, physical devices need code signing, and watchOS is not supported.
Visual grounding (optional, Meta SAM 3.1)
nerve_ground and nerve_tap(prompt=...) find controls that the UI tree cannot label, such as
custom canvases or unlabelled icons. They do this by sending the current screenshot to Meta's
sam-3.1 model. Grounding is off by default, and it needs three things:
pip install 'linc-nerve[grounding]' # adds meta-sam-parser
export NERVE_GROUNDING=1 # opt in: screenshots are uploaded to api.meta.ai
export META_AI_API_KEY=... # or NERVE_KEYCHAIN_SERVICE=<macOS Keychain service>
- License:
meta-sam-parseris distributed under Meta's SAM License, not Apache-2.0. It restricts some fields of use, including ITAR-controlled, military and weapons applications. Read it before you install the extra. Core nerve never imports it. - Privacy: never enable grounding on a device that shows personal data.
- Tap safety: a prompt tap fires only on one clear match, meaning confidence ≥ 0.5 and at least 0.1 ahead of the next match on a known screen size. Otherwise it taps nothing and returns the candidates.
Reference
Configuration
| Environment variable | Default | Effect |
|---|---|---|
NERVE_USAGE_LOG |
redacted |
Local usage log mode: off, redacted or full (see Trust) |
LINC_HOME |
~/.linc |
Where the usage log and recordings live; when set, the device-state database also moves to $LINC_HOME/.local/share/linc-nerve/devices.db (default ~/.local/share/linc-nerve/devices.db) |
NERVE_ACTIONLOG_ROOTS |
$LINC_HOME/nerve/actionlogs |
Colon-separated list of allowed host directory roots for nerve_actionlog_start and nerve_replay files |
WDA_PROJECT_DIR |
(none) | WebDriverAgent checkout (iOS only) |
WDA_TEAM_ID |
(none) | Apple Developer Team ID (physical iOS only) |
NERVE_HTTP_PORT |
8111 |
Port of the optional HTTP daemon: the port the daemon started by nerve bellows listens on and the port nerve doctor probes (nerve daemon takes --port instead) |
LINC_NERVE_DAEMON |
http://127.0.0.1:8111 |
Daemon URL that CLI commands call before falling back to in-process |
ANDROID_ADB_SERVER_PORT / ADB_SERVER_SOCKET |
127.0.0.1:5037 |
adb server nerve talks to (ADB_SERVER_SOCKET as tcp:<port> or tcp:<host>:<port> wins; loopback hosts only) — isolates nerve from the host's devices |
NERVE_ALLOWED_HOSTS / NERVE_ALLOWED_ORIGINS |
(none) | Extra Hosts / browser Origins the daemon accepts |
NERVE_GROUNDING |
(off) | 1 enables SAM 3.1 visual grounding (nerve_ground, nerve_tap(prompt=...), visual_grounding_hint); needs the [grounding] extra |
META_AI_API_KEY |
(none) | Meta API key for grounding (META_API_KEY also accepted) |
NERVE_KEYCHAIN_SERVICE |
(none) | macOS Keychain service to read the Meta API key from when it is not in the environment |
NERVE_OUTPUT_KEEP |
200 |
Maximum number of output files retained per process nerve-output-* temp directory (0 or invalid falls back to 200) |
NERVE_OUTPUT_MAX_AGE_S |
86400 |
Maximum age in seconds (24h default; 0 or invalid falls back to 86400) before an idle nerve-output-* directory is swept on the next process's first output |
Output files
Screenshots (nerve_screenshot, nerve_stream_screenshot, nerve_navigate_screenshot), state/diff captures (nerve_state, nerve_diff), and large nerve_logcat dumps are written to a per-process private (0700) directory <temp dir>/nerve-output-<random>/<serial>_<NNNN>_<tool>.<ext> (under $TMPDIR on macOS, /tmp on Linux), created lazily on first output and kept on process exit so callers can read returned paths after a CLI invocation finishes:
- Retention cap: Each process directory keeps at most
NERVE_OUTPUT_KEEP(default200)<serial>_<NNNN>_<tool>.<ext>files, pruning the oldest (by counter, then mtime) before writing a new one. - Owner lock: Each process holds an exclusive
flockon<dir>/.nerve-output.lockfor its lifetime (the OS drops it when the process exits). A directory whose lock is held — or whose lock state cannot be read — is never removed by the sweep or bynerve cleanup, however long its process (an idle daemon or MCP server) has gone without writing. If a process's directory is deleted anyway, nerve creates a fresh one on the next output. - Stale sweep: On the first output directory creation in a process, nerve sweeps
<temp dir>/nerve-output-*directories owned by the current UID (never following symlinks) that no live process holds and whose newest entry is older thanNERVE_OUTPUT_MAX_AGE_Sseconds (default86400). SetNERVE_OUTPUT_SWEEP=0to disable it (it is also off under pytest unlessNERVE_OUTPUT_SWEEP=1). - On-demand cleanup:
nerve cleanupremoves all current-UID, non-symlinknerve-output-*directories in the temp root except those held by a running nerve process and those modified in the last 60 seconds (nerve cleanup --allremoves the recently modified ones too, never a live process's), printing JSON{"removed": [...], "skipped": [...], "bytes_freed": N}(or text withnerve --human cleanup).
HTTP daemon (optional)
nerve daemon (or nerve bellows, which also serves MCP over stdio) runs an HTTP server on
127.0.0.1:8111: GET /health, GET /devices, POST /tools/<tool_name> with a JSON body, and
GET /stream?device=<serial> for a server-sent-events log stream. CLI commands use the daemon when
one is running and otherwise run the tool in-process. A few stateful tools (recording, streaming,
reservations, diff, session-stats) need the daemon, and say so instead of answering wrongly.
MCP Tools (49)
Tools are registered via @device_tool (requires a device serial) or @global_tool (no device needed) in src/linc_nerve/mcp/*_tools.py. This section — including the count — is generated from those registrations by python -m linc_nerve.docs_gen; tests/test_docs_sync.py fails CI when it is stale. Call nerve_capabilities for the per-platform support matrix.
Discovery & Capabilities
| Tool | Type | Description |
|---|---|---|
nerve_capabilities |
global | Per-platform support matrix for nerve's capability groups |
nerve_discover |
global | List all connected devices (Android + iOS) |
nerve_pool |
global | Show device pool status — who has what reserved |
Screenshots & Streaming
| Tool | Type | Description |
|---|---|---|
nerve_screenshot |
device | Capture one screenshot — a stateless PNG of the current device display |
nerve_stream_screenshot |
device | Pull the current frame from an active screen-mirror streaming session |
nerve_stream_start |
device | Open a live screen-mirror session for warming up fast screenshots |
nerve_stream_status |
global | Report status and health of active screen-mirror streaming sessions |
nerve_stream_stop |
device | Tear down the live mirror session opened by nerve_stream_start |
UI Inspection
| Tool | Type | Description |
|---|---|---|
nerve_diff |
device | Return UI changes since the last nerve_state snapshot on this device |
nerve_elements |
device | Return the UI element tree only (clickable + text widgets) — no image bytes |
nerve_ground |
device | Locate UI controls visually by natural-language concept prompt using Meta SAM 3.1 |
nerve_state |
device | Capture full device state in one call (screenshot + UI elements + foreground) |
Navigation
| Tool | Type | Description |
|---|---|---|
nerve_navigate |
device | Navigate to a named screen of a REGISTERED app (route registry) by its deep link |
nerve_navigate_screenshot |
device | Navigate to a screen and capture a screenshot after the UI settles |
Input
| Tool | Type | Description |
|---|---|---|
nerve_density |
device | Read display density — dpi and the dp-to-px multiplier — for a device |
nerve_key |
device | Press a hardware/system key |
nerve_long_press |
device | Long press at screen coordinates |
nerve_swipe |
device | Two-point gesture from one xy coordinate to another — swipe, drag, or scroll |
nerve_tap |
device | Tap a single point on the device display at known x/y coordinates or by visual prompt |
nerve_type |
device | Type text into the currently focused input field via the soft keyboard |
App Management
| Tool | Type | Description |
|---|---|---|
nerve_apps |
device | List installed apps on the device |
nerve_clear_app_data |
device | Wipe an app's data + cache → first-install state |
nerve_grant_permission |
device | Grant a runtime permission to an app (Android pm grant) — no dialog |
nerve_install |
device | Install an app on the device |
nerve_kill |
device | Force-stop / terminate an app |
nerve_launch |
device | Launch an app by package/bundle ID, optionally opening a deep link URI |
nerve_uninstall |
device | Uninstall an app from the device |
Emulator / Simulator
| Tool | Type | Description |
|---|---|---|
nerve_emulator_list |
global | List available Android emulators (AVDs) and iOS Simulators, and their running state |
nerve_emulator_start |
global | Start an Android emulator (by AVD name) or iOS Simulator (by UDID/Name) |
nerve_emulator_stop |
device | Stop a running Android emulator or iOS Simulator |
nerve_inject_sensor |
device | Inject sensor data into an Android emulator via its telnet console |
Recording
| Tool | Type | Description |
|---|---|---|
nerve_extract_frames |
global | Extract PNG frames at given timestamps from a host-side MP4 recording |
nerve_record_fixed |
device | Record a fixed-length screen video — self-terminating MP4 capture |
nerve_record_start |
device | Begin recording video to disk — open-ended MP4 capture on the device |
nerve_record_stop |
device | Finalise the MP4 file and end the durable recording session |
Action Log
| Tool | Type | Description |
|---|---|---|
nerve_actionlog_start |
device | Start an action log — a JSONL record of every nerve tool call on a device |
nerve_actionlog_stop |
device | Stop the action log on a device and report the file and entry count |
nerve_replay |
device | Replay an action log on a device and report whether its steps ran |
Device Readiness
| Tool | Type | Description |
|---|---|---|
nerve_ensure_ready |
device | Ensure a device is awake + unlocked before UI interaction, and report readiness |
nerve_network |
device | Report whether a device is online — default network transport + validated internet |
Diagnostics & Observability
| Tool | Type | Description |
|---|---|---|
nerve_inspect |
device | Non-invasive post-mortem snapshot of a process — pid, RSS, crash signature |
nerve_logcat |
device | Tail the last N lines from a device's logcat buffer or iOS system log |
nerve_metrics |
global | Performance metrics for nerve commands |
nerve_session_stats |
global | Get state tracking statistics for all devices |
nerve_stream_logs |
device | Get the SSE subscription URL for continuous real-time log streaming |
nerve_usage_stats |
global | Usage analytics over the shared MCP call log (~/.linc/mcp-calls.jsonl) |
Reservation
| Tool | Type | Description |
|---|---|---|
nerve_release |
device | Release a device reservation |
nerve_reserve |
device | Reserve a device exclusively for this session |
Other
| Tool | Type | Description |
|---|---|---|
nerve_device_state |
device | Control Android device power/idle/standby state for adversarial testing |
Trust
- No telemetry, no phone-home. nerve talks to your devices, your local adb server, and — for iOS — the WebDriverAgent it starts. Nothing else.
- A local usage log, under your control. Each MCP tool call is appended to
$LINC_HOME/mcp-calls.jsonl(default~/.linc/mcp-calls.jsonl, rotated at 10 MB) with the tool name, timing, success and parameters. SetNERVE_USAGE_LOG=off|redacted|full:redacted(default) — values of sensitive parameters (text,password,passcode,pin,secret,token,otp) and every value underextrasanduriare replaced by their length only (no hash), including inside nested dicts and lists; binary values become their size, and long strings are truncated. The log file is created owner-only (0600).off— nothing is written.full— raw parameter values, including typed text (exceptnerve_typetext sent withsecret=true, which is length-only in every mode). Opt in only on a machine you trust.
- The daemon is loopback-only. It binds
127.0.0.1, rejects non-loopback Hosts (DNS rebinding) and any browser Origin, and accepts tool calls only asapplication/json. Every value that reaches a device shell is validated or shell-quoted where it is used. Details and how to report a vulnerability: SECURITY.md.
Related projects
| Package | Role |
|---|---|
linc-crucible |
Quality gates, build-and-deploy routing, and visual/a11y baselines (delegates device I/O to nerve) |
linc-spectra |
Runtime debugger (Android JDWP via kotlin-debug-adapter or zero-config jdb; iOS Simulator lldb-dap) |
mobile-agent-bench |
Pre-registered 600-cell benchmark comparing nerve + crucible + spectra against Maestro, mobile-mcp, and agent-device (lincforge.com) |
How this repo works
This is a release mirror of LINC's private repository. The code is built by LINC's AI software factory under human review; each release lands as one commit. Issues are welcome; pull requests by arrangement — see CONTRIBUTING.md.
Built by LINC Innovations — we diagnose flaky device test suites.
Licensed under the Apache License 2.0. Bundles scrcpy-server (Apache-2.0) — see NOTICE.
nerve MCP 질문
nerve MCP는 어떤 도구를 제공하나요?
49개 도구를 제공합니다. 예: nerve_capabilities, nerve_discover, nerve_pool, nerve_screenshot, nerve_stream_screenshot.
nerve는 MCP 에이전트를 위한 대용량 스크린샷을 어떻게 처리하나요?
토큰 사용량을 관리하기 위해 MCP 에이전트용 인라인 이미지는 약 300k 픽셀로 크기가 조정되며, 전체 해상도 파일은 디스크에 보존됩니다.