Come entrare in un contenitore Docker già in esecuzione con un nuovo TTY


545

Ho un contenitore che esegue il servizio Apache in primo piano. Vorrei poter accedere al contenitore da un'altra shell per "curiosare" al suo interno ed esaminare i file. Al momento, se mi collego al contenitore, rimango a guardare il demone Apache e non posso eseguire alcun comando.

È possibile collegare un altro tty a un container in esecuzione? Forse, posso approfittare del fatto che Docker sta effettivamente avvolgendo solo i contenitori LXC? Ho provato sudo lxc-console -n [container-id] -t [1-4]ma sembra che sia stato reso disponibile solo un tty e che sia quello che esegue il demone apache. Forse c'è un modo per abilitare più console lxc durante la compilazione?

Preferirei non configurare e costruire il contenitore con un servizio openssh, se possibile.


7
Ci hai provato docker attach [conainer-id]?
shabbychef,

13
@shabbychef a meno che il docker attach non sia cambiato, il comando attach si collega al tty in esecuzione, non a uno nuovo, quindi il titolo della domanda è "... con nuovo TTY". Questo è il motivo per cui la risposta di seguito non utilizza il comando attach.
Programster

Risposte:


1061

Con la finestra mobile 1.3, c'è un nuovo comando docker exec. Ciò consente di inserire una finestra mobile in esecuzione:

docker exec -it [container-id] bash

30
Ho cambiato questa per essere la risposta corretta (dalla mia) perché questo nuovo metodo, che non era disponibile al momento della domanda, è il miglior metodo IMO attuale.
Programster,

3
Si noti tuttavia che execnon funziona come un normale terminale. Ad esempio, non è possibile modificare l'utente una volta all'interno del contenitore.
Pithikos,

3
@Pithikos: sono in grado di utilizzare exec per eseguire una shell e quindi su someuserper cambiare utente. Esecuzione di Docker 1.4.1
lsh

2
Nota a chiunque legga questa discussione. Sono sicuro docker exec -itche alla fine fornirà una pseudo tty completamente funzionale, ma per ora (versione Docker 1.9.1), ci sono alcune carenze: github.com/docker/docker/issues/8755
blong

18
se viene visualizzato l'errore "exec:" bash ": file eseguibile non trovato in $ PATH ', è possibile provare questo: docker exec -it [container-id] / bin / sh
Dai Kaixian

42

Dovresti usare lo strumento di Jérôme Petazzoni chiamato 'nsenter' per entrare in un container senza usare SSH. Vedi: https://github.com/jpetazzo/nsenter

Installa semplicemente eseguendo: docker run -v /usr/local/bin:/target jpetazzo/nsenter

Quindi utilizzare il comando docker-enter <container-id>per inserire il contenitore.


Questo è il modo giusto Vedi il blog .
Jesse Glick,

5
Con la finestra mobile 1.3, c'è un nuovo comando docker exec. Ciò ti consente di inserire una finestra mobile in esecuzione: docker exec -it <container-id> bash(vedi la mia risposta di seguito)
Michael_Scharf

5
Esiste docker-enterancora? Mi dà command not found.
Snowcrash,

22

Aggiornare

A partire dalla finestra mobile 0.9, affinché i passaggi seguenti ora funzionino, è necessario aggiornare il file /etc/default/docker file con l' '-e lxc'opzione di avvio del daemon docker prima di riavviare il daemon (l'ho fatto riavviando l'host).

aggiorna al file / etc / default / docker

Questo è tutto perché ...

... it [docker 0.9] contiene una nuova astrazione "driver del motore" per rendere possibile l'uso di API diverse da LXC per avviare i container. Fornisce inoltre un nuovo driver del motore basato su una nuova libreria API (libcontainer) in grado di gestire i gruppi di controllo senza utilizzare gli strumenti LXC. Il problema principale è che se fai affidamento su lxc-attach per eseguire azioni sul tuo contenitore, come avviare una shell all'interno del contenitore, che è follemente utile per l'ambiente di sviluppo ...

fonte

Si noti che ciò impedirà al nuovo host di funzionare solo la funzionalità opzionale di rete della finestra mobile 0.11 e verrà visualizzata solo l'interfaccia di loopback. riportare un errore


Si scopre che la soluzione a una domanda diversa era anche la soluzione a questa:

... è possibile utilizzare la finestra mobile ps -notruncper ottenere l'ID contenitore lxc completo e quindi utilizzarelxc-attach -n <container_id> run bash in quel contenitore come root.

Aggiornamento: presto dovrai usare ps --no-truncinvece dips -notrunc che è deprecato.

inserisci qui la descrizione dell'immagine Trova l'ID contenitore completo

inserisci qui la descrizione dell'immagine Immettere il comando lxc attach.

inserisci qui la descrizione dell'immagine In alto viene mostrato il mio processo di Apache che esegue la finestra mobile avviata.


Quindi, non c'è modo di farlo solo con Docker, giusto? Personalmente preferisco non mescolare LXC da solo.
qkrijger,

Esiste un modo per eseguire un comando con lxc-attach invece di avviare bash? grazie!!
joselo,

@qkrijger per quanto ne so, è corretto. Perché preoccuparsi di "mescolare" LXC? Ti rendi conto che la finestra mobile è costruita sulla parte superiore di LXC, giusto?
Programmatore

@joselo Non capisco la tua domanda, ma ti suggerisco di creare un nuovo post con maggiori dettagli? Esistono molti modi per avviare un processo docker, come con bash o come demone con -d ecc.
Programster

@programster sì, me ne rendo conto :) Comunque, usare LXC direttamente in combinazione con Docker sembra un hacking. Divertente, ma non mantenibile. In generale, si dovrebbe codificare nel livello di astrazione in cui si è scelto di lavorare. Se hai davvero bisogno di LXC stesso, potrebbe essere il momento di una richiesta pull su Docker :)
qkrijger

7

Primo passo ottenere l'ID contenitore:

docker ps

Questo ti mostrerà qualcosa di simile

ID CONTENITORE COMANDO IMMAGINE STATO CREATO NOME PORTI

1170fe9e9460 localhost: 5000 / python: env-7e847468c4d73a0f35e9c5164046ad88 "./run_notebook.sh" 26 secondi fa Fino 25 secondi 0.0.0.0:8989->9999/tcp SLURM_TASK-303337_0

1170fe9e9460 è l'id contenitore in questo caso.

In secondo luogo , inserire la finestra mobile:

docker exec -it [container_id] bash

quindi nel caso sopra: docker exec -it 1170fe9e9460 bash


5

Che dire dell'esecuzione di tmux / GNU Screen all'interno del contenitore? Sembra il modo più semplice per accedere a tutti i vty che vuoi con un semplice:

$ docker attach {container id}

Questa è una soluzione ok se sai che vorrai ottenere l'accesso a un contenitore (ad esempio per eseguire il debug), ma ciò non aiuterebbe OP che afferma di voler cercare un contenitore esistente.
Luca Spiller

1
Il mio problema con questa risposta è che le persone hanno già chiesto informazioni sull'uso docker attache ho sottolineato che:...the attach command attaches to the running tty, not a new one, hence the question title is "...with new TTY"
Programmatore

Bene, se il contenitore sta già eseguendo questa soluzione non ti aiuterà, ma se in precedenza ti occupi di lasciare in esecuzione un multiplexer non avrai bisogno di ulteriori tty ... In effetti da quando ho iniziato a usare tmux ne uso uno tty e solo uno per fare tutto ciò di cui ho bisogno, dato che una volta in tmux posso generare tutti i vty che voglio.
cig0

4

nsenterfa quello. Tuttavia, dovevo anche inserire un container in modo semplice e nsenter non era sufficiente per le mie esigenze. In alcune occasioni era difettoso (schermo nero più bandiera -wd non funzionante). Inoltre volevo effettuare il login come utente specifico e in una directory specifica.

Ho finito per creare il mio strumento per inserire i contenitori. Puoi trovarlo su: https://github.com/Pithikos/docker-enter

Il suo utilizzo è facile come

./docker-enter [-u <user>] [-d <directory>] <container ID>

Ho appena provato, molto bello! Su Ubuntu ho dovuto eseguire sudo apt-get build-essential -y gcc docker-enter.c -o docker-enter sudo ./docker-enter <short-container-id> Bello che non devo ottenere l'ID completo come con lxc-attach -n Codebase è abbastanza breve da poter scansionare rapidamente l'intero insieme per cercare qualcosa di dannoso.
Programster

Ho reso disponibile un ebuild su gentoo all'indirizzo github.com/steveeJ/personal-portage-overlay come app-emulation / docker-enter.
stefanjunker,

Ho aggiunto un tutorial / script per questo automatico per gli utenti ubuntu su programster.blogspot.co.uk/2014/01/…
Programster

2

Il modo "nsinit" è:

installa nsinit

git clone git@github.com:dotcloud/docker.git
cd docker
make shell

dall'interno del contenitore:

go install github.com/dotcloud/docker/pkg/libcontainer/nsinit/nsinit

da fuori:

docker cp id_docker_container:/go/bin/nsinit /root/

usalo

cd /var/lib/docker/execdriver/native/<container_id>/
nsinit exec bash

2
docker exec -t -i container_name /bin/bash

Ti porterà alla console dei contenitori.


Sono arrivato a questa domanda perché avevo lo stesso problema. La risposta che sembra simile non ha funzionato per me fino a quando non ho modificato. Posso cancellare questo però.
Danstan,

2
docker exec -ti 'CONTAINER_NAME' sh

or

docker exec -ti 'CONTAINER_ID' sh

1

Ho avviato powershell su un microsoft / iis in esecuzione come demone utilizzando

docker exec -it <nameOfContainer> powershell

Sembra che la domanda riguardasse un contenitore basato su Linux. Questa risposta probabilmente funzionerà solo se si dispone di un contenitore basato su Windows -oppure- se è installata la versione .NET Core di PowerShell, ad esempio PowerShell 6 o versioni successive.
Manfred,

0

Su Windows 10 , ho installato la finestra mobile. Sto eseguendo Jnekins su un contenitore e ho riscontrato lo stesso messaggio di errore. Ecco una guida passo passo per risolvere questo problema:

Passaggio 1: apri gitbash ed esegui la finestra mobile run -p 8080: 8080 -p 50000: 50000 jenkins.

Passaggio 2: aprire un nuovo terminale.

Passaggio 3: eseguire "finestra mobile ps" per ottenere l'elenco del contenitore in esecuzione. Copia l'ID contenitore.

Passo 4: Ora se fai "docker exec -it {id contenitore} sh" o "docker exec -it {id contenitore} bash" riceverai un messaggio di errore simile a "il dispositivo di input non è un TTY. Se lo sei usando mintty, prova a inserire il prefisso "winpty"

Passaggio 5: eseguire il comando " $ winpty docker exec -it {container id} sh "

vola !! Ora sei all'interno del terminal.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.