How to move from standalone container to separate web and data containers


(5minpause) #1

Edit in Sep. 2017:

I wrote this “guide” in May 2015. I do not use Discourse any more (stopped soon after). I do not know if any of these instructions still work or how things are done nowadays.

I managed to migrate to two containers. If anyone else needs instructions, this is how it worked for me.

The process includes backup, setting up separate web and data containers and restore data.

  1. Backup your discourse instance and download backup. You can follow the simple guide or backup and restore later manually.

  2. Stop current standalone container
    ./launcher stop app

  3. copy web_only.yml and data.yml from samples/ to containers/ rename them to whatever you’d like

  4. if you rename them, please pay attention to the entries volumes: in data.yml and web_only.yml
    If you renamed web_only.yml to web_rocks.yml you need to modify the entry like this:

  - volume:
      host: /var/discourse/shared/web_rocks
      guest: /shared
  - volume:
      host: /var/discourse/shared/web_rocks/log/var-log
      guest: /var/log

Do this in data.yml and web_only.yml accordingly.

Setting up data container

Start with data.yml and set a password for the database. Then:

  • run ./launcher bootstrap data (or whatever you renamed data to)
  • if everything goes smoothly you can connect to the container via: ./launcher enter data (again: replace data with your name)
  • Exit the container by exit.

Setting up web container

Let’s modify web_only.yml.

Firstly, change the template and expose ports as your app.yml does.

Secondly, make sure you are linking to the right data container. If you renamed the data.yml to ‘something_else’ put it in for ‘name’.

# Use 'links' key to link containers together, aka use Docker --link flag.
  - link:
      name: data
      alias: data

Although we don’t want to expose ssh or any other ports anymore, you’d still need to expose 80 and 443 port for web access. This depends on whether you have a nginx running in the front and how you connect container with it.

Somewhere in there you’ll find this block:

  • Enter the password you set inside the data container.
  • Enter the data container’s alias you just wrote down. For DB_HOST and for REDIS_HOST. It has to match the links block we mentioned.
  • You probably didn’t change the DB_USERNAME.

You’ll find the values for DISCOURSE_DEVELOPER_EMAILS and DISCOURSE_HOSTNAME and many more. You already have these values in your app.yml. Copy them from there.

In the hooks section remember to set any additional plugins you already use inside app.yml

Now you should be ready to bootstrap it:
./launcher bootstrap web_only (again with your name)

When Discourse is ready, login and restore your site.

After this, everything worked again for me and my discourse installation was running again, but now in two separate containers.

Faster rebuilds?
Losing connection with Redis
Looking up available upgrades via CLI
High Availability
Install a Plugin
When is a rebuild needed, and can we speed it up?
Extreme load times - low disk perf?
Zero downtime rebuild discourse
(Michael Downey) #2

This … didn’t work as expected.

(The instructions are a bit off but I followed the update at Faster rebuilds?

Should the new 2-container installation present an empty/fresh site? I was assuming it would copy all of my settings & data from my app container, but it was brand new. :frowning:

Edit: I did a restore from a backup made just before the process, and it seemed to restore everything. So probably this just needs to be made clear. :slightly_smiling:

(Erick Guan) #3

I updated the guide. Hope it reflects your process.

(Michael Downey) #4

When someone like @sam puts out instructions to rebuild the “app” container for fixes like this one, is it safe to assume it’s generally going to be in the web_only container?

(Sam Saffron) #5

Yes, anything that mixes in the template I hacked get this.


Sorry for the bump on this old conversation, but I had a related issue.

While doing server upgrades that included docker daemon upgrades, docker restarted, but when it did restart, it also restarted the standalone app container, which brought the site back to what it was pre-transitioning to separate containers. After panicking, I stopped the app container, and then started web_only again, and site is back to normal.

But how can I fix this permanently? I tried moving the app.yml file away from the containers folder, but the app docker container still restarts. Should I run ./launcher destroy app ?

P.S. I am mentioning this here, because I did successfully move from a standalone app container to separate data/web_only containers as described here.

(Christoph) #7

Excuse my ignorance but could someone explain to me why this is not the default setup (or an optional setup) in the 30 min install guide?

I understand that using two containers minimizes the downtime during rebuilds and since nobody likes downtime, it seems like everyone would want two containers…

In other words: what’s the catch?

(Joshua Rosenfeld) #8

It’s more complicated to set up? More has to be done during setup? More potential points of failure? Harder to debug if you don’t understand Docker?

(Jay Pfaffman) #9

For people like you and me, there is none.

When the 30 minute install was conceived, it involved editing app.yml with a tool like nano (I’m an Emacs user and even I prefer vi to nano). Having people edit copy and edit two files and bootstrap and start both of them in the right order is on the order of 10 times more complicated. Now that ./discourse-setup is how most people configure Discourse, the setup part could be exactly the same for a two-container setup. I’ve looked in to doing just that & it wouldn’t be very hard.

But even still, with two containers, there would then be a bunch of problems with the data container wasn’t running and then no one would say which way their site was configured and that would be a lot more complicated to help out. Most of the time the web-based upgrade works just fine, and so unless you’re changing your plugin config, there’s not that much of a win for the two-container setup.

I think soon that I’ll start offering a two-container setup along side of my $99 install, but I’ve not gotten around to it.

(Christoph) #10

So is everyone here just pretending that they’re running one container but privately they’re running two?

Well, I guess, maybe even for “people like you and me” it is more convenient with one container, given that you don’t change plugins so often.

On the other hand, on standard troubleshooting advice that keeps coming up is obviously “disable all apps and re-enable them onr by one” and unless you do that by just disabling them under settings, this will give you plenty of downtime with one container…

And when I see that people are talking about 10,000 visits per day, that is quite a few annoyed users, even for half an hour downtime.

Anyway, thanks for explaining. And, yes, you should offer the 2-container install, if only to make it better known :wink:

(Jay Pfaffman) #11

No. Usually if someone posts a problem and they’re running multiple containers, they’ll mention that (probably because it’s a problem specifically with multiple containers), but mostly, if you know how to have multiple containers, it won’t make any difference that you do.

FWIW, it took me nearly 2 years to (bother to) figure it out. And six months of that time I was earning all of my income from Discourse consulting (not to say that the income I earned was a living all of that time).

I’d guess that the vast majority of people running Discourse have a single container. I’d guess that the vast majority of people* who earn some of their income from managing or hosting it* and/or would identify as a “system administrator” run two.

(Net Deamon) #12

It is not that hard too. You have app.yml file which contains both the properties of datasource and web related(which port discourse should run eg 9000, or the plugins config and the custom commands)

So you just divide the app.yml into data.yml and web.yml.
Data.yml will contain the datasources part from app.yml
While the web.yml will contain rest of config.

I usually use nginx webserver infront of discourse.
So I can rebuild another web contianer at say 9001, and reverse proxy to it from nginx.
Then I safely stop the previous web container running at 9000.
This swapping is done in few seconds… So there is no downtime.


Could use some help here:

This is confusing. It states to do a step (set a password) but doesn’t state how to do that aforementioned step… and immediately says “then” do some other stuff. Are we missing instructions on setting this password here?

So I didn’t change any password because I don’t know how or what OP is talking about, but did run ./launcher boostrap data and got the following response:

[...bootstrap command running...]
Successfully bootstrapped, to startup use ./launcher start data

prompt$ ./launcher enter data
Error: No such container: data

Note that I didn’t rename anything, only copied the files. I simply have data.yml and web_only.yml in my /var/discourse/containers directory.


(5minpause) #14

I wrote this “guide” in May 2015. I do not use Discourse any more (stopped soon after). I do not know if any of these instructions still work or how things are done nowadays.


Thanks, people are still linking to it, going to just hire some help. Cheers!

(Jeff Atwood) #17

Thanks for getting it started, we will take it from here!