diff --git a/pygtktalog/__init__.py b/pygtktalog/__init__.py index 55e8c54..338d6f0 100644 --- a/pygtktalog/__init__.py +++ b/pygtktalog/__init__.py @@ -5,50 +5,14 @@ Author: Roman 'gryf' Dobosz, gryf73@gmail.com Created: 2009-05-05 """ - __version__ = "3.0.0" __appname__ = "pyGTKtalog" __copyright__ = "\u00A9 Roman 'gryf' Dobosz" __summary__ = "%s is simple tool for managing file collections." % __appname__ __web__ = "http://github.com/gryf/pygtktalog" -import os -import locale -import gettext - - __all__ = ['dbcommon', 'dbobjects', 'dialogs', 'logger', 'misc'] - -GETTEXT_DOMAIN = 'pygtktalog' -# There should be message catalogs in "locale" directory placed by setup.py -# script. If there is no such directory, let's assume that message catalogs are -# placed in system wide location such as /usr/share/locale by Linux -# distribution package maintainer. -LOCALE_PATH = os.path.join(os.path.abspath(os.path.dirname(__file__)), - 'locale') - -try: - locale.setlocale(locale.LC_ALL, '') -except locale.Error: - # unknown locale string, fallback to C - locale.setlocale(locale.LC_ALL, 'C') - -# for module in gtk.glade, gettext: -# if os.path.exists(LOCALE_PATH): -# module.bindtextdomain(GETTEXT_DOMAIN, LOCALE_PATH) -# else: -# module.bindtextdomain(GETTEXT_DOMAIN) -# module.textdomain(GETTEXT_DOMAIN) - -# register the gettext function for the whole interpreter as "_" -_ = gettext.gettext - -# # wrap errors into usefull message -# def log_exception(exc_type, exc_val, traceback): -# get_logger(__name__).error(exc_val) -# -# sys.excepthook = log_exception diff --git a/pygtktalog/scan.py b/pygtktalog/scan.py index 348f28a..0f38bb2 100644 --- a/pygtktalog/scan.py +++ b/pygtktalog/scan.py @@ -179,8 +179,8 @@ class Scan(object): # self._session.merge(self._files[0]) LOG.debug("Deleting objects whitout parent: %s", str(self._session.query(File) - .filter(File.parent==None).all())) # noqa - self._session.query(File).filter(File.parent==None).delete() # noqa + .filter(File.parent.is_(None)).all())) + self._session.query(File).filter(File.parent.is_(None)).delete() self._session.commit() return self._files @@ -474,7 +474,7 @@ class Scan(object): def _set_image_path(self): """Get or calculate the images path""" image_path = (self._session.query(Config) - .filter(Config.key=="image_path")).one() # noqa + .filter(Config.key == "image_path")).one() if image_path.value == ":same_as_db:": image_path = pygtktalog.misc.calculate_image_path() else: diff --git a/pygtktalog/video.py b/pygtktalog/video.py index 97f22cb..4ab617f 100644 --- a/pygtktalog/video.py +++ b/pygtktalog/video.py @@ -6,12 +6,13 @@ Author: Roman 'gryf' Dobosz, gryf73@gmail.com Created: 2009-04-04 """ +import math import os import shutil -from tempfile import mkdtemp, mkstemp -import math +import tempfile from PIL import Image + from pygtktalog.misc import float_to_string from pygtktalog.logger import get_logger @@ -58,9 +59,9 @@ class Video(object): if 'length' in self.tags and self.tags['length'] > 0: start = self.tags.get('start', 0) length = self.tags['length'] - start - hours = length / 3600 + hours = length // 3600 seconds = length - hours * 3600 - minutes = seconds / 60 + minutes = seconds // 60 seconds -= minutes * 60 length_str = "%02d:%02d:%02d" % (hours, minutes, seconds) self.tags['duration'] = length_str @@ -100,8 +101,8 @@ class Video(object): # for really short movies no_pictures = 4 - tempdir = mkdtemp() - file_desc, image_fn = mkstemp(suffix=".jpg") + tempdir = tempfile.mkdtemp() + file_desc, image_fn = tempfile.mkstemp(suffix=".jpg") os.close(file_desc) self._make_captures(tempdir, no_pictures) self._make_montage(tempdir, image_fn, no_pictures) diff --git a/scripts/cmdcatalog.py b/scripts/cmdcatalog.py index 004bc86..6afd6ff 100755 --- a/scripts/cmdcatalog.py +++ b/scripts/cmdcatalog.py @@ -290,7 +290,7 @@ class Iface(object): def fsck(self): """Fsck orphaned images/thumbs""" image_path = (self.sess.query(dbo.Config) - .filter(dbo.Config.key=='image_path')).one().value # noqa + .filter(dbo.Config.key == 'image_path')).one().value if image_path == ':same_as_db:': image_path = misc.calculate_image_path(None, False) @@ -318,19 +318,19 @@ class Iface(object): if '_t' in fname: obj = (self.sess.query(dbo.Thumbnail) - .filter(dbo.Thumbnail.filename==fname_)).all() # noqa + .filter(dbo.Thumbnail.filename == fname_)).all() if obj: continue obj = (self.sess.query(dbo.Image) - .filter(dbo.Image.filename== # noqa + .filter(dbo.Image.filename == fname_.replace('_t.', '.'))).all() if obj: continue else: obj = (self.sess.query(dbo.Image) - .filter(dbo.Image.filename==fname_)).all() # noqa + .filter(dbo.Image.filename == fname_)).all() if obj: continue diff --git a/tests/scan_test.py b/tests/scan_test.py index 86c57d0..fb57326 100644 --- a/tests/scan_test.py +++ b/tests/scan_test.py @@ -23,7 +23,7 @@ def populate_with_mock_files(dir_): files_no = 0 for file_ in files1: with open(os.path.join(dir_, file_), "wb") as fobj: - fobj.write("\xde\xad\xbe\xef" * len(file_)) + fobj.write(b"\xde\xad\xbe\xef" * len(file_)) files_no += 1 os.symlink(os.path.join(dir_, files1[-1]), os.path.join(dir_, 'link.jpg')) @@ -32,7 +32,7 @@ def populate_with_mock_files(dir_): os.mkdir(os.path.join(dir_, 'directory')) for file_ in files2: with open(os.path.join(dir_, 'directory', file_), "wb") as fobj: - fobj.write("\xfe\xad\xfa\xce" * len(file_)) + fobj.write(b"\xfe\xad\xfa\xce" * len(file_)) files_no += 1 return files_no @@ -178,8 +178,8 @@ class TestScan(unittest.TestCase): self.assertTrue(file_ob is not file2_ob) # While Image objects points to the same file - self.assertTrue(file_ob.images[0].filename == \ - file2_ob.images[0].filename) + self.assertTrue(file_ob.images[0].filename == + file2_ob.images[0].filename) # they are different objects self.assertTrue(file_ob.images[0] is not file2_ob.images[0]) diff --git a/tests/video_test.py b/tests/video_test.py index 1c385ed..7fa27a3 100644 --- a/tests/video_test.py +++ b/tests/video_test.py @@ -7,6 +7,8 @@ """ import os import unittest +from unittest import mock +import io import PIL @@ -130,7 +132,7 @@ ID_AUDIO_RATE=22050 ID_AUDIO_NCH=1 ID_AUDIO_CODEC=ffac3 ID_EXIT=EOF""", - "m.wmv":"""ID_AUDIO_ID=1 + "m.wmv": """ID_AUDIO_ID=1 ID_VIDEO_ID=2 ID_FILENAME=m.wmv ID_DEMUXER=asf @@ -198,6 +200,7 @@ class Readlines(object): def readlines(self): return self.data.split('\n') + def mock_popen(command): key = None if 'midentify' in command: @@ -205,22 +208,25 @@ def mock_popen(command): elif 'jpeg:outdir' in command: # simulate capture for mplayer img_dir = command.split('"')[-2] - img = PIL.Image.new('RGBA', (320, 200)) + img = PIL.Image.new('RGB', (320, 200)) with open(os.path.join(img_dir, "00000001.jpg"), "wb") as fobj: img.save(fobj) return Readlines(key) -os.popen = mock_popen +# os.popen = mock_popen class TestVideo(unittest.TestCase): """test class for retrive midentify script output""" - def test_avi(self): + @mock.patch('os.popen') + def test_avi(self, popen): """test mock avi file, should return dict with expected values""" - avi = Video("m.avi") + fname = "m.avi" + popen.return_value = io.StringIO(DATA[fname]) + avi = Video(fname) self.assertTrue(len(avi.tags) != 0, "result should have lenght > 0") self.assertEqual(avi.tags['audio_format'], '85') self.assertEqual(avi.tags['width'], 128) @@ -233,10 +239,13 @@ class TestVideo(unittest.TestCase): self.assertEqual(avi.tags['duration'], '00:00:04') self.assertEqual(avi.tags['container'], 'avi') - def test_avi2(self): + @mock.patch('os.popen') + def test_avi2(self, popen): """test another mock avi file, should return dict with expected values""" - avi = Video("m1.avi") + fname = "m1.avi" + popen.return_value = io.StringIO(DATA[fname]) + avi = Video(fname) self.assertTrue(len(avi.tags) != 0, "result should have lenght > 0") self.assertEqual(avi.tags['audio_format'], '85') self.assertEqual(avi.tags['width'], 128) @@ -249,9 +258,12 @@ class TestVideo(unittest.TestCase): self.assertEqual(avi.tags['duration'], '00:00:04') self.assertEqual(avi.tags['container'], 'avi') - def test_mkv(self): + @mock.patch('os.popen') + def test_mkv(self, popen): """test mock mkv file, should return dict with expected values""" - mkv = Video("m.mkv") + fname = "m.mkv" + popen.return_value = io.StringIO(DATA[fname]) + mkv = Video(fname) self.assertTrue(len(mkv.tags) != 0, "result should have lenght > 0") self.assertEqual(mkv.tags['audio_format'], '8192') self.assertEqual(mkv.tags['width'], 128) @@ -264,24 +276,30 @@ class TestVideo(unittest.TestCase): self.assertEqual(mkv.tags['duration'], '00:00:04') self.assertTrue(mkv.tags['container'] in ('mkv', 'lavfpref')) - def test_mpg(self): + @mock.patch('os.popen') + def test_mpg(self, popen): """test mock mpg file, should return dict with expected values""" - mpg = Video("m.mpg") + fname = "m.mpg" + popen.return_value = io.StringIO(DATA[fname]) + mpg = Video(fname) self.assertTrue(len(mpg.tags) != 0, "result should have lenght > 0") - self.assertFalse(mpg.tags.has_key('audio_format')) + self.assertFalse('audio_format' in mpg.tags) self.assertEqual(mpg.tags['width'], 128) - self.assertFalse(mpg.tags.has_key('audio_no_channels')) + self.assertFalse('audio_no_channels' in mpg.tags) self.assertEqual(mpg.tags['height'], 96) self.assertEqual(mpg.tags['video_format'], '0x10000001') - self.assertFalse(mpg.tags.has_key('lenght')) - self.assertFalse(mpg.tags.has_key('audio_codec')) + self.assertFalse('lenght' in mpg.tags) + self.assertFalse('audio_codec' in mpg.tags) self.assertEqual(mpg.tags['video_codec'], 'ffmpeg1') - self.assertFalse(mpg.tags.has_key('duration')) + self.assertFalse('duration' in mpg.tags) self.assertEqual(mpg.tags['container'], 'mpeges') - def test_ogm(self): + @mock.patch('os.popen') + def test_ogm(self, popen): """test mock ogm file, should return dict with expected values""" - ogm = Video("m.ogm") + fname = "m.ogm" + popen.return_value = io.StringIO(DATA[fname]) + ogm = Video(fname) self.assertTrue(len(ogm.tags) != 0, "result should have lenght > 0") self.assertEqual(ogm.tags['audio_format'], '8192') self.assertEqual(ogm.tags['width'], 160) @@ -294,9 +312,12 @@ class TestVideo(unittest.TestCase): self.assertEqual(ogm.tags['duration'], '00:00:04') self.assertTrue(ogm.tags['container'] in ('ogg', 'lavfpref')) - def test_wmv(self): + @mock.patch('os.popen') + def test_wmv(self, popen): """test mock wmv file, should return dict with expected values""" - wmv = Video("m.wmv") + fname = "m.wmv" + popen.return_value = io.StringIO(DATA[fname]) + wmv = Video(fname) self.assertTrue(len(wmv.tags) != 0, "result should have lenght > 0") self.assertEqual(wmv.tags['audio_format'], '353') self.assertEqual(wmv.tags['width'], 852) @@ -309,9 +330,12 @@ class TestVideo(unittest.TestCase): self.assertEqual(wmv.tags['duration'], '01:17:32') self.assertEqual(wmv.tags['container'], 'asf') - def test_mp4(self): + @mock.patch('os.popen') + def test_mp4(self, popen): """test mock mp4 file, should return dict with expected values""" - mp4 = Video("m.mp4") + fname = "m.mp4" + popen.return_value = io.StringIO(DATA[fname]) + mp4 = Video(fname) self.assertTrue(len(mp4.tags) != 0, "result should have lenght > 0") self.assertEqual(mp4.tags['audio_format'], 'mp4a') self.assertEqual(mp4.tags['width'], 720) @@ -324,21 +348,31 @@ class TestVideo(unittest.TestCase): self.assertEqual(mp4.tags['duration'], '00:01:09') self.assertEqual(mp4.tags['container'], 'lavfpref') - def test_capture(self): + @mock.patch('shutil.move') + @mock.patch('pygtktalog.video.Image') + @mock.patch('os.listdir') + @mock.patch('shutil.rmtree') + @mock.patch('os.close') + @mock.patch('tempfile.mkstemp') + @mock.patch('tempfile.mkdtemp') + @mock.patch('os.popen') + def test_capture(self, popen, mkdtemp, mkstemp, fclose, rmtree, listdir, + img, move): """test capture with some small movie and play a little with tags""" - avi = Video("m.avi") + fname = 'm.avi' + popen.return_value = io.StringIO(DATA[fname]) + mkdtemp.return_value = '/tmp' + mkstemp.return_value = (10, 'foo.jpg') + listdir.return_value = ['a.jpg', 'b.jpg', 'c.jpg', 'd.jpg'] + + avi = Video(fname) filename = avi.capture() - self.assertTrue(filename != None) - self.assertTrue(os.path.exists(filename)) - file_size = os.stat(filename)[6] - self.assertAlmostEqual(file_size/10000.0, 0.151, 0) - os.unlink(filename) + self.assertIsNotNone(filename) for length in (480, 380, 4): avi.tags['length'] = length filename = avi.capture() self.assertTrue(filename is not None) - os.unlink(filename) avi.tags['length'] = 3 self.assertTrue(avi.capture() is None) @@ -351,7 +385,6 @@ class TestVideo(unittest.TestCase): avi.tags['width'] = 1025 filename = avi.capture() self.assertTrue(filename is not None) - os.unlink(filename) del(avi.tags['length']) self.assertTrue(avi.capture() is None) diff --git a/tox.ini b/tox.ini index 33b1e5b..8e897c6 100644 --- a/tox.ini +++ b/tox.ini @@ -1,9 +1,10 @@ [tox] -envlist = cleanup,py27,pep8 +envlist = cleanup,py3,pep8 usedevelop = True [testenv] +basepython = python3 usedevelop=True setenv = COVERAGE_FILE = .coverage commands = py.test --cov=pygtktalog --cov-report=term-missing