Skip to content

Instantly share code, notes, and snippets.

@pippinsplugins
Created May 2, 2012 19:41
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save pippinsplugins/2579659 to your computer and use it in GitHub Desktop.
Save pippinsplugins/2579659 to your computer and use it in GitHub Desktop.
Trying to change upload directory on "download" post type
<?php
function edd_load_upload_filter() {
add_action('load-edit.php', 'edd_change_downloads_upload_dir');
add_action('load-post.php', 'edd_change_downloads_upload_dir');
}
add_action('admin_init', 'edd_load_upload_filter');
function edd_change_downloads_upload_dir() {
$current_screen = get_current_screen();
if($current_screen->post_type !== 'download') { return; }
add_filter('upload_dir', 'edd_set_upload_dir');
}
function edd_set_upload_dir($upload) {
$upload['subdir'] = '/edd' . $upload['subdir'];
$upload['path'] = $upload['basedir'] . $upload['subdir'];
$upload['url'] = $upload['baseurl'] . $upload['subdir'];
return $upload;
}
@pippinsplugins
Copy link
Author

The add_filter('upload_dir' does not seem to take effect when using the add_action('load-page' hook. It works on admin_init, but then I'm having trouble limiting it to the "download" post type only.

@thomasgriffin
Copy link

You should check to make sure that $current_screen is set in order to prevent any unwanted notices, and I think it should be !== instead of !=?

if ( $current_screen )
    if ( isset( $current_screen->post_type ) && 'download' == $current_screen->post_type )
        add_filter('upload_dir', 'edd_set_upload_dir');

That's just being picky, you really don't need it if you are sure that the object will always be available by then.

@pippinsplugins
Copy link
Author

Yeah, that's definitely true, but I'm not too concerned about that at the moment. I'm more interesting in making the "upload_dir" filter take effect first :)

@thomasgriffin
Copy link

Is 'download' the name of your post type? It seems like you would have namespaced it as edd_download or something like that.

@pippinsplugins
Copy link
Author

Yes, it is the name. It was a terrible decision to not namesapce it, but it's a bit too late at this point, at least until I make some sort of conversion function.

@bradyvercher
Copy link

Based on what I've done before, your admin_init hook should work if you do it like this:

<?php
function edd_load_upload_filter() {
    global $pagenow, $typenow;

    if ( 'download' == $typenow && ( 'edit.php' == $pagenow || 'post.php' == $pagenow ) ) {
        add_filter( 'upload_dir', 'edd_set_upload_dir' );
    }
}
?>

I'm not sure at what point upload_dir filter needs to be hooked, though. Is admin_init early enough?

@pippinsplugins
Copy link
Author

admin_init DOES work for the upload_dir filter, but for some reason $typenow and $pagenow are blank on admin_init

@thomasgriffin
Copy link

I know - you need to set the current screen first. load-$pagehook occurs before the current screen is set. So try set_current_screen() right before you get the current screen.

@deckerweb
Copy link

...you might try the hook "admin_head-{$pagenow}" --- add_action ( 'admin_head-' . $pagenow, '...' );
Nacin mentioned it, regarding the help tabs in 3.3+, here: http://wpdevel.wordpress.com/2011/12/06/help-and-screen-api-changes-in-3-3/ -- I've used it in some plugins recently, and just worked great in conjunction with global $pagenow;

@deckerweb
Copy link

...this loads after WP has loaded it stuff on the current page...

@pippinsplugins
Copy link
Author

That causes everything to be set, but all values are blank:
`WP_Screen Object
(
[action] =>
[base] =>
[id] =>
[is_network] =>
[is_user] =>
[parent_base] =>
[parent_file] =>
[post_type] =>
[taxonomy] =>
[_help_tabs:WP_Screen:private] => Array
(
)

[_help_sidebar:WP_Screen:private] => 
[_options:WP_Screen:private] => Array
    (
    )

[_show_screen_options:WP_Screen:private] => 
[_screen_settings:WP_Screen:private] => 

)`

@bradyvercher
Copy link

I'm not sure, but testing for edit.php and post.php might be the wrong approach. I haven't followed the path of an upload request before, but my guess is that it won't match either of those pages, which is why those globals aren't being set.

@pippinsplugins
Copy link
Author

@deckerweb I don't think that would work because the admin_head loads too late.

@pippinsplugins
Copy link
Author

Trying a different approach now:

<?php
function edd_change_downloads_upload_dir() {
    global $pagenow;

    if($pagenow !== 'post.php' && $pagenow !== 'post-new.php') return;

    if($pagenow == 'post.php') {
        $post = get_post($_GET['post']);
        if($post->post_type != 'download') return;
    }   

    add_filter('upload_dir', 'edd_set_upload_dir');
}
add_action('admin_init', 'edd_change_downloads_upload_dir', 999);

function edd_set_upload_dir($upload) {
    $upload['subdir']   = '/edd' . $upload['subdir'];
    $upload['path'] = $upload['basedir'] . $upload['subdir'];
    $upload['url']  = $upload['baseurl'] . $upload['subdir'];
    return $upload;
}

I've confirmed that the basic checks (I know they are no where complete) work, in terms of limiting the filter to when editing a download, but what is really strange is that the upload_dir filter doesn't work, except when I remove the $pagenow checks . . .

@bradyvercher
Copy link

Not sure if this will help, but just in case I didn't misinterpret what you're trying to do, give this a shot:

<?php
function edd_load_upload_filter() {
    global $pagenow;

    if ( ! empty( $_POST['post_id'] ) && ( 'async-upload.php' == $pagenow || 'media-upload.php' == $pagenow ) ) {
        if ( 'download' == get_post_type( $_REQUEST['post_id'] ) ) {
            add_filter( 'upload_dir', 'edd_set_upload_dir' );
        }
    }
}
add_action('admin_init', 'edd_load_upload_filter');

function edd_set_upload_dir($upload) {
    $upload['subdir']   = '/edd' . $upload['subdir'];
    $upload['path'] = $upload['basedir'] . $upload['subdir'];
    $upload['url'] = $upload['baseurl'] . $upload['subdir'];
    return $upload;
}
?>

@pippinsplugins
Copy link
Author

Aha! That appears to work perfectly. I didn't think about the fact that the media uploader has a different $pagenow id . . .that makes a lot more sense now. Props dude!

@thomasgriffin
Copy link

Ahh, I didn't know you were dealing with the media uploader. :-P In that case, check out the Media.php class file in Soliloquy to see how it is done there - it may be helpful for you in your case as well. :-)

@pippinsplugins
Copy link
Author

@thomasgriffin, whoops, yeah, should have mentioned that. The solution Brady suggested above works perfectly.

@thomasgriffin
Copy link

Sweet deal - glad you got it working. :-)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment