How to auto update an acf field based on the condition? - php

I have two custom post types with acf fields.
Custom Post_A, which has 2 fields - title / submitted
Custom Post_B, which has 2 fields - title / percent
Both Post_A and B have the same title (which is the logged in user's name) and they already exist.
When a field ‘submitted’ has the value ‘done’ in Post_A, I need to automatically update a ‘percent’ field with a value ‘50’ in Post_B.
I tried the following code but it doesn't update ‘50’ to Post_B.
Would you please correct my code?
$posts = get_posts(array(
'author' => get_current_user_id(),
'posts_per_page' => -1,
'post_type' => 'post_a',
'meta_key' => 'submitted',
'meta_value' => 'done'
));
$the_query = new WP_Query( $posts );
$the_count = count($the_query);
if($the_count>0) {
foreach ($the_query as $is_done){
$my_post = array();
$my_post['post_type'] = 'post_b';
$my_post['post_title'] = the_title();
// Update the post into the database
$field_key = "field_606cb546456343";
$value = "50";
update_field( $field_key, $value);
}
}
Thank you.

You can use save_post_{$post->post_type} action hook that will trigger on specific post type. check the below code.
function update_post_b( $post_id, $post, $update ){
$post_a_title = get_the_title( $post_id );
$posts = array(
'author' => get_current_user_id(),
'posts_per_page' => -1,
'post_type' => 'post_b'
);
$post_b = new WP_Query( $posts );
if( $post_b->have_posts() ){ while ( $post_b->have_posts() ) { $post_b->the_post();
if( $post_a_title == get_the_title() ){
update_post_meta( get_the_ID(), 'percent', 50 );
}
} }
}
add_action( 'save_post_post_a', 'update_post_b', 10, 3 );
USEFUL LINKS
save_post_{$post->post_type}

Related

WP_Query does not filter results

Spent 3 days trying to get the WP_Query to work with Elementor, however had no luck so far. Elementor either refuses to process the query or does not filter the posts at all. Can somebody help me and point out some mistakes that I have in my code?
Context: the query looks for current WP user's enrollment records of post_type 'tutor_enrolled' in 'wpv1_posts' and collects IDs of user's enrolled courses into $course_ids[]. The query should then filter only the posts with IDs matching the $course_ids array, therefore displaying all of current user's courses on Elementor frontend.
function custom_query_callback( $query ) {
$current_user = wp_get_current_user();
$args = array(
'post_type' => 'tutor_enrolled',
'author' => $current_user->ID,
);
$enrollments = new WP_Query( $args );
if ( $enrollments->have_posts() ) {
$course_ids = array();
while ( $enrollments->have_posts() ) {
$enrollments->the_post();
$course_ids[] = get_post_field( 'post_parent' );
}
wp_reset_postdata();
$args = array(
'post_type' => 'courses',
'post__in' => $course_ids,
'posts_per_page' => -1,
'orderby' => 'post__in'
);
$query = new WP_Query ( $args );
}
}
}
add_action( 'elementor/query/custom_query_callback', 'custom_query_callback' );
I tried calling get_course_ids() and custom_query_callback() as two separate functions and trying to pass the $course_ids array in $query->set( 'post__in', $course_ids );.
Then I also moved the variables outside of the function, ending up with:
$current_user = wp_get_current_user();
$args = array(
'post_type' => 'tutor_enrolled',
'author' => $current_user->ID,
);
$enrollments = new WP_Query( $args );
if ( $enrollments->have_posts() ) {
$course_ids = array();
while ( $enrollments->have_posts() ) {
$enrollments->the_post();
$course_ids[] = get_post_field( 'post_parent' );
}
wp_reset_postdata();
}
add_action( 'elementor/query/custom_query_callback', function( $query ) {
$query->set( 'post__in', $course_ids );
});
None of the above resolved my issue and kept causing errors in Elementor.

Wordpress previous_post_link() and next_post_link() don't work at CPT

everyone!
There is a problem at Wordpress with CPT and ACF.
I have ACF fields ('previouspost' and 'nextpost) at my CPT "portfolio" posts. I need every post to get previous and next post links to ACF fields. Code, which I use don't make anything, fields are empty, no errors and warnings
function update_portolio_metadata(){
$args = array(
'post_type' => 'portfolio', // Only get the posts
'post_status' => 'publish', // Only the posts that are published
'posts_per_page' => -1 // Get every post
);
$posts = get_posts($args);
foreach ( $posts as $post ) {
$previouslink = previous_post_link();
$nextlink = next_post_link();
update_post_meta( $post->ID, 'previouspost', $previouslink);
update_post_meta( $post->ID, 'nextpost', $nextlink);
}
}
add_action('init','update_portolio_metadata');
Updated, checked and work
function update_portolio_metadata(){
$args = array(
'post_type' => 'portfolio', // Only get the posts
'post_status' => 'publish', // Only the posts that are published
'posts_per_page' => -1 // Get every post
);
$loop = new WP_Query( $args );
while ( $loop->have_posts() ) : $loop->the_post();
$previouslink = get_permalink(get_adjacent_post(false,'',false));
$nextlink = get_permalink(get_adjacent_post(false,'',true));
update_post_meta( get_the_ID(), 'previouspost', $previouslink);
update_post_meta( get_the_ID(), 'nextpost', $nextlink);
endwhile;
}
add_action('init','update_portolio_metadata');
There functions works in the loop only. You can use wp_query instead of get_posts.
Your code should be like this:
$loop = new WP_Query( $args );
while ( $loop->have_posts() ) : $loop->the_post();
$previouslink = get_previous_post_link();
$nextlink = get_next_post_link();
update_post_meta( get_the_ID(), 'previouspost', $previouslink);
update_post_meta( get_the_ID(), 'nextpost', $nextlink);
endwhile;
}

wp_set_object_terms not setting the terms for the post

This code does not set the object terms. Please help me sort out the issue. The code results in the posts list and doesn't set the terms.
I have checked the below data.
The query results in the list of post.
calculation part in the loop results in the value (lesser or greater than 0)
function set_expired_job_categories() {
global $post;
$current_time = time();
$taxonomy = 'current-status';
$job_expired_id = 368;
$job_ongoing_id = 367;
// Set our query arguments
$args = array(
'fields' => 'ids', // Only get post ID's to improve performance
'post_type' => 'job', // Post type
'post_status' => 'publish',
'posts_per_page' => -1,
'tax_query' => array(
'taxonomy' => 'current-status',
'field' => 'slug',
'terms' => array( 'ongoing' ),
),
);
$job_expiration_query = new WP_Query( $args );
// Check if we have posts to delete, if not, return false
if( $job_expiration_query->have_posts() ){
while( $job_expiration_query->have_posts() ){
$job_expiration_query->the_post();
$postid = get_the_ID();
$expire_timestamp = rwmb_meta( 'deadline_date' );
if ( $expire_timestamp ) {
$seconds_between = ( (int)$expire_timestamp - (int)$current_time );
if ( $seconds_between <= 0 ) {
wp_set_object_terms( $postid, (int)$job_expired_id, $taxonomy, true );
wp_remove_object_terms( $postid, (int)$job_ongoing_id, $taxonomy );
}
}
}wp_reset_postdata();
}
}
add_action( 'set_job_categories', 'set_expired_job_categories', 20, 2 );
As it is in the functions file, I need to set the global $wp_taxonomies to populate the taxonomies data initially. Also, instead of using the tag_ID, I have revised with the slug. These two changes helped to work out the code. The revised code is below for reference.
Thank you all for your efforts.
function set_expired_job_categories() {
global $post;
global $wp_taxonomies;
$current_time = time();
$taxonomy = 'current-status';
$job_expired_id = 'expired';
$job_ongoing_id = 'ongoing';
// Set our query arguments
$args = array(
'fields' => 'ids', // Only get post ID's to improve performance
'post_type' => 'job', // Post type
'post_status' => 'publish',
'posts_per_page' => -1,
'tax_query' => array(
'taxonomy' => 'current-status',
'field' => 'slug',
'terms' => array( 'ongoing' ),
),
);
$job_expiration_query = new WP_Query( $args );
// Check if we have posts to set categories, if not, return false
if( $job_expiration_query->have_posts() ){
while( $job_expiration_query->have_posts() ){
$job_expiration_query->the_post();
$postid = get_the_ID();
$expire_timestamp = rwmb_meta( 'deadline_date' );
if ( $expire_timestamp ) {
$seconds_between = ( (int)$expire_timestamp - (int)$current_time );
if ( $seconds_between >= 0 ) {
}else {
wp_set_object_terms( $postid, (int)$job_expired_id, $taxonomy, true );
wp_remove_object_terms( $postid, (int)$job_ongoing_id, $taxonomy );
}
}
}
wp_reset_postdata();
}
}
// hook it to low priority value, due to CPT and Taxonomies
add_action( 'set_job_categories', 'set_expired_job_categories', 20, 2 );
Reference: https://wordpress.org/support/topic/wp_set_object_terms-in-loop-is-not-work-in-taxonomy-cpt/

Total count of advanced custom field values in WordPress

I'm trying to get the total count of a value of a custom field for WooCommerce products. My products are stock of shoes, so for each product I create a custom field for the total pairs quantity. Now I need to display in a new page the total count of pairs.
I tried with this code but the result is always 0
<?php
$pair_total = 0; //my main variable
$posts = get_posts(array(
'posts_per_page' => -1, //get all post
'post_type' => 'product' //my custom post type
));
if( $posts ) {
foreach( $posts as $post ){
setup_postdata( $post );
if (get_field('n_totale')) {
echo get_field('n_totale'); //show individual field(not needed)
$pair_total = get_field('n_totale') + $pair_total; //sum all fields
}
}
wp_reset_postdata();
}?>
<?php echo '<h1>'.$pair_total.'</h1>'//showing the total value;
?>
What can I try next?
check get_field() Try below code.
<?php
$pair_total = 0; //my main variable
$posts = get_posts(array(
'posts_per_page' => -1, //get all post
'post_type' => 'product' //my custom post type
));
if( $posts ) {
foreach( $posts as $post ){
setup_postdata( $post );
if ( get_field( 'n_totale', get_the_ID() ) ) {
$pair_total = $pair_total + (int) get_field('n_totale', get_the_ID() ); //sum all fields
}
}
wp_reset_postdata();
}
echo '<h1>'.$pair_total.'</h1>'//showing the total value;
?>
I solved with this code:
$pair_total_1 = 0; //my main variable
$posts = get_posts(array(
'numberposts' => -1, //get all post, previously was post_per_page
'post_type' => 'product', //my custom post type
'post_status' => 'publish',
'meta_query' => array(
array(
'key' => '_stock_status',
'value' => 'instock',
'compare' => '=',
)
) //I add a query to count only in stock product
));
if( $posts ) {
global $post;
foreach( $posts as $post ){
setup_postdata( $post);
if ( get_field( 'n_totale', get_the_ID() ) ) {
$pair_total_1 = $pair_total_1 + (int) get_field('n_totale', get_the_ID() );
//sum all fields
}
}
wp_reset_postdata();
}
echo '<p>Totale paia disponibili: '.$pair_total_1.'</p>';}//showing the total value
Thanks to all

Wordpress - Meta query with post id

Can I add ID to the $args array? I need to check if the key value pair custom field exists for a particular post. Now it checks if the key value pair exists in any post. Or do I need to perform the query and then check for my value in the returned array?
$args = array(
'post_type' => 'post',
'post_status' => 'publish',
'ID' => $_POST['post_id'],
'meta_query' => array(
array(
'key' => 'claim',
'value' => $user_ID
)
)
);
// perform the query
$query = new WP_Query( $args );
$vid_ids = $query->posts;
if ( empty( $vid_ids ) ) {
add_post_meta( $_POST['post_id'], 'claim', $user_ID );
}else{
echo "sorry";
}
Please reference the Codex entry for post/page parameters for WP_Query().
You can pass single post id with this
$query = new WP_Query( array( 'p' => 7 ) );
If you want to pass multiple post id's use
$myarray = array('100', '222');
$args = array(
'post_type' => 'post',
'post__in' => $myarray
);
// The Query
$the_query = new WP_Query( $args );
Use get_post_meta to get custom field value for your object.
$claims=get_post_meta($ID,'claim');
$exists=false;
if(count($claims)>0)
{
foreach($claims as $claim)
{
if($claim==$user_ID)
{
$exists=true;
break;
}
}
}
if(!$exists)
{
add_post_meta( $_POST['post_id'], 'claim', $user_ID );
}

Categories