Configuration for multiple clients

I have a SaaS application where multiple clients, each with their own Meteor instance. It’s NOT a multi-tenant application. There are a few things I’m running into, for example logos, paypal buttons, etc. that are specific to one client. Also, I can see where at some point maybe one client would like a customization or two (but will push back on this if possible).

I use MUP (pre docker) for deployment.

  1. Should I create a new codebase for each client? Managing several codes bases seems to be a nightmare.

  2. Have one code base but have configuration files and pre deployment scripts to handle things like loading logo files? In this case I wouldn’t know how to handle things like different templates for the paypal button changes, etc.

What’s the best approach for handling this situation?

Packages and configuration files.

Each client gets YourApp::Core.

If they pay for cool feature A. they get YourApp:CoolFeatureA.

Take a look at ReactionCommerce. They have a lovely system of registering and managing extra features as packages.

As a bonus you can work on new features without having to deploy new builds of the core app. Just develop the new feature as a package!

1 Like


How would I go about setting up the application with configuration files? For example, one company logo vs another? The actual logos are a file in the /public directory, I wouldn’t want to keep them all in one directory (for every client) and then load one based on a configuration file, I would think I’d only want to place the logo file in the /public folder for the specific client, that means I’d have to have some pre deployment script to place the right file in the /public directory based on client right?

Also, looking at reactioncommerce/reaction, the readme states:

Currently good for contributing/observing progress, testing. It goes without saying that we’re constantly refactoring, even things that are functionally done. We do not recommend using for production usage yet, unless you are very comfortable with the code, and aren’t risk averse. There are still many parts in development!

I’ve never built a package before. How do I integrate it into my workflow? How do I build, test, debug them? Actually I’d rather say away from the package approach to building this application. To me it’s overly complicated. Just using configuration files and client specific pre-deployment scripts feels more comfortable.

If a client insists on a feature no other client wants, then I’ll cross that bridge when it comes, otherwise my other clients will just get the added feature as far as I’m concerned.

For settings see:

You can also use ENV variables(assuming multiple servers).

To handle assets etc:

  1. Make one new app per client install some common

  2. Add your standard packages (YourApp::Core, YourApp::Accounts, YourApp::FeatureSet).

  3. Add client specific featurs (YourApp::SpecialSauce)

As each client has their own app space each client can have their own public folder with their logos.

Essentially anything common to all your clients goes in a package. Anything specific goes in their app. Although try and keep code/business logic out of those apps and keep them in packages. A requested feature from one client should turn into an optional one for everyone else.

Sure reaction is in beta, but their package registry is a great example of package registration.

Package development:

  • One git repo per package.
  • Clone them all into one folder and put that folder in PACKAGE_DIRS environment variable.
  • Packages will be built as a part of the top level app build.

See for how to write a package. It covers testing and development.

Deployment should be. Update the PACKAGE_DIRS packages. Clone the top level app. Then meteor build as normal!

It might seem complicated to start with and a lot of your code might stay inside YourApp::Core for the moment but once you get the modularity of the application down it becomes easier to test and manage. Code doesn’t bleed around between features and clients that don’t want optional features suffer no code changes which means no re-testing be it QA or UAT. Their app doesn’t change only the app that includes the new features does.

Oh and using pacakges is currently the only way to easily manage the load order of files.