Communitygithub.com

zimodzh/dsh-plugin-dev-skills

Una habilidad de Agente para desarrollar plugins de DeepSeek Harness (DSH): el estándar para plugins/servicios/eventos/herramientas/adaptadores LLM/empaquetado e instalación. Funciona con Claude Code, Codex, DSH, VS Code Copilot y cualquier agente compatible.

¿Qué es dsh-plugin-dev-skills?

Esta habilidad establece el estándar único y autorizado para desarrollar plugins de DeepSeek Harness (DSH). Consolida las convenciones dispersas en la documentación oficial de DSH (tutoriales, manuales de referencia y guías de generación) en flujos de trabajo ejecutables, reglas estrictas y listas de verificación. Como todo en DSH es un plugin (adaptadores de modelo, registro de herramientas, registros de sesión e incluso el propio bucle del agente), esta habilidad garantiza que los desarrolladores extiendan DSH siguiendo su propia arquitectura. Es compatible con Claude Code, DSH, Codex, VS Code Copilot y cualquier agente compatible. La habilidad cubre escenarios como el desarrollo de plugins desde cero, la adición de herramientas para modelos, la creación de capacidades reemplazables (con los roles Definición/Proveedor/Consumidor), la integración de nuevos proveedores de modelos LLM, el empaquetado e instalación de plugins, y el trabajo dentro del monorepo de DSH. Proporciona reglas estrictas para el manejo de dependencias, configuración, registro de eventos y gestión de efectos secundarios, junto con referencias detalladas para cada aspecto técnico.

Compatible con✓Claude Code✓Codex CLI~Cursor
npx skills add zimodzh/dsh-plugin-dev-skills

Preguntar en tu IA favorita

Abre un nuevo chat con esta habilidad de agente ya precargada.

Documentación

Estándar de desarrollo de plugins DSH

Esta habilidad es el estándar único para desarrollar plugins de DeepSeek Harness (DSH): unifica las convenciones dispersas en la documentación oficial de DSH (tutoriales, manuales de referencia y directorios generados) en flujos de trabajo ejecutables, reglas estrictas y listas de verificación. Todo en DSH es un plugin (adaptadores de modelo, registro de herramientas, registros de sesión e incluso el bucle del agente), por lo que actuar según esta habilidad es extender DSH según su propia arquitectura.

Alcance

  • Desarrollo de plugins DSH dentro de un repositorio, basados en archivos: escribir paquetes de plugins, registrar líneas cordis.yml, parches overlay, desarrollar herramientas, conectar modelos, empaquetar e instalar.
  • El desarrollo de paquetes workspace dentro del monorepo de DSH (packages/<group>/<pkg>) también está cubierto por esta habilidad (references/workspace-package.md).
  • Esta habilidad no cubre: plugins dinámicos en sesión (flujos cordis_define/cordis_run) ni edición de combinaciones de presets de agente; estos son cubiertos por habilidades especializadas de cada despliegue o por herramientas oficiales.

Reglas estrictas (obligatorias en cualquier escenario)

  1. La interfaz se rige por la referencia generada. Los nombres de servicios, métodos públicos, firmas de eventos y claves ctx se basan en las páginas de subsistemas generadas automáticamente y en las interfaces TypeScript del repositorio; no inferir la API completa a partir de nombres de servicio, ejemplos o código antiguo, ni mantener una lista estática separada.
  2. Todas las contribuciones son efectos secundarios. Todo lo que se registre a través de ctx (escucha de eventos, herramientas, adaptadores, ctx.effect) se revierte automáticamente al descargar el plugin; no crear efectos secundarios a nivel de proceso o página en el ámbito del módulo; para suscripciones de terceros que no devuelvan un disposer, averiguar activamente el mecanismo de limpieza.
  3. Los listeners waterfall deben llamar a next(). No llamar a next() provoca un cortocircuito intencionado aguas abajo (para interceptación/gateway), no es opcional.
  4. Fallar de forma ruidosa. Si apply lanza una excepción, el proceso termina; si la validación de configuración falla, se debe reportar el error explícitamente; el esquema (schema) debe expresar restricciones completas, no tragar errores silenciosamente en tiempo de ejecución.
  5. Declarar dependencias obligatorias con inject, dependencias opcionales con ctx.get() y comprobación de nulidad. No usar inject para evitar la comprobación de undefined; tampoco acceder directamente a ctx.xxx sin declarar la inyección: los servicios no declarados pueden evaluarse como undefined a través del resolvedor de servicios.
  6. La configuración siempre usa Schemastery. Exportar interface Config y un Schema con el mismo nombre; los valores predeterminados se escriben en el schema; no exportar objetos simples como Config; todos los parámetros que puedan variar entre despliegues deben estar en la configuración.
  7. La ejecución de herramientas devuelve valores JSON estándar, no bloques de contenido. El texto legible por humanos se coloca en output.render; las estrategias de despliegue y los hooks no deben integrarse dentro de la herramienta.
  8. Lo que el modelo ve ya está registrado. Cualquier entrada nueva visible para el modelo debe residir en un mecanismo que pueda reconstruirse a partir de los registros de sesión (nuevos eventos persistentes o mediante agent.inject()), con aserciones de invariantes en tiempo de ejecución.
  9. Priorizar ctx.connection.rpc para paneles de configuración npm. Los paneles semiantendidos del navegador que llaman a métodos del proceso principal deben priorizar Connection RPC (ctx.connection.rpc.handle + ctx.connection.rpc.call); la plantilla está en references/connection-rpc.md. Prohibido el uso de @Remote sin envoltura, manifiestos typert escritos a mano, o createRequire colgando del código fuente de harness. Siguen siendo válidas las rutas generadas por Typert generator y exportadas como ./typert + ./remote en package.json, consumidas por ctx.remote.$mount().

Flujo de trabajo estándar

Escenario A: Crear un nuevo plugin

  1. Determinar qué aporta el plugin (¿servicio? ¿herramienta? ¿escucha?), usar la tabla de «Ubicación de nuevo comportamiento» en references/seams.md para seleccionar el mecanismo.
  2. Crear src/<name>.ts, exportar name, inject (opcional), apply(ctx, config?). Escribir primero como función; cambiar a la forma de clase Service cuando se necesite exponer un servicio.
  3. Bucle de desarrollo local (checkout del código fuente):
mkdir -p scratch-plugin/src
# scratch-plugin/cordis.yml —— patch overlay; la ruta del plugin debe ser absoluta
- insert:
    - id: hello
      name: '/ruta/absoluta/hacia/deepseek-harness/scratch-plugin/src/mi-plugin.ts'
pnpm dsh web --patch ./scratch-plugin/cordis.yml   # abrir http://127.0.0.1:3080
  1. Verificar carga y descarga: el registro de inicio aparece, los recursos se limpian al detener (references/plugin-anatomy.md).

Escenario B: Añadir una herramienta a un modelo

  1. inject: ['tools'], usar defineTool para definir (name/description/parameters/output/execute).
  2. Implementar según las convenciones de execute en references/tools.md: schema DSL para declarar parámetros y salida, execute devuelve valores estándar, respeta exec.signal, opcionalmente presentationMeta/tarjetas UI.
  3. Cuando se necesiten estrategias, colgarlas de eventos tools/* (pre-execute/guard/execute/post-execute/result), no incrustar la estrategia en la herramienta (ejemplo de control de acceso en references/plugin-forms.md).
  4. Reiniciar y verificar la invocación real por parte del modelo.

Escenario C: Capacidad reemplazable (múltiples proveedores)

  1. Según references/three-roles.md, dividir en tres paquetes: Definition / Provider / Consumer (fusionar roles según sea necesario, no dividir de forma preventiva).
  2. Definition posee los tipos Request/Result y el Service abstracto; Provider implementa; Consumer expone como herramienta o consumidor de servicio.
  3. En cordis.yml, listar solo las líneas de Provider y Consumer; cambiar de proveedor solo reemplaza una línea.

Escenario D: Conectar un nuevo proveedor de modelo

  1. Heredar de LlmAdapter e implementar stream(), emitir fragmentos según el protocolo StreamChunk; errores con LlmError con código estable (o terminar en banda con finish { kind: 'error' | 'aborted' }); cada solicitud HTTP debe combinar attributionHeaders() y pasar signal.
  2. ctx.llm.registerAdapter(['<provider>'], adapter); opcionalmente sobrescribir resolveModel()/listModels().
  3. En la composición, configurar provider/model del agente-loop para verificar. Ver detalles en references/llm-adapter.md (incluye 7 obligaciones de protocolo).

Escenario E: Empaquetado e instalación para entrega

  1. Crear paquete de composición: package.json declara dsh.bundle (apuntando a cordis.patch.yml), las líneas de parche referencian el plugin por nombre de paquete; los paquetes de biblioteca solo para importación no declaran dsh.bundle.
  2. Instalación: dsh plugin --profile <name> add <pkg>; primero ejecutar dsh --profile <name> --dump-config para verificar las capas, luego iniciar.
  3. Recordar el orden de las capas y la semántica de reemplazo de líneas completas (references/packaging.md).

Escenario F: Crear un nuevo paquete dentro del monorepo de DSH

Seguir la lista de verificación archivo por archivo en references/workspace-package.md: crear el paquete (package.json invariantes/tsconfig/src/README) → registrar en la configuración raíz → topología y nomenclatura del paquete (tabla de roles) → estructura README Model Experience → comandos de verificación.

Consulta rápida de decisiones

Quiero…MecanismoDetalles
Exponer capacidad a otros pluginsService (forma de clase)references/services.md
Consumir una capacidad existenteinject o ctx.get()references/services.md
Comunicación entre plugins / puntos de extensiónctx.on / ctx.emit y otros eventos (cinco modos de distribución)references/events.md
Hacer que el usuario pueda configurarConfig + Schemasteryreferences/config.md
Añadir capacidad a un modelodefineTool → ctx.tools.register (o JSON Schema sin procesar)references/tools.md
Conectar nuevo proveedor de modeloLlmAdapter + ctx.llm.registerAdapterreferences/llm-adapter.md
Dividir capacidades reemplazablesTres roles (Definition/Provider/Consumer)references/three-roles.md
Distribuir un pluginPaquete de composición + profilereferences/packaging.md
Consultar servicios integrados / ubicaciónDirectorio seam, mapeo de arquitecturareferences/seams.md
Ámbito/Almacenamiento de servicios/Fiber APIctx.extend/isolate/provide/mixin, fiber.*references/context-api.md
Hooks / UI / Paneles / Plugins puente de protocoloCinco formas de extensión + mapeo funcionalidad→mecanismoreferences/plugin-forms.md
Panel semiantendido del navegador llamando al proceso principalctx.connection.rpc.handle/call, endpoint + sobrereferences/connection-rpc.md
Crear un nuevo paquete dentro del repositorio / nomenclaturaLista de workspace + tabla de rolesreferences/workspace-package.md

Lista de verificación antes de finalizar

  • Interfaz verificada contra la referencia generada (servicios/eventos/claves ctx basadas en lo generado), no adivinar la API por el nombre.
  • Todo el registro se realiza a través de ctx (eventos/herramientas/adaptadores/ctx.effect), se puede limpiar al descargar; la limpieza sensible al orden se coloca en el mismo ctx.effect.
  • Dependencias obligatorias declaradas correctamente con inject; dependencias opcionales con manejo de undefined.
  • Si el plugin tiene configuración: Config usa Schemastery, los valores predeterminados están en el schema, la configuración inválida falla ruidosamente al cargar.
  • Si tiene herramientas: execute devuelve valores JSON estándar; render se encarga de lo legible por humanos; las estrategias van por eventos tools/*; respeta exec.signal; declara isConcurrencySafe para concurrencia segura (no declarado → exclusivo).
  • Si tiene listener waterfall: llama y devuelve next() (a menos que sea un cortocircuito intencionado).
  • Si tiene adaptador LLM: protocolo StreamChunk completo (pares de fragmentos, index según primera aparición, usage antes de finish, arguments como cadena JSON sin procesar); errores por una de las dos rutas legales; lanza UNSUPPORTED para campos no soportados; envía finish.replayState si necesita reproducción nativa; pasó attributionHeaders y signal.
  • Líneas de composición y orden de capas correctos; las nuevas líneas son visibles en --dump-config; sin registros residuales tras HMR/reinicio.
  • Si el contenido visible por el modelo cambia: reside en un mecanismo que puede reconstruirse desde los registros.
  • Panel semiantendido del navegador: priorizar ctx.connection.rpc.handle/call; prohibido @Remote sin envoltura, manifiesto typert escrito a mano, createRequire colgando de harness; siguen siendo válidos los artefactos de Typert generator completo + ./typert + ./remote.
  • Nuevo paquete workspace: invariantes de package.json, un solo aggregate, nomenclatura acorde a la tabla de roles, README con estructura Model Experience, y constraints/typecheck/lint/build/hygiene todo en verde.

Archivos de referencia (cargar según sea necesario, no leer todos a la vez)

El índice completo y la tabla de «cuándo leer» están en references/README.md.

  • references/plugin-anatomy.md —— Leer al escribir/modificar un plugin, manejar el ciclo de vida o HMR.
  • references/services.md —— Leer al definir o consumir un servicio, o inyectar dependencias.
  • references/events.md —— Leer al usar eventos para comunicación o escuchar puntos de extensión.
  • references/config.md —— Leer al hacer que un plugin sea configurable.
  • references/context-api.md —— Leer al usar ámbito, almacenamiento de servicios o Fiber API.
  • references/three-roles.md —— Leer al dividir capacidades reemplazables.
  • references/tools.md —— Leer al desarrollar herramientas para modelos.
  • references/llm-adapter.md —— Leer al conectar un nuevo proveedor de modelo.
  • references/plugin-forms.md —— Leer al escribir hooks, UI o plugins puente de protocolo.
  • references/connection-rpc.md —— Leer cuando un panel de configuración npm necesite llamar a métodos del proceso principal; también al encontrar @Remote sin envoltura, manifiesto escrito a mano o createRequire como puente de código fuente.
  • references/packaging.md —— Leer al empaquetar, instalar o entregar un plugin.
  • references/workspace-package.md —— Leer al crear un nuevo paquete dentro del monorepo.
  • references/seams.md —— Leer al consultar servicios integrados, ubicación o mapeo de arquitectura.

Verificación

  • Autocomprobación de formato: name en kebab-case y coincide con el nombre del directorio; description no vacío y conciso (esta habilidad se mantiene dentro de 500 caracteres); el cuerpo usa Markdown estándar; todos los archivos references referenciados existen realmente.
  • Nomenclatura del directorio: El nombre de esta habilidad (name) es dsh-plugin-dev, que es diferente del nombre del repositorio dsh-plugin-dev-skills: al clonar/descomprimir, la carpeta debe renombrarse a dsh-plugin-dev (coincidiendo con name), de lo contrario, los cargadores que se dirigen por nombre de directorio podrían no encontrar esta habilidad.
  • En entornos con CLI skills-ref: ejecutar skills-ref validate ./dsh-plugin-dev.
  • Regresión: después de modificar description, ejecutar el conjunto de evaluación evals/trigger-queries.json (método en evals/README.md del repositorio).
  • Verificación de comportamiento: completar un plugin mínimo según el Escenario A (registro de carga + limpieza de descarga), y luego una herramienta greet según el Escenario B.

Skills relacionados