PHP array (yaml) - add or remove sections of config file - php

I have some software that uses a yaml config file and I want to dynamically add a list of registered users to the config file when they join and remove them when their accounts are deleted.
The config file is as follows:
targets:
users:
- name: AlFredo01
uid: a1fa36h2a5hbd6535c919402ba8cc837bd75abfae
userinfo:
- email: Alfredo01#gmail.com
- gender: male
- country: it
- name: AlFredo02
uid: jmed8d83m4mtjf7f7f8j299d8210sla9010labvab10
userinfo:
- email: Alfredo02#gmail.com
- gender: male
- country: gb
I effectively would like to be able to add in new names and remove by name or UID using a PHP script on register/archive.
All the info needed would be available on registration. On deleting, their UID/Name is stored in the DB exactly how it will be added to the config file.
Can this be achieved, please?
I've never used yaml files before. I've found php-yaml and I can parse the data in to an array and print or dump it.
<?
$parsed = yaml_parse_file('config2.yml');
var_dump($parsed);
?>
The above does dump the data as you would expect. Like below
Array
(
[targets] =>
[users] => Array
(
[0] => Array
(
[name] => AlFredo01
[uid] => a1fa36h2a5hbd6535c919402ba8cc837bd75abfae
[userinfo] => Array
(
[0] => Array
(
[email] => Alfredo01#gmail.com
)
[1] => Array
(
[gender] => male
)
[2] => Array
(
[country] => it
)
)
)
[1] => Array
(
[name] => AlFredo02
[uid] => jmed8d83m4mtjf7f7f8j299d8210sla9010labvab10
[userinfo] => Array
(
[0] => Array
(
[email] => Alfredo02#gmail.com
)
[1] => Array
(
[gender] => male
)
[2] => Array
(
[country] => gb
)
)
)
)
)
I'd like to be able to effectively remove a full block based on UID.
So if I wanted to remove Alfredo02, I'd remove this section
[1] => Array
(
[name] => AlFredo02
[uid] => jmed8d83m4mtjf7f7f8j299d8210sla9010labvab10
[userinfo] => Array
(
[0] => Array
(
[email] => Alfredo02#gmail.com
)
[1] => Array
(
[gender] => male
)
[2] => Array
(
[country] => gb
)
)
)
)
Based on UID: jmed8d83m4mtjf7f7f8j299d8210sla9010labvab10
Additionally, I'd like to be able to add a full section in for a new user.
I've tried basic lines to get things like the array ID to start with but keep getting nothing returned.
$search = array_search('jmed8d83m4mtjf7f7f8j299d8210sla9010labvab10', array_column($parsed, 'uid'));
Could anyone please help me with a method of removing and adding data? Once I can generate a new "output" with data added or removed, I can write that back to the config.yml file.

Through investigation and determination I have figured out a way which allows you to remove from the array and write back to the yml file with the removed block/user.
$search = print_r(array_search('jmed8d83m4mtjf7f7f8j299d8210sla9010labvab10', array_column($parsed[users], 'uid', true)));
unset($parsed[users][$search]);
echo '<pre>' , print_r($parsed) , '</pre>';
yaml_emit_file("config2.yml",$parsed);
This effectively allows you to search for your uid inside of users and then print the result on the page using echo, but you can remove this.
Then writing the whole output back to the yml file using yaml_emit_file.
The next stage will be working out how to add a new user in to the array and write that back where necessary.
I'll update when I get to that point for the benefit of others.

Related

php push an array into an existing array by it's index

I'm having trouble with putting this question to words so ill just use a simple example, hope the title sortof got my problem across.
I'm creating a blog site where I can create blogposts and people can post comments. This is all saved in JSON except for login details which are saved in MySQL.
Now saving the blogposts go fine but I'm now trying to save comments.
Lets say the blogpost array looks like this:
Array
(
[0] => Array
(
[id] => 0
[title] => first blogpost
[content] => blogpost text
)
[1] => Array
(
[id] => 1
[title] => second blogpost
[content] => blogpost 2 text
)
)
Now someone writes a comment on 'second blogpost', I save it into an array like this(user taken from MySQL):
Array
(
[user] => myusername
[comment] => first post was better!
)
Now I want to merge them like this:
Array
(
[0] => Array
(
[id] => 0
[title] => first blogpost
[content] => blogpost text
)
[1] => Array
(
[id] => 1
[title] => second blogpost
[content] => blogpost 2 text
[comments] => Array
(
[user] => myusername
[comment] => first post was better!
)
)
)
I tried searching for a while and I'd expect this to be somewhere on the site already but I can't find it. I tried a couple variations of array_push and array_merge but it always ended up replacing the relevant blogpost instead of adding onto it.
EDIT: Someone noted the new array can't just float around, I think it's better now.
If you had any related key between posts and comments ( like having post_id in comment array ) that would make more sense to merge/put them.
I assume that's your blogpost
Array
(
[0] => Array
(
[id] => 0
[title] => first blogpost
[content] => blogpost text
)
[1] => Array
(
[id] => 1
[title] => second blogpost
[content] => blogpost 2 text
)
)
And your comments should be like:
Array
(
[user] => myusername
[comment] => first post was better!
[post_id] => 1
)
That way, you would be able to find the matched blogpost.
But, outside of your data structure, here is an example to merge an item into an element of an array of array.
A nested loop example.
foreach($posts as &$post){
foreach($comments as $comment){
if($post['id'] == $comment['post_id']){
$post['comments'][] = $comment;
}
}
}
the key here is sending each reference of the element into loop by &$post and then just manipulate them in loop.
Working with indexed arrays. (Like you already have index names as post_id and a comments index as an empty array)
foreach($comments as $comment){
$posts[$comment['post_id']]['comments'][] = $comment;
}
When the blogpost is updated, I assume you can get the id of that blogpost.
Then you can check if your data structure already has a key "comments". If it does not, add the key and create an array containing the comment and the user as the first array.
If it already exists, add a new array with the user and the comment so that there can be multiple comments for each blogpost.
For example using array_map:
$blogPosts = array_map(function ($blogPost) use ($blogPostId, $comment) {
if ($blogPost["id"] === $blogPostId) {
isset($blogPost["comments"]) ? $blogPost["comments"][] = $comment : $blogPost["comments"] = [$comment];
return $blogPost;
}
return $blogPost;
}, $blogPosts);
Php demo
So I fixed it after a bit of thinking
This is the final structure:
Array
(
[0] => Array
(
[id] => 0
[title] => 1st post
[content] => 1st post works!
[date] => 21-01-2019
[comments] => Array
(
[0] => Array
(
[user] => Me
[comment] => hey 1
[date] => 12:02 21-01-2019
)
[1] => Array
(
[user] => Me
[comment] => hey 2
[date] => 12:03 21-01-2019
)
)
)
)
I added a timestamp because of a suggestion here. It's also a simplified version of what I actually use, I tried adding many more comments and on multiple posts which both work.
This is the code, I should mention the ID is in the URL and it's saved as JSON:
$filename = file.json;
$currentArray = json_decode(file_get_contents($filename), true);
$comment = $_POST['comment'];
$username = $_SESSION['username'];
$date = date("H:i d-m-Y");
$id = $_GET['id'];
Pretty straightforward so far, here is how the array is created:
$currentArray[$id]["comments"][] = array (
'user' => $username,
'comment' => $comment,
'date' => $date
);
[$id] saves it to the correct post, ["comments"] saves it to the comments key(or creates it) and the last [] gives every comment a different index inside the ["comments"].
$newJSON = json_encode($currentArray, JSON_PRETTY_PRINT);
file_put_contents($filename, $newJSON);
And lastly encoding it and saving it to JSON.
Hope this helps someone.

How to retrieve an array in URL?

Trying to get data following a shopping cart purchase on the success page but having issues with $_GET. The URL is:
http://domain.com/success.php?customer[email]=email%40gmail.com&order[button][description]=music+download&order[button][id]=89765464465423184847654556&order[button][name]=music&order[button][repeat]=&order[button][resource_path]=%2Fv2%2Fcheckouts%2F9db9d0ef-9cfd-52b9-b2d7-792683d2431d&order[button][subscription]=false
How can I parse the data from this in PHP?
If you print_r $_GET variable, then it will produce output:
Array
(
[customer] => Array
(
[email] => email#gmail.com
)
[order] => Array
(
[button] => Array
(
[description] => music download
[id] => 89765464465423184847654556
[name] => music
[repeat] =>
[resource_path] => /v2/checkouts/9db9d0ef-9cfd-52b9-b2d7-792683d2431d
[subscription] => false
)
)
)
That means you can access your data via $_GET['customer']['email'] and $_GET['order']['button']['description'] etc..
In your example, you are using what is called a query string. In order to retrieve the information from the query string, the $_GET super global exists and you can use it as follows:
$customer_email = $_GET['customer']['email'];
$order_button_description = $_GET['order']['button']['description'];
$order_button_id = $GET['order']['button']['id'];
// etc.
Let me know if that helps.

How to pull out certain value using php and this output

I've come across a weird scenario I do not know how to code around. I'm creating a JSON API for a wordpress site. I'm using the Connections plugin and trying to pull out the "original" image filename. The output of my sql command is this:
{
["options"]=>
string(396) "a:4:{s:5:"entry";a:1:{s:4:"type";s:12:"organization";}s:5:"group";a:1:{s:6:"family";a:0:{}}s:4:"logo";a:2:{s:6:"linked";b:0;s:7:"display";b:0;}s:5:"image";a:3:{s:6:"linked";b:1;s:7:"display";b:1;s:4:"name";a:4:{s:9:"thumbnail";s:25:"invoicelogo_thumbnail.jpg";s:5:"entry";s:21:"invoicelogo_entry.jpg";s:7:"profile";s:23:"invoicelogo_profile.jpg";s:8:"original";s:24:"invoicelogo_original.jpg";}}}"
}
}
I'm using the following command to acquire that:
querystr = "SELECT options FROM {$wpdb->prefix}connections WHERE id= '{$_GET['companyID']}'";
$options = $wpdb->get_results($querystr);
I'm not sure how to pull out the "original" part of this code though as it's not all that organized. Any help would be appreciated.
What you are seeing is the results of a php serialize call
To get at the original name just do this.
$decodedOptions = unserialize($options);
$original = $decodedOptions["image"]["name"]["original"];
Hope that helps
As a side note the deserialized data looks like
Array
(
[entry] => Array
(
[type] => organization
)
[group] => Array
(
[family] => Array
(
)
)
[logo] => Array
(
[linked] =>
[display] =>
)
[image] => Array
(
[linked] => 1
[display] => 1
[name] => Array
(
[thumbnail] => invoicelogo_thumbnail.jpg
[entry] => invoicelogo_entry.jpg
[profile] => invoicelogo_profile.jpg
[original] => invoicelogo_original.jpg
)
)
)

mysql query: load the information into the form fields in the CMS

I've hit a bit of a problem, I'm currently working on a custom CMS that allows the user to change the websites title, description, keywords and footer, as well as various other settings, which are all kept in one mysql table called site_settings which has two columns
setting and content, the setting column holds the settings name, for example title, and the content holds the information such as "welcome to my website", these are loaded into the site by various queries which works great, the trouble im having is I want to load the information into the form fields in the CMS, which I was hoping to do with the following query
$query = mysql_query("SELECT `setting`, `content` FROM `site_settings`");
and then create an array with the information using:
$content = mysql_fetch_array($query);
but the only way to get the information is to make a while statement that cycles through every row until it reaches the end, but what i want to be able to do is use the setting column in my table as the main identifier for retrieving the content
for example at the moment with the while array my arrays look like this:
Array ( [0] => title [1] => title [2] => title [3] => title )
Array ( [0] => keywords [1] => keywords [2] => keywords [3] => keywords )
Array ( [0] => description [1] => description [2] => description [3] => description )
Array ( [0] => footnote [1] => footnote [2] => footnote [3] => footnote )
Array ( [0] => notice_state [1] => notice_state [2] => 1 [3] => 1 )
Array ( [0] => maintenance_state [1] => maintenance_state [2] => 1 [3] => 1 )
Array ( [0] => notice_message [1] => notice_message [2] => notice [3] => notice )
Array ( [0] => maintenance_message [1] => maintenance_message [2] => maintenance [3] => maintenance )
Array ( [0] => about_us [1] => about_us [2] => about us [3] => about us )
Array ( [0] => article_shorten_length [1] => article_shorten_length [2] => 80 [3] => 80 )
so id have to cycle through them all to retrieve all the information, with the following statement:
while($content = mysql_fetch_array($query)) {
echo $content['content'];
}
but what I'm looking to do is put them all into one array with 1 or a few mysql statements like so
Array (
title -> 'welcome to my website',
description -> 'this is my website',
)
etc...
and just echo in the information by calling the setting column from my array without using a while statement and without a separate mysql query for each row like:
$content['title'];
$content['description'];
Is there a way to do this?
Use a loop with mysql_fetch_row:
while ($row = mysql_fetch_row($query))
{
$content[$row[0]] = $row[1];
}
This avoids reading the whole result set into an array that you then discard. It might be more efficient, therefore.
I am really unsure as to what exactly you want. But if I get your question properly, are you looking for the below:
while($content=mysql_fetch_array($query))
$finalResultObj[$content['setting'] ] = $content['content'];
After this, you have an associative array, and (if I have understood your question properly) you would be able to use it like $finalResultObj['setting'] to get the relevant content.
Are you sure, this is what you want?

foreach loops & stdclass objects

I've seen similar questions on here but I can't seem to apply the solutions to my problem. I have a variable called $results which I got from an API. I'll change the proper nouns so as to protect my work's customers:
stdClass Object
(
[out] => stdClass Object
(
[count] => 2
[transactions] => stdClass Object
(
[RealTimeCommissionDataV2] => Array
(
[0] => stdClass Object
(
[adId] => 12345678
[advertiserId] => 123456789
[advertiserName] => Chuck E. Cheese, inc.
[commissionAmount] => 50
[country] => US
[details] => stdClass Object
(
)
[eventDate] => 2009-11-16T09:44:25-08:00
[orderId] => X-XXXXXXXXXX
[saleAmount] => 0
[sid] => 123456789
[websiteId] => 2211944
)
[1] => stdClass Object
(
[adId] => 987654321
[advertiserId] => 12345
[advertiserName] => Chorizon Wireless.
[commissionAmount] => 50
[country] => US
[details] => stdClass Object
(
)
[eventDate] => 2009-11-16T09:58:40-08:00
[orderId] => X-CXXXXXX
[saleAmount] => 0
[sid] => 61-122112
[websiteId] => 1111922
)
)
)
)
)
I shortened it to two entries here but the number of entries will vary, it's the result of a check for transactions in the past hour, there may sometimes be only one and sometimes as many as a dozen.
I want to assign these entries to variables like websiteId1 websiteId2 etc. I know I need to do a foreach loop but can't seem to figure it out. How can I write it so that I get the "[details]" as well?
foreach ($results->out->transactions->RealTimeCommissionDataV2 AS $commissionData) {
// you can access the commissionData objects now, i.e.:
$commissionData->adId;
$commissionData->details;
}
<?
foreach ($result->out->transactions->RealTimeCommissionDataV2 as $item)
{
// do somthing with each item.
print_r($item);
// or the details array
$num_details = sizeof($item->details)
}
I think this is what you want.
EDIT
Updated based on some notes in the documentation. Specifically, these two
a numerically indexed array will not
produce results unless you use
EXTR_PREFIX_ALL or
EXTR_PREFIX_INVALID.
Prefixes are automatically separated
from the array key by an underscore
character.
echo extract( $results->out->transactions->RealTimeCommissionDataV2, EXTR_PREFIX_ALL, 'websiteId' );
// test the extract
print_r( $websiteId_0 );

Categories