1# Copyright (c) 2008-2012 testtools developers. See LICENSE for details. 2 3import os 4import shutil 5import tarfile 6import tempfile 7 8from testtools import TestCase 9from testtools.matchers import ( 10 Contains, 11 DocTestMatches, 12 Equals, 13 ) 14from testtools.matchers._filesystem import ( 15 DirContains, 16 DirExists, 17 FileContains, 18 FileExists, 19 HasPermissions, 20 PathExists, 21 SamePath, 22 TarballContains, 23 ) 24 25 26class PathHelpers(object): 27 28 def mkdtemp(self): 29 directory = tempfile.mkdtemp() 30 self.addCleanup(shutil.rmtree, directory) 31 return directory 32 33 def create_file(self, filename, contents=''): 34 fp = open(filename, 'w') 35 try: 36 fp.write(contents) 37 finally: 38 fp.close() 39 40 def touch(self, filename): 41 return self.create_file(filename) 42 43 44class TestPathExists(TestCase, PathHelpers): 45 46 def test_exists(self): 47 tempdir = self.mkdtemp() 48 self.assertThat(tempdir, PathExists()) 49 50 def test_not_exists(self): 51 doesntexist = os.path.join(self.mkdtemp(), 'doesntexist') 52 mismatch = PathExists().match(doesntexist) 53 self.assertThat( 54 "%s does not exist." % doesntexist, Equals(mismatch.describe())) 55 56 57class TestDirExists(TestCase, PathHelpers): 58 59 def test_exists(self): 60 tempdir = self.mkdtemp() 61 self.assertThat(tempdir, DirExists()) 62 63 def test_not_exists(self): 64 doesntexist = os.path.join(self.mkdtemp(), 'doesntexist') 65 mismatch = DirExists().match(doesntexist) 66 self.assertThat( 67 PathExists().match(doesntexist).describe(), 68 Equals(mismatch.describe())) 69 70 def test_not_a_directory(self): 71 filename = os.path.join(self.mkdtemp(), 'foo') 72 self.touch(filename) 73 mismatch = DirExists().match(filename) 74 self.assertThat( 75 "%s is not a directory." % filename, Equals(mismatch.describe())) 76 77 78class TestFileExists(TestCase, PathHelpers): 79 80 def test_exists(self): 81 tempdir = self.mkdtemp() 82 filename = os.path.join(tempdir, 'filename') 83 self.touch(filename) 84 self.assertThat(filename, FileExists()) 85 86 def test_not_exists(self): 87 doesntexist = os.path.join(self.mkdtemp(), 'doesntexist') 88 mismatch = FileExists().match(doesntexist) 89 self.assertThat( 90 PathExists().match(doesntexist).describe(), 91 Equals(mismatch.describe())) 92 93 def test_not_a_file(self): 94 tempdir = self.mkdtemp() 95 mismatch = FileExists().match(tempdir) 96 self.assertThat( 97 "%s is not a file." % tempdir, Equals(mismatch.describe())) 98 99 100class TestDirContains(TestCase, PathHelpers): 101 102 def test_empty(self): 103 tempdir = self.mkdtemp() 104 self.assertThat(tempdir, DirContains([])) 105 106 def test_not_exists(self): 107 doesntexist = os.path.join(self.mkdtemp(), 'doesntexist') 108 mismatch = DirContains([]).match(doesntexist) 109 self.assertThat( 110 PathExists().match(doesntexist).describe(), 111 Equals(mismatch.describe())) 112 113 def test_contains_files(self): 114 tempdir = self.mkdtemp() 115 self.touch(os.path.join(tempdir, 'foo')) 116 self.touch(os.path.join(tempdir, 'bar')) 117 self.assertThat(tempdir, DirContains(['bar', 'foo'])) 118 119 def test_matcher(self): 120 tempdir = self.mkdtemp() 121 self.touch(os.path.join(tempdir, 'foo')) 122 self.touch(os.path.join(tempdir, 'bar')) 123 self.assertThat(tempdir, DirContains(matcher=Contains('bar'))) 124 125 def test_neither_specified(self): 126 self.assertRaises(AssertionError, DirContains) 127 128 def test_both_specified(self): 129 self.assertRaises( 130 AssertionError, DirContains, filenames=[], matcher=Contains('a')) 131 132 def test_does_not_contain_files(self): 133 tempdir = self.mkdtemp() 134 self.touch(os.path.join(tempdir, 'foo')) 135 mismatch = DirContains(['bar', 'foo']).match(tempdir) 136 self.assertThat( 137 Equals(['bar', 'foo']).match(['foo']).describe(), 138 Equals(mismatch.describe())) 139 140 141class TestFileContains(TestCase, PathHelpers): 142 143 def test_not_exists(self): 144 doesntexist = os.path.join(self.mkdtemp(), 'doesntexist') 145 mismatch = FileContains('').match(doesntexist) 146 self.assertThat( 147 PathExists().match(doesntexist).describe(), 148 Equals(mismatch.describe())) 149 150 def test_contains(self): 151 tempdir = self.mkdtemp() 152 filename = os.path.join(tempdir, 'foo') 153 self.create_file(filename, 'Hello World!') 154 self.assertThat(filename, FileContains('Hello World!')) 155 156 def test_matcher(self): 157 tempdir = self.mkdtemp() 158 filename = os.path.join(tempdir, 'foo') 159 self.create_file(filename, 'Hello World!') 160 self.assertThat( 161 filename, FileContains(matcher=DocTestMatches('Hello World!'))) 162 163 def test_neither_specified(self): 164 self.assertRaises(AssertionError, FileContains) 165 166 def test_both_specified(self): 167 self.assertRaises( 168 AssertionError, FileContains, contents=[], matcher=Contains('a')) 169 170 def test_does_not_contain(self): 171 tempdir = self.mkdtemp() 172 filename = os.path.join(tempdir, 'foo') 173 self.create_file(filename, 'Goodbye Cruel World!') 174 mismatch = FileContains('Hello World!').match(filename) 175 self.assertThat( 176 Equals('Hello World!').match('Goodbye Cruel World!').describe(), 177 Equals(mismatch.describe())) 178class TestTarballContains(TestCase, PathHelpers): 179 180 def test_match(self): 181 tempdir = self.mkdtemp() 182 in_temp_dir = lambda x: os.path.join(tempdir, x) 183 self.touch(in_temp_dir('a')) 184 self.touch(in_temp_dir('b')) 185 tarball = tarfile.open(in_temp_dir('foo.tar.gz'), 'w') 186 tarball.add(in_temp_dir('a'), 'a') 187 tarball.add(in_temp_dir('b'), 'b') 188 tarball.close() 189 self.assertThat( 190 in_temp_dir('foo.tar.gz'), TarballContains(['b', 'a'])) 191 192 def test_mismatch(self): 193 tempdir = self.mkdtemp() 194 in_temp_dir = lambda x: os.path.join(tempdir, x) 195 self.touch(in_temp_dir('a')) 196 self.touch(in_temp_dir('b')) 197 tarball = tarfile.open(in_temp_dir('foo.tar.gz'), 'w') 198 tarball.add(in_temp_dir('a'), 'a') 199 tarball.add(in_temp_dir('b'), 'b') 200 tarball.close() 201 mismatch = TarballContains(['d', 'c']).match(in_temp_dir('foo.tar.gz')) 202 self.assertEqual( 203 mismatch.describe(), 204 Equals(['c', 'd']).match(['a', 'b']).describe()) 205 206 207class TestSamePath(TestCase, PathHelpers): 208 209 def test_same_string(self): 210 self.assertThat('foo', SamePath('foo')) 211 212 def test_relative_and_absolute(self): 213 path = 'foo' 214 abspath = os.path.abspath(path) 215 self.assertThat(path, SamePath(abspath)) 216 self.assertThat(abspath, SamePath(path)) 217 218 def test_real_path(self): 219 tempdir = self.mkdtemp() 220 source = os.path.join(tempdir, 'source') 221 self.touch(source) 222 target = os.path.join(tempdir, 'target') 223 try: 224 os.symlink(source, target) 225 except (AttributeError, NotImplementedError): 226 self.skip("No symlink support") 227 self.assertThat(source, SamePath(target)) 228 self.assertThat(target, SamePath(source)) 229 230 231class TestHasPermissions(TestCase, PathHelpers): 232 233 def test_match(self): 234 tempdir = self.mkdtemp() 235 filename = os.path.join(tempdir, 'filename') 236 self.touch(filename) 237 permissions = oct(os.stat(filename).st_mode)[-4:] 238 self.assertThat(filename, HasPermissions(permissions)) 239 240 241def test_suite(): 242 from unittest import TestLoader 243 return TestLoader().loadTestsFromName(__name__) 244