Implementation help/discussion, affiliated and syndicated content

I’m converting a Drupal site that uses the ‘domain’ module, which allowed us to have one site and database, but multiple ‘domains’ which acted as a filter for displaying content (articles, menus, files, etc).

This allowed us to have subdomains, or subdirectories (either were supported) for automatically filtering the content. For us, ‘domain’ referred to ‘region’ so we had a site.com/us (or us.site.com) and site.com/eu (or site.com/eu) that would filter all the views of content, and content could be ‘syndicated’ across multiple domains as chosen by the editors (called ‘syndicated’). Additionally, different domains(regions) could have different page layouts and different blocks of content.

So, in meteor I replicated this on all the documents in all collections with a simple field on each document that is an array of regions the document is ‘syndicated in’.

Initially, I thought I would use FlowRouter and just set up routes for each region (domain), but as a test, I setup a session variable to accomplish the same.

Then in the relevant template helper function, it pulls the domain session variable and filters content in the relevant helper function.

That worked pretty well and was super fast to develop, but there are a couple of problems:

-Session variables are easy to lose, during development at least, and I would often discover the variable just unset. I understand there are some persistent-session packages that could alleviate this.

-When a user selects a new domain/region from my ui, the changes that occur are ‘too fast’ and disconcerting. Since it isn’t moving to a new route, stuff just magically ‘changes’ and it isn’t super apparent to the user. There is no ‘page reload’, just templates updating content.

  • It seems less ‘automatic’ than I want, and every template has to check the session variable (maybe no way around that), so there is a lot of code duplication and boilerplate.

The other alternative would be to set up flow router to handle it, but I’m not sure if it makes it any easier at the template level. I already have route groups for ‘anonymous users’, ‘authenticated users’ and ‘admin users’ (based on role). I suppose I could create a new route group for ‘domain’, but is that the way to handle it? Do I then need to check flowrouter parameters in every interested template? Should the flowrouter group just set a session variable and then let the templates investigate that?

Should I setup different publications to handle this? Or maybe domain-specific subscriptions to content? If a re-usable template subscribed to one collection via a domain specific meteor function call, where/how does that subscription change when a user changes a route/session variable is set?

anyway, sorry for the rambling post, I just wanted to see if there were some better ideas out there.

thanks,
Cliff

A few points:

  1. there are no real “shortcuts” to this, if you need content segregated by domain and NOT purely by subfolder, you need to handle both those cases

  2. rather than creating flowrouter routes for domains, I’d advise you create a helper function, something like this, putting it on the Meteor namespace means you can access it easily from anywhere, but you could also put it into its own file and import it (probably cleaner). Unless you need to persist the domain on the server (e.g., you set the domain for the connection), I’d steer clear of session variables, they don’t really solve anything on the client apart from being a global variable. As far as I know they don’t even work across tabs (unless you’re using a persisted session var).

Meteor.getDomain = () => {
    return window.location.host; // you could look for the subdirectory here too.
}
  1. If you find that you are duplicating code a lot, extract the common functionality to a function in a new file, and import that wherever you want to use it.

  2. Regarding “too fast” domain change - if you are doing it based on domain or subdirectory, then you would change the URL, it likely wouldn’t refresh - but you can add a transition. Flow router has triggersEnter and triggersExit functions, that get triggered appropriately, you can pop a loading graphic onto the screen in one, and remove it in the other. You can even set a timeout if you want to force a 1 second minimum.

  3. Regarding getting data from flowrouter - you could do it in the template, but a global function to get it will be cleaner, and also easier to mock in the case that you want to do unit tests.