A Meteor application is a mix of client-side JavaScript that runs inside a web browser or PhoneGap mobile app, server-side JavaScript that runs on the Meteor server inside a Node.js container, and all the supporting HTML templates, CSS rules, and static assets. Meteor automates the packaging and transmission of these different components, and it is quite flexible about how you choose to structure those components in your file tree.

Special Directories

By default, any JavaScript files in your Meteor folder are bundled and sent to the client and the server. However, the names of the files and directories inside your project can affect their load order, where they are loaded, and some other characteristics. Here is a list of file and directory names that are treated specially by Meteor:

  • client Any directory named client is not loaded on the server. Similar to wrapping your code inif (Meteor.isClient) { ... }. All files loaded on the client are automatically concatenated and minified when in production mode. In development mode, JavaScript and CSS files are not minified, to make debugging easier. (CSS files are still combined into a single file for consistency between production and development, because changing the CSS file’s URL affects how URLs in it are processed.)HTML files in a Meteor application are treated quite a bit differently from a server-side framework. Meteor scans all the HTML files in your directory for three top-level elements:<head>, <body>, and <template>. The head and body sections are separately concatenated into a single head and body, which are transmitted to the client on initial page load.
  • server Any directory named server is not loaded on the client. Similar to wrapping your code inif (Meteor.isServer) { ... }, except the client never even receives the code. Any sensitive code that you don’t want served to the client, such as code containing passwords or authentication mechanisms, should be kept in the server directory.Meteor gathers all your JavaScript files, excluding anything under the client, public, andprivate subdirectories, and loads them into a Node.js server instance. In Meteor, your server code runs in a single thread per request, not in the asynchronous callback style typical of Node. We find the linear execution model a better fit for the typical server code in a Meteor application.
  • public All files inside a top-level directory called public are served as-is to the client. When referencing these assets, do not include public/ in the URL, write the URL as if they were all in the top level. For example, reference public/bg.png as <img src='/bg.png' />. This is the best place for favicon.ico, robots.txt, and similar files.
  • private All files inside a top-level directory called private are only accessible from server code and can be loaded via the Assets API. This can be used for private data files and any files that are in your project directory that you don’t want to be accessible from the outside.
  • client/compatibility This folder is for compatibility JavaScript libraries that rely on variables declared with var at the top level being exported as globals. Files in this directory are executed without being wrapped in a new variable scope. These files are executed before other client-side JavaScript files.
  • tests Any directory named tests is not loaded anywhere. Use this for any local test code.
  • node_modules For compatibility with node.js tools used alongside Meteor, any directory namednode_modules is not loaded anywhere. node.js packages installed into node_modulesdirectories will not be available to your Meteor code. Use Npm.depends in your packagepackage.js file for that.

The following directories are also not loaded as part of your app code:

  • Files/directories whose names start with a dot, like .meteor and .git
  • packages/: Used for local packages, covered below
  • programs: For legacy reasons
  • cordova-build-override

Files outside special directories

All JavaScript files outside special directories are loaded on both the client and the server. That’s the place for model definitions and other functions. Meteor provides the variablesMeteor.isClient and Meteor.isServer so that your code can alter its behavior depending on whether it’s running on the client or the server.

CSS and HTML files outside special directories are loaded on the client only, and cannot be used from server code.

Example File Structure

The file structure of your Meteor app is very flexible. Here is an example layout that takes advantage of some of the special folders mentioned above.

lib/                      # common code like collections and utilities
lib/methods.js            # Meteor.methods definitions
lib/constants.js          # constants used in the rest of the code

client/compatibility      # legacy libraries that expect to be global
client/lib/               # code for the client to be loaded first
client/lib/helpers.js     # useful helpers for your client code
client/body.html          # content that goes in the <body> of your HTML
client/head.html          # content for <head> of your HTML: <meta> tags, etc
client/style.css          # some CSS code
client/<feature>.html     # HTML templates related to a certain feature
client/<feature>.js       # JavaScript code related to a certain feature

server/lib/permissions.js # sensitive permissions code used by your server
server/publications.js    # Meteor.publish definitions

public/favicon.ico        # app icon

settings.json             # configuration data to be passed to meteor --settings
mobile-config.js          # define icons and metadata for Android/iOS

You can also model your directory structure after the example apps. Run meteor create --example todos and explore the directories to see where all the files in a real app could go.

File Load Order

It is best to write your application in such a way that it is insensitive to the order in which files are loaded, for example by using Meteor.startup, or by moving load order sensitive code into packages, which can explicitly control both the load order of their contents and their load order with respect to other packages. However, sometimes load order dependencies in your application are unavoidable.

There are several load ordering rules. They are applied sequentially to all applicable files in the application, in the priority given below:

  1. HTML template files are always loaded before everything else
  2. Files beginning with main. are loaded last
  3. Files inside any lib/ directory are loaded next
  4. Files with deeper paths are loaded next
  5. Files are then loaded in alphabetical order of the entire path

For example, the files above are arranged in the correct load order. main.html is loaded second because HTML templates are always loaded first, even if it begins with main., since rule 1 has priority over rule 2. However, it will be loaded after nav.html because rule 2 has priority over rule 5.

client/lib/styles.js and lib/feature/styles.js have identical load order up to rule 4; however, since client comes before lib alphabetically, it will be loaded first.

Organizing Your Project

There are three main ways to organize your files into features or components. Let’s say we have two types of objects in our project: apples and oranges.

Method 1: Root-Level Folders

Since the special client, server, and lib directories work if they are anywhere in the path, you can use top-level folders to organize code into modules:

apples/lib/               # code for apple-related features

oranges/lib/              # code for orange-related features

Method 2: Folders inside client/ and server/

lib/apples/               # common code for apples
lib/oranges/              # and oranges

client/apples/            # client code for apples
client/oranges/           # and oranges

server/apples/            # server code for apples
server/oranges/           # and oranges

Method 3: Packages

This is the ultimate in code separation, modularity, and reusability. If you put the code for each feature in a separate package, the code for one feature won’t be able to access the code for the other feature except through exports, making every dependency explicit. This also allows for the easiest independent testing of features. You can also publish the packages and use them in multiple apps with meteor add.

packages/apples/package.js     # files, dependencies, exports for apple feature
packages/apples/<anything>.js  # file loading is controlled by package.js

packages/oranges/package.js    # files, dependencies, exports for orange feature
packages/oranges/<anything>.js # file loading is controlled by package.js

Source: Meteor Documentation

Meteor: Structuring your application

Category: Uncategorized

Join the discussion

Your email address will not be published. Required fields are marked *