I'm trying to get the value of the custom field 'product_url' this code is going in functions.php and I'm using the shortcode in a single post. The custom field 'product_url' exists on this post and is not empty.
function metavalue() {
GLOBAL $post;
$meta = get_post_meta($post->ID, 'product_url', true);
echo $meta;
}
add_shortcode('url_short', 'metavalue');
nothing is being displayed when I use the shortcode. var_dump($meta); will output
string(0) ""
.
You need to pass $postid to your get_post_meta function.
function metavalue() {
global $post;
$meta = get_post_meta($post->ID, 'product_url', true);
return $meta;
}
add_shortcode('url_short', 'metavalue');
How to debug :
Check product or post have product_url value.
get the ID of product / Post you can get via admin edit post /page.
Pass ID as static value in short code function.
function metavalue() {
global $post;
$meta = get_post_meta(112, 'product_url', true); // 112 static postid
return $meta;
}
add_shortcode('url_short', 'metavalue');
Version 2 : Shortcode with parameter
Combine user attributes with known attributes and fill in defaults when needed.
The pairs should be considered to be all of the attributes which are supported by the caller and given as a list. The returned attributes will only contain the attributes in the $pairs list.
If the $atts list has unsupported attributes, then they will be ignored and removed from the final returned list.
function metavalue($atts) {
$atts = shortcode_atts(
array(
'postid' => 1,
), $atts, 'url_short' );
global $post;
$meta = get_post_meta($atts['postid'], 'product_url', true); // 112 static postid
return $meta;
}
add_shortcode('url_short', 'metavalue');
How to use:
[url_short postid=1911]
Related
I'm using a theme template and when i try to get post ID it returns the ID of the template not the ID of the actual single post.
the template ID is: 215
the post ID is: 1911
the following code will only output 215
function metavalue() {
global $post;
$meta = get_post_meta($post->ID, 'product_url', true);
return $meta;
}
add_shortcode('url_short', 'metavalue');
get_the_ID(); the_id(); $post->ID; will also output 215. i need a way to get the actual single post ID so i can get the custom field value from 'product_url'.
I've contacted support with the theme authors on this topic as well but for the time being i've found a way to work around it.
function metavalue() {
global $wp;
$url = home_url( $wp->request );
$correct_post_id = url_to_postid( $url );
$meta = get_post_meta($correct_post_id, 'product_url', true);
return $meta;
}
add_shortcode('url_short', 'metavalue');
function my_relationship_query( $args, $field, $post_id ) {
// only show children of the current post being edited
$args['post_parent'] = $post_id;
// return
return $args;
}
How for example I could pass two parameters as post_id ? Is the only way of doing that includes writing some meta queries ?
Pass an array of post IDs to post_parent__in, per WP_Query (assuming $args is representative of WP_Query params):
$post_id_array = array( $id1, $id2 );
function my_relationship_query( $args, $field, $post_id_array ) {
// only show children of the current post being edited
$args['post_parent__in'] = $post_id_array;
// return
return $args;
}
I know i can use:
global $wp_query;
$wp_query->is_page = true;
For example to set the global is_page conditional to true.
Can i change the global post title in a similar way so it would effect the the_title() returned value?
To clarify things:
I need for a use of a "virtual page" case, where no post is actually loaded and i don't want to use any existing post title. just inject some custom title to the current globals so i will get it when using the_title on the current page.
To modify the title you can use a build in hook of wordpress:
function suppress_if_blurb( $title, $id = null ) {
if ( in_category(' blurb', $id ) ) {
return '';
}
return $title;
}
add_filter( 'the_title', 'suppress_if_blurb', 10, 2 );
https://codex.wordpress.org/Plugin_API/Filter_Reference/the_title
Finally found it. gladly it's very simple :) but this piece of code will also create all other post vars for a "fake post/page":
$post_id = -99; // negative ID, to avoid clash with a valid post
$post = new stdClass();
$post->ID = $post_id;
$post->post_title = 'Some title or other';
$wp_post = new WP_Post( $post );
wp_cache_add( $post_id, $wp_post, 'posts' );
global $wp, $wp_query;
$wp_query->post = $wp_post;
$wp_query->posts = array( $wp_post );
$wp_query->queried_object = $wp_post;
$wp_query->queried_object_id = $post_id;
$wp_query->is_404=false;
$wp_query->is_page=true;
$GLOBALS['wp_query'] = $wp_query;
$wp->register_globals();
More details here!
I wan't to achieve following:
I have to save a duplicate of a newly created post if a user creates a new post (cpt). Afterwards I will set this new post with Polylang to another language as translation for the post created in step one.
Hook into following actions should lead to the desired result:
add_action('new_to_publish', 'duplicate_to_english');
add_action('draft_to_publish', 'duplicate_to_english');
add_action('pending_to_publish', 'duplicate_to_english');
function duplicate_to_english($post)
{
$en_post = pll_get_post($post->ID, 'en');
if(empty($en_post)) {
$new_post = (array) $post;
unset($new_post['ID']);
// INFINITE LOOP
$en_id = wp_insert_post($new_post);
pll_set_post_language($en_id, 'en');
}
}
But unfortunately this will result in an infinite loop (as expected). Now I'm looking for a possibility to avoid this loop. My first idea was to set a $_POST variable and only execute duplication if this variable is set. But I have no idea how to identify a new post. I discovered that WordPress immediately saves an auto-draft on clicking the 'New Post' button so looking for post ID = 0 doesn't work.
Any other approach is highly welcome.
For everyone who needs a solution:
I use the method called to save the meta data to accomplish duplicating my post:
add_action ( 'save_post', 'save_meta', 1, 3 ); // save the custom fields
function save_meta($post_id, $post, $update)
{
// here we check for the transient set in duplicate_post
// if existing delete it end return because we are saving only
// the duplicate. This will avoid infinite loop while saving the
// new translated post
$english = get_transient('saving_english');
if($english) {
delete_transient('saving_english');
return $post->ID;
}
// In case of auto saving draft we can return and don't duplicate the post
if (!wp_verify_nonce($_POST['nonce'], 'nonce')) {
return $post->ID;
}
if (! current_user_can ( 'edit_post', $post->ID )) {
return $post->ID;
}
// collect meta data from $_POST
$item_meta = $_POST['post_meta'];
// Updating meta data for the original post
loop_through_meta($item_meta, $post);
// looking for translated version
$en_id = pll_get_post($post->ID, 'en');
// If the translated post is missing, set transient,
// duplicate the post and category and afterwards write
// the taxonomy entry for polylang
if (empty($en_id)) {
set_transient('saving_english', true);
if ($en_id = duplicate_post($post, $item_meta['title_english'])) {
pll_save_post_translations([
'de' => $post->ID,
'en' => $en_id
]);
}
// If the translated posts already exists deregister the hook
// to avoid infinite loop.
// But note the third parameter priority: It must be the same
// priority as used for registering the hook
} else {
remove_action('save_post', 'save__meta',1);
wp_update_post([
'ID' => $en_id,
'post_title' => $item_meta['title_english']
]);
add_action ( 'save_post', 'save_meta', 1, 3 );
}
// If we have an id save new meta to the translated post
if(!empty($en_id)) {
loopt_through_meta($item_meta, get_post($en_id));
}
}
function duplicate_post ($post, $title)
{
$new_post = (array) $post;
unset($new_post['ID']);
$new_post['post_title'] = $title;
$new_id = wp_insert_post($new_post);
// Here we only need to set the custom category but not
// the Polylang taxonomy.
$taxonomies = get_object_taxonomies($post->post_type);
foreach ($taxonomies as $taxonomy) {
if($taxonomy != 'custom_categories') continue;
$post_terms = wp_get_object_terms($post->ID, $taxonomy, array('fields' => 'slugs'));
wp_set_object_terms($new_id, $post_terms, $taxonomy, false);
}
pll_set_post_language($new_id, 'en');
return $new_id;
}
That's it. Now everytime you create a new post or update an existing post a translated duplicate will be created or updated.
I'm trying to show a list of posts inside a var_dump, this is the actual code:
function deleted_cpt_orders() {
global $post_type, $post;
if ( $post_type == 'cpt_orders' ) {
var_dump($post);
}
}
add_action( 'trashed_post', 'deleted_cpt_orders' );
If i delete only 1 post the var_dump is shown, but if i delete 2 posts or more the result is
NULL
global $post is supposed to hold a single post object. If you delete multiple objects, it won't be set. However, trashed_post hook passes post id, therefore, you can do the following
function deleted_cpt_orders($object_id)
{
$post = get_post($object_id);
if ($post->post_type == 'cpt_orders')
{
var_dump($post);
}
}
add_action('trashed_post', 'deleted_cpt_orders');