Django – dodawanie obsługi nowych komend przez manage.py

Czasami potrzebujemy wykonać jakieś proste, powtarzalne czynności, które można łatwo zautomatyzować. Django posiada mechanizm, który umożliwia dodawanie nowych komend uruchamianych przez manage.py. Wywołanie komendy będzie miało postać:

Dodatkowo, możemy w ten sposób zaprogramować jakieś zadania uruchamiane cyklicznie poprzez crona. Dzięki temu nie musimy wywoływać adresu url tylko uruchamiamy polecenie z linii komend.

Pierwsza komenda

Najprostszym przykładem komendy będzie wypisanie wiadomości na konsolkę. Dla przykładu, niech projekt nazywa się sample a moduł blog. W katalogu sample/blog/management/commands tworzymy plik blog.py. Nazwa pliku jest nazwą komendy. Plik będzie posiadał klasę Command dziedziczącą po BaseCommand. Metoda handle będzie odpowiedzialna za obsłużenie wywołanej komendy. Przykładowy plik wygląda następująco:

Użycie self.stdout.write ułatwi późniejsze testowanie komendy które jest opisane w dalszej części artykułu

Aby sprawdzić poprawność działania komendy wywołujemy z linii komend ./manage.py blog. W wyniku na konsoli powinniśmy ujrzeć napis: Basic command.

Przekazywanie argumentów

Każda komenda może przyjmować argumenty, które będą modyfikować jej działanie. Załóżmy, że chcemy mieć kontrolę nad tym czy zostanie wypisany dodatkowy tekst oraz ile razy zostanie on wypisany. Pierwszym krokiem będzie dodanie parametru mówiącego o tym czy wyświetlić dodatkowy tekst. Do klasy należy dodać metodę add_arguments, która definiuje jakie argumenty będzie przyjmować komenda. Dla przykładowego argumentu powinna ona wyglądać następująco:

Pierwszy argument definiuje skróconą wersję parametru, kolejny długą. Możemy więc dodać parametr na dwa sposoby:

Kolejny parametr definiuje jaka akcja zostanie wykonana jeśli ten parametr się pojawi. Domyślnie wartość jest po prostu zapisywana w pamięci, jednak w tym przypadku chcielibyśmy otrzymać wartość True jeśli parametr się pojawi oraz False jeśli go nie ma. Akcja store_true powoduje zapisanie True jeśli parametr się pojawi (analogicznie istnieje akcja store_false) a wartość domyślna (default=False) powoduje zapisanie False do parametru jeśli go nie ma. Parametr dest definiuje nazwę opcji, pod którą będzie zapisana wartość. Ostatni parametr, help definiuje opis parametru.

Po dodaniu argumentu komendy możemy przejść do użycia go w metodzie handle. Należy zmodyfikować metodę do następującej postaci:

Dodane zostały linie 4 i 5 w których testujemy opcję show. W przypadku gdy show jest prawdą (pojawił się parametr -d lub –display) wyświetlany jest tekst.

Mając cały kod gotowy możemy uruchomić komendę i sprawdzić czy działa poprawnie.

Kolejnym krokiem będzie dodanie opcji pozwalającej zdefiniować ile razy ma zostać wyświetlona linijka tekstu. Do metody add_arguments należy dodać następujący kod:

Parametry są analogiczne jak w poprzednim przykładzie, z tą różnicą, że zostawiamy domyślną akcję, oraz definiujemy typ parametru na liczbę całkowitą (type=int).

Metodę handle modyfikujemy poprzez dodanie pętli:

Wykonanie polecenia:

Spowoduje wyświetlenie tekstu:

Tekst pomocy

W przypadku gdy uruchomimy skrypt manage.py bez argumentów, wyświetlona zostanie lista dostępnych akcji. Dodana przez nas akcja również będzie uwzględniona na wydruku. Uruchomienie manage.py help blog wyświetli listę argumentów wraz z opisem. Na liście pojawią się wszystkie argumenty przyjmowane przez Django, takie jak settings, version, oraz zdefiniowane przez nas wraz z opisem podanym w parametrze help. Przykładowy wydruk z terminala:

Testowanie komendy

Do stworzonej komendy powinniśmy dodać testy aby upewnić się, że działa ona prawidłowo. Zacznijmy od podstawowego testu komendy bez parametrów. Klasa testowa będzie wyglądać następująco:

Uruchomienie testu powinno pokazać, że komenda działa prawidłowo. Możemy dodać jeszcze kilka testów sprawdzających zachowanie komendy z parametrami:

Podsumowanie

Mechanizm komend pozwala zautomatyzować powtarzalne czynności. Czas poświęcony na implementację mechanizmu komend, pozwala zaoszcędzić dużo czasu przy każdym późniejszym uruchomieniu komendy. Więcej na temat dodawania własnych komend można przeczytać w dokumentacji Django pod adresem: https://docs.djangoproject.com/en/1.9/howto/custom-management-commands/. Dokumentacja parametrów parsowania argumentów znajduje się pod adresem: https://docs.python.org/3/library/optparse.html#module-optparse

Pełny kod klasy obsługującej komendę

Leave a Reply

Your email address will not be published. Required fields are marked *