# Node specs

The node spec is arguably the most important component of the codebase.

## Cascade

When a node is being matched against specs, the specs are compared in order of their definition in the `node_specs.yml` file. All matching specs are stored in the node. Then attributes are then read from the matches in first to last order. Any missing attributes will be read from the next match. This will enable the more specific specs to override certain attributes of the more generic ones.

For an example, refer to this project's own `.pls.yml` file.

## Importance

Specs have two functions.

- mark some files with a leading dot as meaningful enough to be shown  
  This can be accomplished with a simple spec containing just a `name`.
- mark some files without a leading dot as meaningless  
  This can be accomplished with a spec with -2 importance.
- decorate files with icons and colors  
  These improve the output both aesthetically and functionally.

## Specification

A node spec instance consists of
- one of
  - [name](#name): `str`
  - [pattern](#pattern): `str`
  - [extension](#extension): `str`
- [icon](#icon): `str?`
- [color](#color): `str?`
- [importance](#importance): `int?`

When matching nodes to specs, care must be taken to ensure that name matches supersede pattern matches which supersede extension matches, by placing them in this specific order.

### name

This is a string which describes the entire file name, including the extension.

#### Examples

- `Pipfile`
  - matches `Pipfile`
  - does not match `Pipfile.lock`

### pattern

This is a string containing a regular expression compared against the entire file name, including the extension. The file is considered to be a match if the regex matches the file name from the start. This is the most versatile of all identification approaches.

Note that these are regex patterns and not globs. Also since the regex is matched from the start of the string, the leading caret `^` is not needed. However, to match the end of the string, a trailing dollar sign `$` is.

#### Examples

- `Dockerfile\b.*`:
  - matches `docker-compose.yml`
  - matches `docker-compose.prod.yml`
  - does not match `docker-compose.yml.prod`

### extension

This is a string which describes the file extension without a leading dot `.` character. To match files to extensions, the entire extension is compared.

#### Examples

- `js`:
  - matches `index.js`
  - does not match `component.jsx`

### icon

The name of the icon to show beside nodes matching this spec. This name must correspond to entries in `emoji_icons.yml` and `nerd_icons.yml` to actually render the icon.

There are some caveats with emojis and nerd icons. These are a result of these icons visually taking up more than one terminal row but only occupying one. Most of these can be resolved by using a more advanced terminal application such as [iTerm2 for macOS](https://iterm2.com).

#### References

- [Nerd Fonts](https://www.nerdfonts.com/cheat-sheet)
- [Emojipedia](https://emojipedia.org)

### color

The name of the color in which to write nodes matching this spec. This must be one of the following.

- name of a standard color
- hex code `#ffffff`
- RGB triplet `rgb(255,255,255)`

#### References

- [Rich docs](https://rich.readthedocs.io/en/stable/appendix/colors.html)

### importance

The visual importance to associate with nodes matching this spec. This must be a number between -2 and 1.

- -2: the least importance, _hidden_  
  This corresponds to regular files you would not want to see at all
- -1: slightly lower importance, _dimmed_  
  This corresponds to autogenerated or downloaded files
- 0: normal importance  
  This is the default importance of all files unless specified
- 1: slightly higher importance, _bold_  
  This corresponds to important files like source code
- 2: the highest importance, _underline_  
  This corresponds to extremely important files that must be immediately seen

## Shorthand spec

In the interest of brevity, `name`, `pattern` and `extension` can be replaced with `names`, `patterns` and `extensions`. These plural forms take an array with the rules applying to each item of the array. These shorthand specs are expanded with each item in the plural key collated with the other attributes.
