19. Разни библиотечки

19. Разни библиотечки

19. Разни библиотечки

1 юни 2015

Полезни щуротии в стандартната библиотека,

... които може би сте виждали.

datetime

datetime е модул, който ви дава основна функционалност за дати

... ама това трябва да сте го виждали вече.

os

os - функционалност от операционната система

os.path - функционалност за работа с пътища във файловата система

... ама и това сте го виждали по време на семестъра

json

Нещо, което може би не сме ви показали

json е модул, който може да сериализира прости Python обекти.

И още...

argparse

модул за обработка на command line параметри

import argparse

parser = argparse.ArgumentParser(description='Process some integers.')
parser.add_argument('integers', metavar='N', type=int, nargs='+',
                    help='an integer for the accumulator')
parser.add_argument('--sum', dest='accumulate', action='store_const',
                    const=sum, default=max,
                    help='sum the integers (default: find the max)')

args = parser.parse_args()
print(args.accumulate(args.integers))

Архивиране и компресия

Сега към малко по-забавни неща,

... които няма да намерите в стандартната библиотека

requests - HTTP for humans

Преди това да обясним какъв му е проблемът на urllib

Да речем, че правим някакви заявки към някакво API и си казваме какво ни връща

Имайки urllib, в стандартната библиотека ще направим ей така:

import urllib.request
import urllib.error
import urllib.parse

gh_url = 'https://api.github.com'

req = urllib.request.Request(gh_url)

password_manager = urllib.request.HTTPPasswordMgrWithDefaultRealm()
password_manager.add_password(None, gh_url, 'user', 'pass')

auth_manager = urllib.request.HTTPBasicAuthHandler(password_manager)
opener = urllib.request.build_opener(auth_manager)

urllib.request.install_opener(opener)

handler = urllib.request.urlopen(req)

print(handler.getcode())
print(handler.getheader('content-type'))

Не трябваше ли нещата в Python да са кратки и лесни?

В питонски стил

import requests

r = requests.get('https://api.github.com', auth=('user', 'pass'))

print(r.status_code)
print(r.headers['content-type'])

Идва си с цялата каруца

> pip install requests

Celery

Celery е дистрибутирана опашка за задачи

Опашките за задачи се използват за разпределяне на работа между нишки и машини

Задачите им са да:

Сelery e използва външна система за подаване на съобщения и я използва за да координира "клиенти" и "worker"-и.

За да се свърши някаква работа "клиент" пуска задача в опашката и системата за подаване на съобщения доставя задачата до worker. Една Celery система обикновено се състои от много много worker-и и системи за подаване на съобщения което прави скалирането на приложението много лесно, а и го прави много надеждно

Какво ви трябва

from celery import Celery

# Първият аргумент трябва да е името на сегашния модул
# Вторият аргумент е адреса на диспечера на съобщения
celery = Celery('hello', broker='amqp://guest@localhost//')

@celery.task
def answer_to_the_question_of_life_universe_and_everything():
    return 42

Performance

Code quality

urwid

pip install urwid

urwid е библиотека за конзолни GUI-та

Съдържа всичко което ви трябва за да направите удобно изцяло конзолно плиожение:

urwid - форматиране на текст и input

import urwid
from urwid import Text, AttrMap, Filler, MainLoop

palette = [
    ('banner', 'black', 'light gray'),
    ('streak', 'black', 'dark red'),
    ('bg', 'black', 'dark blue')]

text_widget = Text(("banner", "Hello World!"), align="center")
map1 = AttrMap(text_widget, "streak")
fill_widget = Filler(map1, valign="middle")
map2 = AttrMap(fill_widget, "bg")

def show_or_exit(key):
    if key in('q', 'Q'):
        raise urwid.ExitMainLoop()
    else:
        text_widget.set_text(repr(key))

loop = MainLoop(map2, palette, unhandled_input=show_or_exit)

if __name__ == "__main__":
    loop.run()

urwid менюта

import urwid

choices = 'Chapman Cleese Gilliam Idle Jones Palin'.split()

def menu(title, choices):
    body = [urwid.Text(title), urwid.Divider()]
    for c in choices:
        button = urwid.Button(c)
        urwid.connect_signal(button, 'click', item_chosen, c)
        body.append(urwid.AttrMap(button, None, focus_map='reversed'))
    return urwid.ListBox(urwid.SimpleFocusListWalker(body))

def item_chosen(button, choice):
    response = urwid.Text(['You chose ', choice, '\n'])
    done = urwid.Button('Ok')
    urwid.connect_signal(done, 'click', exit_program)
    main.original_widget = urwid.Filler(urwid.Pile([response,
        urwid.AttrMap(done, None, focus_map='reversed')]))

def exit_program(button):
    raise urwid.ExitMainLoop()

main = urwid.Padding(menu('Pythons', choices), left=2, right=2)
top = urwid.Overlay(main, urwid.SolidFill('\N{MEDIUM SHADE}'),
    align='center', width=('relative', 60),
    valign='middle', height=('relative', 60),
    min_width=20, min_height=9)

urwid.MainLoop(top, palette=[('reversed', 'standout', '')]).run()

Coverage

pip install coverage

Проверява през каква част от кода ви се изпълнява в дадени случаи

coverage run баба.py
coverage report

Structured logging

ipython и ipdb

pip install ipython ipdb

По-удобен терминал и дебъгър

import ipd; ipdb.set_trace()

Parsley

Покъртително добра библиотека за парсване

re.compile("a(b|c)d+e")
parsley.makeGrammar("foo = 'a' ('b' | 'c') 'd'+ 'e'", {})

parsley.makeGrammar("""
foo = 'a':one baz:two 'd'+ 'e' -> (one, two)
baz = 'b' | 'c'
""", {})

Бира!

На 2015-06-10 в Борисовата градина ще пием бира

Въпроси?