Чи є документація щодо життєвого циклу плагіна?


11

Чи є десь документація, яка пояснює, який життєвий цикл плагінів?

Я запускаю новий плагін у стилі OOP, і я лише дізнався, що мій основний клас інстанціюється дуже багато (завдяки Xdebug та Netbeans).
Цікаво, чому це, і це мене дратує, тому що я створюю об'єкт Dropbox-API, і я дійсно не думав, що WordPress так просто заробить мій основний клас.

Я не знайшов нічого, пов’язаного з життєвим циклом плагінів ні в Codex, ні в Google.


І ось, ви тут шукали ? :)
brasofilo

20
YouPorn завжди можна визначити свій клас як одноплодной stackoverflow.com/questions/203336 / ...
Bainternet

1
Дякую. Я не думав про «кращі практики». Я читав багато речей у Codex, включаючи Керівництво з кодування, але його тут немає. Спробую тоді одноразовий, але все-таки мені здається дивним, що плагін PHP називається кілька разів. Ні? Bainternet будьте обережні зі своїм автозаповненням :)
RitonLaJoie

brasofilo, створення синглтона допоможе, але не дає відповіді на питання: чому код запускається кілька разів всередині мого плагіна? Клас ОО в URL-адресі, яку ви зв'язали, робить саме те, що я роблю
RitonLaJoie

2
Просто довелося поставити +1 питання. Просто для коментаря та оновлень: D
кайзер

Відповіді:


3

Я запускаю новий плагін зі стилем OOP

Що означає для вас стиль OOP? Обгортання всіх своїх функцій заявою класу? Тоді ти робиш це неправильно. Ви неправильно використовуєте клас як простір імен.

і я щойно дізнався, що мій основний клас багато інстанціюється

Так?

class Foo
{
  public function __construct() {
    // assuming your wp-content dir is writeable
    $filename = sprintf( WP_CONTENT_DIR . '/dummyfile-%d.txt', time() );
    $handle = fopen( $filename, 'w' );
    if ( $handle ) {
      fputs( $handle, '-' );
      fclose( $handle );
    }
  }
}

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

Спробуйте і порахуйте кількість створених файлів. Якщо я спробую це, для кожного запиту сторінки створений один файл. Це означає, що лише один екземпляр класу Foo для кожного запиту сторінки.

Спробуємо виклик дій

class Foo
{
    public function __construct() {

        $this->write_file( 'in_constructor' );
        add_action( 'init', array( $this, 'action_test' ), 10, 0 );

    }

    public function action_test() {

        $this->write_file( 'in_method_with_action_call' );

    }

    public function write_file( $filename ) {

      // assuming your wp-content dir is writeable
      $counter = 1;
      $fname = sprintf( WP_CONTENT_DIR . '/%s-%d.txt', $filename, $counter );

      if ( file_exists( $fname ) ) {
        preg_match( '/(\d)\.txt/is', $fname, $match );
          if ( isset( $match[1] ) ) {
              $counter = (int) $match[1] + 1;
              $fname = sprintf( WP_CONTENT_DIR . '/%s-%d.txt', $filename, $counter );
          }
      }

      $handle = fopen( $fname, 'a+' );
      if ( $handle ) {
          fputs( $handle, '-' );
          fclose( $handle );
      } else {
          throw new Exception( "Cannot open file {$fname} for writing" );
      }

    }
}

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

Якщо я заглянув у свій dp-контент, я знайшов два файли. Не більше. Один файл створюється при створенні екземпляра класу. І один створюється, коли виконується виклик дій.

Гаразд, давайте зробимо деякі дурні речі з нашим екземпляром. Видаліть add_action( 'plugins_loaded', .. )і замість цього додайте цей код:

function bar( $foo ) {

    $baz = $foo;
    return $baz;
}

$f = new Foo();
$GLOBALS['foo'] = $f;

$f2 = $f;
$f3 = &$f;

$f4 = bar( $f2 );
$f5 = bar( $f3 );

Скільки файлів ви очікуєте? Я очікую двох. Один від конструктора, один із методу.

Новий екземпляр створюється лише тоді, коли використовується newоператор.

add_action( 'plugins_loaded', 'new_foo', 10, 0 );

function new_foo() {
    // first instance
    new Foo();
}

function bar( $foo ) {
    $baz = $foo;
    return $baz;
}

// second instance here!!
$f = new Foo();
$GLOBALS['foo'] = $f;

$f2 = $f;
$f3 = &$f;

$f4 = bar( $f2 );
$f5 = bar( $f3 );

Зараз я рахую чотири файли. Два з конструктора і два з методу. Це тому, що WordPress спочатку включає плагін, а потім зробить гачок дій plugins_loaded.

Найкраща практика - використовувати гачок дій, plugins_loadedа не створювати екземпляр поза функцією, оскільки, якщо файл плагіна включений де-небудь (наприклад, в інший файл вашого плагіна), кожен екземпляр класу створюється щоразу, коли файл включається. Гак дії plugins_loadedвиконується лише один раз для кожного запиту на сторінку.


0

Що може статися, це те, що ви передаєте копію свого класу у фільтр або дію. Наприклад, якщо ви хочете безпосередньо змінити змінні класу всередині гака чи фільтра, вам слід також передати гак за посиланням

add_action("some_action",array(&$this,"somefunction"))

замість

add_action("some_action",array($this,"somefunction"))

Як зазначає bainternet, ви також можете використовувати однотонний шаблон, щоб переконатися, що конкретний об'єкт інстанціюється лише один раз (додаткові дзвінки повертають посилання на цей об’єкт).

Ви також можете розглянути можливість створення деяких функцій статичними (надаючи їм статичне ключове слово. Зазвичай це робиться для "хелперних" функцій, які не взаємодіють з рештою класу. Статичні методи можна викликати без інстанціювання класу.

Ви також можете передавати статичні функції дії / фільтру:

add_action("some_action",array("ClassName","Method"))

Я також перевірив http://codex.wordpress.org/Plugin_API/Action_Reference і виявив, що плагіни можуть завантажуватися лише на двох етапах запиту (muplugins_loaded та plugins_loaded).


3
Коли об'єкт надсилається аргументом, повертається або призначається іншій змінній, різні змінні не є псевдонімами: вони містять копію ідентифікатора, яка вказує на той самий об'єкт. з посібника PHP . У виклику дії чи фільтрі клас надсилається як аргумент. Оскільки PHP5 не потрібно передавати це як посилання.
Ralf912

Я виправлений
Arevico
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.