Skip to content
This repository
Fetching contributors…

Octocat-spinner-32-eaf2f5

Cannot retrieve contributors at this time

file 133 lines (117 sloc) 5.225 kb
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132
#!/usr/bin/env python
""" film.py: a simple tool to manage your movies review
Simon Rozet, http://atonie.org/

@@ :
- manage directors and writers
- manage actors
- handle non IMDB uri
- markdown support in comment

Requires download and import of Python imdb library from
http://imdbpy.sourceforge.net/ - (warning: installation
will trigger automatic installation of several other packages)

--
Usage:
film.py whoami "John Doe <john@doe.org>"
Initialize the store and set your name and email.
film.py whoami
Tell you who you are
film.py http://www.imdb.com/title/tt0105236/
Review the movie "Reservoir Dogs"
"""
import datetime, os, sys, re, time, imdb
from rdflib import BNode, ConjunctiveGraph, URIRef, Literal, Namespace, RDF

#storefn = os.path.expanduser('~/movies.n3')
storefn = '/home/simon/codes/film.dev/movies.n3'
storeuri = 'file://'+storefn
title = 'Movies viewed by %s'

r_who = re.compile('^(.*?) <([a-z0-9_-]+(\.[a-z0-9_-]+)*@[a-z0-9_-]+(\.[a-z0-9_-]+)+)>$')

DC = Namespace('http://purl.org/dc/elements/1.1/')
FOAF = Namespace('http://xmlns.com/foaf/0.1/')
IMDB = Namespace('http://www.csd.abdn.ac.uk/~ggrimnes/dev/imdb/IMDB#')
REV = Namespace('http://purl.org/stuff/rev#')

class Store:
    def __init__(self):
        self.graph = ConjunctiveGraph()
        if os.path.exists(storefn):
            self.graph.load(storeuri, format='n3')
        self.graph.bind('dc', 'http://purl.org/dc/elements/1.1/')
        self.graph.bind('foaf', 'http://xmlns.com/foaf/0.1/')
        self.graph.bind('imdb', 'http://www.csd.abdn.ac.uk/~ggrimnes/dev/imdb/IMDB#')
        self.graph.bind('rev', 'http://purl.org/stuff/rev#')
    
    def save(self):
        self.graph.serialize(storeuri, format='n3')
    
    def who(self, who=None):
        if who is not None:
            name, email = (r_who.match(who).group(1), r_who.match(who).group(2))
            self.graph.add((URIRef(storeuri), DC['title'], Literal(title % name)))
            self.graph.add((URIRef(storeuri+'#author'), RDF.type, FOAF['Person']))
            self.graph.add((URIRef(storeuri+'#author'), FOAF['name'], Literal(name)))
            self.graph.add((URIRef(storeuri+'#author'), FOAF['mbox'], Literal(email)))
            self.save()
        else:
            return self.graph.objects(URIRef(storeuri+'#author'), FOAF['name'])
        
    def new_movie(self, movie):
        movieuri = URIRef('http://www.imdb.com/title/tt%s/' % movie.movieID)
        self.graph.add((movieuri, RDF.type, IMDB['Movie']))
        self.graph.add((movieuri, DC['title'], Literal(movie['title'])))
        self.graph.add((movieuri, IMDB['year'], Literal(int(movie['year']))))
        self.save()
    
    def new_review(self, movie, date, rating, comment=None):
        review = BNode() # @@ humanize the identifier (something like #rev-$date)
        movieuri = URIRef('http://www.imdb.com/title/tt%s/' % movie.movieID)
        self.graph.add((movieuri, REV['hasReview'], URIRef('%s#%s' % (storeuri, review))))
        self.graph.add((review, RDF.type, REV['Review']))
        self.graph.add((review, DC['date'], Literal(date)))
        self.graph.add((review, REV['maxRating'], Literal(5)))
        self.graph.add((review, REV['minRating'], Literal(0)))
        self.graph.add((review, REV['reviewer'], URIRef(storeuri+'#author')))
        self.graph.add((review, REV['rating'], Literal(rating)))
        if comment is not None:
            self.graph.add((review, REV['text'], Literal(comment)))
        self.save()

    def movie_is_in(self, uri):
        return (URIRef(uri), RDF.type, IMDB['Movie']) in self.graph
        
def help():
    print(__doc__.split('--')[1])

def main(argv=None):
    if not argv:
        argv = sys.argv
    s = Store()
    if argv[1] in ('help', '--help', 'h', '-h'):
        help()
    elif argv[1] == 'whoami':
        if os.path.exists(storefn):
            print(list(s.who())[0])
        else:
            s.who(argv[2])
    elif argv[1].startswith('http://www.imdb.com/title/tt'):
        if s.movie_is_in(argv[1]):
            raise
        else:
            i = imdb.IMDb()
            movie = i.get_movie(argv[1][len('http://www.imdb.com/title/tt'):-1])
            print('%s (%s)' % (movie['title'].encode('utf-8'), movie['year']))
            for director in movie['director']:
                print('directed by: %s' % director['name'].encode('utf-8'))
            for writer in movie['writer']:
                print('written by: %s' % writer['name'].encode('utf-8'))
            s.new_movie(movie)
            rating = None
            while not rating or (rating > 5 or rating <= 0):
                try:
                    rating = int(raw_input('Rating (on five): '))
                except ValueError:
                    rating = None
            date = None
            while not date:
                try:
                    i = raw_input('Review date (YYYY-MM-DD): ')
                    date = datetime.datetime(*time.strptime(i, '%Y-%m-%d')[:6])
                except:
                    date = None
            comment = raw_input('Comment: ')
            s.new_review(movie, date, rating, comment)
    else:
        help()

if __name__ == '__main__':
    main()
Something went wrong with that request. Please try again.