summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--morphlib/morphologyfactory.py21
-rw-r--r--morphlib/morphologyfactory_tests.py27
2 files changed, 42 insertions, 6 deletions
diff --git a/morphlib/morphologyfactory.py b/morphlib/morphologyfactory.py
index 5e3bf7f2..e7ee9323 100644
--- a/morphlib/morphologyfactory.py
+++ b/morphlib/morphologyfactory.py
@@ -27,10 +27,16 @@ class AutodetectError(MorphologyFactoryError):
"Failed to determine the build system of repo %s at "
"ref %s" % (repo_name, ref))
+class NotcachedError(MorphologyFactoryError):
+ def __init__(self, repo_name):
+ MorphologyFactoryError.__init__(self,
+ "Repository %s is not cached locally and there is no "
+ "remote cache specified" % repo_name)
+
class MorphologyFactory(object):
'''An way of creating morphologies which will provide a default'''
- def __init__(self, local_repo_cache, remote_repo_cache):
+ def __init__(self, local_repo_cache, remote_repo_cache=None):
self._lrc = local_repo_cache
self._rrc = remote_repo_cache
@@ -45,18 +51,27 @@ class MorphologyFactory(object):
if self._lrc.has_repo(reponame):
repo = self._lrc.get_repo(reponame)
return repo.cat(sha1, filename)
- else:
+ elif self._rrc is not None:
return self._rrc.cat_file(reponame, sha1, filename)
+ else:
+ raise NotcachedError(reponame)
def _autodetect_text(self, reponame, sha1, filename):
if self._lrc.has_repo(reponame):
repo = self._lrc.get_repo(reponame)
files = repo.list_files(sha1)
- else:
+ elif self._rrc is not None:
files = self._rrc.list_files(reponame, sha1)
+ else:
+ raise NotcachedError(reponame)
bs = morphlib.buildsystem.detect_build_system(lambda x: x in files)
if bs is None:
raise AutodetectError(reponame, sha1)
+ # TODO consider changing how morphs are located to be by morph
+ # name rather than filename, it would save creating a
+ # filename only to strip it back to its morph name again
+ # and would allow future changes like morphologies being
+ # stored as git metadata instead of as a file in the repo
assert filename.endswith('.morph')
morph_name = filename[:-len('.morph')]
morph_text = bs.get_morphology_text(morph_name)
diff --git a/morphlib/morphologyfactory_tests.py b/morphlib/morphologyfactory_tests.py
index 2a0709ed..5748aca0 100644
--- a/morphlib/morphologyfactory_tests.py
+++ b/morphlib/morphologyfactory_tests.py
@@ -17,7 +17,9 @@
import unittest
from morphlib.morph2 import Morphology
-from morphlib.morphologyfactory import MorphologyFactory, AutodetectError
+from morphlib.morphologyfactory import (MorphologyFactory,
+ AutodetectError,
+ NotcachedError)
class FakeRemoteRepoCache(object):
def cat_file(self, reponame, sha1, filename):
@@ -53,6 +55,7 @@ class MorphologyFactoryTests(unittest.TestCase):
self.lrc = FakeLocalRepoCache(self.lr)
self.rrc = FakeRemoteRepoCache()
self.mf = MorphologyFactory(self.lrc, self.rrc)
+ self.lmf = MorphologyFactory(self.lrc, None)
def nosuchfile(self):
raise IOError('File not found')
@@ -60,12 +63,14 @@ class MorphologyFactoryTests(unittest.TestCase):
return False
def test_gets_morph_from_local_repo(self):
- morph = self.mf.get_morphology('reponame', 'sha1', 'foo.morph')
+ morph = self.mf.get_morphology('reponame', 'sha1',
+ 'foo.morph')
self.assertEqual('local-foo', morph['name'])
def test_gets_morph_from_remote_repo(self):
self.lrc.has_repo = self.doesnothaverepo
- morph = self.mf.get_morphology('reponame', 'sha1', 'foo.morph')
+ morph = self.mf.get_morphology('reponame', 'sha1',
+ 'foo.morph')
self.assertEqual('remote-foo', morph['name'])
def test_autodetects_local_morphology(self):
@@ -88,3 +93,19 @@ class MorphologyFactoryTests(unittest.TestCase):
self.rrc.list_files = lambda x: ['.']
self.assertRaises(AutodetectError, self.mf.get_morphology,
'reponame', 'sha1', 'unreached.morph')
+
+ def test_looks_locally_with_no_remote(self):
+ morph = self.lmf.get_morphology('reponame', 'sha1',
+ 'foo.morph')
+ self.assertEqual('local-foo', morph['name'])
+
+ def test_autodetects_locally_with_no_remote(self):
+ self.lr.cat = self.nosuchfile
+ morph = self.lmf.get_morphology('reponame', 'sha1',
+ 'assumed-local.morph')
+ self.assertEqual('assumed-local', morph['name'])
+
+ def test_fails_when_local_not_cached_and_no_remote(self):
+ self.lrc.has_repo = self.doesnothaverepo
+ self.assertRaises(NotcachedError, self.lmf.get_morphology,
+ 'reponame', 'sha1', 'unreached.morph')