phyllisstein / alp

A Python module for Alfred v2 workflows
174 stars 11 forks source link

alp: A Python Module for Alfred Workflows

Formerly PyAl, alp has been trimmed and slimmed to make building Alfred v2 workflows even easier. Not much was lost in the transition---and indeed, some neat things were gained---and so making the transition from PyAl to alp should be relatively easy. All in all, the module is intended to result in fewer lines of repeated code and easy accessibility for newcomers to workflow construction in Alfred and with Python.

alp's primary features include:

However, you can pick and choose from among these by deleting any of the files in the module (except for core.py and the folder core_dependencies); if something is missing, alp will silently ignore it.

To get started, simply download or clone this repository and copy the alp folder into your workflow directory, then import alp. A list of everything alp can do, with appropriate documentation, is below.

Core Functions

These are intended to make some basic rote tasks easier and faster to code. alp defines the following functions:

Feedback System

alp uses a robust and complete implementation of Alfred's feedback system, generating and outputting the required XML for the attributes you specify. This breaks down into a class called Item and a function called feedback.

Fuzzy Search

Github user jlegewie has contributed a stellar fuzzy-searching method to alp. Given a query, a list of strings, dictionaries, tuples, or other lists, and a key function, it returns a ranked list of matching objects. To use it, first get your data into an appropriate list, then call alp.fuzzy_search() with the following parameters: alp.fuzzy_search(query, elements, key, rank, seq). jlegewie has provided the following example:

elements = [{'key': u'ZB7K535R', 'author': u'Reskin 2003', 'title': u'Including Mechanisms in Our Models of Ascriptive Inequality: 2002 Presidential Address'}, {'key': u'DBTD3HQS', 'author': u'Igor & Ronald 2008', 'title': u'Die Zunahme der Lohnungleichheit in der Bundesrepublik. Aktuelle Befunde f\xfcr den Zeitraum von 1998 bis 2005'}, {'key': u'BKTCNEGP', 'author': u'Kirk & Sampson 2013', 'title': u'Juvenile Arrest and Collateral Educational Damage in the Transition to Adulthood'}, {'key': u'9AN4SPKT', 'author': u'Turner 2003', 'title': u'The Structure of Sociological Theory'}, {'key': u'9M92EV6S', 'author': u'Bruhns et al. 1999', 'title': u'Die heimliche Revolution'}, {'key': u'25QBTM5P', 'author': u'Durkheim 1997', 'title': u'The Division of Labor in Society'}, {'key': u'MQ3BHTBJ', 'author': u'Marx 1978', 'title': u'Alienation and Social Class'}, {'key': u'7G4BRU45', 'author': u'Marx 1978', 'title': u'The German Ideology: Part I'}, {'key': u'9ANAZXQB', 'author': u'Llorente 2006', 'title': u'Analytical Marxism and the Division of Labor'}]
query = 'marx'
results = fuzzy_search(query, elements, key=lambda x: '%s - %s' % (x['author'], x['title']))

As you can see, the key access function should extract a searchable string from your data set, and the elements argument should be a list that eventually contains strings. The neat thing about this being a fuzzy search is that mrx would also match many of the Marx elements, and if a mistyped or fragmented query is closer to one good candidate (say "Max") than another (like "Marx"), results will be ranked accordingly.

Notifications

The fact that Alfred's internal workflow workings only make it possible for a workflow to output one string can be frustrating. Enter alp's Notification class. It's used a little something like this:

>>> import alp
>>> n = alp.Notification()
>>> n.notify("Title", "Subtitle", "Informative Text")

The title, subtitle, and informative text should be strings. This will pop up a notification that bears Python's logo but is otherwise indistinguishable from any of Alfred's notices. Currently, this is restricted to sending messages to the user---there's not yet a way to know whether the user clicks the notification, for example---but the problem is being worked on.

HTTP Requests

The modules Requests, requests_cache, and BeautifulSoup are bundled with alp by default. (N.B.: Because they are relatively large, they can be removed from the module by deleting the folder request.) They vastly simplify making and interpreting HTTP requests. The alp Request class provides a quick-and-dirty interface to them, setting up a requests cache, making a request, and passing the returned data to BeautifulSoup for parsing.

Settings Interface

The alp Settings object loads and saves settings in your workflow's designated storage path. On initialization, it looks for a settings file, creating it if it fails to find one and loading the predefined settings if it succeeds. It also defines the following methods:

Keychain Interface

If your workflow needs to store a user's sensitive data, particularly a username--password pair, the safest way to do so is with the Mac OS X Keychain. The Keychain is normally an utter pain in the behind, but alp makes working with it a breeze. Simply initialize alp.Keychain(service) with a service name---for example, your workflow's bundle ID---and then use the following methods:

E-mail

By request, alp can also send simple plaintext messages over e-mail. Initialize the alp.Mail() object with the following parameters: alp.Mail(host, port, SSL, user, pw, sender, to, mimetype, subject, body). SSL should be set to True or False. mimetype should be a string specifying the MIME subtype under "text/" and defaults to "plain" if None is passed. to can be either a single e-mail address or a list of e-mail addresses. Use Mail.notify() to send your message(s):

>>> e = alp.Mail(host, port, SSL, user, pw, sender, to, mimetype, subject, body)
>>> e.notify()

See the list of exceptions that can be raised in the docs.

Help and Support

The Alfred v2 forums are a good place to look for answers, but you can also reach this package's maintenance man, Daniel, at d atsign daniel dot sh or on Twitter at @phyllisstein.

License

alp and all of its components are free to use and distribute however you see fit. Go hog-wild. The author appreciates getting some credit for his work, and the authors of Requests, requests_cache, BeautifulSoup, six, and biplist probably do as well, so it'd be neat if you'd mention us all somewhere. Additionally, donations are gratefully accepted over at my Alfred website.