Variable aus einem Filter in einem anderen Filter verwenden

Ich habe einen Filter für den Gallery-Shortcode, wo ich IDs für Bilder in einem Post erhalte und die IDs benutze, die ich mit ihren Metadaten erhalte. Jetzt brauche ich eine Möglichkeit, die $copyright Variable in einem Filter zu verwenden, um post_content damit ich den Inhalt dieser Variablen wiedergeben kann.

Gibt es eine Möglichkeit, eine Variable in einem anderen Filter wiederzuverwenden oder gibt es einen besseren Weg für das, was ich erreichen möchte?

 function wpse_get_full_size_gallery_images( $gallery, $post, $galleries ) { $ids = explode( ',', $galleries['include'] ); $copyright = array(); foreach( $ids as $id ) $copyright[] = get_post_meta( $id, 'wiki_copyright', true ); return $gallery; } add_filter( 'shortcode_atts_gallery', 'wpse_get_full_size_gallery_images', 10, 3 ); function my_the_content_filter( $content ) { //pass here the copyright array and append it at the end $content .= $copyright; return $content; } add_filter( 'the_content', 'my_the_content_filter', 20 ); 

Solutions Collecting From Web of "Variable aus einem Filter in einem anderen Filter verwenden"

Dies ist wahrscheinlich ein guter Fall für eine globale Variable. Stellen Sie nur sicher, dass es auf ein Array festgelegt ist, bevor Sie es hinzufügen, und auch, wann Sie versuchen, den Inhalt auszugeben. Konvertieren Sie das Array in eine Zeichenfolge, bevor Sie es zum Inhalt hinzufügen.

Stellen Sie außerdem sicher, dass die Metadaten vorhanden sind, bevor Sie sie zum Array hinzufügen. Auf diese Weise werden keine leeren Copyright-Werte hinzugefügt.

GLOBALE VERSION

 function wpse_get_full_size_gallery_images($gallery, $post, $galleries) { // reference the global variable global $copyright; // make sure it's set if( ! isset($copyright)) $copyright = array(); // grab the IDS $ids = explode(',', $galleries[ 'include' ]); foreach($ids as $id) { // get the possible meta $meta = get_post_meta($id, 'wiki_copyright', true); // add them to the copyright array // make sure to only add if it exists if( !empty($meta)) $copyright[] = $meta; } return $gallery; } add_filter('shortcode_atts_gallery', 'wpse_get_full_size_gallery_images', 10, 3); function my_the_content_filter($content) { // reference the global variable global $copyright; // add copyright array converted to string if we have content if( ! empty($copyright)) $content .= implode(',', $copyright); return $content; } add_filter('the_content', 'my_the_content_filter', 20); 

STATISCHE VERSION

Wenn Sie aus irgendeinem Grund keine globalen Variablen verwenden möchten, betrachten Sie eine statische Variable als alternativen Variablenbereich in PHP.

Ein weiteres wichtiges Merkmal des Variablen-Scopings ist die statische Variable. Eine statische Variable existiert nur in einem lokalen functionsbereich, verliert jedoch ihren Wert nicht, wenn die Programmausführung diesen Bereich verlässt.

Da die persistente Variable an einen einzelnen functionsbereich gebunden ist, müssen wir die function außerhalb beliebiger Schleifen erstellen und sie dann zum Hinzufügen von Werten zusätzlich zum Abrufen dieser Werte wiederverwenden.

Wenn Sie einen neuen Wert übergeben füge es hinzu . Wenn Sie keinen Wert übergeben; bekomme alle Werte .

 if( ! function_exists('copyrights')) { function copyrights($value = '') { // only this function has access to $_copyrights static $_copyrights; // expressions can't be assigned as defaults // but we still want to initialize the value if( ! isset($_copyrights)) { $_copyrights = array(); } // if we're passing new values then add them if( ! empty($value)) { $_copyrights[] = $value; return true; // success } else { // otherwise return uniques $unique_list = array_unique($_copyrights); // convert to string before they leave return implode(", ", $unique_list); } } } add_filter('shortcode_atts_gallery', function($gallery, $post, $galleries) { $ids = explode(',', $galleries[ 'include' ]); foreach($ids as $id) if( ! empty($meta = get_post_meta($id, 'wiki_copyright', true))) copyrights($meta); return $gallery; }, 10, 3); add_filter('the_content', function($content) { return $content . copyrights(); }, 20); 

TESTEN

 copyrights ( 123 ); copyrights ( 223 ); copyrights ( 333 ); copyrights ( 123 ); copyrights ( 111 ); copyrights ( 111 ); copyrights ( 111 ); echo ( copyrights() ); // 123, 223, 333, 111 

Singleton VERSION

Ich verwende eigentlich niemals Globals, weil ein Singleton Pattern meine bevorzugte Methode ist.

Die Idee ist, dass Sie alle Ihre Methoden auf eine Instanz einer class anwenden, aber nur über eine statische Methode darauf zugreifen. Auf diese Weise stellt die class sicher, dass nur eine einzige Instanz erstellt wird.

 if( ! class_exists('Copyrights')) { class Copyrights { private $copyrights; private static $instance; // PRIVATE CONSTRUCTOR private function __construct() { // initialize the array $this->copyrights = array(); } // STATIC SINGLETON public static function getInstance() { if(is_null(self::$instance)) { self::$instance = new self(); } return self::$instance; } // PUBLIC METHODS public function toString() { $unique_list = array_unique($this->copyrights); return implode(", ", $unique_list); } public function add($value = '') { if( ! empty($value)) { $this->copyrights[] = $value; } } } } add_filter('shortcode_atts_gallery', function($gallery, $post, $galleries) { $ids = explode(',', $galleries[ 'include' ]); foreach($ids as $id) if( ! empty($meta = get_post_meta($id, 'wiki_copyright', true))) Copyrights::getInstance()->add($meta); return $gallery; }, 10, 3); add_filter('the_content', function($content) { return $content . Copyrights::getInstance()->toString(); }, 20); 

TESTEN

 Copyrights::getInstance()->add ( 123 ); Copyrights::getInstance()->add ( 223 ); Copyrights::getInstance()->add ( 333 ); Copyrights::getInstance()->add ( 123 ); Copyrights::getInstance()->add ( 111 ); Copyrights::getInstance()->add ( 111 ); Copyrights::getInstance()->add ( 111 ); echo Copyrights::getInstance()->toString(); // 123, 223, 333, 111 

SINGLETON PRO POST VERSION

Vielleicht ist der wichtigste Aspekt, der in der Debatte über den global gegenüber the sky is falling übersehen wurde, der the sky is falling ist die obige Lösung ( und Alternativen vorgeschlagen ) nur auf einen einzigen Beitrag gerecht zu werden. Wenn Sie Ihre Urheberrechte in einer Schleife hinzufügen wollten, wären Sie geschockt, weil alle Beiträge zu einem einzigen Array hinzugefügt würden.

Mit der Singleton-class ist das Hinzufügen eines Pro-ID-Singleton Kuchens und wohl die bestmögliche Option .

 if( ! class_exists('Copyrights')) { class Copyrights { private static $instance; private $copyrights; public $post_id; // PRIVATE CONSTRUCTOR private function __construct($post_id) { // save the id $this->post_id = $post_id; // initialize the array $this->copyrights = array(); } // SINGLETON public static function getInstance($post_id = 'NO ID') { if(is_null(self::$instance)) self::$instance = array(); if(is_null(self::$instance[ $post_id ])) { self::$instance[ $post_id ] = new self($post_id); } return self::$instance[ $post_id ]; } // PUBLIC METHODS public function toString() { $unique_list = array_unique($this->copyrights); return implode(", ", $unique_list); } public function add($value = '') { if( ! empty($value)) { $this->copyrights[] = $value; } } } } add_filter('shortcode_atts_gallery', function($gallery, $post, $galleries) { $ids = explode(',', $galleries[ 'include' ]); foreach($ids as $id) if( ! empty($meta = get_post_meta($id, 'wiki_copyright', true))) Copyrights::getInstance($post->ID)->add($meta); return $gallery; }, 10, 3); add_filter('the_content', function($content) { global $post; return $content . Copyrights::getInstance($post->ID)->toString(); }, 20); 

TESTEN

Wie Sie sehen können, hält die Option , ID als Schlüssel zu verwenden, die Dinge flexibel.

 Copyrights::getInstance( 1 )->add ( 123 ); Copyrights::getInstance( 1 )->add ( 223 ); Copyrights::getInstance( 2 )->add ( 333 ); Copyrights::getInstance( 2 )->add ( 123 ); Copyrights::getInstance( 2 )->add ( 111 ); Copyrights::getInstance( 2 )->add ( 111 ); Copyrights::getInstance( 2 )->add ( 111 ); Copyrights::getInstance()->add ( 111 ); Copyrights::getInstance()->add ( 444 ); Copyrights::getInstance()->add ( 555 ); Copyrights::getInstance()->add ( 888 ); echo Copyrights::getInstance( 1 )->toString(); // 123, 223 echo Copyrights::getInstance( 2 )->toString(); // 333, 123, 111 echo Copyrights::getInstance()->toString(); // 111, 444, 555, 888 

An dem Punkt, an dem jemand denkt, dass es eine gute Idee ist, einen temporären Wert in der database zu speichern, weil er PHP nicht versteht, ist es ein guter Zeitpunkt, das Problem zu überdenken.


AKTUALISIEREN

Ich habe die Frage mit einer globalen Variablen getriggers , aber das Problem überdenken Sie, indem Sie nur den Content- Filter-Hook verwenden, wodurch das Problem lokalisiert bleibt.

Wenn the_content läuft, prüfen wir in diesem Fall alle Galerien und geben nur die relevanten Daten aus .

Keine Notwendigkeit für Globals, Statik, Singletons, Optionen oder Zusatzfunktionen.

Das Beste von allem, das wird in einer Schleife ohne Komplikationen funktionieren.

 add_filter('the_content', 'add_copyright_to_content'); function add_copyright_to_content($content) { // pull all galleries from the post $galleries = get_post_galleries(get_post(), false); // no gallery? then let's get out of here if(empty($galleries)) return $content; $all = ''; // gather all ids foreach($galleries as $gallery) $all .= $gallery[ 'ids' ] . ','; // convert them to an array with unique ids $all = array_unique(array_filter(explode(',', $all))); // replace id for copyright info on the image meta foreach($all as $key => $id) $all [ $key ] = get_post_meta($id, 'wiki_copyright', true); // return non-empty values to the end of the content return $content . implode(', ', array_filter($all)); } 

… gibt es vielleicht einen besseren Weg für das, was ich erreichen möchte?

Es gibt immer zusätzliche Optionen zu berücksichtigen. Eine Variable zu globalisieren gehört sicherlich nicht dazu und das sollte man vermeiden. Globalisierung ist ein einfacher Ausweg, um jedes Problem zu lösen, aber glauben Sie mir, dass Sie Tage damit verbringen werden, ein Problem zu debuggen, das Ihnen keine Debugging-Fehler gibt, wenn etwas Ihren globalen Fehler verursacht.

WordPress Alreay machte eine riesige Unordnung mit Globals. Sehen $wp_query einfach die Fragen und Antworten auf dieser Website an und prüfen Sie, wie viele die globalen Variablen $wp_query , $posts und $post als lokale Variablen verwenden.

Ich benutze $copyright als eine Variable, um Datumsinformationen zu halten. Wenn wir $copyright mit einer Folge von IDs globalisieren, wie in Ihrem Fall, wird entweder meine Variable die globale oder die globale wird meine Variable brechen. Das Schlimmste ist, ich würde keine Debug-Fehler bekommen und ich würde nicht wissen, wo meine Werte geändert werden. Also niemals Variablen globalisieren, IMHO, es ist wirklich eine schlechte Übung, da es viele andere Optionen gibt

Eine schnelle Option, die Ihnen in den Sinn kommt, ist das Speichern Ihrer Daten mit der Options-API. Es ist einfach und erfordert keine großen Gemeinkosten, da Optionen zwischengespeichert werden, und sie sind sicher zu verwenden.

Versuchen wir Folgendes: ( HINWEIS: Der gesamte Code ist noch nicht getestet, also stellen Sie sicher, dass Sie dies zuerst auf der lokalen Installation testen. Der Code erfordert auch PHP5.4 +)

 add_filter( 'shortcode_atts_gallery', function ( $gallery, $post, $galleries ) { // Get all the ids $ids = $galleries['include']; // Instead of overloading the shortcode, lets just save the id's for later use if ( !$ids ) // Always make sure we have values return $gallery; // Add our ids in an option $option = get_option( 'custom_copyright_ids' ); if ( false !== $option // Make sure that the option does not yet exist || $option !== $ids // We only want the update if $id's change ) { // Lets update or add our option update_option( 'custom_copyright_ids', $ids ); } return $gallery; }, 10, 3 ); 

Wir können jetzt eine “globale” function erstellen, die wir mitnehmen und ( sicher ) verwenden können, wo wir sie verwenden wollen. ( Die folgende function ist statisch, Sie können sie dynamisch machen )

 function get_global_copyright_ids() { $output = ''; // Get our ids $ids = get_option( 'custom_copyright_ids' ); // Make sure we have a value for $option, either return an empty string if ( false === $ids ) return $output; // We have ids, lets continue // We expect $ids to be an array, so lets turn the string into an array $ids = explode( ',', trim( $ids ) ); foreach ( $ids as $id ) { // Get our post meta $meta = get_post_meta( $id, 'wiki_copyright', true ); if ( !$meta ) continue; // We have meta, add it to our $output string. Add any markup here $output .= $meta } // endforeach $ids // Return our string of post meta return $output; } 

Wir können get_global_copyright_ids() jetzt überall dort verwenden, wo wir wollen

 add_filter( 'the_content', function ( $content ) { // Get our content to add from our "global" function $extra = ''; if ( function_exists( 'get_global_copyright_ids' ) ) { $extra = get_global_copyright_ids(); } if ( !$extra ) return $content; // Append $extra to $content return $content . $extra; }): 

Und dort haben Sie ein viel besseres und sichereres System, das wirklich leicht zu debuggen ist und das Beste von allem ist, dass Sie die globale Reichweite sauber halten !!!