Skip to content

Exceptions

Muhammet Şafak edited this page May 29, 2026 · 1 revision

Exceptions

The package throws a single exception type from its loaders:

\RuntimeException
└── InitPHP\Config\Exceptions\ConfigException

Because it extends the SPL \RuntimeException, existing catch (\RuntimeException $e) blocks continue to work. Most applications will want to catch the more specific type explicitly so the intent is unambiguous.

useInitPHP\Config\Config;
useInitPHP\Config\Exceptions\ConfigException;
try {
Config::setFile('db', '/path/to/missing.php');
} catch (ConfigException$e) {
error_log($e->getMessage());
}

When it is raised

Every failure mode has a dedicated named constructor with a consistent message.

TriggerNamed constructorMessage
setFile() path does not existConfigException::fileNotFound()Configuration file "…" was not found.
setFile() target lacks a .php extensionConfigException::notAPhpFile()Configuration file "…" must have a ".php" extension.
setFile() file does not return an arrayConfigException::fileMustReturnArray()Configuration file "…" must return an array.
setDir() path is not a directoryConfigException::notADirectory()"…" is not a valid directory.
setDir() directory cannot be readConfigException::directoryNotReadable()Could not read the directory "…".
setClass() class name does not existConfigException::classNotFound()Class "…" was not found.

File not found

Config::setFile('db', __DIR__ . '/config/db.php');
// ConfigException:// Configuration file "/…/config/db.php" was not found.

File does not return an array

A loaded file must return an associative array:

// config/bad.phpecho'oops'; // no return
Config::setFile('bad', __DIR__ . '/config/bad.php');
// ConfigException:// Configuration file "/…/config/bad.php" must return an array.

Wrong extension

Config::setFile('db', __DIR__ . '/config/db.ini');
// ConfigException:// Configuration file "/…/config/db.ini" must have a ".php" extension.

Unknown class

Config::setClass('App\\Config\\DoesNotExist');
// ConfigException:// Class "App\Config\DoesNotExist" was not found.

Catching it

useInitPHP\Config\Config;
useInitPHP\Config\Exceptions\ConfigException;
try {
Config::setDir('app', __DIR__ . '/config');
} catch (ConfigException$e) {
fwrite(STDERR, $e->getMessage() . PHP_EOL);
exit(1);
}

Tolerating an optional file

A missing override file is often expected. Catch and ignore:

try {
Config::setFile('local', __DIR__ . '/config/local.php');
} catch (ConfigException) {
// Optional override — safe to skip when absent.
}

Re-throwing from your own boundary

If you wrap the package in a service of your own, re-throw as your own domain type and preserve the original as $previous:

useInitPHP\Config\Exceptions\ConfigException;
useInitPHP\Config\Library;
finalclass ConfigLoader
{
publicfunctionload(string$dir): Library
{
try {
return (newLibrary())->setDir('app', $dir);
} catch (ConfigException$e) {
thrownew \App\BootstrapException(
'Application config could not be loaded: ' . $e->getMessage(),
0,
$e,
);
}
}
}

Things that look like errors but aren't

The read API is deliberately forgiving — these never throw:

SituationWhat happens
get('missing')Returns $default (default: null).
remove('missing')Silent no-op.
setArray() / setFile() with a null nameMerges into the root instead of failing.
Config::reset() with no active instanceSilent no-op.
Config::get('does.not.exist'); // null
Config::get('does.not.exist', 'fallback'); // 'fallback'
Config::remove('does.not.exist'); // no-op, no exception

Related reading

Clone this wiki locally