# Files

Every file in a snippet's folder, including files in nested folders, loads by
its extension once the folder holds a `snippet.json`:

| Extension | How it loads                                                                      |
| --------- | --------------------------------------------------------------------------------- |
| `.php`    | Included on the snippet's hook, `init` by default.                                |
| `.css`    | Enqueued as a stylesheet.                                                         |
| `.scss`   | Compiled to CSS and enqueued as a stylesheet.                                     |
| `.js`     | Enqueued as a script in the page footer, or as a JavaScript module with `module`. |

Other files, such as a `README.md` or images, are kept but never loaded.

Without per-file options every file follows the snippet's
[configuration](/docs/byte/snippets/configuration.md): PHP on the snippet's hook,
stylesheets and scripts in its contexts, all of them under its conditions.

## PHP files

Every `.php` file in the folder runs, nested ones included, so keep files that
must not run on their own, such as templates you include from other code,
outside the snippet folder. A PHP file runs only when its very first
characters are `<?php`; a file that starts with whitespace or a byte order
mark, or is empty, is skipped. The guard Byte puts in front of a file that
starts outside PHP does not count, so a template still never runs on its own.
Each file is included once per request.

Byte writes every PHP file with `defined('ABSPATH') || exit;` as its first
statement, so the file runs nothing when its URL is requested outside
WordPress; [Sources](/docs/byte/snippets/sources.md#the-default-source) says
where the line goes.

Byte keeps the list of snippets, their files and their `snippet.json` settings
between requests and reads the folders again only when one changes: when Byte
writes or deletes a file, or when a folder or a `snippet.json` changes on disk,
so files you add or edit over SFTP or Git show on the next request.

## SCSS files

SCSS compiles on the server, and the compiled CSS is cached in
`uploads/sleek-byte/scss-cache`. The cache is rebuilt when the file is newer
than its cached CSS; a change to a partial alone does not rebuild the files
that import it, so save those too.

A file whose name starts with an underscore, such as `_variables.scss`, is a
partial: it is never enqueued on its own, but other SCSS files import it.
Imports resolve against the file's own folder and the folder above it. A file
that fails to compile is not enqueued, and the compiler's error goes to an
error log of its own rather than the snippet's runtime log.

## Handles and dependencies

Byte registers every CSS, SCSS and JavaScript file under the handle
`sleek-byte-<snippet>-<file>`: `<snippet>` is the snippet's folder path inside
its source, sanitised like a post slug with each slash turned into a hyphen,
and `<file>` is the file name without its extension. In a snippet folder named
`checkout-tweaks`, `assets/base.css` is `sleek-byte-checkout-tweaks-base`, and
another file can depend on it:

```json
{
  "files": {
    "assets/base.css": {},
    "assets/enhanced.css": {
      "dependencies": ["sleek-byte-checkout-tweaks-base"]
    },
    "assets/interactive.js": {
      "dependencies": ["jquery", "wp-api"]
    },
    "assets/modern.js": {
      "module": true
    }
  }
}
```

Two files of the same name in one snippet, such as `a/style.css` and
`b/style.css`, share a handle and only one of them loads, so give them
distinct names.

## Organising a snippet

Byte reads any folder structure, so group the files by what they do:

```text
woocommerce-extras/
├── assets/
│   ├── checkout.css
│   └── checkout-validation.js
├── includes/
│   ├── cart-functions.php
│   └── checkout-hooks.php
├── index.php
└── snippet.json
```

```json
{
  "name": "WooCommerce extras",
  "files": {
    "includes/checkout-hooks.php": { "hook": "wp" },
    "assets/checkout-validation.js": { "dependencies": ["jquery"] }
  }
}
```

Start without `files` and add an entry only for a file that needs to load
differently from the rest of its snippet.
