|
1 | 1 | --- |
2 | 2 | title: Configuration |
| 3 | +description: "Tempest takes a unique approach at configuration, which provides an excellent developer experience due to its inherent support from code editors." |
3 | 4 | --- |
4 | 5 |
|
5 | | -## Configuration |
| 6 | +## Overview |
6 | 7 |
|
7 | | -As mentioned, configuration is represented by objects in Tempest. Tempest provides many configuration classes for you, although the framework is designed to use them as little as possible. Whenever you need fine-grained control over part of the framework's config, you can overwrite Tempest's default config by creating one or more `*.config.php` files, anywhere in your project. Each `*.config.php` file should return one config object. |
| 8 | +Within Tempest, configuration is represented by objects. This allows code editors to provide static insights and autocompletion during edition, resulting in an unmatched developer experience. |
| 9 | + |
| 10 | +Even though Tempest is designed to use as little configuration as possible, many configuration classes are available. This way, when fine-grained control over a specific part of the framework is needed, the default configuration can be overwritten. |
| 11 | + |
| 12 | +## Configuration files |
| 13 | + |
| 14 | +Files ending with `*.config.php` are recognized by Tempest's [discovery](../4-internals/02-discovery) as configuration objects, and will be registered as [singletons](./01-container#singletons) in the container. |
| 15 | + |
| 16 | +```php src/postgres.config.php |
| 17 | +use Tempest\Database\Config\PostgresConfig; |
| 18 | +use function Tempest\env; |
| 19 | + |
| 20 | +return new PostgresConfig( |
| 21 | + host: env('DB_HOST'), |
| 22 | + port: env('DB_PORT'), |
| 23 | + username: env('DB_USERNAME'), |
| 24 | + password: env('DB_PASSWORD'), |
| 25 | + database: env('DB_DATABASE'), |
| 26 | +); |
| 27 | +``` |
| 28 | + |
| 29 | +The configuration object above instructs Tempest to use PostgreSQL as its database, replacing the framework's default database, SQLite. |
| 30 | + |
| 31 | +## Accessing configuration objects |
| 32 | + |
| 33 | +To access a configuration object, you may inject it from the container like any other dependency. |
8 | 34 |
|
9 | 35 | ```php |
10 | | -// app/database.config.php |
| 36 | +use Tempest\Core\AppConfig; |
| 37 | + |
| 38 | +final readonly class HomeController |
| 39 | +{ |
| 40 | + public function __construct( |
| 41 | + private AppConfig $config, |
| 42 | + ) {} |
| 43 | + |
| 44 | + public function __invoke(): View |
| 45 | + { |
| 46 | + return view('home.view.php', environment: $this->config->environment); |
| 47 | + } |
| 48 | +} |
| 49 | +``` |
| 50 | + |
| 51 | +## Updating configuration objects |
11 | 52 |
|
12 | | -use Tempest\Database\DatabaseConfig; |
13 | | -use Tempest\Database\Connections\MySqlConnection; |
| 53 | +To update a property in a configuration object, you may simply assign a new value. Due to the object being a singleton, the modification will be persisted throught the rest of the application's lifecycle. |
| 54 | + |
| 55 | +```php |
| 56 | +use Tempest\Support\Random; |
| 57 | +use Tempest\Vite\ViteConfig; |
| 58 | + |
| 59 | +$this->viteConfig->nonce = Random\secure_string(length: 40); |
| 60 | +``` |
| 61 | + |
| 62 | +Alternatively, you may completely override the configuration instance by calling the `config()` method of the container, registering the new object as a singleton. |
| 63 | + |
| 64 | +```php |
| 65 | +$this->container->config(new SQLiteConfig( |
| 66 | + path: root_path('database.sqlite'), |
| 67 | +)); |
| 68 | +``` |
| 69 | + |
| 70 | +## Creating your own configuration |
| 71 | + |
| 72 | +As your application grows, you may need to create your own configuration objects. Such a use case could be an integration with Slack, where an API token and an application ID would be required. |
| 73 | + |
| 74 | +You may first create a class representing the configuration needed for your feature. It can have default values for its properties, and even methods if needed. |
| 75 | + |
| 76 | +```php src/Slack/SlackConfig.php |
| 77 | +final class SlackConfig |
| 78 | +{ |
| 79 | + public function __construct( |
| 80 | + public string $token, |
| 81 | + public string $baseUrl, |
| 82 | + public string $applicationId, |
| 83 | + public string $userAgent, |
| 84 | + ) {} |
| 85 | +} |
| 86 | +``` |
| 87 | + |
| 88 | +The next step is to register this configuration object in the container. This can be done by creating a `slack.config.php` file, which will be discovered by Tempest and registered as a [singleton](./01-container#singletons). |
| 89 | + |
| 90 | +```php src/Slack/slack.config.php |
14 | 91 | use function Tempest\env; |
15 | 92 |
|
16 | | -return new DatabaseConfig( |
17 | | - connection: new MySqlConnection( |
18 | | - host: env('DB_HOST'), |
19 | | - port: env('DB_PORT'), |
20 | | - username: env('DB_USERNAME'), |
21 | | - password: env('DB_PASSWORD'), |
22 | | - database: env('DB_DATABASE'), |
23 | | - ), |
| 93 | +return new SlackConfig( |
| 94 | + token: env('SLACK_API_TOKEN'), |
| 95 | + baseUrl: env('SLACK_BASE_URL', default: 'https://slack.com/api'), |
| 96 | + applicationId: env('SLACK_APP_ID'), |
| 97 | + userAgent: env('USER_AGENT'), |
24 | 98 | ); |
25 | 99 | ``` |
26 | 100 |
|
27 | | -Project-level configuration files will be discovered automatically, and will overwrite Tempest's default config. In this example, the default `DatabaseConfig` object will be overwritten by your custom one, using MySQL instead of SQLite, and retrieving its credentials from environment variables. |
| 101 | +You may now inject the `SlackConfig` class into a service, a controller, an action, or anything that can be resolved by the container. |
| 102 | + |
| 103 | +```php src/Slack/SlackConnector.php |
| 104 | +final class SlackConnector extends HttpConnector |
| 105 | +{ |
| 106 | + public function __construct( |
| 107 | + private readonly SlackConfig $slackConfig, |
| 108 | + ) { |
| 109 | + } |
28 | 110 |
|
29 | | -### Config Cache |
| 111 | + public function resolveBaseUrl(): string |
| 112 | + { |
| 113 | + return $this->slackConfig->baseUrl; |
| 114 | + } |
| 115 | + |
| 116 | + // ... |
| 117 | +} |
| 118 | +``` |
30 | 119 |
|
31 | | -Config files are cached by Tempest, you can read more about caching in the [dedicated chapter](/docs/framework/caching). You can enable or disable config cache with the `{txt}{:hl-property:CONFIG_CACHE:}` environment variable. |
| 120 | +## Configuration cache |
32 | 121 |
|
33 | | -```env |
34 | | -{:hl-comment:# .env:} |
| 122 | +During development, Tempest will discover configuration files every time the framework is booted. In a production environment, you should bypass this process to improve the performance by setting the `{txt}{:hl-property:CONFIG_CACHE:}` environment variable to `true`. |
35 | 123 |
|
| 124 | +```env .env |
36 | 125 | {:hl-property:CONFIG_CACHE:}={:hl-keyword:true:} |
37 | 126 | ``` |
0 commit comments