[SQL] Wordpress - statystyka komentarzy, najczęściej komentujący

Wpis opisuje akcję dosłownie sprzed chwili. Napisał do mnie m4tx z prośbą o napisanie zapytania SQL, które pobierało by komentarze z Wordpressa, każdemu użytkownikowi przypisując ilość napisanych przez niego komentarzy. Jestem zdziwiony, gdyż udało mi się to zrobić za pierwszym razem (potem musiałem jedynie dodać DISTINCT-a, o którym zapomniałem).

Jak pewnie wie, każdy kto programuje, w tej dziedzinie mało co wychodzi za pierwszym razem :D Tak czy siak postanowiłem podzielić się swoim dziełem:

SELECT DISTINCT comment_author AS author, (SELECT COUNT(comment_ID) FROM wp_comments WHERE comment_author = author) AS amount FROM wp_comments WHERE comment_approved = 1 ORDER BY amount DESC

Takie oto zagnieżdżone zapytanie doskonale rozwiązuje nasz problem :) Poniżej demonstruję wynik działania zapytania na danych z mojego bloga (to nie jest pełny wynik rzecz jasna :) nie ma sensu wkładać do screena całych danych)

Wynik zapytania

[SQL] Wordpress - pobieranie najdłuższych wpisów

Witam, dziś bez zbędnego gadania, będzie bardzo krótko.

Przedstawiam to proste zapytanie SQL, które pobierze tytuły wpisów i ilość słów w nich zawartych oraz posortuje po ich ilości.

SELECT
  post_title, 
  (LENGTH(post_content) - LENGTH(REPLACE(post_content, ' ', ''))) AS words
FROM 
  wp_posts
WHERE
  post_status = 'publish' AND post_type = 'post'
ORDER BY
  words DESC

Tak, to tyle. Na koniec screen z fragmentem wyniku działania na przykładzie mojego bloga:

Wynik zapytania

Amen, dobranoc państwu :)

Backupowanie baz danych MySQL z poziomu PHP

Na samym początku zaznaczam, że pierwowzór skryptu przedstawionego poniżej nie jest mojego autorstwa! Skrypt znalazłem tutaj (skrypt na samym dole artykułu). Dokonałem w nim kilku przeróbek i w tym miejscu zostawiam dla potomnych - może się komuś przyda!

{{{ more }}}

Wprowadzone zmiany:

  • Umieszczenie daty wykonania backupu na górze zrzutu bazy
  • Lekkie ogarnięcie kodu PHP. Wiem, że wiele mu brakuje - jak komuś chce się bawić, to proszę bardzo - dla mnie aktualnie liczy się fakt, że skrypt działa
  • Zmiana formatu nazwy pliku (na taki który mi bardziej odpowiada :P). Jakby się komuś nie podobał, to zmiana jest przecież banalna.
  • Możliwość ustawienia katalogu w którym będą lądowały backupy
  • Kilka zmian czysto estetycznych
<?php
header('Content-type: text/html; charset=utf8');

try{
    // KONFIGURACJA - START
    $dbName = 'revival'; // Nazwa bazy danych do zbackupowania
    $dbHost = 'localhost'; // Nazwa serwera baz danych
    $dbUser = 'root'; // Nazwa użytkownika
    $dbPass = ''; // Hasło

    $backupsDir = 'backups'; // Katalog do którego będą zapisywane backupy. Bez końcowego ukośnika!
    // KONFIGURACJA - STOP
    // Dalej lepiej nie ruszać!

    // Stworzenie nowego obiektu klasy PDO
    $pdo = new PDO("mysql:host=$dbHost;dbname=$dbName", $dbUser, $dbPass, array(PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES utf8"));
    $pdo -> setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
    $sqlResult = $pdo -> query("SHOW tables FROM $dbName");

    // Stworzenie nagłówka informacyjnego
    $sqlData = "-- Data wykonania kopii: ".date('d.m.Y')." r. o godzinie ".date('H:i')."
    -- Baza: $dbName
    SET SQL_MODE=\"NO_AUTO_VALUE_ON_ZERO\";";

    while ($queryTable = $sqlResult -> fetch(PDO::FETCH_ASSOC)){
        $sqlTable = $queryTable['Tables_in_'.$dbName];
        $sqlResultB = $pdo -> query("SHOW CREATE TABLE $sqlTable");
        $queryTableInfo = $sqlResultB -> fetch(PDO::FETCH_ASSOC);

        // Dodanie nagłówków dla konkretnych tabel
        $sqlData .= "\n\n--
        -- Struktura dla tabeli `$sqlTable`
        --\n\n";
        $sqlData .= $queryTableInfo['Create Table'] . ";\n";
        $sqlData .= "\n\n--
        -- Wartości tabeli `$sqlTable`
        --\n\n";

        $sqlResultC = $pdo -> query("SELECT * FROM $sqlTable");

        // Stworzenie INSERT-a dla każdego rekordu
        while ($queryRecord = $sqlResultC -> fetch(PDO::FETCH_ASSOC)) {
            $sqlData .= "INSERT INTO `$sqlTable` VALUES (";
            $sqlRecord = '';
            foreach( $queryRecord as $sqlField => $sqlValue ) {
                $sqlRecord .= "'$sqlValue',";
            }
            $sqlData .= substr($sqlRecord, 0, -1);
            $sqlData .= ");\n";
        }
    }

    // Zapisujemy wynik do pliku
    file_put_contents($backupsDir.'/backup_'.$dbName.'_'.date('d_m_Y').'.sql', $sqlData);
    echo 'Backup został zapisany.';
}

catch(PDOException $e){
    echo 'Połączenie nie mogło zostać utworzone: '.$e->getMessage();
}

Skrypt umieścić u siebie na FTP i uzupełnić sekcję konfiguracyjną. Wywoływać ręcznie (poprzez wpisanie URL-a) albo przez CRON-a.

Musisz koniecznie pamiętać o zabezpieczeniu katalogu z backupami (chociażby przez plik .htaccess). Dobrze by było też zabezpieczyć sam skrypt backupujący, aby nikt nie zajechał nam bazy danych przez wywoływanie w pętli.

Mimo tego, że skrypt testowałem, to nie biorę żadnej odpowiedzialności za jakiekolwiek szkody wynikłe z jego korzystania! Boisz się to nie używaj.

Mam nadzieję, że ten skrypt pomoże Wam w tworzeniu kopii swoich baz danych i sprawi, że będzie się to działo częściej niż raz na rok :P. Bo jak wiadomo:

"Ludzie dzielą się na tych, którzy robią backupy i tych, którzy zaczną je robić".

Pozdrawiam.

PS: Jakby ktoś zdecydował się rozbudować ten skrypt np. o wysyłanie backupów na e-mail czy ich uploadowanie na zewnętrzny serwer FTP, to niech go udostępni, może innym też się przyda.

Dwa nowe skrypty w Dev Center

Żeby moje nowe Dev Center (opublikowane wczoraj) nie świeciło pustkami toteż napisałem dwa nowe skrypty, które w dniu dzisiejszym dochodzą do jego skromnych zasobów.

Postanowiłem odpicować dwie z klas, których używanych przeze mnie w IronCMS-ie. Upiekłem przy tym dwie pieczenie na jednym ogniu. Po pierwsze: zyskałem nowe skrypty do kolekcji, a po drugie uzyskałem mocno poprawione klasy do użytku w kolejnych wersjach CMS-a (a te się powoli budują…).

Nie ma sensu się rozpisywać. Po prostu prezentuję:

Klasa do obsługi MySQL oraz powiązana z nią klasa loggera zdarzeń.

Wszelkie komentarze mile widziane ;)

[PHP] Pobranie najnowszych wpisów z WordPressa

W tym wpisie przedstawię prosty skrypt pobierający ostatnie wpisy z bloga opartego na WordPressie. Skrypt powinien działać co najmniej na wszystkich WP z gałęzi 3.x

Prezentuję dwie leciutko się różniące wersje pod wyświetlanie dokładnie jednego ostatniego wpisu i wyświetlaniu określonej ilości ostatnich wpisów.

Wersja na jeden wpis

<?php
// Database config
$db['host'] = 'serwer_twojej_bazy';
$db['user'] = 'nazwa_usera';
$db['pass'] = 'haselko';
$db['name'] = 'nazwa_bazy_danych';

@mysql_connect ($db['host'], $db['user'], $db['pass']) or die ('Nie udało się połączyć z bazą danych');
@mysql_select_db ($db['name']) or die('Nie udało się wybrać bazy danych.');

// Get title of newest post
$query = mysql_query ("SELECT `post_title` FROM `wp_posts` WHERE `post_status` = 'publish' AND `post_type`='post' ORDER BY `post_date`  DESC LIMIT 1") or die ('Nie udało się pobrać najnowszego wpisu');

$row = mysql_fetch_array ($query);
$post_title = $row['post_title'];
echo $post_title;
mysql_close();

Wersja na wiele wpisów

<?php
// Database config
$db['host'] = 'serwer_twojej_bazy';
$db['user'] = 'nazwa_usera';
$db['pass'] = 'haselko';
$db['name'] = 'nazwa_bazy_danych';
// Other config
$num_posts  = '5';

@mysql_connect ($db['host'], $db['user'], $db['pass']) or die ('Nie udało się połączyć z bazą danych');
@mysql_select_db ($db['name']) or die('Nie udało się wybrać bazy danych.');

// Get titles of newests posts
$query = mysql_query ("SELECT `post_title` FROM `wp_posts` WHERE `post_status` = 'publish' AND `post_type`='post' ORDER BY `post_date`  DESC LIMIT $num_posts;") or die ('Nie udało się pobrać najnowszego wpisu');

echo '<ul>';
while ($row = mysql_fetch_array ($query)) {
   echo "t<li>";
   echo $row['post_title'];
   echo "</li>n";
}
echo '</ul>';

mysql_close();

Sercem obu tych skryptów jest jedno zapytanie czyli:

SELECT `post_title` FROM `wp_posts` WHERE `post_status` = 'publish' AND `post_type`='post' ORDER BY `post_date`  DESC LIMIT *

różnicą jest jedynie różna wartość ustawienia LIMIT. W pierwszym skrypcie wynosi ona oczywiście jeden, ponieważ pobieramy tylko jeden wpis, a więc tylko jeden rekord. W drugim zaś zależy od ustawienia odpowiedniej zmiennej $num_posts w konfiguracji skryptu.

Oba warianty skryptu różnią się też oczywiście sposobem wyświetlenia pobieranych danych. W pierwszym jest to zwyczajne wywołanie funkcji mysql_fetch_array, w drugim zaś wypadku jest ona użyta w pętli, a wpisy pokazywane są jako lista nieuporządkowana, co można dość łatwo zmodyfikować do swoich potrzeb.

Przedstawione skrypty stanowią tylko swoisty "rdzeń". Musimy oprawić je w ramy dokumentu HTML i ewentualnie możemy ustawić dla nich style CSS.

Zdaję sobie sprawę, że przedstawione skrypty dla wielu osób mogą się wydawać banalne i źle napisane (przecież nie użyłem PDO i miliona wyjątków), ale mam nadzieję, że choć dla jednej początkującej osoby ten prosty skrypt stanie się jakąś bazą do dalszego eksperymentowania z SQL i PHP.