Compare commits
3 Commits
55e0ad611c
...
edfd5886eb
Author | SHA1 | Date | |
---|---|---|---|
edfd5886eb | |||
ed1b9fdb17 | |||
23560bb1fc |
@ -24,7 +24,8 @@ class AlbumCollageGenerator {
|
|||||||
$this->text_color = $this->hex_to_rgb('#ececec');
|
$this->text_color = $this->hex_to_rgb('#ececec');
|
||||||
$this->western_font = plugin_dir_path(__FILE__) . 'assets/co1251n.ttf';
|
$this->western_font = plugin_dir_path(__FILE__) . 'assets/co1251n.ttf';
|
||||||
$this->japanese_font = plugin_dir_path(__FILE__) . 'assets/BIZUDPMincho-Regular.ttf';
|
$this->japanese_font = plugin_dir_path(__FILE__) . 'assets/BIZUDPMincho-Regular.ttf';
|
||||||
$this->blacklisted_artists = array('Drake', 'Mac Miller'); // placeholder values
|
$this->blacklisted_artists = array('Drake', 'Mac Miller', 'Kendrick Lamar');
|
||||||
|
$this->blacklisted_albums = array('OK Computer OKNOTOK 1997 2017');
|
||||||
}
|
}
|
||||||
|
|
||||||
public function register_endpoint() {
|
public function register_endpoint() {
|
||||||
@ -111,20 +112,39 @@ class AlbumCollageGenerator {
|
|||||||
|
|
||||||
private function get_top_albums($year, $month) {
|
private function get_top_albums($year, $month) {
|
||||||
// Prepare placeholders for blacklisted artists
|
// Prepare placeholders for blacklisted artists
|
||||||
$placeholders = array_fill(0, count($this->blacklisted_artists), '%s');
|
$artist_placeholders = array_fill(0, count($this->blacklisted_artists), '%s');
|
||||||
$placeholders_str = implode(', ', $placeholders);
|
$artist_placeholders_str = implode(', ', $artist_placeholders);
|
||||||
|
|
||||||
// Merge all parameters for $wpdb->prepare
|
// Prepare placeholders for blacklisted albums
|
||||||
|
$album_placeholders = array_fill(0, count($this->blacklisted_albums), '%s');
|
||||||
|
$album_placeholders_str = implode(', ', $album_placeholders);
|
||||||
|
|
||||||
|
// Initialize query parts
|
||||||
|
$artist_condition = '';
|
||||||
|
$album_condition = '';
|
||||||
$query_params = array($year, $month);
|
$query_params = array($year, $month);
|
||||||
$query_params = array_merge($query_params, $this->blacklisted_artists);
|
|
||||||
|
|
||||||
|
// Handle blacklisted artists
|
||||||
|
if (!empty($this->blacklisted_artists)) {
|
||||||
|
$artist_condition = "AND author NOT IN ($artist_placeholders_str)";
|
||||||
|
$query_params = array_merge($query_params, $this->blacklisted_artists);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle blacklisted albums
|
||||||
|
if (!empty($this->blacklisted_albums)) {
|
||||||
|
$album_condition = "AND album_name NOT IN ($album_placeholders_str)";
|
||||||
|
$query_params = array_merge($query_params, $this->blacklisted_albums);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Prepare the SQL query with updated ORDER BY in ranked_covers
|
||||||
$query = $this->db->prepare(
|
$query = $this->db->prepare(
|
||||||
"WITH ranked_covers AS (
|
"WITH ranked_covers AS (
|
||||||
SELECT
|
SELECT
|
||||||
album_name,
|
album_name,
|
||||||
author,
|
author,
|
||||||
cover_url,
|
cover_url,
|
||||||
ROW_NUMBER() OVER (PARTITION BY album_name, author ORDER BY time DESC) as rn
|
id, -- Ensure id is selected for ordering
|
||||||
|
ROW_NUMBER() OVER (PARTITION BY album_name, author ORDER BY id DESC) as rn
|
||||||
FROM song_scrobbles
|
FROM song_scrobbles
|
||||||
WHERE cover_url != '' AND cover_url IS NOT NULL
|
WHERE cover_url != '' AND cover_url IS NOT NULL
|
||||||
),
|
),
|
||||||
@ -137,8 +157,8 @@ class AlbumCollageGenerator {
|
|||||||
FROM song_scrobbles
|
FROM song_scrobbles
|
||||||
WHERE YEAR(time) = %d AND MONTH(time) = %d
|
WHERE YEAR(time) = %d AND MONTH(time) = %d
|
||||||
AND album_name != '' AND album_name IS NOT NULL
|
AND album_name != '' AND album_name IS NOT NULL
|
||||||
-- Exclude blacklisted artists
|
$artist_condition
|
||||||
AND author NOT IN ($placeholders_str)
|
$album_condition
|
||||||
-- Exclude albums with '¥' symbol in album_name or author
|
-- Exclude albums with '¥' symbol in album_name or author
|
||||||
AND album_name NOT LIKE '%%¥%%'
|
AND album_name NOT LIKE '%%¥%%'
|
||||||
AND author NOT LIKE '%%¥%%'
|
AND author NOT LIKE '%%¥%%'
|
||||||
@ -310,12 +330,64 @@ class AlbumCollageGenerator {
|
|||||||
$x = $left_margin + $col * ($album_size + $gap);
|
$x = $left_margin + $col * ($album_size + $gap);
|
||||||
$y = $top_margin + $row * ($album_size + $gap);
|
$y = $top_margin + $row * ($album_size + $gap);
|
||||||
|
|
||||||
|
// Detect the image type
|
||||||
|
$image_type = @exif_imagetype($albums[$i]->cover_url);
|
||||||
|
$album_cover = false;
|
||||||
|
|
||||||
|
switch ($image_type) {
|
||||||
|
case IMAGETYPE_JPEG:
|
||||||
$album_cover = @imagecreatefromjpeg($albums[$i]->cover_url);
|
$album_cover = @imagecreatefromjpeg($albums[$i]->cover_url);
|
||||||
|
break;
|
||||||
|
case IMAGETYPE_PNG:
|
||||||
|
$album_cover = @imagecreatefrompng($albums[$i]->cover_url);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
// Unsupported image type
|
||||||
|
$album_cover = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
if ($album_cover !== false) {
|
if ($album_cover !== false) {
|
||||||
|
// If the image is PNG, preserve transparency
|
||||||
|
if ($image_type === IMAGETYPE_PNG) {
|
||||||
|
imagealphablending($album_cover, true);
|
||||||
|
imagesavealpha($album_cover, true);
|
||||||
|
}
|
||||||
|
|
||||||
$this->apply_retro_effects($album_cover);
|
$this->apply_retro_effects($album_cover);
|
||||||
imagecopyresampled($image, $album_cover, $x, $y, 0, 0, $album_size, $album_size, imagesx($album_cover), imagesy($album_cover));
|
|
||||||
|
// If the main image has transparency and the album cover is PNG, preserve it
|
||||||
|
if ($image_type === IMAGETYPE_PNG) {
|
||||||
|
imagecopyresampled(
|
||||||
|
$image,
|
||||||
|
$album_cover,
|
||||||
|
$x,
|
||||||
|
$y,
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
$album_size,
|
||||||
|
$album_size,
|
||||||
|
imagesx($album_cover),
|
||||||
|
imagesy($album_cover)
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
imagecopyresampled(
|
||||||
|
$image,
|
||||||
|
$album_cover,
|
||||||
|
$x,
|
||||||
|
$y,
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
$album_size,
|
||||||
|
$album_size,
|
||||||
|
imagesx($album_cover),
|
||||||
|
imagesy($album_cover)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
imagedestroy($album_cover);
|
imagedestroy($album_cover);
|
||||||
} else {
|
} else {
|
||||||
|
// Draw placeholder rectangle
|
||||||
$placeholder_color = imagecolorallocate($image, 100, 100, 100);
|
$placeholder_color = imagecolorallocate($image, 100, 100, 100);
|
||||||
imagefilledrectangle($image, $x, $y, $x + $album_size, $y + $album_size, $placeholder_color);
|
imagefilledrectangle($image, $x, $y, $x + $album_size, $y + $album_size, $placeholder_color);
|
||||||
}
|
}
|
||||||
@ -553,5 +625,3 @@ class AlbumCollageGenerator {
|
|||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
new AlbumCollageGenerator();
|
|
286
album-scores.php
Normal file
286
album-scores.php
Normal file
@ -0,0 +1,286 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
if ( ! defined( 'ABSPATH' ) ) {
|
||||||
|
exit; // Exit if accessed directly
|
||||||
|
}
|
||||||
|
|
||||||
|
class AlbumScoreManager {
|
||||||
|
|
||||||
|
private $scrobbles_table;
|
||||||
|
private $scores_table;
|
||||||
|
|
||||||
|
public function __construct() {
|
||||||
|
global $wpdb;
|
||||||
|
$this->scrobbles_table = 'song_scrobbles'; // Added $wpdb->prefix for table names
|
||||||
|
$this->scores_table = 'album_scores';
|
||||||
|
|
||||||
|
// Add admin menu
|
||||||
|
add_action( 'admin_menu', array( $this, 'add_admin_menu' ) );
|
||||||
|
|
||||||
|
// Enqueue admin scripts
|
||||||
|
add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_admin_scripts' ) );
|
||||||
|
|
||||||
|
// Add AJAX handler
|
||||||
|
add_action( 'wp_ajax_asm_update_score', array( $this, 'ajax_update_score' ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Enqueue custom JavaScript for handling AJAX requests
|
||||||
|
*/
|
||||||
|
public function enqueue_admin_scripts( $hook ) {
|
||||||
|
// Only enqueue on our plugin's admin page
|
||||||
|
if ( $hook !== 'toplevel_page_album-score-manager' ) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Enqueue the script
|
||||||
|
wp_enqueue_script(
|
||||||
|
'asm-admin-script',
|
||||||
|
plugin_dir_url( __FILE__ ) . 'js/asm-admin.js', // You'll create this file next
|
||||||
|
array( 'jquery' ),
|
||||||
|
'1.1',
|
||||||
|
true
|
||||||
|
);
|
||||||
|
|
||||||
|
// Localize script to pass AJAX URL and nonce
|
||||||
|
wp_localize_script(
|
||||||
|
'asm-admin-script',
|
||||||
|
'asm_ajax_obj',
|
||||||
|
array(
|
||||||
|
'ajax_url' => admin_url( 'admin-ajax.php' ),
|
||||||
|
'nonce' => wp_create_nonce( 'asm_ajax_nonce' ),
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add a new menu item under the WordPress admin sidebar
|
||||||
|
*/
|
||||||
|
public function add_admin_menu() {
|
||||||
|
add_menu_page(
|
||||||
|
'Album Score Manager', // Page title
|
||||||
|
'Album Scores', // Menu title
|
||||||
|
'manage_options', // Capability
|
||||||
|
'album-score-manager', // Menu slug
|
||||||
|
array( $this, 'admin_page' ), // Callback function
|
||||||
|
'dashicons-awards', // Icon
|
||||||
|
6 // Position
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Admin page callback
|
||||||
|
*/
|
||||||
|
public function admin_page() {
|
||||||
|
if ( ! current_user_can( 'manage_options' ) ) {
|
||||||
|
wp_die( __( 'You do not have sufficient permissions to access this page.' ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
global $wpdb;
|
||||||
|
|
||||||
|
// Fetch albums sorted by total plays
|
||||||
|
$albums = $wpdb->get_results(
|
||||||
|
"SELECT album_name, COUNT(*) as play_count
|
||||||
|
FROM `{$this->scrobbles_table}`
|
||||||
|
WHERE album_name IS NOT NULL
|
||||||
|
GROUP BY album_name
|
||||||
|
ORDER BY play_count DESC",
|
||||||
|
OBJECT
|
||||||
|
);
|
||||||
|
|
||||||
|
// Fetch existing scores
|
||||||
|
$existing_scores = $wpdb->get_results(
|
||||||
|
"SELECT album_name, score, author, cover_url FROM `{$this->scores_table}`",
|
||||||
|
ARRAY_A
|
||||||
|
);
|
||||||
|
|
||||||
|
$scores_assoc = array();
|
||||||
|
foreach ( $existing_scores as $score ) {
|
||||||
|
$scores_assoc[ $score['album_name'] ] = array(
|
||||||
|
'score' => $score['score'],
|
||||||
|
'author' => $score['author'],
|
||||||
|
'cover_url' => $score['cover_url'],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Prepare latest author and cover_url from song_scrobbles
|
||||||
|
$latest_entries = $this->get_latest_song_scrobbles( $albums );
|
||||||
|
|
||||||
|
?>
|
||||||
|
<div class="wrap">
|
||||||
|
<h1>Album Score Manager</h1>
|
||||||
|
<table class="widefat fixed striped">
|
||||||
|
<thead>
|
||||||
|
<tr>
|
||||||
|
<th>Album Name</th>
|
||||||
|
<th>Author</th>
|
||||||
|
<th>Cover</th>
|
||||||
|
<th>Total Plays</th>
|
||||||
|
<th>Score</th>
|
||||||
|
<th>Status</th> <!-- Column to show update status -->
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody>
|
||||||
|
<?php if ( ! empty( $albums ) ) : ?>
|
||||||
|
<?php foreach ( $albums as $album ) :
|
||||||
|
$album_name = esc_html( $album->album_name );
|
||||||
|
$play_count = intval( $album->play_count );
|
||||||
|
|
||||||
|
// Fetch latest song_scrobbles entry for this album
|
||||||
|
$latest_entry = isset( $latest_entries[ $album->album_name ] ) ? $latest_entries[ $album->album_name ] : null;
|
||||||
|
|
||||||
|
$latest_author = $latest_entry ? esc_html( $latest_entry->author ) : '';
|
||||||
|
$latest_cover_url = $latest_entry ? esc_url( $latest_entry->cover_url ) : '';
|
||||||
|
|
||||||
|
// Existing scores
|
||||||
|
$current_score = isset( $scores_assoc[ $album->album_name ]['score'] ) ? esc_html( $scores_assoc[ $album->album_name ]['score'] ) : '';
|
||||||
|
$current_author = isset( $scores_assoc[ $album->album_name ]['author'] ) ? esc_html( $scores_assoc[ $album->album_name ]['author'] ) : $latest_author;
|
||||||
|
$current_cover_url = isset( $scores_assoc[ $album->album_name ]['cover_url'] ) ? esc_url( $scores_assoc[ $album->album_name ]['cover_url'] ) : $latest_cover_url;
|
||||||
|
?>
|
||||||
|
<tr id="asm-row-<?php echo esc_attr( $album->album_name ); ?>">
|
||||||
|
<td><?php echo $album_name; ?></td>
|
||||||
|
<td><?php echo $current_author; ?></td>
|
||||||
|
<td>
|
||||||
|
<img loading="lazy" src="<?php echo $current_cover_url; ?>" width=128>
|
||||||
|
|
||||||
|
</td>
|
||||||
|
<td><?php echo $play_count; ?></td>
|
||||||
|
<td>
|
||||||
|
<select class="asm-score-dropdown" data-cover="<?php echo $current_cover_url; ?>" data-author="<?php echo $current_author; ?>" data-album="<?php echo esc_attr( $album->album_name ); ?>" style="width: 100%;">
|
||||||
|
<option value="">-- Select Score --</option>
|
||||||
|
<?php
|
||||||
|
$score_options = array( 'F', 'C', 'B', 'A', 'S', 'S+' );
|
||||||
|
foreach ( $score_options as $option ) : ?>
|
||||||
|
<option value="<?php echo $option; ?>" <?php selected( $current_score, $option ); ?>>
|
||||||
|
<?php echo $option; ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</td>
|
||||||
|
<td class="asm-status">
|
||||||
|
<!-- Status messages will appear here -->
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
<?php else : ?>
|
||||||
|
<tr>
|
||||||
|
<td colspan="6">No albums found.</td>
|
||||||
|
</tr>
|
||||||
|
<?php endif; ?>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<?php
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Fetch the latest song_scrobbles entry for each album
|
||||||
|
*
|
||||||
|
* @param array $albums Array of album objects
|
||||||
|
* @return array Associative array with album_name as key and latest entry as value
|
||||||
|
*/
|
||||||
|
private function get_latest_song_scrobbles( $albums ) {
|
||||||
|
global $wpdb; // Ensure $wpdb is declared as global
|
||||||
|
|
||||||
|
if ( empty( $albums ) ) {
|
||||||
|
return array();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Initialize an array to hold the latest entries
|
||||||
|
$latest_entries = array();
|
||||||
|
|
||||||
|
foreach ( $albums as $album ) {
|
||||||
|
$latest_entry = $wpdb->get_row( $wpdb->prepare(
|
||||||
|
"SELECT author, cover_url
|
||||||
|
FROM `{$this->scrobbles_table}`
|
||||||
|
WHERE album_name = %s
|
||||||
|
ORDER BY id DESC
|
||||||
|
LIMIT 1",
|
||||||
|
$album->album_name
|
||||||
|
) );
|
||||||
|
|
||||||
|
if ( $latest_entry ) {
|
||||||
|
$latest_entries[ $album->album_name ] = $latest_entry;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $latest_entries;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* AJAX handler to update a single album's score
|
||||||
|
*/
|
||||||
|
public function ajax_update_score() {
|
||||||
|
// Check nonce
|
||||||
|
check_ajax_referer( 'asm_ajax_nonce', 'nonce' );
|
||||||
|
|
||||||
|
// Check user capabilities
|
||||||
|
if ( ! current_user_can( 'manage_options' ) ) {
|
||||||
|
wp_send_json_error( 'Unauthorized user.' );
|
||||||
|
wp_die();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get and sanitize input
|
||||||
|
$album = isset( $_POST['album'] ) ? sanitize_text_field( $_POST['album'] ) : '';
|
||||||
|
$score = isset( $_POST['score'] ) ? sanitize_text_field( $_POST['score'] ) : '';
|
||||||
|
$cover_url = isset( $_POST['cover_url'] ) ? esc_url_raw( $_POST['cover_url'] ) : '';
|
||||||
|
$author = isset( $_POST['author'] ) ? sanitize_text_field( $_POST['author'] ) : '';
|
||||||
|
|
||||||
|
// Validate input
|
||||||
|
$valid_scores = array( 'F', 'C', 'B', 'A', 'S', 'S+' );
|
||||||
|
if ( empty( $album ) || empty( $score ) || ! in_array( $score, $valid_scores, true ) ) {
|
||||||
|
wp_send_json_error( 'Invalid input.' );
|
||||||
|
wp_die();
|
||||||
|
}
|
||||||
|
|
||||||
|
global $wpdb;
|
||||||
|
|
||||||
|
// Check if the album already has a score
|
||||||
|
$existing = $wpdb->get_var( $wpdb->prepare(
|
||||||
|
"SELECT id FROM `{$this->scores_table}` WHERE `album_name` = %s",
|
||||||
|
$album
|
||||||
|
) );
|
||||||
|
|
||||||
|
if ( $existing ) {
|
||||||
|
// Update existing record
|
||||||
|
$updated_rows = $wpdb->update(
|
||||||
|
$this->scores_table,
|
||||||
|
array(
|
||||||
|
'score' => $score,
|
||||||
|
'author' => $author,
|
||||||
|
'cover_url' => $cover_url,
|
||||||
|
),
|
||||||
|
array( 'id' => $existing ),
|
||||||
|
array( '%s', '%s', '%s' ),
|
||||||
|
array( '%d' )
|
||||||
|
);
|
||||||
|
|
||||||
|
if ( false !== $updated_rows ) {
|
||||||
|
wp_send_json_success( 'Score updated successfully.' );
|
||||||
|
} else {
|
||||||
|
wp_send_json_error( 'Failed to update score.' );
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// Insert new record
|
||||||
|
$inserted_rows = $wpdb->insert(
|
||||||
|
$this->scores_table,
|
||||||
|
array(
|
||||||
|
'album_name' => $album,
|
||||||
|
'score' => $score,
|
||||||
|
'author' => $author,
|
||||||
|
'cover_url' => $cover_url,
|
||||||
|
),
|
||||||
|
array( '%s', '%s', '%s', '%s' )
|
||||||
|
);
|
||||||
|
|
||||||
|
if ( false !== $inserted_rows ) {
|
||||||
|
wp_send_json_success( 'Score added successfully.' );
|
||||||
|
} else {
|
||||||
|
wp_send_json_error( 'Failed to add score.' );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
wp_die();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
49
js/asm-admin.js
Normal file
49
js/asm-admin.js
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
jQuery(document).ready(function($) {
|
||||||
|
// Listen for changes on any score dropdown
|
||||||
|
$('.asm-score-dropdown').on('change', function() {
|
||||||
|
var dropdown = $(this);
|
||||||
|
var album = dropdown.data('album');
|
||||||
|
var score = dropdown.val();
|
||||||
|
|
||||||
|
// Get the author and cover_url from the respective inputs in the same row
|
||||||
|
var row = $('#asm-row-' + album);
|
||||||
|
var author = dropdown.data('author');
|
||||||
|
var cover_url = dropdown.data('cover');
|
||||||
|
|
||||||
|
// Status cell
|
||||||
|
var statusCell = row.find('.asm-status');
|
||||||
|
|
||||||
|
if (score === '') {
|
||||||
|
// If no score is selected, do not proceed
|
||||||
|
statusCell.html('<span style="color: orange;">No score selected.</span>');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Show loading message
|
||||||
|
statusCell.html('<span style="color: blue;">Updating...</span>');
|
||||||
|
|
||||||
|
// AJAX request
|
||||||
|
$.ajax({
|
||||||
|
url: asm_ajax_obj.ajax_url,
|
||||||
|
type: 'POST',
|
||||||
|
data: {
|
||||||
|
action: 'asm_update_score',
|
||||||
|
nonce: asm_ajax_obj.nonce,
|
||||||
|
album: album,
|
||||||
|
score: score,
|
||||||
|
author: author,
|
||||||
|
cover_url: cover_url
|
||||||
|
},
|
||||||
|
success: function(response) {
|
||||||
|
if (response.success) {
|
||||||
|
statusCell.html('<span style="color: green;">' + response.data + '</span>');
|
||||||
|
} else {
|
||||||
|
statusCell.html('<span style="color: red;">' + response.data + '</span>');
|
||||||
|
}
|
||||||
|
},
|
||||||
|
error: function() {
|
||||||
|
statusCell.html('<span style="color: red;">AJAX error.</span>');
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
@ -13,8 +13,10 @@ if (!defined('ABSPATH')) {
|
|||||||
|
|
||||||
// Include the separate plugins
|
// Include the separate plugins
|
||||||
require_once(plugin_dir_path(__FILE__) . 'album-collage-generator.php');
|
require_once(plugin_dir_path(__FILE__) . 'album-collage-generator.php');
|
||||||
|
require_once(plugin_dir_path(__FILE__) . 'album-scores.php');
|
||||||
require_once(plugin_dir_path(__FILE__) . 'scrobble-handler.php');
|
require_once(plugin_dir_path(__FILE__) . 'scrobble-handler.php');
|
||||||
|
|
||||||
// Initialize both classes
|
// Initialize both classes
|
||||||
new AlbumCollageGenerator();
|
new AlbumCollageGenerator();
|
||||||
new ScrobbleHandler();
|
new ScrobbleHandler();
|
||||||
|
new AlbumScoreManager();
|
||||||
|
@ -21,6 +21,9 @@ class ScrobbleHandler {
|
|||||||
add_action('admin_menu', array($this, 'add_admin_menu'));
|
add_action('admin_menu', array($this, 'add_admin_menu'));
|
||||||
add_action('admin_init', array($this, 'register_settings'));
|
add_action('admin_init', array($this, 'register_settings'));
|
||||||
register_activation_hook(__FILE__, array($this, 'activate_plugin'));
|
register_activation_hook(__FILE__, array($this, 'activate_plugin'));
|
||||||
|
|
||||||
|
// Add action to handle form submission
|
||||||
|
add_action('admin_post_image_scrobble_upload', array($this, 'handle_image_upload'));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function activate_plugin() {
|
public function activate_plugin() {
|
||||||
@ -56,7 +59,7 @@ class ScrobbleHandler {
|
|||||||
// Sanitize and retrieve parameters from the request
|
// Sanitize and retrieve parameters from the request
|
||||||
$author = sanitize_text_field($request->get_param('author'));
|
$author = sanitize_text_field($request->get_param('author'));
|
||||||
$album_title = sanitize_text_field($request->get_param('album_title'));
|
$album_title = sanitize_text_field($request->get_param('album_title'));
|
||||||
$song_title = sanitize_text_field($request->get_param('song_title')); // New parameter
|
$song_title = sanitize_text_field($request->get_param('song_title'));
|
||||||
|
|
||||||
// Validate required parameters
|
// Validate required parameters
|
||||||
if (empty($author)) {
|
if (empty($author)) {
|
||||||
@ -91,6 +94,21 @@ class ScrobbleHandler {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Save the image and create attachment
|
||||||
|
$result = $this->save_image_and_create_attachment($image_data, $author, $title, $image_hash, $album_title);
|
||||||
|
|
||||||
|
if (is_wp_error($result)) {
|
||||||
|
return $result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Return a successful response with the image URL
|
||||||
|
return new WP_REST_Response(
|
||||||
|
array('url' => $result),
|
||||||
|
200
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
private function save_image_and_create_attachment($image_data, $author, $title, $image_hash, $album_title = '') {
|
||||||
// Get the upload directory information
|
// Get the upload directory information
|
||||||
$upload_dir = wp_upload_dir();
|
$upload_dir = wp_upload_dir();
|
||||||
|
|
||||||
@ -137,17 +155,18 @@ class ScrobbleHandler {
|
|||||||
// Save the image hash in the attachment's metadata for future duplicate checks
|
// Save the image hash in the attachment's metadata for future duplicate checks
|
||||||
update_post_meta($attach_id, 'image_hash', $image_hash);
|
update_post_meta($attach_id, 'image_hash', $image_hash);
|
||||||
|
|
||||||
|
// Save the artist and album_title in attachment metadata for future lookups
|
||||||
|
if (!empty($album_title)) {
|
||||||
|
update_post_meta($attach_id, 'artist', strtolower($author));
|
||||||
|
update_post_meta($attach_id, 'album_title', strtolower($album_title));
|
||||||
|
}
|
||||||
|
|
||||||
// Retrieve the URL of the newly created attachment
|
// Retrieve the URL of the newly created attachment
|
||||||
$image_url = wp_get_attachment_url($attach_id);
|
$image_url = wp_get_attachment_url($attach_id);
|
||||||
|
|
||||||
// Return a successful response with the image URL
|
return $image_url;
|
||||||
return new WP_REST_Response(
|
|
||||||
array('url' => $image_url),
|
|
||||||
200
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private function get_attachment_by_hash($hash) {
|
private function get_attachment_by_hash($hash) {
|
||||||
$args = array(
|
$args = array(
|
||||||
'post_type' => 'attachment',
|
'post_type' => 'attachment',
|
||||||
@ -171,6 +190,128 @@ class ScrobbleHandler {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private function get_attachment_by_artist_album($artist, $album_title) {
|
||||||
|
global $wpdb; // Access the global $wpdb object
|
||||||
|
|
||||||
|
// Primary method: Query attachments based on artist and album title
|
||||||
|
$args = array(
|
||||||
|
'post_type' => 'attachment',
|
||||||
|
'post_status' => 'inherit',
|
||||||
|
'posts_per_page' => 1,
|
||||||
|
'meta_query' => array(
|
||||||
|
'relation' => 'AND',
|
||||||
|
array(
|
||||||
|
'key' => 'artist',
|
||||||
|
'value' => strtolower($artist),
|
||||||
|
'compare' => '='
|
||||||
|
),
|
||||||
|
array(
|
||||||
|
'key' => 'album_title',
|
||||||
|
'value' => strtolower($album_title),
|
||||||
|
'compare' => '='
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
$query = new WP_Query($args);
|
||||||
|
|
||||||
|
if ($query->have_posts()) {
|
||||||
|
// Attachment found via primary method
|
||||||
|
return wp_get_attachment_url($query->posts[0]->ID);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Sanitize and prepare the variables
|
||||||
|
$album_name_lower = strtolower($album_title);
|
||||||
|
$author_lower = strtolower($artist);
|
||||||
|
$table_name = 'song_scrobbles';
|
||||||
|
|
||||||
|
// Prepare the SQL query using $wpdb->prepare to prevent SQL injection
|
||||||
|
$prepared_query = $wpdb->prepare(
|
||||||
|
"
|
||||||
|
SELECT cover_url
|
||||||
|
FROM {$table_name}
|
||||||
|
WHERE LOWER(album_name) = %s
|
||||||
|
AND LOWER(author) = %s
|
||||||
|
ORDER BY id DESC
|
||||||
|
LIMIT 1
|
||||||
|
",
|
||||||
|
$album_name_lower,
|
||||||
|
$author_lower
|
||||||
|
);
|
||||||
|
|
||||||
|
// Execute the query and retrieve the cover URL
|
||||||
|
$cover_url = $wpdb->get_var($prepared_query);
|
||||||
|
|
||||||
|
if ($cover_url) {
|
||||||
|
// Optional: Validate the URL or process it as needed
|
||||||
|
return esc_url($cover_url);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Try fetching from Apple iTunes
|
||||||
|
$remote_album_url = $this->fetch_and_save_album_cover($artist, $album_title);
|
||||||
|
if ($remote_album_url) {
|
||||||
|
return esc_url($remote_album_url);
|
||||||
|
}
|
||||||
|
|
||||||
|
// If both methods fail, return null
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
function normalize_names(string $author, string $songName, string $albumName): array
|
||||||
|
{
|
||||||
|
// Define the album name mapping
|
||||||
|
$albumNameMapping = [
|
||||||
|
'Nirvana' => [
|
||||||
|
'In Utero (20th Anniversary Remaster)' => 'In Utero',
|
||||||
|
'Nevermind (Deluxe Edition)' => 'Nevermind',
|
||||||
|
'Bleach: Deluxe Edition' => 'Bleach'
|
||||||
|
]
|
||||||
|
];
|
||||||
|
|
||||||
|
// Apply the album name mapping if applicable
|
||||||
|
if ($albumName && isset($albumNameMapping[$author])) {
|
||||||
|
foreach ($albumNameMapping[$author] as $variant => $standardized) {
|
||||||
|
// Use case-insensitive comparison
|
||||||
|
if (strcasecmp($albumName, $variant) === 0) {
|
||||||
|
$albumName = $standardized;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Define a regex pattern to remove remaster annotations like "(2022 Remaster)"
|
||||||
|
$remasterPattern = '/\(\d+\s+Remaster\)/i';
|
||||||
|
|
||||||
|
// Remove remaster annotations from song and album names
|
||||||
|
$songName = preg_replace($remasterPattern, '', $songName);
|
||||||
|
$albumName = preg_replace($remasterPattern, '', $albumName);
|
||||||
|
|
||||||
|
// Define a regex pattern to remove "(Deluxe Edition)" and "(Deluxe Version)" (case-insensitive)
|
||||||
|
$deluxePattern = '/\(deluxe\s+(edition|version)\)/i';
|
||||||
|
|
||||||
|
// Remove "(Deluxe Edition)" and "(Deluxe Version)" from album names
|
||||||
|
$albumName = preg_replace($deluxePattern, '', $albumName);
|
||||||
|
|
||||||
|
// === Added Normalization for "COLLECTORS EDITION." ===
|
||||||
|
|
||||||
|
// Define a regex pattern to remove "COLLECTORS EDITION." at the end of album names
|
||||||
|
$collectorsPattern = '/\bCollectors\s+Edition\.?$/i';
|
||||||
|
|
||||||
|
// Remove "COLLECTORS EDITION." from album names
|
||||||
|
$albumName = preg_replace($collectorsPattern, '', $albumName);
|
||||||
|
|
||||||
|
// ====================================================
|
||||||
|
|
||||||
|
// Trim any extra whitespace that might have resulted from the removal
|
||||||
|
$songName = trim($songName);
|
||||||
|
$albumName = trim($albumName);
|
||||||
|
|
||||||
|
return [
|
||||||
|
'song_name' => $songName,
|
||||||
|
'album_name' => $albumName,
|
||||||
|
];
|
||||||
|
}
|
||||||
|
|
||||||
public function scrobble($request) {
|
public function scrobble($request) {
|
||||||
global $wpdb;
|
global $wpdb;
|
||||||
$data = $request->get_json_params();
|
$data = $request->get_json_params();
|
||||||
@ -186,8 +327,12 @@ public function scrobble($request) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
$table_name = 'song_scrobbles';
|
$table_name = 'song_scrobbles';
|
||||||
|
$author = isset($data['author']) ? $data['author'] : null;
|
||||||
$cover_url = isset($data['cover_url']) ? $data['cover_url'] : null;
|
$cover_url = isset($data['cover_url']) ? $data['cover_url'] : null;
|
||||||
$album_name = isset($data['album_name']) ? $data['album_name'] : null;
|
|
||||||
|
$normalized = $this->normalize_names($data['author'], $data['song_name'], $data['album_name']);
|
||||||
|
$song_name = $normalized['song_name'];
|
||||||
|
$album_name = $normalized['album_name'];
|
||||||
|
|
||||||
// If 'album_name' is not provided, 'cover_url' must be present
|
// If 'album_name' is not provided, 'cover_url' must be present
|
||||||
if (empty($album_name)) {
|
if (empty($album_name)) {
|
||||||
@ -202,26 +347,16 @@ public function scrobble($request) {
|
|||||||
// If 'album_name' is provided but 'cover_url' is not, attempt to retrieve it from existing entries
|
// If 'album_name' is provided but 'cover_url' is not, attempt to retrieve it from existing entries
|
||||||
if (empty($cover_url)) {
|
if (empty($cover_url)) {
|
||||||
// Prepare case-insensitive search
|
// Prepare case-insensitive search
|
||||||
$song_name_lower = strtolower($data['song_name']);
|
|
||||||
$album_name_lower = strtolower($album_name);
|
|
||||||
$author_lower = strtolower($data['author']);
|
$author_lower = strtolower($data['author']);
|
||||||
|
$album_name_lower = strtolower($album_name);
|
||||||
|
|
||||||
// Query to find the most recent matching entry
|
// Try to find attachment
|
||||||
$query = $wpdb->prepare(
|
$cover_url = $this->get_attachment_by_artist_album($data['author'], $album_name);
|
||||||
"SELECT cover_url FROM $table_name
|
if (!isset($cover_url)) {
|
||||||
WHERE LOWER(album_name) = %s AND LOWER(author) = %s
|
|
||||||
ORDER BY id DESC
|
|
||||||
LIMIT 1",
|
|
||||||
$album_name_lower, $author_lower
|
|
||||||
);
|
|
||||||
|
|
||||||
$cover_url = $wpdb->get_var($query);
|
|
||||||
|
|
||||||
// If no matching entry is found, return an error
|
// If no matching entry is found, return an error
|
||||||
if (!$cover_url) {
|
|
||||||
return new WP_Error(
|
return new WP_Error(
|
||||||
'missing_cover_url',
|
'missing_cover_url',
|
||||||
'Cover URL not provided and no existing entry found for the given album and author',
|
$cover_url,
|
||||||
array('status' => 400)
|
array('status' => 400)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -232,7 +367,7 @@ public function scrobble($request) {
|
|||||||
$result = $wpdb->insert(
|
$result = $wpdb->insert(
|
||||||
$table_name,
|
$table_name,
|
||||||
array(
|
array(
|
||||||
'song_name' => $data['song_name'],
|
'song_name' => $song_name,
|
||||||
'album_name' => $album_name, // This can be null
|
'album_name' => $album_name, // This can be null
|
||||||
'cover_url' => $cover_url,
|
'cover_url' => $cover_url,
|
||||||
'author' => $data['author'],
|
'author' => $data['author'],
|
||||||
@ -250,7 +385,6 @@ public function scrobble($request) {
|
|||||||
return new WP_REST_Response(array('message' => 'Scrobble saved successfully'), 201);
|
return new WP_REST_Response(array('message' => 'Scrobble saved successfully'), 201);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public function add_admin_menu() {
|
public function add_admin_menu() {
|
||||||
add_options_page(
|
add_options_page(
|
||||||
'Image Scrobble Settings',
|
'Image Scrobble Settings',
|
||||||
@ -259,6 +393,236 @@ public function scrobble($request) {
|
|||||||
'image-scrobble-settings',
|
'image-scrobble-settings',
|
||||||
array($this, 'settings_page')
|
array($this, 'settings_page')
|
||||||
);
|
);
|
||||||
|
|
||||||
|
// Add submenu page for uploading attachments
|
||||||
|
add_options_page(
|
||||||
|
'Upload Album Cover',
|
||||||
|
'Upload Album Cover',
|
||||||
|
'manage_options',
|
||||||
|
'image-scrobble-upload',
|
||||||
|
array($this, 'upload_form_page')
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function upload_form_page() {
|
||||||
|
?>
|
||||||
|
<div class="wrap">
|
||||||
|
<h1>Upload Album Cover</h1>
|
||||||
|
<?php
|
||||||
|
if (isset($_GET['message'])) {
|
||||||
|
$message = sanitize_text_field($_GET['message']);
|
||||||
|
if ($message == 'upload_success') {
|
||||||
|
echo '<div class="updated"><p>Album cover uploaded successfully.</p></div>';
|
||||||
|
} elseif ($message == 'duplicate_image') {
|
||||||
|
echo '<div class="error"><p>An image with this content already exists.</p></div>';
|
||||||
|
} elseif ($message == 'upload_error') {
|
||||||
|
echo '<div class="error"><p>Error during file upload.</p></div>';
|
||||||
|
} elseif ($message == 'not_an_image') {
|
||||||
|
echo '<div class="error"><p>The uploaded file is not a valid image.</p></div>';
|
||||||
|
} elseif ($message == 'missing_fields') {
|
||||||
|
echo '<div class="error"><p>Please fill in all required fields.</p></div>';
|
||||||
|
} elseif ($message == 'upload_failed') {
|
||||||
|
echo '<div class="error"><p>Failed to upload image.</p></div>';
|
||||||
|
} else {
|
||||||
|
echo '<div class="error"><p>An unknown error occurred.</p></div>';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
?>
|
||||||
|
<form method="post" action="<?php echo admin_url('admin-post.php'); ?>" enctype="multipart/form-data">
|
||||||
|
<?php wp_nonce_field('image_scrobble_upload', 'image_scrobble_upload_nonce'); ?>
|
||||||
|
<input type="hidden" name="action" value="image_scrobble_upload">
|
||||||
|
<table class="form-table">
|
||||||
|
<tr valign="top">
|
||||||
|
<th scope="row">Artist</th>
|
||||||
|
<td>
|
||||||
|
<input type="text" name="artist" value="" required />
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr valign="top">
|
||||||
|
<th scope="row">Album Title</th>
|
||||||
|
<td>
|
||||||
|
<input type="text" name="album_title" value="" required />
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr valign="top">
|
||||||
|
<th scope="row">Album Cover Image</th>
|
||||||
|
<td>
|
||||||
|
<input type="file" name="album_cover" accept="image/*" required />
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
<?php submit_button('Upload Album Cover'); ?>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
<?php
|
||||||
|
}
|
||||||
|
|
||||||
|
public function fetch_and_save_album_cover($artist_name, $album_name) {
|
||||||
|
// Encode the artist and album name for the URL
|
||||||
|
$search_term = urlencode($artist_name . ' ' . $album_name);
|
||||||
|
|
||||||
|
// Construct the iTunes Search API URL
|
||||||
|
$api_url = "https://itunes.apple.com/search?term={$search_term}&entity=album&limit=10";
|
||||||
|
|
||||||
|
// Fetch the API response
|
||||||
|
$response = wp_remote_get($api_url);
|
||||||
|
|
||||||
|
// Check for errors in the API request
|
||||||
|
if (is_wp_error($response)) {
|
||||||
|
return new WP_Error(
|
||||||
|
'api_request_failed',
|
||||||
|
'Failed to connect to the iTunes API.',
|
||||||
|
array('status' => 500)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Decode the JSON response
|
||||||
|
$body = wp_remote_retrieve_body($response);
|
||||||
|
$data = json_decode($body, true);
|
||||||
|
|
||||||
|
// Check if the API returned any results
|
||||||
|
if (empty($data['results'])) {
|
||||||
|
return new WP_Error(
|
||||||
|
'no_results',
|
||||||
|
'No album found matching the provided artist and album name.',
|
||||||
|
array('status' => 404)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Initialize a variable to store the matched album
|
||||||
|
$matched_album = null;
|
||||||
|
|
||||||
|
// Iterate through the results to find an exact match
|
||||||
|
foreach ($data['results'] as $album) {
|
||||||
|
$api_artist_name = strtolower($album['artistName']);
|
||||||
|
$api_album_name = strtolower($album['collectionName']); // or 'collectionCensoredName'
|
||||||
|
|
||||||
|
// Normalize the input and API data for comparison
|
||||||
|
$input_artist_name = strtolower($artist_name);
|
||||||
|
$input_album_name = strtolower($album_name);
|
||||||
|
|
||||||
|
// Remove any extra whitespace and special characters
|
||||||
|
$api_artist_name = preg_replace('/\s+/', ' ', trim($api_artist_name));
|
||||||
|
$api_album_name = preg_replace('/\s+/', ' ', trim($api_album_name));
|
||||||
|
$input_artist_name = preg_replace('/\s+/', ' ', trim($input_artist_name));
|
||||||
|
$input_album_name = preg_replace('/\s+/', ' ', trim($input_album_name));
|
||||||
|
|
||||||
|
// Compare the artist and album names
|
||||||
|
if ($api_artist_name === $input_artist_name && $api_album_name === $input_album_name) {
|
||||||
|
$matched_album = $album;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if a matched album was found
|
||||||
|
if (!$matched_album) {
|
||||||
|
return new WP_Error(
|
||||||
|
'no_exact_match',
|
||||||
|
'No exact match found for the provided artist and album name.',
|
||||||
|
array('status' => 404)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get the artwork URL and modify it
|
||||||
|
$artwork_url = $matched_album['artworkUrl100'];
|
||||||
|
$artwork_url_500 = str_replace('100x100bb', '1000x1000bb', $artwork_url);
|
||||||
|
|
||||||
|
// Fetch the image data
|
||||||
|
$image_response = wp_remote_get($artwork_url_500);
|
||||||
|
|
||||||
|
// Check for errors in the image request
|
||||||
|
if (is_wp_error($image_response)) {
|
||||||
|
return new WP_Error(
|
||||||
|
'image_request_failed',
|
||||||
|
'Failed to fetch the album cover image.',
|
||||||
|
array('status' => 500)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Retrieve the image data
|
||||||
|
$image_data = wp_remote_retrieve_body($image_response);
|
||||||
|
|
||||||
|
// Check if image data was retrieved
|
||||||
|
if (empty($image_data)) {
|
||||||
|
return new WP_Error(
|
||||||
|
'empty_image_data',
|
||||||
|
'No image data was returned from the iTunes API.',
|
||||||
|
array('status' => 500)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Generate a hash of the image data to check for duplicates
|
||||||
|
$image_hash = md5($image_data);
|
||||||
|
|
||||||
|
// Call the provided method to save the image and create an attachment
|
||||||
|
return $this->save_image_and_create_attachment(
|
||||||
|
$image_data,
|
||||||
|
$artist_name,
|
||||||
|
$album_name,
|
||||||
|
$image_hash,
|
||||||
|
$album_name // Passing the album title
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function handle_image_upload() {
|
||||||
|
// Check if current user has permission
|
||||||
|
if (!current_user_can('manage_options')) {
|
||||||
|
wp_die('Unauthorized user');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Verify nonce
|
||||||
|
check_admin_referer('image_scrobble_upload', 'image_scrobble_upload_nonce');
|
||||||
|
|
||||||
|
// Get the posted data
|
||||||
|
$artist = sanitize_text_field($_POST['artist']);
|
||||||
|
$album_title = sanitize_text_field($_POST['album_title']);
|
||||||
|
|
||||||
|
// Check if required fields are present
|
||||||
|
if (empty($artist) || empty($album_title) || empty($_FILES['album_cover'])) {
|
||||||
|
wp_redirect(add_query_arg('message', 'missing_fields', wp_get_referer()));
|
||||||
|
exit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle the uploaded file
|
||||||
|
$file = $_FILES['album_cover'];
|
||||||
|
|
||||||
|
// Check for upload errors
|
||||||
|
if ($file['error'] !== UPLOAD_ERR_OK) {
|
||||||
|
wp_redirect(add_query_arg('message', 'upload_error', wp_get_referer()));
|
||||||
|
exit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if the file is an image
|
||||||
|
$check = getimagesize($file['tmp_name']);
|
||||||
|
if ($check === false) {
|
||||||
|
wp_redirect(add_query_arg('message', 'not_an_image', wp_get_referer()));
|
||||||
|
exit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Read the image data
|
||||||
|
$image_data = file_get_contents($file['tmp_name']);
|
||||||
|
|
||||||
|
// Generate a hash of the image data to check for duplicates
|
||||||
|
$image_hash = md5($image_data);
|
||||||
|
|
||||||
|
// Check if an image with this hash already exists to prevent duplicates
|
||||||
|
$existing_attachment = $this->get_attachment_by_hash($image_hash);
|
||||||
|
if ($existing_attachment) {
|
||||||
|
wp_redirect(add_query_arg('message', 'duplicate_image', wp_get_referer()));
|
||||||
|
exit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Save the image and create attachment (using same logic as create_image)
|
||||||
|
$image_url = $this->save_image_and_create_attachment($image_data, $artist, $album_title, $image_hash, $album_title);
|
||||||
|
|
||||||
|
if (is_wp_error($image_url)) {
|
||||||
|
wp_redirect(add_query_arg('message', 'upload_failed', wp_get_referer()));
|
||||||
|
exit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Redirect back with success message
|
||||||
|
wp_redirect(add_query_arg('message', 'upload_success', wp_get_referer()));
|
||||||
|
exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function register_settings() {
|
public function register_settings() {
|
||||||
@ -288,6 +652,3 @@ public function scrobble($request) {
|
|||||||
<?php
|
<?php
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Initialize the plugin
|
|
||||||
new ScrobbleHandler();
|
|
||||||
|
Loading…
Reference in New Issue
Block a user