PHP Config.ini file parsing with multi-level arrays - php

I have a config.ini file that has a number of these types of variables:
site.social.twitter = "URL"
site.social.facebook = "URL"
site.social.google-plus = "URL"
I use PHP's built-in function to parse the INI.
$config = parse_ini_file(__DIR__ ."/../config.ini");
The next step is to get this (site.social.twitter)
to become an array.
$config['site']['social']['twitter']
You could just 'explode()', but it doesn't quite get there. Is there any simpler solutions to something like this?

OK, so you can look at using sections and the array syntax for INI files such as:
[site]
social[twitter] = URL
social[facebook] = URL
social[google-plus] = URL
Then pass true as the second argument:
$config = parse_ini_file(__DIR__ ."/../config.ini", true);
Or to build using your existing INI structure (adapted from How to access and manipulate multi-dimensional array by key names / path?):
$array = array();
foreach($config as $path => $value) {
$temp = &$array;
foreach(explode('.', $path) as $key) {
$temp =& $temp[$key];
}
$temp = $value;
}
$config = $array;
print_r($config);

Does simply referencing $config['site']['social'] get you the array you want? According to the documentation this should yield:
Array
(
[twitter] => "URL"
[facebook] => "URL"
[google-plus] => "URL"
)

Related

PHP Add New Index to Multidimentional Array Without Notice

Take this example:
$data = array();
$data['a']['one'] = 'test';
This will throw a notice because $data['a'] doesn't exist. So instead, I always do this:
$data = array();
$data['a'] = array();
$data['a']['one'] = 'test';
Or if I'm in a loop, something like this:
$data = array();
foreach ($items as $item) {
if (!isset($data['a'])) {
$data['a'] = array();
}
$data['a']['one'] = $item->getId();
}
This gets really reptitive in the code and messy. I know that I could write some kind of array_push alternative function to handle this, but I'm wondering if there is a way to do this with existing PHP methods.
Initialising the entire array (all keys, sub arrays etc) somewhere first is not practical.
This means remembering and maintaining it - when you have new data not previously accounted for, you have to also add it to the array initialisation.
(Urgh)
I would least delcare the var as an array ($data = array();) then you don't need is_array() - which is an annoying single line of code before you even do anything useful (two lines including the closing brace..).
However, your checking is not needed.
Your code checks if the array's sub array has been set, and if not you set it as an array and then set the data onto it.
This is not necessary, as you can set data in an array even if some of the sub keys/arrays had not previously been set.
For example this code (this is the entire file and all code ran) won't throw an error, warning, or notice:
$data['a']['one']['blah']['foo'] = 'test';
print_r($data);
echo $data['a']['one']['blah']['foo'];
The above outputs:
Array ([a] => Array ( [one] => Array ( [blah] => Array ( [foo] => test ) ) ) )
test
The above code will not return any warning/notice/errors.
Also notice I didn't even have $data = array().
(although you want to, as you likely use foreach and that initialisation negates the need for using is_array).
That was with error_reporting(-1);
TL;DR; - The Answer
So to answer your question, in your code you could do this (and receive no errors/notices/warnings):
$data = array();
// more data setting the array up
foreach ($items as $item) {
$data['a']['one'] = $item->getId();
}
You might wish to look into ArrayObject class, the following runs without errors or warnings
<?php
error_reporting(E_ALL| E_NOTICE);
ini_set('display_errors', 1);
$ar = new ArrayObject();
$ar['foo']['bar'] = 1;
assert($ar['foo']['bar'] === 1);
Checkout the ideone
Create the array during assignment:
$data=[];
$data['a'] = ['one' => 'test'];
Or create the whole structure in one go
$data = ['a'=>['one'=>'test']];
I dont believe there are any built in methods that suit your needs: PHP array functions
Maybe creating your own function would be the neatest way to achieve this. Or, depending on your use case you could create your array of data to add to key a separately like below:
$data = array();
$array_data = array();
foreach ($items as $key => $item) {
$array_data[$key] = $item->getId(); // presuming your 'one' is a dynamic key
}
$data['a'] = $array_data;
Whether or not this a better than your approach is a matter of opinion I suppose.
You can bypass notices by adding #. Also you can disable notices which I don't recommend at all.
I think there are better ways to write such codes:
$a['one'] = 'test';
$a['two'] = 'test';
$data['a'] = $a;
or:
$data['a'] = ['one'=>'test', 'two'=>'test']
or:
$data = ['a'=>['one'=>'test', 'two'=>'test']];
The methods that multiple people have suggested to simply create the array as a multidimensional array from the beginning is typically not an option when dealing with dynamic data. Example:
$orderItems = array();
foreach ($items as $item) {
$oId = $order->getId();
if (!isset($orderItems[$oId])) {
$orderItems[$oId] = array();
}
$pId = $item->getPackageNumber();
if (!isset($orderItems[$oId][$pId])) {
$orderItems[$oId][$pId] = array('packages'=>array());
}
$orderItems[$oId][$pId][] = $item;
}
It sounds like I need to create a function to do this for me. I created this recursive function which seems to do the job:
function array_md_push(&$array, $new) {
foreach ($new as $k => $v) {
if (!isset($array[$k])) {
$array[$k] = array();
}
if (!is_array($v)) {
array_push($array[$k], $v);
} else {
array_md_push($array[$k], $v);
}
}
}
$test = array();
$this->array_md_push($test, array('a' => array('one' => 'test')));
$this->array_md_push($test, array('a' => array('one' => 'test two')));
$this->array_md_push($test, array('a' => array('two' => 'test three')));
$this->array_md_push($test, array('b' => array('one' => 'test four')));
Which gives me this:
array(2) {
["a"] => array(2) {
["one"] => array(2) {
[0] => string(4) "test"
[1] => string(8) "test two"
}
["two"] => array(1) {
[0] => string(10) "test three"
}
}
["b"] => array(1) {
["one"] => array(1) {
[0] => string(9) "test four"
}
}
}
This works. You do not need to set as an empty array
$data['a']['one'] = 'test';

How to store each array value in a variable with PHP

I have an array that looks something like this:
Array
(
[2] => http://www.marleenvanlook.be/admin.php
[4] => http://www.marleenvanlook.be/checklogin.php
[5] => http://www.marleenvanlook.be/checkupload.php
[6] => http://www.marleenvanlook.be/contact.php
)
What I want to do is store each value from this array to a variable (using PHP). So for example:
$something1 = "http://www.marleenvanlook.be/admin.php";
$something2 = "http://www.marleenvanlook.be/checklogin.php";
...
You can use extract():
$data = array(
'something1',
'something2',
'something3',
);
extract($data, EXTR_PREFIX_ALL, 'var');
echo $var0; //Output something1
More info on http://br2.php.net/manual/en/function.extract.php
Well.. you could do something like this?
$myArray = array("http://www.marleenvanlook.be/admin.php","http://www.marleenvanlook.be/checklogin.php","etc");
$i = 0;
foreach($myArray as $value){
${'something'.$i} = $value;
$i++;
}
echo $something0; //http://www.marleenvanlook.be/admin.php
This would dynamically create variables with names like $something0, $something1, etc holding a value of the array assigned in the foreach.
If you want the keys to be involved you can also do this:
$myArray = array(1 => "http://www.marleenvanlook.be/admin.php","http://www.marleenvanlook.be/checklogin.php","etc");
foreach($myArray as $key => $value){
${'something'.$key} = $value;
}
echo $something1; //http://www.marleenvanlook.be/admin.php
PHP has something called variable variables which lets you name a variable with the value of another variable.
$something = array(
'http://www.marleenvanlook.be/admin.php',
'http://www.marleenvanlook.be/checklogin.php',
'http://www.marleenvanlook.be/checkupload.php',
'http://www.marleenvanlook.be/contact.php',
);
foreach($something as $key => $value) {
$key = 'something' . $key;
$$key = $value;
// OR (condensed version)
// ${"something{$key}"} = $value;
}
echo $something2;
// http://www.marleenvanlook.be/checkupload.php
But the question is why would you want to do this? Arrays are meant to be accessed by keys, so you can just do:
echo $something[2];
// http://www.marleenvanlook.be/checkupload.php
What I would do is:
$something1 = $the_array[2];
$something2 = $the_array[4];

How to replace an array with new array value in a file

I want to replace an array code inside my php file with new array dynamically
For e.g
<?php
$my_Array = array("key1" => "valu1");
?>
to
<?php
$my_Array = array("key2" => "valu2");
?>
Is that possible?
You can do this using url parameters like below.
Your url should be like mywebsite.com/test.php?key1=value1&key2=value2
In your php file
$myarray = array();
foreach ($_GET as $key => $value) {
$myarray[$key] = $value;
}
print_r($myarray);
Output should be like below
Array ( [key1] => value1 [key2] => value2 )
If it's saved in file and you need to replace it, use something like this:
<?php
$file = 'filename.php'; // path to the file
$data = file_get_contents($file);
$old = array("key1","valu1"); // old values to replace
$new = array("key2","valu2"); // the new values
$data = str_replace($old,$new,$data);
file_put_contents($file,$data);
?>
Is this what you need?

Change values in the innermost part of PHP associative array

I would like to append a string to the values of a nested associative array in PHP.
The following is my array
$styles = array(
'Screen' => array(
"master.css",
"jquery-jvectormap-1.0.css"),
'handheld' => array("mobile.css")
);
Looping over it to change it in the following way fails.
foreach($media as $medium => $filename)
foreach($filenames as &$filename)
$filename = "/styles/".$filename;
Prefixing $medium with & just causes a syntax error.
This also fails.
function prepend($prefix,$string)
{
return $prefix.$string;
}
foreach($media as &$medium)
$medium = array_map(prepend("/styles"),$medium);
What is the simplest way to prefix "/styles/" to those css filenames given this data structure?
Try this:
$styles = array(
'Screen' => array(
"master.css",
"jquery-jvectormap-1.0.css"),
'handheld' => array("mobile.css")
);
foreach($styles as $k=>$v){
foreach($v as $a=>$b){
$styles[$k][$a] = '/styles/'.$b;
}
}
print_r($styles);
Try this:
foreach($styles as $medium => &$filenames) {
foreach($filenames as &$filename) {
$filename = "/styles/".$filename;
}
}
Some tips:
Use braces to structure your nested code. This will give you (and php) a better understanding of what is you meant
Use Indenting. This will give you a better overview.
Name the Iterating-Variable using the singular of the Array-Variable (ie. foreach($apples as $apple)). This will give you an extra hint with which variable you're dealing with.
Good Luck!
foreach($media as $medium => $filenames) {
foreach($filenames as $key => $filename) {
$media[$medium][$key] = "/styles/" . $filename;
}
}

Adding elements to an array using key/value in PHP?

I know I can add elemnts to an array like this:
$arr = array("foo" => "bar", 12 => true);
Now, how can I do that in a foreach using dynamic values? I have this code:
foreach ($values as $value) {
$imagePath = $value->getImagePath();
$dependsOn = $value->getDependsOn();
$dependsOn = explode(':', $dependsOn);
$dependsOnOptionValueTitle = trim($dependsOn[1]);
array_push($paths, $dependsOnOptionValueTitle => $imagePath); // not working
}
How can I add key/value pairs to my $paths array?
Instead of
array_push($paths, $dependsOnOptionValueTitle => $imagePath); // not working
you should be able to use
$paths[$dependsOnOptionValueTitle] = $imagePath;
From what I can see, this is what you're trying to do:
$paths[$dependsOnOptionValueTitle] = $imagePath;
Comment if I'm wrong and I'll try to fix it.

Categories