Opened 14 years ago
Last modified 2 years ago
#14017 assigned enhancement
New template "tag": get_custom_field()
Reported by: | filosofo | Owned by: | obenland |
---|---|---|---|
Milestone: | Future Release | Priority: | normal |
Severity: | normal | Version: | 3.0 |
Component: | Posts, Post Types | Keywords: | has-patch needs-unit-tests dev-feedback |
Focuses: | template | Cc: |
Description
It would be helpful to have a way to retrieve a custom field value that is somewhat agnostic of current context.
Current way to do this
In the header (i.e., before the Loop), one has to access the currently-queried object to get a custom value, with something like this:
$value = get_post_meta($GLOBALS['wp_query']->get_queried_object_id(), 'field', true);
In the Loop:
$value = get_post_meta(get_the_ID(), 'field', true);
And, lots of tutorials out there tell people to do things like the following, with varying degrees of success (depending on variable scope):
$value = get_post_meta($id, 'field', true);
or
$value = get_post_meta($post->ID, 'field', true);
My proposed function (or "template tag")
mixed get_custom_field ( string $fieldname [, int $post_id ] )
$value = get_custom_field('field');
It picks the current object like so:
Passed post object ID? / \ yes no | | use it | | within Loop? / \ yes no | | use current | Loop ID | | currently queried object is singular? / \ yes no | | use its ID ID = 0
Attachments (1)
Change History (17)
#3
@
14 years ago
- Keywords commit removed
Not convinced about the naming of this.
It really irks me that we call post meta by two different names and promoting that more here is not good IMHO.
Can we not just extend get_post_meta() to have this behaviour if passed a 0 id?
#4
@
14 years ago
I don't really care about the name, so please suggest one. However, they're called "Custom Fields" on the post edit page, so it seems like the reasonable name to me. The name of the db table the actual data is stored in is irrelevant to the person using the API, right?
I think changing get_post_meta
to accept 0 as an argument like that is going to have serious backwards-compatibility issues, because get_post_meta
should fail when given an invalid ID. And then they still have to add "true" to make sure they get a string.
My general idea is to make the lives of template designers easier.
#5
follow-up:
↓ 6
@
14 years ago
I don't care what we call it, but it's a very nifty function.
get_post_meta_field()?
#6
in reply to:
↑ 5
@
14 years ago
Replying to nacin:
I don't care what we call it, but it's a very nifty function.
Got to agree with you there! :)
#7
@
14 years ago
- Keywords 3.2-early added
- Milestone changed from 3.1 to Future Release
This is possibly a nifty idea.
But it is past the time for introducing new apis in 3.1
We should consider this for 3.2 though
#8
follow-up:
↓ 9
@
14 years ago
How about we make a WP_Post class, with a custom_field() method:
echo $post->custom_field( 'key' );
Of course, it could be extended with other methods too.
#9
in reply to:
↑ 8
@
14 years ago
- Cc mikeschinkel@… added
Replying to scribu:
How about we make a WP_Post class, with a custom_field() method:
echo $post->custom_field( 'key' );Of course, it could be extended with other methods too.
+1
#10
@
13 years ago
- Cc jared@… added
- Keywords changed from has-patch, 3.2-early to has-patch 3.2-early
edit: not sure why its playing with the keywords
#13
@
10 years ago
There is a way to retrieve a custom field value that is somewhat agnostic of current context: post_custom()
(#).
I suppose we could introduce a function that is a bit more coherent with the naming conventions of template tags, and which optionally also accepts a post id:
<?php /** * Retrieve the value for a post meta field. * * @since 4.0.0 * * @param string $key The meta key to retrieve. * @param int $post_id Optional. Post ID. * * @return mixed The value of meta data field or an empty string. */ function get_post_meta_value( $key, $post_id = 0 ) { return get_post_meta( get_post( $post_id )->ID, $key, true ); }
But one could make the argument that it is not strictly necessary. If they're looking for a meta value of a specific post, they can use get_post_meta()
. If they're looking for a meta value of the current post, they can use post_custom()
.
#14
@
9 years ago
- Keywords 2nd-opinion removed
- Owner changed from filosofo to obenland
- Status changed from new to assigned
Do you want to do anything here?
#16
@
2 years ago
As mentioned by @obenland in comment 13, post_custom() is already available.
There is also get_post_custom_values(), which returns an array of values for the given field.
Following that, this works:
<?php function get_post_custom_value( $key = '', $post_id = 0 ) { $value = get_post_custom_values( $key, $post_id ); return $value ? maybe_unserialize( $value[0] ) : null; } // Usage var_dump( get_post_custom_value( 'my_custom_field' ) );
- Is consistent with existing naming i.e.
post_custom()
,get_post_custom()
,get_post_custom_values()
. - Lets get_post_custom() handle checks on
$post_id
. - Reduces maintenance.
- Reduces the number of unit tests required.
However, get_post_custom_values()
is in use by 789 plugins and 140 themes.
While I don't have the strict number of plugins and themes using get_post_meta()
- because I don't want to write the regex for excluding default meta fields 😝 - a cursory glance at plugins using get_post_meta()
ref and plugins using get_post_meta( get_the_ID()...
ref suggests that get_post_meta()
is used significantly more often for custom fields - likely for the reasons mentioned in this ticket's description.
Therefore, do we:
- as the current patch does, introduce a new function that also tries to use the current queried object and has a name more consistent with
get_post_meta()
in hopes it would make transitioning more likely. - introduce something like
get_post_custom_value()
above for consistency with the already available functions, since any new function will be mentioned in a dev note anyway. - don't introduce a new function, as the community already widely uses
get_post_meta()
and adding a new function might just introduce another asset for the BC-promise?
This makes a lot of sense. A friend was asking how to do this earlier, and I went through the same thought process as above when explaining it. +1