Add some comments and members-visibility changes for MovieLister example

This commit is contained in:
Roman Mogilatov 2016-03-20 17:43:21 +02:00
parent 22691553fb
commit 064a1653fd
9 changed files with 109 additions and 34 deletions

View File

@ -5,3 +5,13 @@ Example implementation of dependency injection in Python from Martin Fowler's
article about dependency injection and inversion of control: article about dependency injection and inversion of control:
http://www.martinfowler.com/articles/injection.html http://www.martinfowler.com/articles/injection.html
Instructions for running:
.. code-block:: bash
python _create_db.py
python app_csv.py
python app_db.py

View File

@ -38,7 +38,7 @@ def main(movie_lister):
persons and then prints all movies that were released in 2015. persons and then prints all movies that were released in 2015.
:param movie_lister: Movie lister instance :param movie_lister: Movie lister instance
:type movie_lister: :py:class:`movies.listers.MovieLister` :type movie_lister: movies.listers.MovieLister
""" """
print movie_lister.movies_directed_by('Francis Lawrence') print movie_lister.movies_directed_by('Francis Lawrence')
print movie_lister.movies_directed_by('Patricia Riggen') print movie_lister.movies_directed_by('Patricia Riggen')

View File

@ -47,7 +47,7 @@ def main(movie_lister):
persons and then prints all movies that were released in 2015. persons and then prints all movies that were released in 2015.
:param movie_lister: Movie lister instance :param movie_lister: Movie lister instance
:type movie_lister: :py:class:`movies.listers.MovieLister` :type movie_lister: movies.listers.MovieLister
""" """
print movie_lister.movies_directed_by('Francis Lawrence') print movie_lister.movies_directed_by('Francis Lawrence')
print movie_lister.movies_directed_by('Patricia Riggen') print movie_lister.movies_directed_by('Patricia Riggen')

View File

@ -1 +0,0 @@
movies.*

View File

@ -0,0 +1,3 @@
The Hunger Games: Mockingjay - Part 2,2015,Francis Lawrence
The 33,2015,Patricia Riggen
Star Wars: Episode VII - The Force Awakens,2015,JJ Abrams
1 The Hunger Games: Mockingjay - Part 2 2015 Francis Lawrence
2 The 33 2015 Patricia Riggen
3 Star Wars: Episode VII - The Force Awakens 2015 JJ Abrams

View File

@ -1,4 +1,11 @@
"""Movies package.""" """Movies package.
Top-level package of movies library. This package contains catalog of movies
module components - ``MoviesModule``. It is recommended to use movies library
functionality by fetching required instances from ``MoviesModule`` providers.
Each of ``MoviesModule`` providers could be overridden.
"""
from . import finders from . import finders
from . import listers from . import listers

View File

@ -1,59 +1,87 @@
"""Movie finders.""" """Movie finders module.
This module contains all finder implementations.
"""
import csv import csv
class MovieFinder(object): class MovieFinder(object):
"""Movie finder.""" """Movie finder component.
Movie finder component is responsible for fetching movies data from
different storages.
"""
def __init__(self, movie_model): def __init__(self, movie_model):
"""Initializer.""" """Initializer.
self.movie_model = movie_model
:param movie_model: Movie model's factory
:type movie_model: (object) -> movies.models.Movie
"""
self._movie_model = movie_model
def find_all(self): def find_all(self):
"""Return all found movies. """Return all found movies.
:rtype: list[:py:class:`Movie`] :rtype: list[movies.models.Movie]
:return: List of movie instances. :return: List of movie instances.
""" """
raise NotImplementedError() raise NotImplementedError()
class CsvMovieFinder(MovieFinder): class CsvMovieFinder(MovieFinder):
"""Movie finder that fetches movies info from csv file.""" """Movie finder that fetches movies data from csv file."""
def __init__(self, movie_model, csv_file, delimeter): def __init__(self, movie_model, csv_file, delimeter):
"""Initializer.""" """Initializer.
self.csv_file = csv_file
self.delimeter = delimeter :param movie_model: Movie model's factory
:type movie_model: (object) -> movies.models.Movie
:param csv_file: Path to csv file with movies data
:type csv_file: str
:param delimeter: Csv file's delimeter
:type delimeter: str
"""
self._csv_file = csv_file
self._delimeter = delimeter
super(CsvMovieFinder, self).__init__(movie_model) super(CsvMovieFinder, self).__init__(movie_model)
def find_all(self): def find_all(self):
"""Return all found movies. """Return all found movies.
:rtype: list[:py:class:`Movie`] :rtype: list[movies.models.Movie]
:return: List of movie instances. :return: List of movie instances.
""" """
with open(self.csv_file) as csv_file: with open(self._csv_file) as csv_file:
reader = csv.reader(csv_file, delimiter=self.delimeter) reader = csv.reader(csv_file, delimiter=self._delimeter)
return [self.movie_model(*row) for row in reader] return [self._movie_model(*row) for row in reader]
class SqliteMovieFinder(MovieFinder): class SqliteMovieFinder(MovieFinder):
"""Movie finder that fetches movies info from sqlite database.""" """Movie finder that fetches movies data from sqlite database."""
def __init__(self, movie_model, database): def __init__(self, movie_model, database):
"""Initializer.""" """Initializer.
self.database = database
:param movie_model: Movie model's factory
:type movie_model: (object) -> movies.models.Movie
:param database: Connection to sqlite database with movies data
:type database: sqlite3.Connection
"""
self._database = database
super(SqliteMovieFinder, self).__init__(movie_model) super(SqliteMovieFinder, self).__init__(movie_model)
def find_all(self): def find_all(self):
"""Return all found movies. """Return all found movies.
:rtype: list[:py:class:`Movie`] :rtype: list[movies.models.Movie]
:return: List of movie instances. :return: List of movie instances.
""" """
with self.database: with self._database:
rows = self.database.execute('SELECT name, year, director ' rows = self._database.execute('SELECT name, year, director '
'FROM movies') 'FROM movies')
return [self.movie_model(*row) for row in rows] return [self._movie_model(*row) for row in rows]

View File

@ -1,11 +1,22 @@
"""Movie listers.""" """Movie listers module.
This module contains all lister implementations.
"""
class MovieLister(object): class MovieLister(object):
"""Movie lister.""" """Movie lister component.
Movie lister component provides several methods for filtering movies by
specific criteria.
"""
def __init__(self, movie_finder): def __init__(self, movie_finder):
"""Initializer.""" """Initializer.
:param movie_finder: Movie finder instance
:type movie_finder: movies.finders.MovieFinder
"""
self.movie_finder = movie_finder self.movie_finder = movie_finder
def movies_directed_by(self, director): def movies_directed_by(self, director):
@ -14,7 +25,7 @@ class MovieLister(object):
:param director: Director's name :param director: Director's name
:type director: str :type director: str
:rtype: list[:py:class:`Movie`] :rtype: list[movies.models.Movie]
:return: List of movie instances. :return: List of movie instances.
""" """
return [movie for movie in self.movie_finder.find_all() return [movie for movie in self.movie_finder.find_all()
@ -26,7 +37,7 @@ class MovieLister(object):
:param year: Release year :param year: Release year
:type year: int :type year: int
:rtype: list[:py:class:`Movie`] :rtype: list[movies.models.Movie]
:return: List of movie instances. :return: List of movie instances.
""" """
return [movie for movie in self.movie_finder.find_all() return [movie for movie in self.movie_finder.find_all()

View File

@ -1,17 +1,34 @@
"""Movie models.""" """Movie models module.
This module contains all model implementations.
"""
class Movie(object): class Movie(object):
"""Movie model.""" """Base movie model."""
def __init__(self, name, year, director): def __init__(self, name, year, director):
"""Initializer.""" """Initializer.
:param name: Movie's name
:type name: str
:param year: Year, when movie was released
:type year: int
:param director: Name of person, that directed the movie
:type director: str
"""
self.name = str(name) self.name = str(name)
self.year = int(year) self.year = int(year)
self.director = str(director) self.director = str(director)
def __repr__(self): def __repr__(self):
"""Return string representation of movie instance.""" """Return string representation of movie instance.
:rtype: str
:return: Movie's string representation.
"""
return '{0}(name={1}, year={2}, director={3})'.format( return '{0}(name={1}, year={2}, director={3})'.format(
self.__class__.__name__, self.__class__.__name__,
repr(self.name), repr(self.name),