วิธีทำให้ปลั๊กอินจำเป็นต้องใช้ในธีม wp โดยไม่ต้องใช้คำสั่งแบบมีเงื่อนไข php เมื่อเรียกใช้ฟังก์ชันแต่ละตัวจากปลั๊กอินนั้น


10

หนึ่งในธีม Wordpress ของฉันต้องการปลั๊กอินของบุคคลที่สามบางตัวเพื่อให้ทำงานได้อย่างถูกต้อง

เวลาส่วนใหญ่ที่ฉันเคยเรียกใช้ฟังก์ชั่นจากปลั๊กอินของบุคคลที่สามโดยใช้คำสั่งแบบมีเงื่อนไขเช่น

    if(function_exist('plugin_function')) {
             plugin_function() // do something
    }

สมมติว่าฉันต้องใช้ปลั๊กอินหนึ่งตัวผ่านหลายไฟล์ในธีมของฉัน ... ฉันต้องการหลีกเลี่ยงการใช้เงื่อนไข IF จำนวนมาก ... มีวิธีที่เหมาะสมในการติดตั้งปลั๊กอินเฉพาะใน WP หรือติดตั้งให้ดียิ่งขึ้น หากพวกเขาหายไปก่อนเปิดใช้งานชุดรูปแบบ?

ขอบคุณ

คำตอบ:


7

is_plugin_active()ค่อนข้างบอบบาง: มันจะแตกเมื่อผู้เขียนปลั๊กอินเปลี่ยนชื่อไฟล์หลักหรือเมื่อผู้ใช้เปลี่ยนชื่อไดเรกทอรีหรือไฟล์หลักของปลั๊กอิน เป็นการดีกว่าที่จะตรวจสอบว่ามีฟังก์ชั่นสาธารณะบางอย่างอยู่หรือไม่

เพื่อหลีกเลี่ยงการทำการตรวจสอบแต่ละครั้งที่คุณต้องการฟังก์ชั่นปลั๊กอินบางอย่างคุณสามารถแสดงข้อความในพื้นที่ผู้ดูแลระบบ:

add_action( 'admin_notices', 'my_theme_dependencies' );

function my_theme_dependencies() {
  if( ! function_exists('plugin_function') )
    echo '<div class="error"><p>' . __( 'Warning: The theme needs Plugin X to function', 'my-theme' ) . '</p></div>';
}

อีกทางเลือกหนึ่งคือการใช้บางอย่างเช่นhttp://tgmpluginactivation.com/


หากผู้เขียนปลั๊กอินเปลี่ยนชื่อฟังก์ชั่นที่คุณถามด้วยfunction_existsผู้ใช้ปกติก็จะได้รับข้อความว่าเขาไม่ได้ติดตั้งปลั๊กอินที่ใช้ปลั๊กอินตัวอื่น ปัญหาคือว่าผู้ใช้จริงจะมีปลั๊กอินที่ติดตั้งแล้วเพียงแค่สงสัยว่าทำไมมันdoens't ทำงาน โอ้และฉันจะไม่ลงคะแนนให้คุณอย่างนั้น
ไกเซอร์

หากคุณสนใจเกี่ยวกับการลงคะแนนคุณควรลบคะแนน Q ด้วยตัวเองเนื่องจากเป็นคะแนนที่ดี
ไกเซอร์

หากผู้เขียนปลั๊กอินเปลี่ยนชื่อฟังก์ชั่นเขาจะได้รับการร้องเรียนจากผู้ใช้จำนวนมากมากกว่าถ้าเขาจะเปลี่ยนชื่อไฟล์
scribu

และฉันลงคะแนนคำตอบของคุณเพราะมันไม่ได้ตอบคำถาม IMO หรือคุณต้องการให้ฉันลงคะแนนอย่างซ่อนเร้นโดยไม่มีคำอธิบายให้?
scribu

ฉันแค่พูดถึง downvote ไม่ใช่ความคิดเห็น ความคิดเห็นของตัวเองก็โอเคเพราะหัวข้อนี้เป็นสิ่งที่ต้องมีการสนทนา ฉันจะเพิ่มคำตอบอีกครั้งเนื่องจากความคิดของฉันที่เกินความคิดเห็นยาวเกิน โปรดแก้ไขคำตอบเพื่อให้เราสามารถเก็บผลลัพธ์การสนทนาไว้ในการแก้ไขเพื่อให้ทุกคนติดตามได้ ขอบคุณ
ไกเซอร์

1

แม้ว่าสิ่งนี้จะไม่ป้องกันไม่ให้ชุดรูปแบบแตกหักเมื่อปลั๊กอินถูกปิดใช้งาน แต่ฉันจะดูบทความที่ลื่นไหลเกี่ยวกับปลั๊กอิน"วิธีแสดงประกาศผู้ดูแลระบบสำหรับชุดรูปแบบที่จำเป็น" ฉันไม่เคยพอใจกับแนวคิดของธีมที่บังคับให้ติดตั้งปลั๊กอินดังนั้นนี่จึงเป็นตัวเลือกที่ดีที่สุดถัดไป

อีกหนึ่งความคิดที่รวดเร็ว: ฉันไม่เคยลองสิ่งนี้ แต่ฉันสงสัยว่าคุณสามารถหาวิธีที่ชาญฉลาดในการเก็บ hooks หลายอันในเงื่อนไขเดียวหรือไม่ บางทีคุณอาจแยกฟังก์ชั่นที่มีเงื่อนไขทั้งหมดในไฟล์ที่แตกต่างออกไปและต้องการมันต่อเมื่อif( function_exists( 'plugin_function' ) )ส่งคืนtrue(ด้วยความเข้าใจว่านี่เป็นการตรวจสอบที่ไม่สมบูรณ์


0

is_plugin_active()หากคุณจำเป็นต้องใช้มันเพียงหน้าปลั๊กอินแล้วมี หากคุณต้องการมันข้างนอกคุณควรคัดลอก / วางฟังก์ชั่นคอร์ในธีมของคุณและนำมันกลับมาใช้ใหม่:

if ( ! is_admin() )
{
/**
 * Check whether the plugin is active by checking the active_plugins list.
 *
 * @since 2.5.0
 *
 * @param string $plugin Base plugin path from plugins directory.
 * @return bool True, if in the active plugins list. False, not in the list.
 */
function is_plugin_active( $plugin ) {
    return in_array( $plugin, (array) get_option( 'active_plugins', array() ) ) || is_plugin_active_for_network( $plugin );
}
}

เงื่อนไขหลีกเลี่ยงข้อผิดพลาดใด ๆ กับการกำหนดฟังก์ชั่นสองครั้ง


ไม่ได้ตอบคำถามจริงๆ มันแทนที่if(function_exist('plugin_function'))ด้วยif(is_plugin_active('plugin-file.php'))
scribu

0

หมายเหตุ:คำตอบนี้อยู่ที่นี่เพื่อให้การสนทนาระหว่าง @scribu และ @kaiser ง่ายขึ้น Mods: โปรดอย่าลบ ผู้ใช้ / ผู้อ่าน: โปรดอย่าลงคะแนน หากคุณต้องการติดตามการสนทนาให้ดูที่บันทึกการแก้ไข / แก้ไข หากคุณต้องการเข้าร่วมการสนทนาให้แก้ไขคำตอบ หากการสนทนามีผลก็จะถูกทำเครื่องหมายเช่นนั้น ขอบคุณ.


สถานการณ์

นอกจากนี้ยังมีสถานการณ์ที่แตกต่างกันซึ่งมีน้ำหนักแตกต่างกันซึ่งคุณสามารถพึ่งพาปลั๊กอินได้ (ตัวอย่างเป็นเพียงตัวละครเท่านั้น) ปลั๊กอิน "(พาเรนต์)" สามารถแลกเปลี่ยนกับ "ธีม" จากมุมมองพาเรนต์

  1. (ยาก) ปลั๊กอินลูกที่ขยายการทำงานหรือเปลี่ยนแปลงการแสดงผล (และที่คล้ายกัน) ของปลั๊กอินที่มีอยู่และดังนั้นจึงไม่สามารถอยู่ได้หากไม่มีพาเรนต์ ตัวอย่าง: BuddyPress » BuddyPress-FunkyCommentDisplay
  2. (ปกติ) ปลั๊กอินที่มีการขยายการทำงานเมื่อเปิดใช้งานปลั๊กอินลูก ตัวอย่าง: jQueryAttachmentCarousel » jQuerySlideDeck
  3. (อ่อน) ปลั๊กอินที่เพิ่งเพิ่มคุณสมบัติ ตัวอย่าง: DisneyWonderlandTheme » MickeysSocialLinks

ในต่อไปนี้ฉันพยายามที่จะร่างสิ่งที่เกิดขึ้นเมื่อคุณอัปเดตปลั๊กอิน "อื่น ๆ " และการตรวจสอบไม่ทำงานอีกต่อไป

  • โฆษณา 1) ปลั๊กอินไม่สามารถใช้งานได้หากไม่เปิดใช้งาน BuddyPress »สิ่งต่าง ๆ เสียหายอย่างสมบูรณ์
  • โฆษณา 2) ปลั๊กอินไม่สามารถให้ตัวเลือกในการเปลี่ยนจาก Carousel เป็น SlideDeck »แสดงสาย (ฉันคิดว่าสไตล์นั้นได้รับการแก้ไขเป็น SlideDeck)
  • โฆษณา 3) MickeysSocialLinks หายไป

ตรวจสอบ

มีความเป็นไปได้ที่ imho สามวิธีในการตรวจสอบหากคุณต้องการทราบว่าปลั๊กอินใช้งานอยู่หรือไม่:

  • A. มีโฟลเดอร์อยู่หรือไม่?
  • B. ไฟล์หลัก - ตัวเลือก'active_plugins'- มีอยู่หรือไม่?
  • C. มีฟังก์ชันเฉพาะหรือไม่?

ถ้าตอนนี้ฉันใช้ปลั๊กอินตัวตรวจสอบการเชื่อมโยงภายในของฉันเป็นตัวอย่างซึ่งไม่มี API สาธารณะและไม่ได้หมายถึงการขยายดังนั้นฉันจะไม่เห็นเหตุผล (ในฐานะผู้เขียน) ที่จะไม่เปลี่ยนการตั้งชื่อฟังก์ชั่นภายในตามความต้องการ . ดังนั้นหากใครบางคนพยายามที่จะ piggyback บนปลั๊กอินนี้แล้วสิ่งต่าง ๆ ก็จะพัง (ขึ้นอยู่กับฟังก์ชั่นและความหนาแน่นของการรวมกลุ่ม) ในการอัปเดต เช่นเดียวกับชื่อไฟล์ ฉันไม่มีเหตุผลที่แท้จริง (นอกเหนือจากนั้นปลั๊กอินจะถูกปิดการใช้งานในการอัปเดต) เพื่อไม่เปลี่ยนชื่อไฟล์ สิ่งเดียวที่ทำให้ฉันไม่สามารถเปลี่ยนชื่อโฟลเดอร์ได้คือการตรวจสอบและแจ้งเตือนการอัปเดตทำงานกับชื่อไฟล์ - หากเป็นโฮสต์ใน repo อย่างเป็นทางการ

ดังนั้นฉันจะพูดว่าจากจุดอ่อน (ง่ายต่อการเปลี่ยนแปลง) ไปจนถึงสิ่งที่ยากที่สุด (มากพูดกับการเปลี่ยนแปลง) ส่วนหนึ่งของปลั๊กอิน (หลัก) จะเป็น:

ฟังก์ชั่น»ชื่อไฟล์หลัก»โฟลเดอร์


เมื่อฉันบอกว่าการตรวจสอบฟังก์ชั่นนั้นมีความเปราะบางน้อยกว่าการใช้is_plugin_active()ฉันสันนิษฐานว่าฟังก์ชั่นที่เป็นปัญหานั้นเป็นสิ่งที่ผู้เขียนปลั๊กอินสนับสนุน ตัวอย่างที่ดีที่สุดคือwp_pagenavi()แท็กเทมเพลตที่เสนอโดยปลั๊กอิน WP-PageNavi

ปัญหาในการกำหนดการพึ่งพาคือไม่มีวิธีมาตรฐานในการระบุปลั๊กอินที่ไม่เกี่ยวข้องกับชื่อไฟล์

ความคิดเพิ่มเติมเกี่ยวกับเรื่อง:

http://wordpress.org/support/topic/plugin-plugin-dependencies-unreliable-plugin-namingidentifying-scheme


ฉันเดาว่าเราสามารถสรุปได้สามจุด:

  • เราได้พูดคุยเกี่ยวกับหัวข้อที่แตกต่างกันเล็กน้อย
  • เรายอมรับว่าไม่มีวิธีกันกระสุนเพื่อหลีกเลี่ยงสิ่งที่ฉันคิดว่าเป็นหัวข้อ
  • จากความเข้าใจในคำถามคุณได้เสนอวิธีการที่ถูกต้อง

วิธีที่ฉลาดที่สุดที่ฉันสามารถคิดได้ว่าฉันเคยเห็นในปลั๊กอิน (มากไป) ที่:

// inside the plugin file:
add_action( 'plugin_custom_hook', 'plugin_trigger' );
// inside some template:
do_action( 'plugin_custom_hook' );

โดยไม่ได้คิดถึงรายละเอียดมากเกินไป แต่ฉันคิดว่าคุณสามารถขอให้คุณแจ้งให้ทราบในตัวกรอง 'ทั้งหมด' และตรวจสอบภายในตัวกรองปัจจุบันถ้ามันถูกเรียกเมื่อคุณอยู่ในshutdownตะขอ ... ?


การใช้ hooks จะทำงานได้ดีสำหรับการพึ่งพา 'ปกติ' และ 'อ่อนแอ' ข้อเสียเปรียบเพียงอย่างเดียวคือคุณยังคงต้องใช้function_exists()หรือis_plugin_active()หากคุณต้องการหยุดหากไม่สามารถพึ่งพาได้ การใช้ตัวกรอง 'ทั้งหมด' สำหรับนั้นจะแพงเกินไป IMO

@scibu เป้าหมายนี้เป็นหัวข้อ "ของคุณ" (ฉันพูดเรื่องของฉันไปแล้ว) :)

ดังนั้นโดยทั่วไปถ้าคุณต้องการการพึ่งพา - และคุณมีผู้เขียนที่ดี - จากนั้นเขาสามารถเสนอเบ็ดแทน / แทนแท็กแม่แบบ เนื่องจากปลั๊กอินจะเชื่อมต่อเข้าด้วยกันเฉพาะเมื่อมีการขอติดตั้งหรือไม่ต้องทำอะไรเลย และในอีกด้านหนึ่งคุณจะไม่มีข้อผิดพลาดเมื่อไม่มีปลั๊กอิน

นี่คือส่วนที่ยาก (หรือมากกว่าของ Q): การเขียนแจ้งผู้ดูแลระบบจะแจ้งให้ผู้ใช้เกี่ยวกับ dependancy "คุณจำเป็นต้องติดตั้ง» DisneyWonderLinks «" array_keys( $GLOBALS['wp_filter']['template_tag_like_hook'] )คุณสามารถตรวจสอบ ฉันไม่แน่ใจว่าจะใช้งานได้หรือไม่ แต่อาร์เรย์ควรจะสามารถเข้าถึงได้ทั้งสองด้าน (สาธารณะ / ผู้ดูแลระบบ)


ที่จะไม่ทำงาน เพียงเพราะการลงทะเบียนโทรกลับไปที่ตะขอไม่ได้หมายความว่าเบ็ดจะถูกเรียกเมื่อคาดหวัง สิ่งเดียวที่จะเรียงลำดับของงานคือการใช้เบ็ด 'ปิด' ซึ่งคุณกล่าวถึงก่อนหน้านี้:

add_action( 'shutdown', function() {
  if ( !did_action( 'template_tag_like_hook' ) )
    echo 'Problem.';
} );

แน่นอนว่าสิ่งนี้จะถูกพิมพ์ที่ด้านล่างสุดหลังจาก</html>แท็กบนส่วนหน้า (เนื่องจากเป็นที่ที่แท็กแม่แบบใช้งานตามปกติ) ซึ่งไม่ได้ใช้งานมากนัก

คุณสามารถลองเก็บข้อความไว้ใน wp_options จากนั้นแสดงมันในพื้นที่ admin แต่นั่นจะเปิดเวิร์มกระป๋องใหม่ทั้งหมด: การทำให้ใช้ไม่ได้ปลั๊กอินการแคชเป็นต้น


สำหรับเร็กคอร์ดนี่เป็นวิธีที่ไม่ได้ใช้ในการทำงานของไซต์ มันทำให้ฉันนึกถึงc2.com/cgi/wiki
scribu

ใช่แล้ว. แต่ฉันไม่รู้ว่าเราจะสามารถทำการสนทนาต่อไปได้อย่างไรโดยไม่ซ่อนจากผู้อ่านในภายหลัง
ไกเซอร์

ฉันไม่คิดว่าการโพสต์คำถามจะทำให้เกิดการอภิปราย :) แต่มันน่าสนใจจริง ๆ และฉันขอบคุณทั้งความพยายามและเวลาของคุณในการให้คำแนะนำและการอภิปรายที่รอบคอบ ฉันคิดว่าคำแนะนำจาก scribu (หนึ่งในหลาย ๆ ที่) ในการใช้คลาสการเปิดใช้งาน TGM สามารถเสนอวิธีแก้ปัญหาให้กับคำตอบของฉันอย่างน้อยในมุมมองเชิงปฏิบัติเพียงอย่างเดียวฉันจะมองมัน อย่างไรก็ตามฉันยังคงจับตาดูการอภิปรายทั้งหมดเพราะยังมีวิธีการอื่นที่เสนอให้เข้าใจในบางสถานการณ์และน่าสนใจมากสำหรับฉันที่จะอ่านขอบคุณ!
unfulvio
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.