Cum să obții $image_id după încărcare cu media_sideload_image()

21 mar. 2012, 18:43:23
Vizualizări: 14.5K
Voturi: 14

Vreau să încarc o imagine și să o setez ca imagine reprezentativă pentru un articol. Am încercat următorul cod:

$image_id = media_sideload_image($image_url, $post_id, $post_id);
update_post_meta($post_id, '_thumbnail_id', $image_id);

Dar funcția media_sideload_image() nu returnează image_id, ci codul HTML al imaginii. Cum pot obține image_id?

0
Toate răspunsurile la întrebare 8
4
30

Iată un exemplu despre cum să ocoliți această limitare folosind acțiuni/hook-uri:

function new_attachment( $att_id ){
    // postul în care a fost încărcat atașamentul este părintele atașamentului!

    // preia postul atașamentului
    $att = get_post( $att_id );

    // preia părintele acestuia
    $post_id = $att->post_parent;

    // setează postul recomandat
    set_post_thumbnail( $post_id, $att_id );
}

// adaugă funcția de mai sus pentru a prinde crearea atașamentelor
add_action('add_attachment','new_attachment');

// încarcă atașamentul din URL
media_sideload_image($image_url, $post_id, $post_id);

// acum avem imaginea, iar funcția de mai sus s-a declanșat deja, setând ID-ul miniaturii în proces, așa că eliminăm hook-ul pentru a nu mai cauza probleme 
remove_action('add_attachment','new_attachment');

Ideea este că atunci când rulează media_sideload_image, acesta:

  • descarcă imaginea
  • o adaugă ca un atașament (un post de tip attachment)
  • apoi atașează acel atașament la postul al cărui ID l-ai furnizat ($post_id)

Problema ta este că nu furnizează ID-ul postului de atașament nou creat.

Dar, când un atașament este creat, o acțiune este declanșată conținând ID-ul său. Putem să ne conectăm la aceasta înainte de a crea atașamentul și să salvăm miniatura recomandată cu ID-ul postului pe care ni l-a furnizat, apoi să ne deconectăm după aceea.

21 mar. 2012 18:56:45
Comentarii

Genial! Asta a fost foarte util.

MTT MTT
11 dec. 2014 19:43:30

Dacă acest răspuns ți-a rezolvat întrebarea, poți să îl marchezi ca corect?

Tom J Nowell Tom J Nowell
11 dec. 2014 21:07:28

Nu pot citi engleza ta. Poate cineva să editeze acest post?

HiDd3N HiDd3N
20 dec. 2016 12:58:25

@HiDd3N Am simplificat o parte din engleză folosită, ar trebui să conțină cuvinte mai comune cu un nivel de lectură mai scăzut

Tom J Nowell Tom J Nowell
20 dec. 2016 16:55:46
0
13

Nu mai este nevoie de soluțiile mai vechi.

Puteți obține ID-ul cu un al patrulea parametru ($return) setat la 'id'

<?php media_sideload_image($file, $post_id, $desc, $return); ?> 

https://codex.wordpress.org/Function_Reference/media_sideload_image

2 nov. 2017 00:05:31
0

Am construit o funcție pentru a obține ID-ul din baza de date, căutând după URL.

function get_attachment_id_from_src ($image_src) {
  global $wpdb;
  $query = "SELECT ID FROM {$wpdb->posts} WHERE guid='$image_src'";
  $id = $wpdb->get_var($query);
  return $id;
}

Puteți obține URL-ul (în loc de cod HTML) cu un al patrulea parametru setat la 'src' Codex: media_sideload_image()

$src = media_sideload_image($url, $item_id, $desc,'src');
get_attachment_id_from_src($src);
19 mai 2016 15:02:10
1

@Tom J Nowell are răspunsul corect. Am găsit o altă alternativă (folosind funcții diferite) explicată aici, dar îmi place mai mult această soluție.

În cazul meu, am un array $posts cu toate articolele pe care vreau să le inserez și un array separat $media (cu aceleași chei $nid ca $posts) care conține fișierele media. Codul meu este aceeași soluție ca a lui Tom, dar refactorizată pentru a folosi o funcție anonimă:

foreach( $posts as $nid=>$post )
    $posts[$nid]['ID'] = wp_insert_post( $post );

foreach( $posts as $nid=>$post )
    foreach( $media[$nid] as $m=>$mitem ) {

        if( 0 == $m ) add_action( 'add_attachment',
            function( $att_id ) use ($posts, $nid, $mitem) {
                update_post_meta($posts[$nid]['ID'], '_thumbnail_id', $att_id);
                $posts[$nid]['media_urls'][] = $mitem['url'];
            }
        );
        media_sideload_image($mitem['url'], $post['ID']);
        remove_all_actions( 'add_attachment' );
    }

În cazul meu, presupun că primul element din fiecare $media[$nid] ar trebui să fie imaginea reprezentativă pentru articolul respectiv.

WordPress ar trebui cu siguranță să modifice media_sideload_image() pentru a returna $id. De fapt, funcția are acest lucru la îndemână, vezi codul sursă aici. De fapt, există un ticket pentru această îmbunătățire și chiar există patch-uri pe care le poți aplica pe core în acest moment dacă dorești.

23 oct. 2014 02:48:40
Comentarii

Se pare că va fi reparat în versiunea 4.8

Tom Auger Tom Auger
9 mai 2017 23:03:33
0

Căutam o soluție și am decis să analizez codul funcției <a href="https://codex.wordpress.org/Function_Reference/media_sideload_image" rel="nofollow noreferrer">media_sideload_image()</a>, care s-a dovedit a fi foarte simplu. Aceasta utilizează <a href="https://codex.wordpress.org/Function_Reference/media_handle_sideload" rel="nofollow noreferrer">media_handle_sideload()</a> care ne oferă ID-ul atașamentului.

Am modificat funcția pentru a returna ID-ul atașamentului în loc de codul HTML al imaginii și am adăugat posibilitatea de a trimite un nou nume de fișier.

function media_sideload_image_custom($file, $post_id, $desc = null, $file_name = null)
{
    if ( ! empty($file) ) {
        // Descarcă fișierul într-o locație temporară
        $tmp = download_url( $file );

        // corectează numele fișierului pentru query strings
        if( empty($file_name) ) { 
            preg_match('/[^\?]+\.(jpg|JPG|jpe|JPE|jpeg|JPEG|gif|GIF|png|PNG)/', $file, $matches);
            $file_array['name'] = basename($matches[0]);
        } else {
            $file_array['name'] = sanitize_file_name($file_name);
        }
        $file_array['tmp_name'] = $tmp;

        // Dacă apare o eroare la stocarea temporară, șterge fișierul
        if ( is_wp_error( $tmp ) ) {
            @unlink($file_array['tmp_name']);
            $file_array['tmp_name'] = '';
        }

        // efectuează validarea și stocarea
        $id = media_handle_sideload( $file_array, $post_id, $desc );

        // Dacă apare o eroare la stocarea permanentă, șterge fișierul
        if ( is_wp_error($id) ) {
            @unlink($file_array['tmp_name']);
        }
        return $id;
    }
    return null;
}
20 mai 2017 18:40:52
0

Poți folosi media_handle_sideload în loc de media_sideload_image. De asemenea, dacă folosești această funcție în functions.php, nu uita să adaugi următoarele trei linii.

require_once(ABSPATH . 'wp-admin/includes/media.php');
require_once(ABSPATH . 'wp-admin/includes/file.php');
require_once(ABSPATH . 'wp-admin/includes/image.php');

$id = media_handle_sideload( $file_array, $post_id );
var_dump($id);
24 feb. 2023 15:37:35
1

Am analizat funcția, https://developer.wordpress.org/reference/functions/media_sideload_image/ -- are un al 4-lea argument, "return_type" care specifică răspunsul. Dacă dorești ID-ul, adaugă al 4-lea argument cu valoarea 'id'

18 ian. 2024 01:28:08
Comentarii

Mulțumesc! Da, răspunsul lui Olaf cred că conține asta

Rup Rup
22 ian. 2024 12:24:57
1

În acest exemplu, media_sideload_image() este folosită pentru a încărca imaginea, iar apoi get_posts() este utilizat pentru a interoga postul de atașament căutând un atașament cu cheia meta _wp_attached_file care se potrivește cu numele fișierului imaginii

  // Descarcă și atașează imaginea

    $attachment_id = media_sideload_image($image_url, $post_id);
    
    // Obține ID-ul atașamentului prin interogarea postului de atașament
    $attachment = get_posts(array('post_type' => 'attachment', 'posts_per_page' => 1, 'post_status' => 'inherit', 'meta_query' => array(array('key' => '_wp_attached_file', 'value' => basename($image_url)))));
    if (!empty($attachment)) {
        $image_id = $attachment[0]->ID;
        
        // Acum ai $image_id
        echo "ID-ul imaginii: $image_id";
    } else {
        echo "Nu s-a putut obține ID-ul imaginii.";
    }
18 ian. 2024 08:36:26
Comentarii

Dar media_sideload_image poate returna ID-ul postului pentru tine, așa cum se întâmplă în majoritatea celorlalte răspunsuri de aici.

Rup Rup
19 ian. 2024 12:18:42