Configuring Module Directories, Aliases, Fallbacks, and Conditions

The resolve configuration key provides options to locate your project's node module directories, create package and workspace aliases, a fallback mechanism for resolving packages, and custom conditions for package exports.

resolve 

  • Description: Provides ways to manage your NodeJS project's module directories, create aliases, set fallback mechanisms, and customize package exports.
  • Type: Object {}
  • Properties: packageRoots, alias, workspaceAlias, fallback, customConditions

Property: packageRoots (Array) 

To find project modules, Codux automatically searches for npm packages in the project's node_modules folder located in the project's root directory. You can widen the search to include assets from other locations by using the packageRoots property.
The packageRoots property resolves module paths using unique patterns. For example, to import modules from a folder named shared/components in /client/src, you can add /client/src to the packageRoots configuration like this:
1
2
3
4
5
6
7
8
{  
    "resolve": {
        "packageRoots": [
            "client/src",
      "node_modules"
        ]
    }
}  
Important!
It's important to include node_modules along with your other directories when configuring this property so that all necessary packages resolve.

Property: alias (Obj) 

Aliases are a useful technique for making code more manageable. They allow you to use shorter names for packages and templates, making your code more concise and easier to read. For example, you can use aliases when you want to tell your bundler to always use package "xzy" when it comes across references to package "abc".
In TypeScript React, you can define an alias for an imported module using the as keyword. For instance, if you want to import the a_ridiculously_long_module_name module and give it an alias of short_name, you can do so as follows:
1
import short_name from 'a_ridiculously_long_module_name';
You can also define aliases for specific functions within a module using the same syntax:
1
import { long_function_name as short_function_name } from 'a_ridiculously_long_module_name';
You can even alias an import using the as keyword. For example, if you want to import Something1 from "my-module.js" and give it an alias of MySomething, you can do so as follows:
1
import { Something1 as MySomething } from "my-module.js";
For importing default exports, you'd alias the import directly:
1
import MySomething from "my-module.js";
Aliases make it easier to manage your code by reducing the amount of text that needs to be written and read. They also make your code more readable by allowing you to use shorter names for packages and templates.
To use aliases in your code, configure them like this:
1
2
3
4
5
6
7
{  
  "resolve": {
    "alias": {
      "abc": "xzy",
      "abc/*": "xzy/*"
    }
  }
}  
All references to 'abc' in the code will be interpreted as reference to the 'xzy' package, while references to 'abc/' point to the 'xzy/'.

Property: workspaceAlias (Obj) 

Implementing package aliases can be labor-intensive, especially when dealing with many packages in a repository or monorepo. Instead of individually mapping every package within the repo to a path (a task that later requires ongoing management and upkeep as well), consider using workspace aliases.
Workspace aliases are similar to package aliases, but they always resolve all packages within a monorepo simultaneously. For instance, let's consider two packages named 'a' and 'b'. Instead of mapping each one individually like this:
1
2
3
4
5
6
7
8
9
10
11
{  
    "resolve": {
        "alias": {
            "a": "a/src/index.ts",
            "a/dist/*": "a/src/*",
            "b": "b/src/index.ts",
            "b/dist/*": "b/src/*",
            "package-a/dist/*": "package-a/sources/*"
        }
    }
}  
… we could use the workspaceAlias property to automatically resolve the packages like this:
1
2
3
4
5
6
7
8
{  
    "resolve": {
        "workspaceAlias": {
            ".": "./src/index.ts",
            "./dist/*": "./src/*"
        },
    }
}  
This way, all packages within the monorepo are resolved simultaneously, making it easier to manage your codebase.

Property: fallback (Obj) 

Fallbacks are useful when modules cannot be found in their regular or alias-based directories. This feature ensures that even if a specified module isn't found, your project remains functional by looking for an alternative or 'fallback' alias.
For instance, you can use fallbacks when working with CSS and JavaScript. If a browser cannot handle media queries, you can use a fallback to ensure that the page remains functional. Here's an example of a fallback:
1
2
3
4
5
6
7
8
{  
    "resolve": {
        "fallback": {
            "path": false,
            "stream": "./polyfills/stream.browser"
        }
    }
}  
In this example, whenever the stream package cannot resolve, the package will resolve from ./polyfills/stream.browser instead. Also, every time that the path tries to resolve, it will be given an empty object instead.

Property: customConditions (Array) 

Custom conditions for package exports allows you to add additional conditions on top of the defaults set by Codux (Codux automatically adds module, browser, import, and require). The default conditionals should be enough for most projects, but for development purposes, for example, you may want special conditions. For more information on conditional exports, see here.
When you import a package, you can specify the package name and the inner file to import a specific file within the package. If the package doesn't have a defined exports field, you can import any file from the package. The exports field allows you to specify the API that routes you to the files you need.
For instance, you can use custom conditions to specify the flag that is used in the package.json exports. By setting it in the resolver's conditions (like we do here), we tell the resolver that it can resolve to that potential package.json condition (without it, it might route to a different file, maybe under the "default" or other condition).
Here's an example configuration:
1
2
3
4
5
{  
  "resolve": {
    "customConditions": ["project-src"]
  }
}