LLMS_Admin_Media_Protection_Attachment_Settings
Contents
Source Source
File: includes/admin/class-llms-admin-media-protection-attachment-settings.php
class LLMS_Admin_Media_Protection_Attachment_Settings {
public function __construct() {
add_filter( 'attachment_fields_to_edit', array( $this, 'attachment_fields_to_edit' ), 10, 2 );
add_filter( 'attachment_fields_to_save', array( $this, 'attachment_fields_to_save' ), 10, 2 );
}
/**
* Add the media protection settings to the attachment edit screen
*
* @param array $form_fields Array of form fields
* @param object $post WP_Post object
* @return array
*/
public function attachment_fields_to_edit( $form_fields, $post ) {
$selected_product_html = $protection_warning_html = '';
$selected_product_id = get_post_meta( $post->ID, '_llms_media_protection_product_id', true );
if ( $selected_product_id && ( $selected_product = get_post( $selected_product_id ) ) ) {
$selected_product_html = sprintf( '<option value="%d" selected="selected">%s</option>', $selected_product->ID, $selected_product->post_title );
}
$protector = new LLMS_Media_Protector();
if ( ! $protector->is_media_protected( $post->ID ) ) {
// translators: %s is a link to the LifterLMS documentation.
$protection_warning_html = '<div class="llms-media-protection-warning">' . sprintf( __( 'This media is not protected. If you select a product here, the media will be moved to the protected uploads directory and existing links to the media will no longer work. %1$sLearn More%2$s', 'lifterlms' ), '<a target="_blank" href="https://lifterlms.com/docs/how-protected-media-files-work/?utm_source=LifterLMS%20Plugin&utm_medium=Media&utm_campaign=Backend%20Help%20Page">', '</a>' ) . '</div>';
}
$form_fields['llms_media_protection_post'] = array(
'label' => __( 'LifterLMS Media Protection:', 'lifterlms' ),
'input' => 'html',
// TODO: Add selected course/membership to the select2 dropdown if known for this attachment post.
'html' => "$protection_warning_html<select id='attachments-" . $post->ID . "-llms_media_protection_post' class='llms-posts-select2' data-no-view-button='true' data-allow_clear='false' data-post-type='course,llms_membership' name='attachments[" . $post->ID . "][llms_media_protection_post]'>$selected_product_html</select>",
'helps' => $protector->is_media_protected( $post->ID ) ? sprintf( __( 'Access is restricted to the selected course/membership. %1$sLearn More%2$s', 'lifterlms' ), '<a target="_blank" href="https://lifterlms.com/docs/how-protected-media-files-work/?utm_source=LifterLMS%20Plugin&utm_medium=Media&utm_campaign=Backend%20Help%20Page">', '</a>' ) : '',
);
/**
* Filter the LifterLMS media protection attachment field.
*
* @since 10.0.0
*
* @param array $field Attachment field definition.
* @param WP_Post $post Attachment post object.
* @param LLMS_Media_Protector $protector Media protector instance.
*/
$form_fields['llms_media_protection_post'] = apply_filters( 'llms_media_protection_attachment_field', $form_fields['llms_media_protection_post'], $post, $protector );
return $form_fields;
}
/**
* Save the media protection settings
*
* @param array $post Array of post data
* @param array $attachment Array of attachment data
* @return array
*/
public function attachment_fields_to_save( $post, $attachment ) {
if ( ! empty( $attachment['llms_media_protection_post'] ) ) {
if ( $this->move_attachment_to_protected_dir( $post['ID'] ) ) {
update_post_meta( $post['ID'], '_llms_media_protection_product_id', absint( $attachment['llms_media_protection_post'] ) );
}
}
return $post;
}
/**
* Move an existing media attachment over to the protected folder.
*
* @param $attachment_id
* @since 9.0.0
*
* @return bool
*/
function move_attachment_to_protected_dir( $attachment_id ) {
// Get attachment metadata.
$metadata = wp_get_attachment_metadata( $attachment_id );
$file = get_attached_file( $attachment_id );
// Get the protected upload directory.
$protector = new LLMS_Media_Protector();
// We could check that the file is in the protected folder, but currently there's no "unprotect" method.
if ( $protector->is_media_protected( $attachment_id ) ) {
return false;
}
$protected_dir = $protector->get_upload_basedir();
global $wp_filesystem;
if ( empty( $wp_filesystem ) ) {
require_once ABSPATH . '/wp-admin/includes/file.php';
WP_Filesystem();
}
$new_file = str_replace( wp_upload_dir()['basedir'], wp_upload_dir()['basedir'] . untrailingslashit( $protected_dir ), $file );
if ( ! $wp_filesystem->is_dir( dirname( $new_file ) ) ) {
wp_mkdir_p( dirname( $new_file ) );
}
if ( $wp_filesystem->move( $file, $new_file ) ) {
// Move thumbnails if they exist.
if ( ! empty( $metadata['sizes'] ) ) {
$base_dir = dirname( $file );
$new_base_dir = dirname( $new_file );
// Multiple registered sizes can share the same physical file.
$moved_files = array();
foreach ( $metadata['sizes'] as $size => $size_info ) {
if ( in_array( $size_info['file'], $moved_files, true ) ) {
continue;
}
$old_thumb = $base_dir . '/' . $size_info['file'];
$new_thumb = $new_base_dir . '/' . $size_info['file'];
if ( ! $wp_filesystem->exists( $old_thumb ) ) {
error_log( 'Registered metadata thumbnail file does not exist. Skipping. ' . $old_thumb );
continue;
}
if ( ! $wp_filesystem->move( $old_thumb, $new_thumb ) ) {
error_log( 'Unable to move protected file. Thumbnail moving failed: ' . $old_thumb . ' to ' . $new_thumb );
// Move the file back along with any thumbnails we already moved.
$wp_filesystem->move( $new_file, $file );
foreach ( $moved_files as $moved_file ) {
$old_thumb = $base_dir . '/' . $moved_file;
$new_thumb = $new_base_dir . '/' . $moved_file;
if ( $wp_filesystem->exists( $new_thumb ) ) {
$wp_filesystem->move( $new_thumb, $old_thumb );
}
}
return false;
}
$moved_files[] = $size_info['file'];
}
}
// Update attachment location in database.
update_attached_file( $attachment_id, $new_file );
// This only exists with images it seems.
if ( array_key_exists( 'file', $metadata ) ) {
$metadata['file'] = ltrim( $protected_dir, '/' ) . $metadata['file'];
wp_update_attachment_metadata( $attachment_id, $metadata );
}
$protector->add_authorization_meta_to_media_post( $attachment_id );
return true;
}
error_log( 'Unable to move protected file, check permissions on the protected directory or existing file with the same name: ' . $file );
return false;
}
}
Expand full source code Collapse full source code View on GitHub
Methods Methods
- __construct
- attachment_fields_to_edit — Add the media protection settings to the attachment edit screen
- attachment_fields_to_save — Save the media protection settings
- move_attachment_to_protected_dir — Move an existing media attachment over to the protected folder.