WP প্লাগইনে কোনও ক্লাস শুরু করার সর্বোত্তম উপায়?


89

আমি একটি প্লাগইন তৈরি করেছি এবং অবশ্যই আমার হয়ে আমি একটি সুন্দর ওও পদ্ধতির সাথে যেতে চেয়েছিলাম। এখন আমি যা করছি তা এই ক্লাসটি তৈরি করা এবং তার ঠিক নীচে এই শ্রেণীর একটি উদাহরণ তৈরি করা:

class ClassName {

    public function __construct(){

    }
}

$class_instance = new ClassName();  

আমি ধরে নিচ্ছি যে এই ক্লাসটি চালু করার আরও একটি WP উপায় রয়েছে এবং আমি তখন লোকদের কাছে এসে বললাম যে তারা একের init()চেয়ে কোনও ফাংশন করতে পছন্দ করে __construct()। এবং একইভাবে আমি কয়েক জনকে নিম্নলিখিত হুক ব্যবহার করে দেখতে পেলাম:

class ClassName {

    public function init(){

    }
}
add_action( 'load-plugins.php', array( 'ClassName', 'init' ) );

সাধারণত লোডের উপরে ডাব্লুপি ক্লাসের উদাহরণ তৈরির সর্বোত্তম উপায় হিসাবে বিবেচিত হয় এবং এটি বিশ্বব্যাপী অ্যাক্সেসযোগ্য পরিবর্তনশীল হিসাবে রয়েছে?

দ্রষ্টব্য: আকর্ষণীয় দিক হিসাবে আমি লক্ষ্য করেছি যে এর register_activation_hook()মধ্যে থেকে ডেকে আনা যেতে পারে __construct, init()দ্বিতীয় উদাহরণটি ব্যবহার করে এটি কল করা যায় না। সম্ভবত এই বিষয়টিতে কেউ আমাকে আলোকিত করতে পারে।

সম্পাদনা: সমস্ত উত্তরের জন্য ধন্যবাদ, ক্লাসের মধ্যেই সূচনাটি কীভাবে পরিচালনা করা যায় তা নিয়ে সুস্পষ্ট বিতর্ক রয়েছে, তবে আমি মনে করি সাধারণত add_action( 'plugins_loaded', ...);এটির উত্সাহ দেওয়ার সর্বোত্তম উপায় হ'ল একটি খুব ভাল sens কমত্য আছে ...

সম্পাদনা: কেবল বিষয়গুলিকে বিভ্রান্ত করার জন্য, আমি এটি ব্যবহৃতও দেখেছি (যদিও আমি নিজে এই পদ্ধতিটি ব্যবহার করব না কারণ একটি সুন্দর ওও ক্লাসকে কোনও ফাংশনে রূপান্তরিত করার বিষয়টি মনে হচ্ছে):

// Start up this plugin
add_action( 'init', 'ClassName' );
function ClassName() {
    global $class_name;
    $class_name = new ClassName();
}

1
শেষ সম্পাদনা সম্পর্কে, যদি এটি শ্রেণীর মতো একই প্লাগইন ফাইলে থাকে তবে এটি কিছুটা অকেজো হয়ে যায়। আমি বর্ণিত পদ্ধতি অনুসারে আপনি ক্লাসটি ইনস্ট্যান্ট করতে পারেন। এমনকি এটি একটি পৃথক ফাইলে থাকলেও এটি এখনও কিছুটা অর্থহীন। আমি দেখতে পাচ্ছি কেবলমাত্র যদি আপনি এমন একটি মোড়ক ফাংশন তৈরি করতে চান যা আপনার প্লাগইন ফাইলের বাইরে কোনও ক্লাস ইনস্টল করতে সক্ষম করে, থিমের মধ্যেও on তবুও, আমাকে জিজ্ঞাসা করতে হবে এর পিছনে কী যুক্তি রয়েছে কারণ শর্তসাপেক্ষ এবং হুকের সঠিক ব্যবহারের ফলে ইনস্ট্যান্টেশনের উপর জরিমানা শস্য নিয়ন্ত্রণের অনুমতি দেওয়া উচিত যা আপনি পরিবর্তে প্লাগইন ব্যবহারের দিকে মনোযোগ দিতে পারবেন।
আদম

আমি এটির সাথে একমত, তবে আমি ভেবেছিলাম এটি বেশিরভাগ ডাব্লুপি প্লাগইনগুলিতে পাওয়া যায় বলে এটি রাখা ভাল।
কলপাইচ

উত্তর:


60

ভাল প্রশ্ন, অনেকগুলি পন্থা রয়েছে এবং এটি আপনি কী অর্জন করতে চান তার উপর নির্ভর করে।

আমি প্রায়শই করি;

add_action( 'plugins_loaded', array( 'someClassy', 'init' ));

class someClassy {

    public static function init() {
        $class = __CLASS__;
        new $class;
    }

    public function __construct() {
           //construct what you see fit here...
    }

    //etc...
}

আড্ডার ঘরের মধ্যে এই বিষয়টি নিয়ে সাম্প্রতিক কিছু আলোচনার ফলস্বরূপ যে আরও নিখুঁত একটি নিখুঁত উদাহরণ এসেছে তা ডব্লিউপিএসই সদস্য টোসচো এই সংক্ষিপ্ত বিবরণে দেখা যাবে

খালি নির্মাণকারীর পদ্ধতির।

উপরোক্ত সংক্ষিপ্তসার থেকে নেওয়া সুবিধাগুলি / অসুবিধাগুলির একটি অংশ এখানে রইল যা খালি নির্মাণকারীর পদ্ধতির সম্পূর্ণ উদাহরণ দেয়।

  • সুবিধাদি:

    • ইউনিট পরীক্ষাগুলি কোনও হুককে স্বয়ংক্রিয়ভাবে সক্রিয় না করে নতুন দৃষ্টান্ত তৈরি করতে পারে। কোন একক না।

    • গ্লোবাল ভেরিয়েবলের দরকার নেই।

    • যে কেউ প্লাগইন দৃষ্টান্তের সাথে কাজ করতে চায় সে কেবল T5_Plugin_Class_Demo :: get_instance () কল করতে পারে।

    • নিষ্ক্রিয় করা সহজ।

    • তবুও বাস্তব ওওপি: কোনও কাজের পদ্ধতি স্থির নয়।

  • অসুবিধা:

    • পড়া কি কঠিন?

আমার মতে অসুবিধা হ'ল এটি একটি দুর্বল কারণ তাই এটি আমার পক্ষে পছন্দ হওয়া উচিত, তবে আমি একমাত্র ব্যবহার করি না। প্রকৃতপক্ষে আরও কয়েকটি ভারী ওজন এই বিষয়ে শীঘ্রই তাদের গ্রহণযোগ্যতা নিয়ে এই বিষয়ে সন্দেহ প্রকাশ করবে কারণ এই বিষয়টিকে ঘিরে কিছু ভাল মতামত রয়েছে যা ভয়েস করা উচিত।


দ্রষ্টব্য: আমাকে টাস্কো থেকে সংক্ষিপ্ত উদাহরণটি খুঁজে বের করতে হবে যা একটি প্লাগইনের মধ্যে যে কোনও শ্রেণীর ইনস্ট্যান্ট করতে হবে তার প্রতিযোগিতা যা প্রত্যেকে এর পক্ষে ভাল দেখায়, তার উপরের লিঙ্কটি এটি করার অনুকূল উপায় ছিল, তবে অন্যান্য উদাহরণগুলি এই বিষয়টির পক্ষে একটি ভাল বিপরীতে সরবরাহ করে। আশা করি টসচো এখনও ফাইলটিতে আছে।

দ্রষ্টব্য: WPSE উত্তর প্রাসঙ্গিক উদাহরণ এবং তুলনা সাথে এই বিষয়ে। এছাড়াও ওয়ার্ডপ্রেসে উদাহরণস্বরূপ সর্বোত্তম সমাধান।

add_shortcode( 'baztag', array( My_Plugin::get_instance(), 'foo' ) );
class My_Plugin {

    private $var = 'foo';

    protected static $instance = NULL;

    public static function get_instance() {

        // create an object
        NULL === self::$instance and self::$instance = new self;

        return self::$instance; // return the object
    }

    public function foo() {

        return $this->var; // never echo or print in a shortcode!
    }
}

অ্যাডঅ্যাকশন ('প্লাগিন_লোড', ...) এর মধ্যে পার্থক্য কী হবে; এবং যোগ_অ্যাকশন ('লোড-প্লাগইনস.এফপি', ...); উদাহরণটি আমি পরে ব্যবহার করেছি
কলপাইচ

1
লোড-প্লাগইনস.এফপি যা বুঝে তা থেকে, যদিও এটি কাজ করে তবে মূল update.phpফাইলের সাথে সম্পর্কিত এবং এটি সাধারণ ডিফল্ট ক্রিয়াকলাপের অংশ নয় যা শুরুতে চলাকালীন আগুনের ঘটনাগুলির ক্রম সম্পর্কে নির্ভর করা উচিত এবং সেই কারণে আমি পছন্দ করি এই ক্ষেত্রে এই হুকগুলি প্রয়োগ হয় যা প্রয়োগ হয় plugins_loaded। আমি প্রায়শই যখন অ্যাকশন রেফারেন্স হয় তখন তার দ্রুত স্ন্যাপশট হিসাবে এটি উল্লেখ করি । আমার ব্যাখ্যা সম্পূর্ণভাবে সম্পূর্ণ নয়।
আদম

4
আমি এই একক মত মত পদ্ধতির পছন্দ। তবে আমি আপনার আরম্ভের ক্রিয়া হুক হিসাবে প্লাগইন_ লোড ব্যবহার করে প্রশ্ন করি। এই হুকটি বোঝা যাচ্ছে সমস্ত প্লাগইন লোড হওয়ার পরে চালানো হবে। এটির পরে ingুকিয়ে দিয়ে, আপনি সেই হুককে হাইজ্যাকিংয়ের মতো এবং অন্য প্লাগইনগুলি বা প্লাগইন-লোড হওয়া থিমগুলির সাথে দ্বন্দ্ব বা স্টার্টআপ-সিকোয়েন্স ইস্যুতে মজা করতে পারেন। আপনার প্রারম্ভিককরণ পদ্ধতিটি চালানোর জন্য আমি কোনও পদক্ষেপ নিতে চাই না। প্লাগইন আর্কিটেকচারটি কোনও ক্রিয়ায় নয়, ইনলাইন চালানোর জন্য ডিজাইন করা হয়েছিল।
টম অগার

2
নোট করুন যে আপনি যদি ব্যবহার করেন register_activation_hook()তবে plugins_loadedক্রিয়াটি ট্রিগার হওয়ার আগে আপনাকে সেই ফাংশনটি কল করতে হবে ।
জির্ট

1
অতিরিক্ত তথ্য হিসাবে, @ মাইকসচিনেল এবং মন্তব্যগুলিতে ডিকাস থেকে এই পোস্টটি দেখুন। হার্ডকোর
wp.com/2012/…

78

আসল প্রশ্ন জিজ্ঞাসার ঠিক ২ বছর পরে এখানে পৌঁছেছি, আমি কয়েকটি বিষয় উল্লেখ করতে চাই। (আমাকে কখনও অনেক কিছু দেখানোর জন্য জিজ্ঞাসা করবেন না )।

সঠিক হুক

একটি প্লাগইন ক্লাস ইনস্ট্যান্ট করতে, সঠিক হুক ব্যবহার করা উচিত। এটির জন্য কোনও সাধারণ নিয়ম নেই, কারণ এটি শ্রেণি কী করে তার উপর নির্ভর করে।

খুব প্রথম দিকের হুক ব্যবহার করা "plugins_loaded"প্রায়শই বোধগম্য হয় না কারণ এর মতো একটি হুক অ্যাডমিন, ফ্রন্ট্যান্ড এবং এজেএক্স অনুরোধের জন্য বহিস্কার করা হয় তবে খুব সম্ভবত পরবর্তী সময়ে হুক আরও ভাল হয় কারণ এটি যখন প্রয়োজন তখনই প্লাগইন ক্লাস ইনস্ট্যান্ট করতে দেয়।

যেমন টেমপ্লেটগুলির জন্য স্টাফ তৈরি করে এমন একটি শ্রেণিতে তা ইনস্ট্যান্ট করা যেতে পারে "template_redirect"

সাধারণভাবে বলা খুব বিরল যে কোনও শ্রেণিকে "wp_loaded"বরখাস্ত করার আগে তাত্ক্ষণিকভাবে চালানো দরকার।

গড ক্লাস নেই

যেমন পুরোনো উত্তর উদাহরণ একটি বর্গ মত নামে ব্যবহার ব্যবহৃত সকল শ্রেণীর সর্বাধিক "Prefix_Example_Plugin"বা "My_Plugin"... এই ইঙ্গিত করে যে সেখানে সম্ভবত একটি হল মূল প্লাগইন জন্য ক্লাস।

ঠিক আছে, যদি না কোনও একক শ্রেণীর দ্বারা প্লাগইন তৈরি না করা হয় (যার ক্ষেত্রে এটি প্লাগইন নামের পরে নামকরণ করা একেবারে যুক্তিসঙ্গত হয়), যাতে পুরো প্লাগইন পরিচালনা করে এমন একটি ক্লাস তৈরি করা (যেমন একটি প্লাগইনের প্রয়োজনীয় সমস্ত হুক যুক্ত করা বা অন্য সমস্ত প্লাগইন ক্লাস ইনস্ট্যান্ট করা) ) godশ্বর বস্তুর উদাহরণ হিসাবে, এটি একটি খারাপ অভ্যাস হিসাবে বিবেচনা করা যেতে পারে ।

অবজেক্ট ওরিয়েন্টেড প্রোগ্রামিং কোডটি সলিড হওয়া উচিত যেখানে "এস" "একক দায়িত্বের নীতি" হিসাবে দাঁড়ায় ।

এর অর্থ প্রতিটি শ্রেণীর একটি কাজ করা উচিত। ওয়ার্ডপ্রেস প্লাগইন বিকাশে এর অর্থ হ'ল বিকাশকারীগণ একটি প্রধান প্লাগইন ক্লাস ইনস্ট্যান্ট করার জন্য একটি একক হুক ব্যবহার করা এড়ানো উচিত , তবে শ্রেণীর দায়িত্ব অনুযায়ী বিভিন্ন শ্রেণি ইনস্ট্যান্ট করতে বিভিন্ন হুক ব্যবহার করা উচিত।

কন্সট্রাক্টরের হুকগুলি এড়িয়ে চলুন

এই যুক্তিটি এখানে অন্যান্য উত্তরে প্রবর্তিত হয়েছে, তবে আমি এই ধারণাটিটি মন্তব্য করতে চাই এবং এই অন্য উত্তরটি সংযুক্ত করতে চাই যেখানে ইউনিট পরীক্ষার পরিধিতে এটি বেশ বিস্তৃতভাবে ব্যাখ্যা করা হয়েছে।

প্রায় 2015: পিএইচপি 5.2 জোম্বিদের জন্য

১৪ ই আগস্ট ২০১৪ সাল থেকে, পিএইচপি 5.3 জীবনের শেষ পর্যায়ে পৌঁছেছে । এটা অবশ্যই মারা গেছে। পিএইচপি 5.4 সমস্ত 2015 এর জন্য সমর্থনযোগ্য হতে চলেছে, এর অর্থ এটি যে মুহুর্তে লিখছি সেই মুহূর্তে অন্য বছরের জন্য।

তবে, ওয়ার্ডপ্রেস এখনও পিএইচপি 5.2 সমর্থন করে, তবে কারওই একক লাইন কোডের লিখন লেখা উচিত নয় যা সেই সংস্করণটিকে সমর্থন করে, বিশেষত যদি কোডটি ওওপি হয়।

বিভিন্ন কারণ রয়েছে:

  • পিএইচপি 5.2 অনেক দিন আগে মারা গেছে, এর জন্য কোনও সুরক্ষা সংশোধন করা হয় না, এর অর্থ এটি সুরক্ষিত নয়
  • পিএইচপি 5.3 পিএইচপি, বেনামে ফাংশন এবং নেমস্পেসেএলারদের সাথে অনেকগুলি বৈশিষ্ট্য যুক্ত করেছে
  • পিএইচপি এর নতুন সংস্করণগুলি অনেক দ্রুত । পিএইচপি বিনামূল্যে। এটি আপডেট করা নিখরচায়। আপনি যদি আরও দ্রুত, আরও সুরক্ষিত কোনও ব্যবহার করতে পারেন তবে কেন ধীর, সুরক্ষিত সংস্করণটি ব্যবহার করবেন?

আপনি যদি পিএইচপি 5.4+ কোড ব্যবহার করতে না চান তবে কমপক্ষে 5.3+ ব্যবহার করুন

উদাহরণ

এই মুহুর্তে এখন পর্যন্ত আমি যা বলেছি তার ভিত্তিতে পুরানো উত্তরগুলি পর্যালোচনা করার সময় এসেছে।

একবার আমাদের আর 5.2 এর যত্ন নেওয়ার দরকার নেই, আমরা নেমস্পেস ব্যবহার করতে পারি এবং করব।

একক দায়িত্বের নীতিটি আরও ভালভাবে ব্যাখ্যা করার জন্য, আমার উদাহরণে 3 টি শ্রেণি ব্যবহার করা হবে, একটি এমন একটি যা সম্মুখভাগে কিছু করে, একটি ব্যাকএন্ডে এবং তৃতীয়টি উভয় ক্ষেত্রে ব্যবহৃত হয়।

প্রশাসন শ্রেণি:

namespace GM\WPSE\Example;

class AdminStuff {

   private $tools;

   function __construct( ToolsInterface $tools ) {
     $this->tools = $tools;
   }

   function setup() {
      // setup class, maybe add hooks
   }

}

সামনের শ্রেণি:

namespace GM\WPSE\Example;

class FrontStuff {

   private $tools;

   function __construct( ToolsInterface $tools ) {
     $this->tools = $tools;
   }

   function setup() {
      // setup class, maybe add hooks
   }

}

সরঞ্জাম ইন্টারফেস:

namespace GM\WPSE\Example;

interface ToolsInterface {

   function doSomething();

}

এবং একটি সরঞ্জাম শ্রেণি, অন্য দুটি দ্বারা ব্যবহৃত:

namespace GM\WPSE\Example;

class Tools implements ToolsInterface {

   function doSomething() {
      return 'done';
   }

}

এই ক্লাসগুলি থাকার পরে, আমি তাদের যথাযথ হুক ব্যবহার করে তাত্ক্ষণিকভাবে চালাতে পারি। কিছুটা এইরকম:

require_once plugin_dir_path( __FILE__ ) . 'src/ToolsInterface.php';
require_once plugin_dir_path( __FILE__ ) . 'src/Tools.php';

add_action( 'admin_init', function() {

   require_once plugin_dir_path( __FILE__ ) . 'src/AdminStuff.php';
   $tools = new GM\WPSE\Example\Tools;
   global $admin_stuff; // this is not ideal, reason is explained below
   $admin_stuff = new GM\WPSE\Example\AdminStuff( $tools ); 
} );

add_action( 'template_redirect', function() {

   require_once plugin_dir_path( __FILE__ ) . 'src/FrontStuff.php';
   $tools = new GM\WPSE\Example\Tools;
   global $front_stuff; // this is not ideal, reason is explained below
   $front_stuff = new GM\WPSE\Example\FrontStuff( $tools );    
} );

নির্ভরতা বিপর্যয় এবং নির্ভরতা ইনজেকশন

উপরের উদাহরণে আমি উপরে বর্ণিত প্রয়োগগুলিতে প্রয়োগ করে বিভিন্ন হুকগুলিতে বিভিন্ন ক্লাস ইনস্ট্যান্ট করতে নেমস্পেস এবং বেনাম ফাংশন ব্যবহার করেছি।

নোটস্পেসগুলি কীভাবে কোনও উপসর্গ ছাড়াই ক্লাস তৈরি করতে দেয় তা নোট করুন।

আমি অন্য ধারণাটি প্রয়োগ করেছি যা পরোক্ষভাবে উপরে উল্লিখিত ছিল: নির্ভরতা ইনজেকশন , এসএলআইডি সংক্ষিপ্ত আকারে ডিপেন্ডেন্সি ইনভার্শন নীতি , "ডি" প্রয়োগ করা একটি পদ্ধতি ।

Toolsশ্রেণী "ইনজেকশনের" হয় অন্য দুটি ক্লাসের যখন তারা instantiated, তাই এই ভাবে এটা দায়িত্ব আলাদা করা সম্ভব।

তদতিরিক্ত , AdminStuffএবং FrontStuffক্লাসগুলি টাইপ হিন্টিং ব্যবহার করে ঘোষণার জন্য তাদের প্রয়োগ করে এমন একটি শ্রেণীর প্রয়োজন ToolsInterface

এইভাবে আমাদের বা ব্যবহারকারীরা যারা আমাদের কোড ব্যবহার করেন তারা একই ইন্টারফেসের বিভিন্ন প্রয়োগ ব্যবহার করতে পারে, যা আমাদের কোডটিকে একটি কংক্রিট শ্রেণিতে নয় বরং বিমূর্ততার জন্য তৈরি করে: নির্ভরতা বিপরীতকরণের নীতিটি ঠিক তাই।

তবে উপরের উদাহরণটি আরও উন্নত করা যেতে পারে। আসুন দেখুন কিভাবে।

Autoloader

আরও ভাল পঠনযোগ্য ওওপি কোড লেখার একটি ভাল উপায় হ'ল প্রকারের (ইন্টারফেস, ক্লাস) সংজ্ঞাটি অন্য কোডের সাথে মিশ্রণ না করা এবং প্রতিটি ধরণের নিজস্ব ফাইলে রাখা put

এই বিধিটি পিএসআর -1 কোডিং মান 1 এর মধ্যে একটি

যাইহোক, এটি করার জন্য, একটি ক্লাস ব্যবহার করতে সক্ষম হবার আগে এতে থাকা ফাইলটি থাকা দরকার।

এটি অপ্রতিরোধ্য হতে পারে, তবে পিএইচপি কোনও শ্রেণীর প্রয়োজন হলে স্বয়ংক্রিয়ভাবে লোড করার জন্য ইউটিলিটি ফাংশন সরবরাহ করে, একটি কলব্যাক ব্যবহার করে যা এর নামের উপর ভিত্তি করে কোনও ফাইল লোড করে।

নেমস্পেস ব্যবহার করে এটি খুব সহজ হয়ে যায়, কারণ এখন ফর্মালার কাঠামোর সাথে নেমস্পেস স্ট্রাকচারের মিল পাওয়া সম্ভব।

এটি কেবল সম্ভব নয়, তবে এটি আরেকটি পিএসআর মান (বা আরও ভাল 2: পিএসআর -0 এখন হ্রাস করা হয়েছে, এবং পিএসআর -4 )।

এই মানদণ্ড অনুসরণ করে কাস্টম অটোলোডারকে কোড না করেই অটোলোড হ্যান্ডেল করে এমন বিভিন্ন সরঞ্জাম ব্যবহার করা সম্ভব।

আমার বলতে হবে যে ওয়ার্ডপ্রেস কোডিং স্ট্যান্ডার্ডগুলিতে ফাইল নামকরণের জন্য বিভিন্ন বিধি রয়েছে।

সুতরাং ওয়ার্ডপ্রেস কোর জন্য কোড লেখার সময়, বিকাশকারীদের ডাব্লুপি বিধি অনুসরণ করতে হবে, তবে কাস্টম কোড লেখার সময় এটি বিকাশকারী পছন্দ, তবে পিএসআর স্ট্যান্ডার্ড ব্যবহার করা ইতিমধ্যে লিখিত সরঞ্জামগুলি 2 ব্যবহার করা আরও সহজ ।

গ্লোবাল অ্যাক্সেস, রেজিস্ট্রি এবং পরিষেবা লোকেটার প্যাটার্নস।

ওয়ার্ডপ্রেসে প্লাগইন ক্লাস ইনস্ট্যান্ট করার সময় সবচেয়ে বড় সমস্যা হ'ল কোডের বিভিন্ন অংশ থেকে কীভাবে সেগুলি অ্যাক্সেস করা যায়।

ওয়ার্ডপ্রেস নিজেই বিশ্বব্যাপী পদ্ধতির ব্যবহার করে : ভেরিয়েবলগুলি বিশ্বব্যাপী স্কোপে সংরক্ষিত হয়, এগুলি সর্বত্র অ্যাক্সেসযোগ্য। প্রতিটি ডাব্লুপি ডেভেলপার globalতাদের কেরিয়ারে হাজারবার শব্দটি টাইপ করে ।

এটি উপরের উদাহরণের জন্যও আমি ব্যবহার করেছি তবে এটি মন্দ

এই উত্তরটি কেন আমাকে আরও ব্যাখ্যা করার অনুমতি দেওয়ার জন্য ইতিমধ্যে অনেক দীর্ঘ, তবে "গ্লোবাল ভেরিয়েবল অশুভ" এর জন্য এসইআরপিতে প্রথম ফলাফলগুলি পড়া ভাল সূচনা পয়েন্ট।

তবে কীভাবে বৈশ্বিক চলক এড়ানো সম্ভব?

বিভিন্ন উপায় আছে।

এখানে কিছু পুরানো উত্তর স্থির দৃষ্টিকোণ পদ্ধতির ব্যবহার করে ।

public static function instance() {

  if ( is_null( self::$instance ) ) {
    self::$instance = new self;
  }

  return self::$instance;
}

এটি সহজ এবং চমত্কার সূক্ষ্ম, তবে আমরা যে শ্রেণীতে অ্যাক্সেস করতে চাই তার জন্য প্যাটার্নটি প্রয়োগ করতে বাধ্য করে।

তদুপরি, এই পদ্ধতিটি approachশ্বর শ্রেণীর ইস্যুতে পড়ার পথে অনেক সময় ফেলে, কারণ বিকাশকারীরা এই পদ্ধতিটি ব্যবহার করে একটি প্রধান শ্রেণিকে অ্যাক্সেসযোগ্য করে তোলে এবং তারপরে এটি অন্য সমস্ত শ্রেণীর অ্যাক্সেসের জন্য ব্যবহার করে।

আমি alreadyশ্বর শ্রেণিটি কতটা খারাপ তা ইতিমধ্যে ব্যাখ্যা করেছি, সুতরাং যখন কোনও প্লাগইন কেবল এক বা দুটি শ্রেণীর অ্যাক্সেসযোগ্য করে তোলে তখন স্ট্যাটিক দৃষ্টিকোণ পদ্ধতির good

এর অর্থ এই নয় যে এটি কেবলমাত্র কয়েকটি ক্লাসের প্লাগইনগুলির জন্য ব্যবহার করা যেতে পারে, আসলে, যখন নির্ভরতা ইনজেকশন নীতিটি সঠিকভাবে ব্যবহৃত হয়, তখন বিশ্বব্যাপী একটি বিশাল সংখ্যক অ্যাক্সেসযোগ্য না করে বেশ জটিল অ্যাপ্লিকেশন তৈরি করা সম্ভব is বস্তুর।

যাইহোক, কখনও কখনও প্লাগইনগুলিকে কিছু ক্লাস অ্যাক্সেসযোগ্য করা প্রয়োজন এবং সেই ক্ষেত্রে স্থির দৃষ্টিকোণ পদ্ধতির অপ্রতিরোধ্য।

আর একটি সম্ভাব্য পন্থা হ'ল রেজিস্ট্রি প্যাটার্নটি ব্যবহার করা ।

এটি এটির একটি খুব সাধারণ বাস্তবায়ন:

namespace GM\WPSE\Example;

class Registry {

   private $storage = array();

   function add( $id, $class ) {
     $this->storage[$id] = $class;
   }

   function get( $id ) {
      return array_key_exists( $id, $this->storage ) ? $this->storage[$id] : NULL;
   }

}

এই শ্রেণিটি ব্যবহার করে কোনও আইডি দ্বারা রেজিস্ট্রি অবজেক্টে অবজেক্টগুলি সংরক্ষণ করা সম্ভব, সুতরাং একটি রেজিস্ট্রি অ্যাক্সেস থাকাতে সমস্ত বস্তুর অ্যাক্সেস থাকা সম্ভব। অবশ্যই যখন কোনও জিনিস প্রথমবারের জন্য তৈরি করা হয় তখন এটি রেজিস্ট্রিতে যুক্ত করা দরকার।

উদাহরণ:

global $registry;

if ( is_null( $registry->get( 'tools' ) ) ) {
  $tools = new GM\WPSE\Example\Tools;
  $registry->add( 'tools', $tools );
}

if ( is_null( $registry->get( 'front' ) ) ) {
  $front_stuff = new GM\WPSE\Example\FrontStuff( $registry->get( 'tools' ) );    
  $registry->add( 'front', front_stuff );
}

add_action( 'wp', array( $registry->get( 'front' ), 'wp' ) );

উপরের উদাহরণটি পরিষ্কার করে দেয় যে রেজিস্ট্রি কার্যকর হওয়ার জন্য বিশ্বব্যাপী অ্যাক্সেসযোগ্য হওয়া দরকার। একমাত্র রেজিস্ট্রি জন্য একটি বৈশ্বিক পরিবর্তনশীল খুব খারাপ নয়, তবে অ-বিশ্বব্যাপী বিশোধবাদীদের ক্ষেত্রে কোনও রেজিস্ট্রি বা স্থির পরিবর্তনশীল সহ কোনও ফাংশন কার্যকর করা সম্ভব:

function gm_wpse_example_registry() {
  static $registry = NULL;
  if ( is_null( $registry ) ) {
    $registry = new GM\WPSE\Example\Registry;
  }
  return $registry;
}

প্রথমবার ফাংশনটি বলা হলে এটি রেজিস্ট্রি ইনস্ট্যান্ট করবে, পরবর্তী কলগুলিতে এটি কেবল এটি ফিরিয়ে দেবে।

বিশ্বব্যাপী কোনও শ্রেণিকে অ্যাক্সেসযোগ্য করার জন্য আরেকটি ওয়ার্ডপ্রেস-নির্দিষ্ট পদ্ধতি ফিল্টার থেকে কোনও অবজেক্টের উদাহরণ ফিরিয়ে আনছে। এটার মতো কিছু:

$registry = new GM\WPSE\Example\Registry;

add_filter( 'gm_wpse_example_registry', function() use( $registry ) {
  return $registry;
} );

এর পরে সর্বত্র রেজিস্ট্রি প্রয়োজন:

$registry = apply_filters( 'gm_wpse_example_registry', NULL );

আর একটি প্যাটার্ন যা ব্যবহার করা যায় তা হ'ল সার্ভিস লোকেটার প্যাটার্ন । এটি রেজিস্ট্রি প্যাটার্নের মতো, তবে সার্ভিস লোকেটারগুলি নির্ভরতা ইনজেকশন ব্যবহার করে বিভিন্ন শ্রেণিতে পাস করা হয়।

এই প্যাটার্নটির মূল সমস্যাটি হ'ল এটি ক্লাসের নির্ভরতাগুলি কোডগুলি বজায় রাখা এবং পড়া আরও শক্ত করে তোলে to

ডিআই পাত্রে

রেজিস্ট্রি বা সার্ভিস লোকেটারকে বিশ্বব্যাপী অ্যাক্সেসযোগ্য করার জন্য যে পদ্ধতি ব্যবহার করা হোক না কেন, সেখানে বস্তুগুলি সংরক্ষণ করতে হবে এবং সংরক্ষণের আগে সেগুলি তাত্ক্ষণিক করা দরকার need

জটিল অ্যাপ্লিকেশনগুলিতে, যেখানে বেশ কয়েকটি ক্লাস রয়েছে এবং তাদের মধ্যে বেশ কয়েকটি নির্ভরশীলতা রয়েছে, তাত্ক্ষণিক ক্লাসে প্রচুর কোডের প্রয়োজন হয়, যাতে বাগের সম্ভাবনা বৃদ্ধি পায়: যে কোডটি বিদ্যমান নেই সেগুলিতে বাগ থাকতে পারে না।

গত বছরগুলিতে এমন কিছু পিএইচপি লাইব্রেরি প্রকাশিত হয়েছে যা পিএইচপি বিকাশকারীদের সহজেই বস্তুর উদাহরণ ইনস্ট্যান্ট করতে এবং সঞ্চয় করতে সহায়তা করে, স্বয়ংক্রিয়ভাবে তাদের নির্ভরতা সমাধান করে।

এই লাইব্রেরিগুলি নির্ভরশীলতা ইনজেকশন ধারক হিসাবে পরিচিত কারণ তারা নির্ভরতাগুলি সমাধান করার ক্লাস ইনস্ট্যান্ট করতে সক্ষম এবং অবজেক্টগুলি সংরক্ষণ করতে এবং যখন প্রয়োজন হয় তখন তাদের ফিরিয়ে আনতে সক্ষম হয়, একটি রেজিস্ট্রি অবজেক্টের অনুরূপ অভিনয় করে।

সাধারণত, ডিআই কন্টেনারগুলি ব্যবহার করার সময়, বিকাশকারীদের অ্যাপ্লিকেশনটির প্রতিটি শ্রেণীর জন্য নির্ভরতা সেটআপ করতে হয় এবং তারপরে প্রথমে কোনও শ্রেণিতে কোডের প্রয়োজন হয় যখন এটি যথাযথ নির্ভরতা সহ ইনস্ট্যান্ট হয় এবং পরবর্তী অনুরোধগুলিতে একই উদাহরণটি বারবার ফিরে আসে same ।

কিছু ডিআই কনটেইনার কনফিগারেশন ছাড়াই স্বয়ংক্রিয়ভাবে নির্ভরতা আবিষ্কার করতে সক্ষম, তবে পিএইচপি প্রতিবিম্ব ব্যবহার করে ।

কিছু পরিচিত ডিআই কনটেইনার হলেন:

এবং আরও অনেক কিছু.

আমি উল্লেখ করতে চাই যে সাধারণ প্লাগইনগুলির জন্য, কেবলমাত্র কয়েকটি শ্রেণি এবং শ্রেণীর মধ্যে অনেকগুলি নির্ভরশীলতা নেই, সম্ভবত এটি ডিআই পাত্রে ব্যবহার করা ভাল নয়: স্ট্যাটিক উদাহরণ পদ্ধতি বা একটি গ্লোবাল অ্যাক্সেসযোগ্য রেজিস্ট্রি ভাল সমাধান তবে জটিল প্লাগিনগুলির জন্য একটি ডিআই কনটেইনার সুবিধা সুস্পষ্ট হয়ে যায়।

অবশ্যই, এমনকি ডিআই কনটেইনার অবজেক্টগুলিকে অ্যাপ্লিকেশনটিতে ব্যবহার করার জন্য অ্যাক্সেসযোগ্য হতে হবে এবং সেই উদ্দেশ্যে উপরে প্রদর্শিত পদ্ধতিগুলির মধ্যে একটি, গ্লোবাল ভেরিয়েবল, স্ট্যাটিক উদাহরণ ভেরিয়েবল, ফিল্টার মাধ্যমে রিটার্নিং অবজেক্ট ব্যবহার করা সম্ভব।

সুরকার

ডিআই কনটেইনার ব্যবহার করার অর্থ প্রায়শই তৃতীয় পক্ষের কোড ব্যবহার করা। আজকাল, পিএইচপি-তে, যখন আমাদের একটি বাহ্যিক লিব ব্যবহার করা প্রয়োজন (সুতরাং কেবল ডিআই পাত্রে নয়, তবে কোনও কোড যা অ্যাপ্লিকেশনের অংশ নয়) কেবল এটি ডাউনলোড করে আমাদের অ্যাপ্লিকেশন ফোল্ডারে রেখে দেওয়া ভাল অভ্যাস হিসাবে বিবেচিত হয় না। এমনকি যদি আমরা সেই অন্য কোডের টুকরোটির লেখক।

বাহ্যিক নির্ভরতা থেকে একটি অ্যাপ্লিকেশন কোড ডেকে আউট করা আরও ভাল সংস্থার, আরও ভাল নির্ভরযোগ্যতা এবং কোডটির আরও বিশুদ্ধতার লক্ষণ ।

সুরকার , পিএইচপি নির্ভরতা পরিচালনা করার জন্য পিএইচপি সম্প্রদায়ের ডি-ফ্যাক্টো স্ট্যান্ডার্ড। পাশাপাশি ডাব্লুপি সম্প্রদায়তে মূলধারার দিকে যেতে খুব দূরে , এটি এমন একটি সরঞ্জাম যা প্রতিটি পিএইচপি এবং ওয়ার্ডপ্রেস বিকাশকারী কমপক্ষে জানা উচিত, যদি না ব্যবহার করে।

এই উত্তরটি আরও আলোচনার অনুমতি দেওয়ার জন্য ইতিমধ্যে বইয়ের আকারের, এবং এখানে সুরকারকে নিয়ে আলোচনা করা সম্ভবত বিষয়বস্তু নয়, এটি কেবলমাত্র সম্পূর্ণতার জন্যই উল্লেখ করা হয়েছিল।

আরও তথ্যের জন্য সুরকারের সাইটটিতে যান এবং @ মিনিস্টের দ্বারা সজ্জিত এই মিনিসাইটকে একটি পঠন দেওয়াও মূল্যবান


1 পিএসআর হ'ল পিএইচপি মানক বিধিগুলি পিএইচপি ফ্রেমওয়ার্ক ইন্টারপ গ্রুপ দ্বারা প্রকাশিত

2 অন্যান্য বিষয়গুলির মধ্যে সুরকার (একটি লাইব্রেরি যা এই উত্তরে উল্লেখ করা হবে) এর মধ্যে একটি অটোলোডার ইউটিলিটিও রয়েছে।


1
একটি অতিরিক্ত নোট, পিএইচপি 5.3 এছাড়াও জীবনের শেষ। একজন দায়িত্বশীল হোস্ট অপ্রাপ্তির হিসাবে কমপক্ষে 5.4 অফার করবে ডিফল্ট না হলে
টম জে নওয়েল

2
"১৪ ই আগস্ট ২০১৪ সাল থেকে, পিএইচপি 5.3 জীবনের শেষ পর্যায়ে পৌঁছেছে It's এটি অবশ্যই মারা গেছে" " "পিএইচপি 5.2 এর অধীনে প্রথম লাইনটি জম্বিদের জন্য রয়েছে" @ টমজেএনওয়েল
গাজাজাজাপ

3
শুধু ভাবছি, আপনি "প্রচুর জিনিস" দেখতে দেখতে কী দেখবেন? ;-)
মাইকচিন্কেল

গ্লোবাল ভেরিয়েবলগুলি এড়ানোর প্রচেষ্টায়, আমি ফাংশন এবং স্ট্যাটিক ভেরিয়েবল সহ রেজিস্ট্রি প্যাটার্নের ধারণা পছন্দ করি। প্রথমবার ফাংশনটি বলা হলে এটি রেজিস্ট্রি ইনস্ট্যান্ট করবে, পরবর্তী কলগুলিতে এটি কেবল এটি ফিরিয়ে দেবে।
মাইকেল একলন্ড

10

আমি নিম্নলিখিত কাঠামো ব্যবহার:

Prefix_Example_Plugin::on_load();

/**
 * Example of initial class-based plugin load.
 */
class Prefix_Example_Plugin {

    /**
     * Hooks init (nothing else) and calls things that need to run right away.
     */
    static function on_load() {

        // if needed kill switch goes here (if disable constant defined then return)

        add_action( 'init', array( __CLASS__, 'init' ) );
    }

    /**
     * Further hooks setup, loading files, etc.
     *
     * Note that for hooked methods name equals hook (when possible).
     */
    static function init(  ) {


    }
}

নোট:

  • এখনই দৌড়াতে হবে এমন জিনিসগুলির জন্য স্থান নির্ধারণ করেছে
  • টুইটগুলির জন্য অক্ষম / ওভাররাইড করা সহজ (এক initপদ্ধতি অবলম্বন করা )
  • আমি কখনও মনে করি না যে আমি কখনই প্লাগইন ক্লাসের প্রয়োজন / প্রয়োজনীয় অবজেক্টটি ব্যবহার করেছি - এর ট্র্যাক রাখা প্রয়োজন, ইত্যাদি; এটি উদ্দেশ্য দ্বারা সত্যই জাল নেমস্পেসিং, ওওপি নয় (বেশিরভাগ সময়)

দাবি অস্বীকার আমি এখনও ইউনিট টেস্ট ব্যবহার করি না ( মাইপ্লেটে অনেক কিছু ) এবং আমি শুনেছি যে স্ট্যাটিক তাদের জন্য কম পছন্দনীয় হতে পারে। আপনার এটির ইউনিট পরীক্ষার প্রয়োজন হলে এই বিষয়ে আপনার গবেষণাটি করুন।


3
আমি জানি ইউনিট টেস্টিংয়ের ক্ষেত্রে বড় লোকেরা স্থির / সিঙ্গলটন সমাধানগুলি পছন্দ করেন না। আমি মনে করি আপনি যদি স্ট্যাটিক ব্যবহার করে কী অর্জন করার চেষ্টা করছেন এবং আপনি যদি তা সম্পূর্ণরূপে বুঝতে চান তবে তা করার পদ্ধতি সম্পর্কে অবগত হন তবে এই জাতীয় পদ্ধতিগুলি বাস্তবায়নের জন্য এটি পুরোপুরি ঠিক fine স্ট্যাক ওভারফ্লো
অ্যাডাম

এটি আমাকে সত্যিই ভাবতে বাধ্য করেছে। তাহলে কেন একটি ক্লাস ব্যবহার করুন এবং কেবল সাধারণ উপসর্গযুক্ত ফাংশনে ফিরে যাবেন না। আমরা কি ক্লিনার ফাংশন / পদ্ধতির নাম রাখার জন্য এটি করি? আমি বোঝাতে চাইছি তাদের "স্ট্যাটিক" বি 4 দিয়ে বাসা বেঁধেছে এটি কি আরও বেশি পাঠযোগ্য? নামের সংঘাতের সুযোগটি একক শ্রেণীর নামের মতোই যদি আপনি প্রপার প্রিফিক্স ব্যবহার করেন বা আমি কিছু মিস করছি?
জেমস মিচ

1
@ জেমসমিচ হ্যাঁ, সমস্ত স্থিতিশীল পদ্ধতিগুলি বেশিরভাগ ক্ষেত্রে কেবল ডাব্লুপি-তে ব্যবহৃত নকল নাম স্থান সহ ফাংশন। তবে ক্লাসগুলির এই ক্ষেত্রে খাঁটি ফাংশনগুলির থেকে কিছু সুবিধা রয়েছে যেমন অটোলোড এবং উত্তরাধিকার। ইদানীং আমি স্থিতিশীল পদ্ধতিগুলি থেকে এবং নির্ভরতা ইনজেকশন ধারক দ্বারা সংগঠিত প্রকৃত তাত্ক্ষণিক বস্তুর দিকে এগিয়ে চলেছি।
রর্স্ট

3

এটি সমস্ত কার্যকারিতা উপর নির্ভর করে।

আমি একবার একটি প্লাগইন তৈরি করেছি যা স্ক্রিপ্টগুলি নিবন্ধভুক্ত করে যখন কনস্ট্রাক্টরকে ডেকে আনা হয় তাই আমাকে এটিকে হুকের কাছে রেখে দিতে হয়েছিল wp_enqueue_scripts

আপনার functions.phpফাইলটি লোড হওয়ার পরে আপনি যদি এটি কল করতে চান , আপনি $class_instance = new ClassName();যেমন উল্লেখ করেছেন তেমন নিজেই একটি উদাহরণ তৈরি করতে পারেন ।

আপনি গতি এবং মেমরির ব্যবহার বিবেচনা করতে চাইতে পারেন। আমি কোনও বিষয়ে অবগত নই, তবে আমি কল্পনা করতে পারি যে কিছু ক্ষেত্রে অনাবৃত হুক রয়েছে। এই হুকটিতে আপনার উদাহরণ তৈরি করে আপনি কিছু সার্ভারের সংস্থানগুলি সংরক্ষণ করতে পারেন।


এর জন্য দুর্দান্ত ধন্যবাদ, আমি মনে করি উপরোক্ত প্রশ্নের দুটি পয়েন্টও আছে। অন্যটি হচ্ছে __ কনস্ট্রাক্ট উপযুক্ত কিনা বা init () ক্লাসটি আরম্ভ করার জন্য আরও ভাল উপায়।
কলপাইচ

1
ভাল আমি একটি স্ট্যাটিক init()পদ্ধতিতে যাব যাতে ক্লাসের উদাহরণটিকে ক্লাসের অন্য স্কোপের পরিবর্তে স্কোপ বলা হয় যেখানে আপনি সম্ভবত বিদ্যমান ভেরিয়েবলগুলি ওভাররাইট করতে পারেন।
টিম এস

0

আমি জানি এটি কয়েক বছর বয়সী, তবে এর মধ্যে পিএইচপি 5.3 বেনাম পদ্ধতিগুলিকে সমর্থন করে , তাই আমি এটি নিয়ে এসেছি:

add_action( 'plugins_loaded', function() { new My_Plugin(); } );

এবং কোনওভাবে আমি এটি সবচেয়ে পছন্দ করি। আমি নিয়মিত কনস্ট্রাক্টর ব্যবহার করতে পারি এবং আমার ওওপি কাঠামোগুলিকে গোলমেলে এমন কোনও "আরআইআই" বা "অন_লোড" পদ্ধতি সংজ্ঞায়িত করার দরকার নেই।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.