I have a custom role, called "dealer". Once they have posted a new post, they cannot delete it. It's important they cannot update the date either, and I'm a little stuck on how to do this. It looks like the old D/M/Y is preserved in the $_POST global, so I thought I'd over write any updated information for the date with this. Check out my code;

function rd_dealer_save_post($post_id)
$post_author_id = $_POST['post_author'];
//test if this author is a dealer based on the caps
if(!current_user_can('delete_published_posts'. $post_author_id))
    $_POST['mm'] = $_POST['hidden_mm'];
    $_POST['jj'] = $_POST['hidden_jj'];
    $_POST['aa'] = $_POST['hidden_aa'];
    $_POST['hh'] = $_POST['hidden_hh'];
    $_POST['mn'] = $_POST['hidden_mn']; 
add_action('save_post', 'rd_dealer_save_post');

Is my action correct? Any thoughts as this doesn't seem to work...

Thanks, Dan.

  • 2
    What's with the 'delete_published_posts'. $post_author_id? Get rid of the ID part, and it should do... – tfrommen Sep 7 '13 at 12:58
  • Yeah, should be a comma..! – Dan Sep 8 '13 at 11:53

As @t-f pointed out in his comment to question, you have an error on checking current user capability: 'delete_published_posts'. $post_author_id simply doesn't exist.

After that, for your scope probably is a better hookin the filter wp_insert_post_data instead of the action save_post: because this one run when the post was already saved / updated, so if something is wrong you have to change and update again.

Hooking wp_insert_post_data filter, you can change the data that are being updated before update is ran, so this will improve performance.

add_filter('wp_insert_post_data', 'prevent_post_change', 20, 2);

function prevent_post_change( $data, $postarr ) {
  if ( ! isset($postarr['ID']) || ! $postarr['ID'] || current_user_can('delete_published_posts') )
    return $data;
  $old = get_post($postarr['ID']); // old post
  // prevent changing date
  $data['post_date'] =  $old->post_date 
  $data['post_date_gmt'] =  $old->post_date_gmt 
  // prevent sent to trash
  if ( $data['post_status'] == 'trash' ) $data['post_status'] = $old->post_status;
  return $data;
  • Thanks, this is great, Pity I couldn't figure it out myself, but on the plus side, your code works well and I learnt a new hook (wp_insert_post_data). Thanks – Dan Sep 8 '13 at 11:53
  • 1
    Although, I had to change this piece of code isset($postarr['ID'] because the ID is 0 before a new post is published, so I did $postarr['ID'] == 0 – Dan Sep 8 '13 at 13:39
  • @Dan good catch. I've edited my answer, mantaining ! isset($postarr['ID']) and adding || ! $postarr['ID'] – gmazzap Sep 8 '13 at 13:57
  • Yes, that's the right idea. != 0 is ok, but !isset is better I think. Thanks again for your help on this one. – Dan Sep 8 '13 at 18:00
  • Without ! isset($postarr['ID']) even the $postarr['ID'] == 0 check in the if will output a notice if the $postarr['ID'] is not defined at all. Can this ever happen? I'm not sure, but better be sure ;) @Dan – gmazzap Sep 8 '13 at 18:11

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.