Leave a Reply

3 comments

  1. I normalize the output of these functions using this logic:

    1. Cast the value to an array. If it is not an array already, it will be converted to an array with one element, which is the value it was, e.g. (array) false becomes array (false).
    2. Use array_filter, which, when not passed a callable, simply filters falsy values from the array.

    Here is this logic in action:

    foreach (array_filter((array) get_post_meta($id, $meta_key)) as $value) {
        // ...
    }
    

    Warning: This will strip all falsy values, e.g. if your meta value is zero or an empty string, it will be not be iterated through.

  2. If you always need an array, just use get_post_custom( get_the_ID() ) and extract the value that you need by key.

    $meta = get_post_custom( get_the_ID() );
    $target = ! isset( $meta['your_key'] ) ?: $meta['your_key'];
    

    Your return value will either be FALSE (so you can test with ! against it), or your value.

  3. get_post_meta() does not return false if the key doesn’t exist.

    Return Value

    • If only
      $id is set it will return all meta values in an associative
      array.
    • If $single is set to false, or left
      blank, the function returns an array containing all values of the
      specified key.
    • If $single is set to true,
      the function returns the first value of the specified key (not in an
      array)

    If there is nothing to return the function will return an empty array unless
    $single has been set to true, in which case an empty string is returned.

    http://codex.wordpress.org/Function_Reference/get_post_meta#Return_Value

    If you look at the source, you will see that get_post_meta() is a wrapper around get_metadata() which is used to retrieve data in several different contexts.

    get_metadata() will return false if you give it very bad information, but that should never happen with the get_post_meta() wrapper unless the ID is not set or is empty or is set to something that won’t caste to an int. For example:

    $meta = get_post_meta($id, 'nonexistent');
    var_dump($meta);
    

    Or

    $id = '';
    $meta = get_post_meta($id, 'nonexistent');
    var_dump($meta);
    

    Or

    $id = 'abc';
    $meta = get_post_meta($id, 'nonexistent');
    var_dump($meta);
    

    Whereas, setting $id to any integer or numeric string will result in an empty array.

    Your analysis of the function is wrong. Whatever is going wrong with your code is going wrong before the call to get_post_meta(). You really should be checking that $id is correct before trying to use it.

    From another perspective, simply returning an empty array for all case would be providing less feedback, less information, for applications that need it. If you don’t need the extra feedback the code is trivial and can be don in several ways. I prefer:

    $id = 'abc';
    $meta = get_post_meta($id, 'abcdbroken');
    if (!empty($meta)) {
      foreach ($meta as $value) {
          // ...
      }
    }
    

    But if your PHP is recent enough, you could also use a shortcut ternary, which makes for very succinct code:

    $meta = (get_post_meta($id, 'abcdbroken')) ?: array();