Wordpress update data from api - php

I have a plugin to create posts with data from an API. I have to check the state of the data on the api every time, if there is a change, it will update the posts and acf fields. I have a post title check so as not to duplicate posts. But how can I check posts correctly so that I can update acf fields every time if there is new data and not duplicate posts?
if( isset( $_POST['enable'] ) ) {
// JOB API
$url='https://api.com/test/';
$result = file_get_contents( $url );
$result_data = json_decode( $result );
foreach ($result_data as $job) {
$ref_code = $job->RefCode;
$post_title = $job->JobTitle;
$post_exists = post_exists( $post_title );
$job_id = $job->JobId;
$job_date = date('Y-m-d h:i:s', strtotime($job->Published));
if (!get_page_by_title($post_title, 'OBJECT', 'jobs') ) {
$data = array(
'post_type' => 'jobs',
'post_title' => $post_title,
'post_status' => 'publish',
'post_date' => $job_date,
'post_date_gmt' => $job_date
);
$post_id = wp_insert_post( $data );
wp_set_object_terms( $post_id, 'regulare-job', 'jobscat', 'post_tag' );
// Job DATA API
$job_api_url ='https://api.com/test/' . $ref_code;
$job_api_result = file_get_contents( $job_api_url );
$result_data = json_decode( $job_api_result );
//Update ACF fields
update_field( 'location', $job->RegionCity, $post_id );
update_field( 'job_intro', $result_data->Intro, $post_id );
update_field( 'job_offer', $result_data->data[0]->Text, $post_id );
update_field( 'job_requirement', $result_data->data[1]->Text, $post_id );
update_field( 'text_c2', $result_data->data[2]->Text, $post_id );
update_field( 'single_job_ref_code', $result_data->RefCode, $post_id );
}
}
}

I customized your code with some parts how i achieved it for myself.
It might need some customization. (See comments within code for additional info)
What I do:
1.) check if post is already existing based on your title (and get its id)
2.) if it is already existing => update data (ACF-Fields)
3.) if it is not existing => create new post and update meta data (ACF-Fields)
To fill the acf-fields I use a custom function based on ACF-Field-Keys.
You can also create a custom cron job to run this function every (minute, hour...)
function api_fetcher_function(){
if( isset( $_POST['enable'] ) ) {
// JOB API
$url='https://api.com/test/';
$result = file_get_contents( $url );
$result_data = json_decode( $result );
foreach ($result_data as $job) {
$ref_code = $job->RefCode;
$post_title = sanitize_title($job->JobTitle);
/* check if CPT-Post with given slug already exists */
$existing_post = get_page_by_path($post_title,'OBJECT', 'jobs');
$job_id = $job->JobId;
$job_date = date('Y-m-d h:i:s', strtotime($job->Published));
/* if post doesnt exist create a new one */
if($existing_post === null){
$inserted_post = wp_insert_post([
'post_name' => $post_title,
'post_title' => $post_title,
'post_type' => 'jobs',
'post_status' => 'publish',
'post_date' => $job_date,
'post_date_gmt' => $job_date
]);
/* continue after successful insert (single item) */
/* special error handling can be placed within if */
if( is_wp_error($inserted_post)){
continue;
}
/* Update Meta Info of new post */
updateJobsMeta($job, $inserted_post);
}else{
$existing_job_id = $existing_post->ID;
/*you can add some additional check if you have some timestamps within your api and ACF */
/*$existing_jobs_timestamp might not be needed => based on your available data*/
$existing_jobs_timestamp = get_field('updated_at', $existing_job_id);
/*if you have some timestamps to use*/
if($job->Published >= $existing_jobs_timestamp){
updateJobsMeta($job ,$existing_job_id);
}
/*if you dont have some timestamps to use just remove the if around the update function and the $existing_jobs_timestamp*/
}
}
}
}
function updateJobsMeta($job ,$id){
$ref_code = $job->RefCode;
$job_api_url ='https://api.com/test/' . $ref_code;
$job_api_result = file_get_contents( $job_api_url );
$result_data = json_decode( $job_api_result );
/* Update Fillable list based on your needs => keys can be found within your acf group in wp-backend (might be hidden by default) */
$fillable = [
'field_5f312082435dd' => $job->JobId,
'field_5f312095435de' => $job->JobTitle,
'acf_field_key....' => $job->Published
...
];
/* updates fields based on acf-key */
foreach($fillable as $key => $name){
update_field( $key, $name, $id);
}
}

Related

WORDPRESS: wp_set_post_terms not adding tags to CPT

I build a form that allow users to register sells using the frontend. I'm trying to make it pass some taxonomies that will be used to create a filter later, but even with wp_set_post_terms function the taxonomy is not being checked/tick'd at the backend when the user add/select it at the frontend.
Here is the code snippet:
<?php
global $wpdb;
global $wp_taxonomies;
$user_id = get_current_user_id();
if(isset($_POST['submitted'])) {
if($_POST['submitted'] == 'f16fca78e22e3f296692e5bbe0b5f7f0597a0bf9') {
$codigo_reserva = $_POST['codigo-reserva'];
$pax_principal = $_POST['pax-principal'];
$tag_acomodacao = $_POST['tag-acomodacao'];
$quantidade_pax = $_POST['quantidade-pax'];
$check_in = $_POST['check-in'];
$check_out = $_POST['check-out'];
$valor_venda = $_POST['valor-venda'];
$args = array(
'post_type' => 'vendas',
'post_title' => $codigo_reserva,
'post_status' => 'private',
'post_author' => $user_id,
);
$post_id = wp_insert_post($args);
$post_tags = array($tag_acomodacao);
wp_set_post_terms($post_id, $post_tags, 'acomodacao_reserva', true);
update_field('venda_pax_principal', $pax_principal, $post_id);
update_field('venda_pax_qtd', $quantidade_pax, $post_id);
update_field('checkin_venda', $check_in, $post_id);
update_field('checkout_venda', $check_out, $post_id);
update_field('venda_valor', $valor_venda, $post_id);
}
}
Everything works well except the taxonomy
Already tried to initialize $wp_taxonomies, use the explode function at the second parameter of wp_set_post_terms, pass the array as slug, and pass the array as ID

WordPress, retrieving the ID of the user profile page currently being edited

I'm in the process of developing a WordPress plugin. When editing a user's profile page, I need to be able to retrieve the ID of that user (not the currently logged in user).
I'm using the Advanced Custom fields plugin, and using a load filter for the function in question.
add_filter( 'acf/load_field/name=funbotic_parents', 'funbotic_load_parents' );
function funbotic_load_parents( $field ) {
$args = array(
'role' => 'customer',
'orderby' => 'display_name',
'order' => 'ASC',
);
$parent_data_array = get_users( $args );
// Clear choices array in case it was previously set.
$field['choices'] = array();
foreach ( $parent_data_array as $parent ) {
$parent_ID = $parent->ID;
$parent_display_name = $parent->display_name;
$field['choices'][$parent_ID] = $parent_display_name;
}
$current_user = (int) $_GET['user_id'];
$previously_associated_parents = get_user_meta( $current_user_id, 'funbotic_parents' );
if ( empty( $previously_associated_parents ) || is_null( $previously_associated_parents ) ) {
update_user_meta( $current_user_id, 'funbotic_previously_associated_parents', $previously_associated_parents );
} else {
$new_meta = funbotic_clean_array( $previously_associated_parents );
update_user_meta( $current_user_id, 'funbotic_previously_associated_parents', $new_meta );
}
return $field;
}
The line $current_user = (int) $_GET['user_id']; is returning null. Is there a way to pull 'user_id' from the URL? It's not an ideal solution but at this point I'm starting to get desperate. The URL looks like this:
http://dev-funbotic.local/wp-admin/user-edit.php?user_id=115&wp_http_referer=%2Fwp-admin%2Fusers.php%3Fs%3Dtest%26action%3D-1%26new_role%26course_id%26group_id%26paged%3D1%26action2%3D-1%26new_role2
You can try getting the current url and breaking it down to query params like this:
$query = explode('&', $_SERVER['QUERY_STRING']);
$params = array();
if(!empty($query[0])){
foreach( $query as $param ){
list($name, $value) = explode('=', $param, 2);
$params[urldecode($name)][] = urldecode($value);
}
}
then you can access the user_id by $params['user_id'][0]

WordPress: function trashs post type with a new copy of the post

I'm using the following function to trash a custom post type for events.
After an event took place, I delete the trash manually.
I found out, that the posts are still published after they should be deleted. The Version in the trash seems to be a new copy (with a new ID) of the original post?
Is there anything in the function which may produce such an error?
Here is my script:
<?php
function get_delete_old_events() {
$past_query = date('Y-m-d', strtotime('-1 day'));
// WP_Query arguments
$args = array(
'fields' => 'ids', // Only get post ID's to improve performance
'post_type' => array( 'event' ), //post type
'posts_per_page' => '-1',//fetch all posts,
'meta_query' => array(
'relation' => 'AND',
array(
'key' => 'gid_22',
'value' => $past_query,
'compare' => '<='
)
)
);
// The Query
$query = new WP_Query( $args );
// The Loop
if ( $query->have_posts() ) {
while ( $query->have_posts() ) {
$query->the_post();
// do something
$headers[] = 'From: Mail <mail#example.com>';
$postid = get_the_ID();
$post = get_post($postid);
$author = get_userdata($post->post_author);
$subject = "subject....: ".$post->post_title."";
$message = "..."
;
wp_mail($author->user_email, $subject, $message, $headers);
wp_trash_post( $id );
// Also tried with this:
// wp_trash_post( $postid );
}
} else {
// no posts found
return false;
}
// Restore original Post Data
wp_reset_postdata();
}
// expired_post_delete hook fires when the Cron is executed
add_action( 'old_event_delete', 'get_delete_old_events' );
// Add function to register event to wp
add_action( 'wp', 'register_daily_events_delete_event');
function register_daily_events_delete_event() {
// Make sure this event hasn't been scheduled
if( !wp_next_scheduled( 'old_event_delete' ) ) {
// Schedule the event
wp_schedule_event( time(), 'hourly', 'old_event_delete' );
}
}
?>
If you click the trash link then by default Wordpress will keep it for 30 days before permanently deleting it.
wp_trash_post moves an item to the trash if the 30 days havent passed and deletes it if they have, so it's working as I would expect it.
If you want to permanently delete a file straight away use wp_delete_post($post_id, true);
I found my mistake... I'm setting the ID of the post as $postid and using $id instead...

Wordpress front end posting to multiple blog in multisite with advanced custom field

I am using advanced custom field frond end posting.
<?php
function my_pre_save_post( $post_id )
{
// check if this is to be a new post
if( $post_id != 'new' )
{
return $post_id;
}
// Create a new post
$post = array(
'post_status' => 'draft' ,
'post_title' => 'A title, maybe a $_POST variable' ,
'post_type' => 'post' ,
);
// insert the post
$post_id = wp_insert_post( $post );
// update $_POST['return']
$_POST['return'] = add_query_arg( array('post_id' => $post_id), $_POST['return'] );
// return the new ID
return $post_id;
}
add_filter('acf/pre_save_post' , 'my_pre_save_post' );
?>
I want to use this method
<?php
$original_blog_id = get_current_blog_id(); // get current blog
$bids = array(1,2); // all the blog_id's to loop through
foreach($bids as $bid):
switch_to_blog($bid); //switched to blog with blog_id $bid
// ... your code for each blog ...
endforeach ;
switch_to_blog( $original_blog_id ); //switched back to current blog
?>
How can I Post to multiple blog at same time. please help me.
Problem Solved!. I got a solution from here.
http://support.advancedcustomfields.com/forums/topic/front-end-posting-to-multiple-blog/

Wordpress csv import duplicate

I've used an adapted version of a csv import plugin for wordpress. It imports the csv to create and update posts. To update existing posts I've added an edit that finds the post id by title, then if it exists it overwrites, otherwise it creates a new post.
Problem is that it seems to not be very reliable! If I import the same csv several times it over-writes most of them but I get a few duplicates. Is there any way I can make this more reliable, or is there another way I can deal with duplicate posts?
main function for creating posts here
function create_post($data, $options) {
extract($options);
//edit 1 added here
global $wpdb;
//end
$data = array_merge($this->defaults, $data);
$type = $data['csv_post_type'] ? $data['csv_post_type'] : 'post';
$valid_type = (function_exists('post_type_exists') &&
post_type_exists($type)) || in_array($type, array('post', 'page'));
if (!$valid_type) {
$this->log['error']["type-{$type}"] = sprintf(
'Unknown post type "%s".', $type);
}
$new_post = array(
'post_title' => convert_chars($data['csv_post_title']),
'post_content' => wpautop(convert_chars($data['csv_post_post'])),
'post_status' => $opt_draft,
'post_type' => $type,
'post_date' => $this->parse_date($data['csv_post_date']),
'post_excerpt' => convert_chars($data['csv_post_excerpt']),
'post_name' => $data['csv_post_slug'],
'post_author' => $this->get_auth_id($data['csv_post_author']),
'tax_input' => $this->get_taxonomies($data),
'post_parent' => $data['csv_post_parent'],
);
// edit 2 here
$new_post['ID'] = $wpdb->get_var( "SELECT ID FROM $wpdb->posts WHERE post_title = '" . $data['csv_post_title'] . "'" );
// ends
// pages don't have tags or categories
if ('page' !== $type) {
$new_post['tags_input'] = $data['csv_post_tags'];
// Setup categories before inserting
$cats = $this->create_or_get_categories($data, $opt_cat);
$new_post['post_category'] = $cats['post'];
}
// edit 3
if(!empty($new_post['ID'])) {
$id = wp_update_post($new_post);
} else {
$id = wp_insert_post($new_post);
}
// ends
if ('page' !== $type && !$id) {
// cleanup new categories on failure
foreach ($cats['cleanup'] as $c) {
wp_delete_term($c, 'category');
}
}
return $id;
}
thanks
Fixed! I used the built in wordpress function, get_page_by_title . Here is the code I used to target the correct post.
if (!get_page_by_title( $bpp_title, 'OBJECT', 'publications')) {
$id = wp_insert_post($new_post);
} else {
$bpp_page = get_page_by_title( $bpp_title, 'OBJECT', 'publications');
$new_post['ID'] = $bpp_page->ID;
$id = wp_update_post($new_post);
}

Categories