SSD Nodes Learn 🎉 VPS da $5.50/mese
Guide Matt ConnorDi Matt Connor · Aggiornato 2026-08-21

Configurare dsh: chiavi API, modelli ed endpoint

Scopri dove dsh salva la configurazione su Linux, come usare una chiave DeepSeek o un endpoint Ollama locale e quali dati escono dal PC in ogni modalità.

Dove dsh conserva la configurazione

dsh (DeepSeek Harness) conserva la configurazione in una sola directory: $DSH_HOME, che per impostazione predefinita è ~/.dsh. Tutto ciò che si imposta nella Web UI viene scritto lì come file di testo semplice. Copiando questa directory su un altro server, il nuovo sistema si comporta come quello originale.

Quattro percorsi contengono tutti gli elementi che verranno modificati.

  • ~/.dsh/settings.yaml contiene le impostazioni scritte manualmente e tramite la UI, inclusi i percorsi dei provider e dei modelli.
  • ~/.dsh/.credentials.yaml contiene i secret. Le impostazioni conservano solo un riferimento a una credenziale, quindi il valore della chiave si trova in un unico file.
  • ~/.dsh/profiles/ contiene i profili denominati, mentre ~/.dsh/storages/ contiene le sessioni salvate.
  • ~/.dsh/cordis.patch.yml è il livello di override personalizzato. Viene applicato alla configurazione integrata per ogni profilo.

DeepSeek ha presentato l'harness come developer preview con licenza MIT il 17 August 2026 e il README specifica che sono previste modifiche che possono interrompere la compatibilità. I nomi dei campi e i percorsi riportati in questa guida corrispondono alla documentazione del repository disponibile ad August 2026. Prima di copiare la configurazione da una guida, inclusa questa, confrontali con la documentazione della versione installata, perché una preview può rinominare gli elementi tra una release e l'altra.

Il minimo onesto per ottenere il primo output

dsh richiede Node.js 22.19 o una versione successiva della serie 22, oppure la versione 24 o successiva. Node 23 non rientra in questo intervallo. Controlla prima la versione, perché una versione incompatibile causa un errore all'avvio che può sembrare dovuto a un pacchetto danneggiato.

node -v
npx @deepseek-ai/dsh web

npx scarica il pacchetto dal registro npm e avvia l'interfaccia Web su http://127.0.0.1:3080. Si associa all'indirizzo di loopback, quindi la porta non è raggiungibile da un'altra macchina anche se il firewall la consente. Su un VPS, inoltrala tramite SSH invece di aprire la porta 3080 a Internet.

ssh -N -L 3080:127.0.0.1:3080 you@your-server

Apri http://127.0.0.1:3080 sul laptop, quindi vai a Settings e Models. La scheda DeepSeek contiene un solo campo per la chiave API. Incolla la chiave ottenuta da platform.deepseek.com e salvala. Il percorso del modello diventa immediatamente utilizzabile, senza riavvio, perché il server in esecuzione memorizza la credenziale e risolve il riferimento al momento dell'utilizzo. Raggiungere l'interfaccia Web di dsh su un server remoto descrive il caso del tunnel e del reverse proxy, mentre installare DeepSeek Harness su un VPS descrive la preparazione del server presupposta da questa guida.

Dopo il salvataggio, controlla ciò che ha creato l'applicazione.

ls -la ~/.dsh
stat -c '%a %n' ~/.dsh/.credentials.yaml

Dovresti vedere settings.yaml, .credentials.yaml e profiles/. Se stat restituisce una modalità diversa da 600, esegui chmod 600 ~/.dsh/.credentials.yaml. Un file delle credenziali leggibile dal gruppo o da tutti gli utenti espone la chiave a ogni altro account del server.

Per la prima esecuzione senza browser basta un comando.

npx @deepseek-ai/dsh --profile headless "summarise the files in this directory"

Il profilo headless esegue una singola sessione e stampa la risposta finale.

Variabili d'ambiente o file di configurazione

Esistono due modi per fornire una chiave a dsh, ma non sono intercambiabili.

Un provider del catalogo (DeepSeek, Anthropic, OpenAI e gli altri provider inclusi nell'elenco predefinito) riceve la chiave dalla pagina Models. Il valore viene inserito in ~/.dsh/.credentials.yaml e le impostazioni contengono soltanto un riferimento alla chiave. Dopo il salvataggio, la Web UI non mostra più la chiave.

Un provider personalizzato può invece indicare una variabile d'ambiente tramite apiKeyEnv. Questa è la struttura riportata nella documentazione per ~/.dsh/settings.yaml.

llm-pi-ai:
  providers:
    my-gateway:
      apiKeyEnv: GATEWAY_API_KEY
      api: openai-completions
      baseURL: https://gateway.example/v1
      models:
        - id: legacy-chat
        - id: vision-preview
          input: [text, image]

Aggiungi prima un provider tramite la Web UI, quindi apri ~/.dsh/settings.yaml e copia la struttura generata. Durante un'anteprima per sviluppatori, la struttura annidata è l'elemento più soggetto a modifiche e il file appena generato dall'applicazione è sempre aggiornato.

apiKeyEnv viene letto dall'ambiente del processo dsh, non dalla shell di login. Una chiave esportata in una sessione interattiva non è visibile a un'unità systemd. Di conseguenza, la stessa configurazione che funziona quando esegui manualmente dsh web restituisce MISSING_CREDENTIAL tramite un servizio. Fornisci all'unità un file dedicato.

[Service]
EnvironmentFile=/etc/dsh/dsh.env

Imposta per questo file i permessi 600 e assegnane la proprietà all'utente con cui viene eseguito il servizio.

Scelta dei modelli e ID che non può essere rinominato

Ogni provider configurato appare nel selettore dei modelli. La selezione di un modello lo imposta anche come predefinito per le nuove sessioni. Le sessioni già esistenti mantengono il modello registrato al loro interno, quindi il cambio non modifica le conversazioni precedenti.

Il Provider ID è permanente. Le richieste, le sessioni salvate, i modelli predefiniti e i riferimenti alle credenziali puntano tutti a questo ID, quindi non è disponibile alcun pulsante per rinominarlo. Per cambiarlo, è necessario creare un nuovo provider ed eliminare quello precedente. Scegli un nome che possa restare valido nel tempo: local-ollama invece di test2.

I modelli sono di tipo solo testo, salvo diversa dichiarazione. Aggiungi input: [text, image] a una voce del modello per dichiarare il supporto alle immagini oppure imposta defaultInput a livello di route come fallback per i modelli non descritti dal catalogo. La route chat-completions di DeepSeek supporta esclusivamente il testo e non può essere configurata diversamente, quindi un'immagine allegata a quella route viene rifiutata prima dell'invio.

Indirizzare dsh a un endpoint locale per mantenere il codice sul server

Ollama espone un'API compatibile con OpenAI su http://127.0.0.1:11434/v1. dsh può utilizzare qualsiasi URL di base compatibile con OpenAI tramite un provider personalizzato, quindi i due componenti comunicano direttamente. Configurare prima il server del modello: self-hosting di un LLM con Ollama su un VPS descrive l'installazione e il download del modello.

Verificare che l'endpoint risponda prima di modificare dsh.

ollama list
curl -s http://127.0.0.1:11434/v1/models

ollama list stampa il tag esatto di ogni modello scaricato. Copiare questa stringa. curl restituisce gli stessi modelli in formato JSON. Un elenco vuoto indica che Ollama è in esecuzione ma non contiene modelli scaricati. Connection refused indica che Ollama non è in esecuzione oppure non è in ascolto sulla porta 11434.

A questo punto aggiungere il provider. Ollama richiede il campo della chiave API, ma ne ignora il valore. È quindi sufficiente usare una stringa non vuota.

llm-pi-ai:
  providers:
    local-ollama:
      apiKeyEnv: OLLAMA_API_KEY
      api: openai-completions
      baseURL: http://127.0.0.1:11434/v1
      models:
        - id: <the exact tag printed by ollama list>

Esportare la variabile nell'ambiente in cui sarà visibile al processo dsh.

sudo install -d -m 700 /etc/dsh
printf 'OLLAMA_API_KEY=ollama\n' | sudo tee /etc/dsh/dsh.env
sudo chmod 600 /etc/dsh/dsh.env

Tre errori coprono quasi tutti i tentativi non riusciti. MISSING_CREDENTIAL indica che dsh non è riuscito a leggere la variabile indicata da apiKeyEnv. Controllare quindi l'ambiente del processo, non quello del terminale. UNKNOWN_MODEL indica che id non corrisponde a un modello configurato. Confrontarlo con ollama list carattere per carattere, incluso il tag dopo i due punti. Un errore 401 durante il recupero dei modelli disponibili proviene dal rilevamento dei modelli, che richiama GET /models sull'URL di base. Gli endpoint che non espongono questo percorso richiedono l'inserimento manuale dei modelli.

Un altro problema comune riguarda l'URL di base. Lasciare /v1 fuori dall'URL fa sì che le richieste raggiungano percorsi non gestiti da Ollama. La chiamata restituisce quindi un errore 404 e il modello non viene eseguito. Il suffisso fa parte dell'interfaccia compatibile con OpenAI e non è un elemento decorativo.

Se Ollama viene eseguito su un'altra macchina, l'indirizzo di quella macchina diventa l'URL di base. I prompt attraversano quindi la rete in chiaro tramite HTTP semplice. Mantenere Ollama sullo stesso host oppure proteggerlo con TLS (Transport Layer Security) e autenticazione: proteggere un endpoint Ollama esposto.

Cosa lascia la macchina in ciascuna modalità

Con una chiave DeepSeek, ogni richiesta viene inviata all'API di DeepSeek. La richiesta contiene il prompt, il contenuto dei file letti dall'agente per elaborare la risposta, l'output dei comandi eseguiti e gli eventuali risultati degli strumenti che l'agente decide di includere. Il codice sorgente rientra in questo payload ogni volta che l'agente apre un file. Questo è il funzionamento di un modello ospitato ed è il motivo per cui è importante valutare in quale directory avviare l'agente.

Con un altro provider del catalogo o con un gateway aziendale, lo stesso payload viene inviato a quel fornitore. L'URL di base indica esattamente la destinazione.

Con un endpoint locale, la richiesta al modello viene inviata a 127.0.0.1:11434 e resta sul computer. Nessuna parte del codice raggiunge un fornitore di modelli. Tuttavia, tre tipi di traffico attraversano ancora la rete. npx scarica il pacchetto dal registro npm. Qualsiasi strumento eseguito dall'agente può accedere autonomamente a Internet, inclusi i server MCP (model context protocol) collegati, descritti in dettaglio in eseguire server MCP su un VPS. Inoltre, può essere trasmessa la telemetria, se la abiliti.

La telemetria è disabilitata finché non esprimi il consenso. DSH_TELEMETRY_MODE è l'interruttore del consenso; i valori non impostati, vuoti o non riconosciuti vengono interpretati come DISABLED. In questo stato dsh non crea alcun provider, processore o exporter OpenTelemetry (OTel), quindi un profilo nuovo non effettua alcuna richiesta di rete per la telemetria. FEEDBACK_ONLY abilita la condivisione dei log di sessione attivata dal feedback. FULL abilita anche la reportistica del launcher. Il flusso della sessione può esportare contenuti della sessione, dati degli strumenti, prompt e percorsi dell'area di lavoro; considera quindi FULL come l'invio del tuo lavoro a DeepSeek.

Per un blocco completo che non dipende dall'impostazione corretta della stringa della modalità, imposta DSH_TELEMETRY_DISABLED=1. Qualsiasi valore non vuoto costituisce un'esclusione esplicita e viene letto prima dell'avvio dell'esecuzione; il codice del progetto non può quindi riattivare la telemetria durante la sessione. L'indirizzo predefinito del collector è harness-telemetry.deepseeksvc.com. È utile conoscerlo quando analizzi i log del firewall.

Verifica l'impostazione invece di considerarla affidabile. Con un'attività in esecuzione, elenca le connessioni in uscita mantenute dal processo.

sudo ss -tnp | grep -i node

Nella modalità con modello locale dovresti vedere la connessione di loopback a 11434 e nessuna connessione verso un indirizzo pubblico. Qualsiasi altra connessione deve essere identificata prima di proseguire. Cosa invia un agente di coding all'esterno esegue lo stesso controllo su altri harness e spiega come interpretare il risultato.

Dove non devono essere memorizzati i secret

  • Cronologia della shell. export DEEPSEEK_API_KEY=sk-... viene scritto in ~/.bash_history in testo in chiaro e resta lì molto tempo dopo la rotazione della chiave. Anteponi uno spazio al comando quando è impostato HISTCONTROL=ignorespace oppure evita la shell e scrivi il valore direttamente in un file con modalità 600.
  • File dot versionati. Una chiave in ~/.bashrc o ~/.zshrc è a un solo git add di distanza da un repository pubblico se gestisci i file dot con git. Esegui git grep -I -n 'sk-' in quel repository prima del push.
  • settings.yaml. Usa apiKeyEnv per i provider personalizzati, in modo che il file contenga il nome di una variabile invece di un secret. I file di configurazione vengono incollati nei report dei problemi e nelle chat di supporto. I file delle credenziali no.
  • Output di env e screenshot del terminale. Qualsiasi comando che stampa l'intero ambiente stampa anche la chiave.
  • Backup. Vale la pena salvare ~/.dsh, ma .credentials.yaml al suo interno è un secret attivo. Escludi quel file oppure cifra l'archivio.

Queste regole non sono specifiche di dsh e tenere i secret fuori dai file env di Compose affronta lo stesso problema sul lato dei container dello stesso server.

Gestire una developer preview

Blocca la versione che hai testato, perché una preview può modificare una chiave di configurazione in una patch release e impedire al provider di caricarsi. Mantieni settings.yaml e cordis.patch.yml sotto controllo versione, escludendo il file delle credenziali, così puoi verificare cosa è cambiato dopo un aggiornamento.

Due flag sono utili quando un profilo non si comporta come previsto. --dump-default-config stampa la configurazione predefinita composta senza avviare il servizio, mentre --dump-config stampa nello stesso modo la configurazione composta del profilo. Il confronto mostra quali modifiche ha effettivamente apportato il tuo livello di override ed è più rapido che esaminare manualmente i vari livelli.

dsh --profile web --dump-config

Quando qualcosa si rompe dopo un aggiornamento, esegui prima questo comando. Una chiave spostata tra una release e l'altra compare nel dump come ramo mancante e la correzione consiste in una modifica di una sola riga, non nella reinstallazione.

FAQ

Dove archivia dsh la mia chiave API di DeepSeek?

In $DSH_HOME/.credentials.yaml, che corrisponde a ~/.dsh/.credentials.yaml se non imposti personalmente DSH_HOME. La pagina Models scrive la chiave in quel file e le impostazioni contengono soltanto un riferimento, quindi il secret resta concentrato in un unico file. Verifica i permessi con stat -c '%a %n' ~/.dsh/.credentials.yaml e impostali su 600 se sono meno restrittivi. Un provider personalizzato può evitare del tutto il file indicando una variabile d'ambiente con apiKeyEnv.

Come posso configurare dsh per usare un modello locale invece dell'API di DeepSeek?

Aggiungi un provider personalizzato il cui URL di base punti al tuo endpoint locale compatibile con OpenAI. Per Ollama è http://127.0.0.1:11434/v1, con api: openai-completions e un modello id copiato esattamente da ollama list. Ollama richiede un valore per la chiave API, ma lo ignora, quindi è sufficiente qualsiasi stringa non vuota. Verifica che l'endpoint risponda con curl -s http://127.0.0.1:11434/v1/models prima di modificare la configurazione di dsh, perché un endpoint non raggiungibile e una configurazione errata producono errori simili.

dsh invia il mio codice altrove per impostazione predefinita?

Con un modello ospitato, sì. Il prompt e il contenuto dei file letti dall'agent vengono inclusi nella richiesta API inviata a quel provider. Con un endpoint locale, la richiesta viene inviata al loopback e resta sulla macchina. La telemetria è un flusso separato ed è disabilitata per impostazione predefinita: quando non è impostato, DSH_TELEMETRY_MODE restituisce DISABLED e in questo stato non viene creato alcun exporter. Imposta DSH_TELEMETRY_DISABLED=1 per un opt-out, che viene letto prima dell'avvio dell'esecuzione.

Perché dsh segnala MISSING_CREDENTIAL quando la mia variabile è impostata?

Perché dsh legge dal proprio ambiente di processo la variabile indicata da apiKeyEnv. Una variabile esportata nella shell non viene resa disponibile a un servizio systemd, alla sessione di un altro utente o a un processo avviato prima dell'esportazione. Inserisci il valore in un EnvironmentFile con permessi 600 per l'unità oppure esportalo nella stessa shell da cui avvii dsh. Verifica il contenuto effettivamente disponibile al processo in esecuzione con sudo tr '\0' '\n' < /proc/$(pgrep -f dsh | head -1)/environ.

Quale versione di Node.js richiede dsh?

Node.js 22.19 o una versione successiva della linea 22, oppure la versione 24 o una successiva. Node 23 non rientra nell'intervallo supportato. Esegui node -v prima di qualsiasi altra operazione, perché un errore di avvio causato da un runtime non supportato può sembrare un'installazione danneggiata e indurre a reinstallare il pacchetto invece del runtime.