Jak zbudować wtyczkę

40

To nie jest pytanie o to, jak zbudować wtyczkę WordPress. Raczej, jakie, jeśli w ogóle, przewodniki można zastosować do tego, jak złożyć architekturę plików dowolnej wtyczki.

Niektóre inne języki programowania lub biblioteki mają bardzo kontrolowane sposoby organizowania katalogów i plików. Czasami jest to denerwujące i podkreśla swobodę, jaką oferuje PHP, ale z drugiej strony wtyczki WordPress są zestawiane w dowolny sposób określony przez ich autora.

Nie ma właściwej odpowiedzi , ale mam nadzieję, że dopracuję sposób, w jaki ja i inni tworzymy wtyczki, aby były bardziej przyjazne dla innych programistów, aby się rozłączyli, łatwiej debugować, łatwiej nawigować i być może bardziej wydajne.

Ostatnie pytanie: jaki według Ciebie jest najlepszy sposób na zorganizowanie wtyczki?

Poniżej znajduje się kilka przykładowych struktur, ale w żadnym wypadku nie jest to wyczerpująca lista. Dodaj własne rekomendacje.

Zakładana domyślna struktura

  • /wp-content
    • /plugins
      • /my-plugin
        • my-plugin.php

Metoda Model View Controller (MVC)

  • /wp-content
    • /plugins
      • /my-plugin
        • /controller
          • Controller.php
        • /model
          • Model.php
        • /view
          • view.php
        • my-plugin.php

Trzy części MVC:

  • W modelu współgra z bazą danych, zapytań oraz zapisywania danych i zawiera logikę.
  • Kontroler będzie zawierać szablon tagi i funkcje, że widok będzie wykorzystują.
  • Widok odpowiada wyświetlania danych dostarczonych przez model tak skonstruowany przez kontroler.

Organizowane według metody typu

  • /wp-content
    • /plugins
      • /my-plugin
        • /admin
          • admin.php
        • /assets
          • css/
          • images/
        • /classes
          • my-class.php
        • /lang
          • my-es_ES.mo
        • /templates
          • my-template.php
        • /widgets
          • my-widget.php
        • my-plugin.php

WordPress Plugin Boilerplate

Dostępne na Github

Na podstawie interfejsu API wtyczki , standardów kodowania i standardów dokumentacji .

  • /wp-content
    • /plugins
      • /my-plugin
        • /admin
          • /css
          • /js
          • /partials
          • my-plugin-admin.php
        • /includes
          • my_plugin_activator.php
          • my_plugin_deactivator.php
          • my_plugin_i18n.php
          • my_plugin_loader.php
          • my_plugin.php
        • /languages
          • my_plugin.pot
        • /public
          • /css
          • /js
          • /partials
          • my-plugin-public.php
        • LICENSE.txt
        • README.txt
        • index.php
        • my-plugin.php
        • uninstall.php

Luźno zorganizowana metoda

  • /wp-content
    • /plugins
      • /my-plugin
        • css/
        • images/
        • js/
        • my-admin.php
        • my-class.php
        • my-template.php
        • my-widget.php
        • my-plugin.php
rozwijalność
źródło
To nie jest prawdziwe pytanie, ale nie zamierzam głosować blisko, ale oflagowałem, aby uczynić to Wiki Wiki. Btw: Myślę, że perfekcja nazw plików nie ma sensu.
kaiser
Dzięki, wolałbym, żeby to była wiki społeczności. Wydaje mi się, że prefiksowanie plików w ten sposób nie ma większego sensu, ale często to widziałem.
developdaly
1
Innym ubocznym punkt może bardziej semantycznie poprawne nazwy folderów css/, images/i js/będzie styles/, images/i scripts/.
Andrew Odri,

Odpowiedzi:

16

Pamiętaj, że wszystkie wtyczki są „kontrolerami” według standardów WP.

Zależy to od tego, co ma zrobić wtyczka, ale we wszystkich przypadkach starałbym się oddzielić wyjście ekranu od kodu PHP w jak największym stopniu.

Oto jeden ze sposobów, aby to zrobić z łatwością - najpierw zdefiniuj funkcję, która ładuje szablon:

function my_plugin_load_template(array $_vars){

  // you cannot let locate_template to load your template
  // because WP devs made sure you can't pass
  // variables to your template :(
  $_template = locate_template('my_plugin', false, false);

  // use the default one if the theme doesn't have it
  if(!_$template)
    $_template = 'views/template.php';

  // load it
  extract($_vars);        
  require $template;
}

Teraz, jeśli wtyczka korzysta z widżetu do wyświetlania danych:

class Your_Widget extends WP_Widget{

  ...      
  public function widget($args, $instance){

    $title = apply_filters('widget_title', $instance['title'], $instance, $this->id_base);

    // this widget shows the last 5 "movies"
    $posts = new WP_Query(array('posts_per_page' => 5, 'post_type' => 'movie')); 

    if($title)
      print $before_title . $title . $after_title;

    // here we rely on the template to display the data on the screen
    my_plugin_load_template(array(

      // variables you wish to expose in the template
     'posts'    => $posts,          
    ));

    print $before_widget;
  }
  ...

}

Szablon:

<?php while($posts->have_posts()): $posts->the_post(); ?>

<p><?php the_title(); ?></p> 

<?php endwhile; ?>

Pliki:

/plugins/my_plugin/plugin.php           <-- just hooks 
/plugins/my_plugin/widget.php           <-- widget class, if you have a widget
/themes/twentyten/my_plugin.php         <-- template
/plugins/my_plugin/views/template.php   <-- fallback template

Gdzie umieścić CSS, JS, obrazy lub jak zaprojektować pojemnik na haczyki, jest mniej ważne. To chyba kwestia osobistych preferencji.

onetrickpony
źródło
6

To zależy od wtyczki. Oto moja podstawowa struktura dla prawie każdej wtyczki:

my-plugin/
    inc/
        Any additional plugin-specific PHP files go here
    lib/
        Library classes, css, js, and other files that I use with many
        plugins go here
    css/
    js/
    images/
    lang/
        Translation files
    my-plugin.php
    readme.txt

To byłoby coś, co trafiłoby do libfolderu.

Jeśli jest to szczególnie złożona wtyczka z dużą ilością funkcji administracyjnych, dodałbym adminfolder zawierający wszystkie te pliki PHP. Jeśli wtyczka działa podobnie jak zamiana dołączonych plików motywu , może to oznaczać również folder templatelub theme.

Struktura katalogów może wyglądać następująco:

my-plugin/
    inc/
    lib/
    admin/
    templates/
    css/
    js/
    images/
    lang/
    my-plugin.php
    readme.txt
chrisguitarguy
źródło
Czy umieścisz także pliki css i js administratora w folderze / admin? Zatem mając inne / css i / js w / admin?
urok93
6

IMHO, najłatwiejszą, najmocniejszą i najłatwiejszą w utrzymaniu trasą jest użycie struktury MVC, a WP MVC jest zaprojektowany tak, aby pisanie wtyczek MVC było bardzo łatwe (choć jestem trochę stronniczy). Dzięki WP MVC możesz po prostu tworzyć modele, widoki i kontrolery, a wszystko inne jest obsługiwane za kulisami.

Dla sekcji publicznej i administracyjnej można tworzyć osobne kontrolery i widoki, a cała platforma wykorzystuje wiele natywnych funkcji WordPress. Struktura pliku i duża część funkcjonalności jest dokładnie taka sama, jak w najpopularniejszych frameworkach MVC (Rails, CakePHP itp.).

Więcej informacji i samouczek można znaleźć tutaj:

Tomek
źródło
5

Używamy kombinacji wszystkich metod. Po pierwsze, używamy Zend Framework 1.11 w naszych wtyczkach i dlatego musieliśmy użyć podobnej struktury dla plików klas z powodu mechanizmu automatycznego ładowania.

Struktura naszej podstawowej wtyczki (która jest używana przez wszystkie nasze wtyczki jako podstawa) wygląda podobnie:

webeo-core/
    css/
    images/
    js/
    languages/
    lib/
        Webeo/
            Core.php
        Zend/
            /** ZF files **/
        Loader.php
    views/
    readme.txt
    uninstall.php
    webeo-core.php
  1. WordPress wywołuje webeo-core.phpplik w folderze głównym wtyczki.
  2. W tym pliku ustawimy ścieżkę dołączania PHP i zarejestrujemy haki aktywacji i dezaktywacji wtyczki.
  3. Mamy także Webeo_CoreLoaderklasę w tym pliku, która ustawia niektóre stałe wtyczek, inicjuje autoloader klasy i wywołuje metodę instalacji Core.phpklasy w lib/Webeofolderze. Działa to na plugins_loadedhaku akcji z priorytetem 9.
  4. Core.phpKlasa jest nasz plugin plik bootstrap. Nazwa oparta jest na nazwie wtyczek.

Jak widać, w libfolderze znajduje się podkatalog dla wszystkich naszych pakietów dostawców ( Webeo, Zend). Wszystkie paczki podrzędne wewnątrz dostawcy mają strukturę według samego modułu. W przypadku nowego Mail Settingsformularza administratora mielibyśmy następującą strukturę:

webeo-core/
    ...
    lib/
        Webeo/
            Form/
                Admin/
                    MailSettings.php
                Admin.php
            Core.php
            Form.php

Nasze sub-wtyczki mają tę samą strukturę z jednym wyjątkiem. Wchodzimy o poziom głębiej do folderu dostawcy, aby rozwiązać konflikty nazw podczas zdarzenia automatycznego ładowania. Nazywamy też klasę boostrap wtyczek E.g. Faq.phppriorytetem 10wewnątrz plugins_loadedhaka.

webeo-faq/ (uses/extends webeo-core)
    css/
    images/
    js/
    languages/
    lib/
        Webeo/
            Faq/
                Faq.php
                /** all plugin relevant class files **/
    views/
    readme.txt
    uninstall.php
    webeo-faq.php

Prawdopodobnie zmienię nazwę libfolderu vendorsi przeniosę wszystkie foldery publiczne (css, obrazy, js, języki) do folderu o nazwie publicw następnym wydaniu.

rofflox
źródło
5

Jak wielu tutaj już odpowiedziało To naprawdę zależy od tego, co powinna zrobić wtyczka, ale oto moja podstawowa struktura:

my-plugin/
    admin/
        holds all back-end administrative files
        js/
            holds all back-end JavaScript files
        css/                    
            holds all back-end CSS files
        images/
            holds all back-end images
        admin_file_1.php        back-end functionality file
        admin_file_2.php        another back-end functionality file 
    js/
        holds all front end JavaScript files
    css/
        holds all fronted CSS files
    inc/
        holds all helper classes
    lang/                   
        holds all translation files
    images/
        holds all fronted images
    my-plugin.php               main plugin file with plugin meta, mostly includes,action and filter hooks
    readme.txt                  
    changelog.txt
    license.txt
Bainternet
źródło
4

Popieram następujący układ wtyczek, jednak zwykle zmienia się on w zależności od wymagań wtyczek.

wp-content/
    plugins/
        my-plugin/
            inc/
                Specific files for only this plugin
                admin/ 
                    Files for dealing with administrative tasks
            lib/
                Library/helper classes go here
            css/
                CSS files for the plugin
            js/
                JS files
            images/
                Images for my plugin
            lang/
                Translation files
        plugin.php 
            This is the main file that calls/includes other files 
        README 
            I normally put the license details in here in addition to helpful information 

Muszę jeszcze stworzyć wtyczkę WordPress wymagającą architektury w stylu MVC, ale gdybym to zrobił, ułożyłbym ją w osobnym katalogu MVC, który sam zawiera widoki / kontrolery / modele.

tajemnica
źródło
4

Moja logika, im większa wtyczka, tym więcej struktury używam.
W przypadku dużych wtyczek zwykle używam MVC.
Używam tego jako punktu wyjścia i pomijam to, co nie jest potrzebne.

controller/
    frontend.php
    wp-admin.php
    widget1.php
    widget2.php
model/
    standard-wp-tables.php // if needed split it up
    custom-tabel1.php
    custom-tabel2.php
view/
    helper.php
    frontend/
        files...php
    wp-admin/
        files...php
    widget1/
        file...php
    widget2/
        file...php
css/
js/
image/
library/  //php only, mostly for Zend Framework, again if needed
constants.php //tend to use it often
plugin.php //init file
install-unistall.php  //only on big plugins
janw
źródło
3

Wszystkie moje wtyczki mają tę strukturę, która wydaje się być bardzo podobna do tego, co robi większość innych programistów:

plugin-folder/
    admin/
        css/
            images/
        js/
    core/
    css/
        images/
    js/
    languages/
    library/
    templates/
    plugin-folder.php
    readme.txt
    changelog.txt
    license.txt

plugin-folder.php to zazwyczaj klasa, która ładuje wszystkie wymagane pliki z folderu core /. Najczęściej na haku init lub plugins_loaded.

Kiedyś też prefiksowałem wszystkie moje pliki, ale jak zauważyłem @kaiser powyżej, jest to naprawdę zbędne i ostatnio postanowiłem usunąć go z wszelkich przyszłych wtyczek.

Biblioteka / folder zawiera wszystkie zewnętrzne biblioteki pomocnicze, od których wtyczka może zależeć.

W zależności od wtyczki w katalogu głównym wtyczki może znajdować się również plik uninstall.php. Jednak przez większość czasu jest to obsługiwane przez register_uninstall_hook ().

Oczywiście niektóre wtyczki mogą nie wymagać plików administratora, szablonów itp., Ale powyższa struktura działa dla mnie. W końcu musisz po prostu znaleźć strukturę, która działa dla ciebie, a następnie trzymać się jej.

Mam również wtyczkę startową, opartą na powyższej strukturze, której używam jako punktu wyjścia dla wszystkich moich wtyczek. Wszystko, co muszę wtedy zrobić, to wyszukać / zamienić prefiksy funkcji / klasy i ruszyć. Kiedy wciąż prefiksowałem moje pliki, to był dodatkowy krok, który musiałem zrobić (i dość denerwujący), ale teraz muszę tylko zmienić nazwę folderu wtyczek i głównego pliku wtyczek.

shabushabu
źródło
0

Mniej powszechnym podejściem do struktury plików i katalogów wtyczki jest podejście typu pliku. Warto tutaj wspomnieć o kompletności:

plugin-name/
    js/
        sparkle.js
        shake.js
    css/
        style.css
    scss/
        header.scss
        footer.scss
    php/
        class.php
        functions.php
    plugin-name.php
    uninstall.php
    readme.txt

Każdy katalog zawiera tylko pliki tego typu. Warto zauważyć, że takie podejście jest niewystarczające, gdy masz wiele typów plików, .png .gif .jpgktóre mogą być logicznie przechowywane w jednym katalogu, images/na przykład.

henrywright
źródło