parse_ini_file
Reads a configuration file in php.ini format and returns its settings as an array.
parse_ini_file(string $filename, bool $process_sections = false, int $scanner_mode = INI_SCANNER_NORMAL): array|false- Added in PHP 4.0
Parameters
| Parameter | Type | Description |
|---|---|---|
$filename | string | Path to the ini file to parse. |
$process_sectionsoptional | bool= false | When true, the result is nested one level deep, keyed by [section] name. |
$scanner_modeoptional | int= INI_SCANNER_NORMAL | INI_SCANNER_NORMAL, INI_SCANNER_RAW (no interpolation or escaping) or INI_SCANNER_TYPED (bool/int/null preserved). |
Return value
array|falseAn associative array of settings on success, or false on failure.
Errors
Emits an E_WARNING and returns false when the file cannot be read; syntax errors also produce a warning.
Changelog
- PHP 5.6.1INI_SCANNER_TYPED was added, so booleans, integers and null keep their native types instead of becoming strings.
By default every value comes back as a string: debug = true yields the string "1", while debug = false and debug = off both yield the empty string "". The trap is that "0" and "" are the only falsy results — a quoted debug = "false" comes back as the string "false", which is truthy in a naive check.
Example
When to use it
- Load per-environment database credentials from a config.ini kept outside the document root.
- Read a feature-flag file that non-developers maintain, without a config library.
- Parse a legacy application's settings file during a migration script.
Frequently asked questions
Why are my ini booleans strings instead of true and false?
Because the default scanner mode returns everything as a string. Pass INI_SCANNER_TYPED as the third argument to get real bool, int and null values.
What is the difference between parse_ini_file and parse_ini_string?
parse_ini_file() takes a path and reads from disk; parse_ini_string() takes the ini text you already have in memory. The parsing rules and the second and third parameters are identical.
Is it safe to keep passwords in an ini file?
Only if the file sits outside the document root, since web servers serve .ini files as plain text. If it must live under the web root, deny access at the server level or prefix the file with a PHP exit line and give it a .php extension.
More examples
Typed versus untyped values
In NORMAL mode you get string(1) "1", string(1) "3" and empty strings. In TYPED mode the same file yields bool(true), int(3), NULL and bool(false) — the difference that stops `if ($cfg['retries'])` behaving oddly.
<?php
file_put_contents('flags.ini', "debug = true\nretries = 3\nproxy = null\nquiet = off\n");
echo "NORMAL:\n";
var_dump(parse_ini_file('flags.ini'));
echo "TYPED:\n";
var_dump(parse_ini_file('flags.ini', false, INI_SCANNER_TYPED));
unlink('flags.ini');Sections and missing files
Without process_sections the two url keys collide and only the last survives — a silent config bug. With it, each section becomes its own sub-array. A missing file returns false, so always test the return value.
<?php
file_put_contents('multi.ini', "[prod]\nurl = https://example.test\n[dev]\nurl = http://localhost\n");
$flat = parse_ini_file('multi.ini'); // last value wins
$sectioned = parse_ini_file('multi.ini', true);
echo $flat['url'], "\n";
echo $sectioned['dev']['url'], "\n";
var_dump(@parse_ini_file('nope.ini')); // false + warning
unlink('multi.ini');Values that need quoting
The password contains ?, ! and & which are reserved characters in ini syntax; double-quoting makes them literal. Unquoted, the same line would raise a parse warning and drop the key.
<?php
file_put_contents('q.ini', 'password = "p@ss!w0rd?&"' . "\nplain = simple\n");
$cfg = parse_ini_file('q.ini');
echo $cfg['password'], "\n";
echo $cfg['plain'], "\n";
unlink('q.ini');
Discussion