by PerryLink
TypeSafe Jev for DeepSeek Harness, the Model Context Protocol, and plain Node: typed judgments instead of prose, offline by default.
# Add to your Claude Code skills
git clone https://github.com/PerryLink/jevcoreSee how jevcore compares with popular alternatives.
jevcore is an open-source ai agents skill for AI coding assistants such as Claude Code, Codex CLI, and ChatGPT, built by PerryLink. TypeSafe Jev for DeepSeek Harness, the Model Context Protocol, and plain Node: typed judgments instead of prose, offline by default. It has 52 GitHub stars.
jevcore's catalog security scan is still queued. You can run an instant dependency and prompt-injection check now with the "Scan for vulnerabilities" button above.
Clone the repository with "git clone https://github.com/PerryLink/jevcore" and add it to your Claude Code skills directory (see the Installation section above).
jevcore is primarily written in TypeScript. It is open-source under PerryLink on GitHub, so you can review or fork the full source.
Yes. SkillsLLM lists many other AI Agents skills you can browse and compare side by side. Open the AI Agents category from the badge at the top of this page, or use the Related Skills and comparison links further down to weigh jevcore against similar tools.
No comments yet. Be the first to share your thoughts!
⚠️ Third-Party Software Notice
This skill is third-party open-source software developed and hosted independently on GitHub. SkillsLLM is an informational directory and does not control or maintain the underlying repository.
Any security checks, ratings, or warnings displayed by SkillsLLM are automated and limited in scope. They do not constitute a security certification or guarantee that the software is safe, error-free, or free from malicious code, vulnerabilities, compromised dependencies, or prompt-injection risks.
Review the source code, permissions, dependencies, and configuration before installing or running any third-party skill. Use is at your own risk. To the maximum extent permitted by applicable law, SkillsLLM is not liable for losses arising from third-party software.
The deep catalog scan for this skill is still queued. Run an instant dependency check now instead.
TypeSafe Jev for DeepSeek Harness and any other MCP host.
Jev is not a chat model. It answers typed questions — noul (yes/no), choice, score — and returns
calibrated probabilities. It does not write prose, and asking it to is a category error. This project
gives an agent exactly that surface, and nothing more.
Offline by default. Egress disclosed. Nothing default-on.
这个插件是 DSH 插件家族的一员(40+ 个,全部 Apache-2.0)。如果你在用,给个 star —— 它不会解锁任何功能,但会让下一个人在搜索里更容易找到它。
English: part of a 40+ plugin family for DeepSeek Harness. If it is useful, a star helps the next person find it — nothing is gated behind it.
| Package | What it is | Use it when |
|---|---|---|
jevcore |
The decisions. Imports nothing from DeepSeek Harness or Cordis. | You want Jev in a plain script, a service, or your own harness |
jevcore-dsh |
The DSH plugin: one service, three tools, two opt-in gates | You are running DeepSeek Harness |
jevcore-mcp |
The same three tools over MCP, with a stdio binary | Your host speaks MCP but is not DSH |
The adapters are thin on purpose. packages/dsh is four files: it declares tool schemas and
translates hook payloads. Everything decision-shaped — the primitives, the providers, the egress
contract, the policy, the gates — lives in core, so a new adapter cannot drift from the guarantees
the others make.
One runtime requirement differs across the three: jevcore-dsh tracks the harness and needs
Node ^22.19.0 || >=24.0.0, while jevcore and jevcore-mcp need >=20.
Between 2026-09-17 and 09-20, nineteen plugins appeared that wire Jev into DSH. Auditing their source found a consistent pattern: the module labelled guard, gate, or warden was also the module shipping prompts, tool arguments, and file contents to a third party, and the README generally did not say so. Several were enabled by default. One gate could be reconfigured by the model it was guarding.
This project is the same idea with those failure modes designed out:
| Property | How it is guaranteed here |
|---|---|
| No network call unless you ask for one | Default provider is an offline mock; the live path needs both provider: live and a resolved credential |
| Every transmission named before it happens | One startup log line per feature: off or SENDS <feature> { fields } |
| Gates register nothing when disabled | Verified by test, not by policy — a disabled gate adds no event listener at all |
| The model cannot widen its own constraints | No tool exposes gate configuration |
| A judge that cannot answer never means "allow" | Undecided resolves through explicit config, defaulting to ask |
This is the part worth reading before installing.
Transmission is decided per feature, and every feature defaults to off. The plugin prints its own contract at load:
[jevcore] provider=mock endpoint=none egress=OFF (no network calls will be made; every answer is synthetic)
[jevcore] ready - provider=mock - gates: safety=off context=off
With provider: live and every feature enabled, the same report becomes explicit about what leaves:
[jevcore] provider=live endpoint=https://api.typesafe.ai egress=ON
[jevcore] SENDS tool:jev_ask { state<=16000c questions<=4000c }
[jevcore] SENDS tool:jev_rank { state<=16000c questions<=4000c }
[jevcore] SENDS tool:jev_check { state<=16000c questions<=4000c }
[jevcore] SENDS gate:safety { state<=8000c questions<=2000c }
[jevcore] SENDS gate:context { state<=6000c questions<=2000c }
[jevcore] redaction is best-effort; it removes named fields and known secret shapes, and cannot
recognise an unrecognised secret in free text
| Feature | Off by default? | What it sends |
|---|---|---|
tool:jev_ask |
runs when the model calls it | the arguments the model passed, after redaction |
tool:jev_rank |
runs when the model calls it | the query plus every candidate |
tool:jev_check |
runs when the model calls it | the claim and its evidence |
gate:safety |
yes — explicit opt-in | the tool name, its arguments, the workspace root |
gate:context |
yes — explicit opt-in | a large tool result the agent just received |
The tools transmit only when the model chooses to call them, which is visible in the transcript. The gates would run on every matching tool call, which is not, so they are opt-in.
Before anything is sent, src/redact.ts runs two passes: values under sensitive field names
(password, token, apiKey, authorization, …) are replaced wholesale, and secret-shaped strings
that survive into free text are pattern-matched (Bearer …, sk-…, ts_live_…, AWS/GitHub/Google
key shapes, JWTs, private-key headers, credentials in connection strings).
This is a mitigation, not a permission. A secret that sits under an unrecognised key name and does not match a known shape will pass through. If that possibility is unacceptable for your workload, do not enable the live provider.
dsh plugin --profile <profile> add jevcore-dsh
Or from a checkout:
dsh plugin --profile <profile> add /absolute/path/to/jevcore/packages/dsh
packages/dsh imports jevcore by name, so a checkout also needs core
resolvable from the profile (add /absolute/path/to/jevcore/packages/core).
Then confirm the row activated — the plugin list should show jev as active,
not failed — and check the startup report in the log.
For a host that speaks MCP, the same three tools are available over stdio:
npx -y jevcore-mcp
To wire it into DeepSeek Harness specifically, install a configuration-only bundle whose patch inserts the harness's own MCP client:
- insert:
- id: jev-mcp
name: '@deepseek-ai/dsh-mcp-client'
config:
serverName: jev
transport: stdio
command: npx
args: ['-y', 'jevcore-mcp']
env:
TYPESAFE_API_KEY: '<the key>'
failOnStartupError: true
The env map is not optional: DSH strips every credential-shaped name — anything containing KEY, PASSWORD, SECRET or TOKEN, in any case — from the environment it hands a spawned server, then merges this map back in afterwards. A key exported in your shell never arrives, and the server stays on the offline mock without reporting an error.
The provider is chosen from the environment:
| Variable | Effect |
|---|---|
TYPESAFE_API_KEY |
Selects the TypeSafe route when present |
OPENROUTER_API_KEY |
Selects the OpenRouter route when present and no TypeSafe key is set |
JEV_PROVIDER |
mock, live, or openrouter — overrides the heuristic above |
TYPESAFE_MODEL / OPENROUTER_MODEL |
Model id for the selected route |
TYPESAFE_BASE_URL / OPENROUTER_BASE_URL |
API root for the selected route |
With neither key it stays on the offline mock. Unlike the plugin, the MCP server
resolves its credential once at startup, so a missing key with
JEV_PROVIDER=live is a startup error rather than a per-call surprise.
Its egress report goes to stderr, never stdout — on a stdio transport stdout is the protocol channel, and a stray line there would corrupt the stream.
There are two routes to Jev. Both call the same models and both return the same typed answers; they differ in who holds your credential and whose servers see your state.
TypeSafe directly — use this if you have a key from console.typesafe.ai:
- insert:
- id: jev
name: 'jevcore-dsh'
config:
provider: live
apiKeyRef: TYPESAFE_API_KEY # a reference, never the key
model: jev-latest
Through OpenRouter — use this if a TypeSafe key is impractical and you
already have an OpenRouter key. OpenRouter serves the
System One models at the same POST /v1/systemone path TypeSafe does, one level
below its own API root, so this is the documented route to Jev rather than an
approximation of it:
- insert:
- id: jev
name: 'jevcore-dsh'
config:
provider: openrouter
openRouterApiKeyRef: OPENROUTER_API_KEY
model: jev-latest # a bare `jev-*` id, or `typesafe/jev-1.13`
The route is reached by pointing the official @typesafe-ai/sdk at
https://openrouter.ai/api with your OpenRouter key — OpenRouter's own
documented integration, so there is no second client to keep in step.
Two things to know about the OpenRouter route:
usage.costUsd
is populated here and absent there.The model id must be a System One one. jev-latest bare is the default and needs
no prefix; typesafe/ is accepted on a versioned id such as `typesa