# Native Shell Access to Containers

**URL:** <https://forums.suse.com/t/native-shell-access-to-containers/1821>\
**Category:** Rancher 1.x\
**Created:** [February 22, 2016, 5:34pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821 "2016-02-22T17:34:04Z")\
**Posts on this page:** 17\
**Page:** 1

<div class="post-metadata">

**Author:** ![marcqualie](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/marcqualie/32/921_2.png) [@marcqualie](https://forums.suse.com/u/marcqualie)\
**Post date:** [February 22, 2016, 5:34pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/1 "2016-02-22T17:34:04Z")

</div>

I’m having trouble trying to get a console that isn’t in the web UI. Part of my usual process when working with Rails applications is to attach to a running container and run various administration commands via the rails console.

I can’t find anywhere in the API that would allow me to attach to STDIN and STDOUT for a container so my only option currently is using the web UI which is inconvenient and not the best experience outputting log data. This also prevents me from doing automated tasks from CI environments such as running migrations.

After reading through the forums I saw someone suggest downloading the machine config, getting the ssh-key, ssh-ing into the host then running `docker exec $CONTAINER_ID bash` directly but this is a very involved and manual process. Even exposing the machine config from the API would be helpful here as I could query the container/stack name, find it’s host, then download the config and script the whole process to get a tunnelled ssh connection.

Are there any plans to offer such functionality in the future?

---

<div class="post-metadata">

**Author:** ![marcqualie](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/marcqualie/32/921_2.png) [@marcqualie](https://forums.suse.com/u/marcqualie)\
**Post date:** [February 22, 2016, 5:52pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/2 "2016-02-22T17:52:39Z")

</div>

I was able to find some information on the API but I’m not 100% clear on which commands to send to the websocket endpoint once the terminal is created.

- POST /v1/containers/:id?action=execute
- Connect to the wws:// url in the API response
- Can’t find documentation from here for websocket communication

---

<div class="post-metadata">

**Author:** ![vincent](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/vincent/32/7156_2.png) [@vincent](https://forums.suse.com/u/vincent)\
**Post date:** [February 22, 2016, 6:56pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/3 "2016-02-22T18:56:58Z")

</div>

The [command you supply in the body](http://docs.rancher.com/rancher/api/api-resources/containerExec/) of the POST is run with the equivalent of `docker exec` and the resulting WebSocket is binary and sends/receives frames that directly connect stdin/out from the command.

`tty` defaults to `true` so you probably want to change it to `false` unless you speak VT100 😄. The UI contains a terminal emulator and the Shell action is is roughly calling it with

```auto
{
  "command": ["/bin/bash"],
  "attachStdin": true,
  "attachStdout": true,
  "tty": true
}

```

(the actual command is much longer and weirder to handle cases where bash isn’t available and some other edge cases)

---

<div class="post-metadata">

**Author:** ![marcqualie](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/marcqualie/32/921_2.png) [@marcqualie](https://forums.suse.com/u/marcqualie)\
**Post date:** [February 23, 2016, 7:00pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/4 "2016-02-23T19:00:04Z")

</div>

Thanks @vincent those comments were very helpful.

I created [https://github.com/marcqualie/rancher-shell](https://github.com/marcqualie/rancher-shell) which allows me to carry on my workflow as I’m used to. Very basic currently but does everything I need and is more convinient than the web UI when working with a few environments simultaneously.

Looking through the source code of rancher-ui was also extremely helpful when building the frames and knowing to base64 encode/decode the data.

Really enjoying Rancher and looking forward integrating it deeper into our infrastructure.

---

<div class="post-metadata">

**Author:** ![vincent](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/vincent/32/7156_2.png) [@vincent](https://forums.suse.com/u/vincent)\
**Post date:** [February 23, 2016, 7:01pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/5 "2016-02-23T19:01:58Z")

</div>

ah d’oh, I forgot about the base64 because it’s not actually a binary socket 😄. Cool project, thanks for sharing.

---

<div class="post-metadata">

**Author:** ![marcqualie](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/marcqualie/32/921_2.png) [@marcqualie](https://forums.suse.com/u/marcqualie)\
**Post date:** [March 5, 2016, 11:55pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/6 "2016-03-05T23:55:58Z")

</div>

@vincent is there a timeout on the WebSocket or the container? If I leave the session idle for about 15 seconds it disconnects every time.

I can’t find any documentation on a timeout period or a ping command to keep the connection alive.

---

<div class="post-metadata">

**Author:** ![vincent](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/vincent/32/7156_2.png) [@vincent](https://forums.suse.com/u/vincent)\
**Post date:** [March 6, 2016, 1:21am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/7 "2016-03-06T01:21:48Z")

</div>

There is no timeout on our side… Are you doing SSL termination or similar proxying?

---

<div class="post-metadata">

**Author:** ![marcqualie](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/marcqualie/32/921_2.png) [@marcqualie](https://forums.suse.com/u/marcqualie)\
**Post date:** [March 6, 2016, 3:32am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/8 "2016-03-06T03:32:13Z")

</div>

Ah, that may explain it. I have [https://github.com/tutumcloud/haproxy](https://github.com/tutumcloud/haproxy) in front of the rancher server for SSL termination and proxy-ing. Looking at their docs it seems their default timeout is 50s so I may see if I can increase it for just wss:// connections and see if that fixes it.

---

<div class="post-metadata">

**Author:** ![Amala](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/amala/32/448_2.png) [@Amala](https://forums.suse.com/u/Amala)\
**Post date:** [April 1, 2016, 1:13am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/9 "2016-04-01T01:13:40Z")

</div>

I did something which worked well. I run my command in a screen as part of the command.

In a “Run Once” container you use `screen rails c` or equivalent. Just start it with screen. Then after it has started you can use “Execute Shell” and in the shell you do `screen -x` to join the screen previously started.

A few extra commands and you have to have `screen` installed on the container. But the advantage is the console stays running.

EDIT:

Nevermind. The screen does not stay active after you do a single “Execute Shell”. So it only stays alive for one session. It is not persistent. Not too bad, but annoying that you cannot have a persistent console. I tried a few combinations of Interactive and TTY.

---

<div class="post-metadata">

**Author:** ![toanpt3](https://avatars.discourse-cdn.com/v4/letter/t/65b543/32.png) [@toanpt3](https://forums.suse.com/u/toanpt3)\
**Post date:** [June 23, 2016, 4:21am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/11 "2016-06-23T04:21:52Z")

</div>

HI marcqualie

I see Rancher or Shipyard can make Terminal on web browser to container.  
I know they use API docker, but I do not know how to do.  
you can talk in more detail is not?  
Thank you.

---

<div class="post-metadata">

**Author:** ![marcqualie](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/marcqualie/32/921_2.png) [@marcqualie](https://forums.suse.com/u/marcqualie)\
**Post date:** [June 23, 2016, 2:50pm UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/12 "2016-06-23T14:50:49Z")

</div>

Hey @toanpt3

I am not sure exactly how it’s done within rancher internals, but they expose the functionality over websockets to make the integration simple for the web browser integration. The tool I created above ([https://github.com/marcqualie/rancher-shell](https://github.com/marcqualie/rancher-shell)) uses that exposed websocket technology to allow the same functionality from the command line.

@vincent shared the documentation above for the websockets ([http://docs.rancher.com/rancher/api/api-resources/containerExec/](http://docs.rancher.com/rancher/api/api-resources/containerExec/)) and may be able to shed some light on the internals if you are wanting to build this kind of functionality directly on top of the Docker API.

---

<div class="post-metadata">

**Author:** ![vincent](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/vincent/32/7156_2.png) [@vincent](https://forums.suse.com/u/vincent)\
**Post date:** [June 24, 2016, 12:14am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/13 "2016-06-24T00:14:58Z")

</div>

The way it works in Docker is calling `exec` in the Docker Remote API on the host and running a shell like `bash`: [https://docs.docker.com/engine/reference/api/docker\_remote\_api\_v1.20/#exec-create](https://docs.docker.com/engine/reference/api/docker_remote_api_v1.20/#exec-create) . There’s also an equivalent in the CLI: [https://docs.docker.com/engine/reference/commandline/exec/](https://docs.docker.com/engine/reference/commandline/exec/)

---

<div class="post-metadata">

**Author:** ![toanpt3](https://avatars.discourse-cdn.com/v4/letter/t/65b543/32.png) [@toanpt3](https://forums.suse.com/u/toanpt3)\
**Post date:** [June 24, 2016, 5:33am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/14 "2016-06-24T05:33:07Z")

</div>

hi  
Thank you for the feedback, the problem I want to be able to use the API directly Docker [https://docs.docker.com/engine/reference/api/docker\_remote\_api\_v1.23/](https://docs.docker.com/engine/reference/api/docker_remote_api_v1.23/)  
Currently you have solved this problem yet?. If the matter has not been, we can exchange its own in this regard.

Thank you very much.

---

<div class="post-metadata">

**Author:** ![demarant](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/demarant/32/497_2.png) [@demarant](https://forums.suse.com/u/demarant)\
**Post date:** [July 19, 2016, 8:37am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/16 "2016-07-19T08:37:42Z")

</div>

@marqualie  
I felt also a bit limited by the built-in shell provided by rancher. So I have tried this shell web application "gotty"

> **[yudai/gotty](https://github.com/yudai/gotty)**
>
> gotty - Share your terminal as a web application

Here is the docker version

[https://hub.docker.com/r/dit4c/gotty/](https://hub.docker.com/r/dit4c/gotty/)

It works quite well. Maybe worth giving it a try.

---

<div class="post-metadata">

**Author:** ![toanpt3](https://avatars.discourse-cdn.com/v4/letter/t/65b543/32.png) [@toanpt3](https://forums.suse.com/u/toanpt3)\
**Post date:** [July 22, 2016, 6:15am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/17 "2016-07-22T06:15:39Z")

</div>

Hi @marcqualie.

I have enable debug on rancher, i get websocket URL:  
[![](http://forums.suse.com//uploads/suse/original/2X/7/762cec3d6725a36ef9f5af5e7b72bd53d17374fd.jpg) ](http://forums.suse.com//uploads/suse/original/2X/7/762cec3d6725a36ef9f5af5e7b72bd53d17374fd.jpg)  
After,i use wscat to connect this URL socket, connected but cannot execute command sample Rancher shell exec on web:  
[![](http://forums.suse.com//uploads/suse/original/2X/7/762cec3d6725a36ef9f5af5e7b72bd53d17374fd.jpg) ](http://forums.suse.com//uploads/suse/original/2X/7/762cec3d6725a36ef9f5af5e7b72bd53d17374fd.jpg)  
What did I do wrong?, I want one interface or as the exec shell rancher to do?  
Thank you

---

<div class="post-metadata">

**Author:** ![vincent](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/vincent/32/7156_2.png) [@vincent](https://forums.suse.com/u/vincent)\
**Post date:** [July 22, 2016, 8:42am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/18 "2016-07-22T08:42:36Z")

</div>

The websocket frames are base64 encoded in both directions (because they can contain control chars and invalid what looks like UTF-8 sequences, etc… But binary frames are a pain).

Also the token is generated from the previous request to the exec action, and that is where the command to execute goes. And the tokens are only good for 5 minutes once issued.

---

<div class="post-metadata">

**Author:** ![fangli](https://sea2.discourse-cdn.com/flex022/user_avatar/forums.suse.com/fangli/32/1618_2.png) [@fangli](https://forums.suse.com/u/fangli)\
**Post date:** [August 23, 2016, 6:40am UTC](https://forums.suse.com/t/native-shell-access-to-containers/1821/19 "2016-08-23T06:40:01Z")

</div>

Hi finally we have solution now.

We just created a very powerful rancher ssh cli to get this done:  
[https://github.com/fangli/rancherssh](https://github.com/fangli/rancherssh)

Native SSH Client for Rancher Containers, provided a powerful native terminal to manage your docker containers.

You may want to give it a try, stars are welcome!
