1# -*- encoding: UTF-8
2from __future__ import unicode_literals
3
4import os
5import stat
6
7from six import text_type
8
9from fs.opener import open_fs
10from fs.enums import ResourceType
11from fs import walk
12from fs import errors
13from fs.test import UNICODE_TEXT
14
15
16class ArchiveTestCases(object):
17    def make_source_fs(self):
18        return open_fs("temp://")
19
20    def build_source(self, fs):
21        fs.makedirs("foo/bar/baz")
22        fs.makedir("tmp")
23        fs.writetext("Файл", "unicode filename")
24        fs.writetext("top.txt", "Hello, World")
25        fs.writetext("top2.txt", "Hello, World")
26        fs.writetext("foo/bar/egg", "foofoo")
27        fs.makedir("unicode")
28        fs.writetext("unicode/text.txt", UNICODE_TEXT)
29
30    def compress(self, fs):
31        pass
32
33    def load_archive(self):
34        pass
35
36    def remove_archive(self):
37        pass
38
39    def setUp(self):
40        self.source_fs = source_fs = self.make_source_fs()
41        self.build_source(source_fs)
42        self.compress(source_fs)
43        self.fs = self.load_archive()
44
45    def tearDown(self):
46        self.source_fs.close()
47        self.fs.close()
48        self.remove_archive()
49
50    def test_repr(self):
51        repr(self.fs)
52
53    def test_str(self):
54        self.assertIsInstance(text_type(self.fs), text_type)
55
56    def test_readonly(self):
57        with self.assertRaises(errors.ResourceReadOnly):
58            self.fs.makedir("newdir")
59        with self.assertRaises(errors.ResourceReadOnly):
60            self.fs.remove("top.txt")
61        with self.assertRaises(errors.ResourceReadOnly):
62            self.fs.removedir("foo/bar/baz")
63        with self.assertRaises(errors.ResourceReadOnly):
64            self.fs.create("foo.txt")
65        with self.assertRaises(errors.ResourceReadOnly):
66            self.fs.setinfo("foo.txt", {})
67
68    def test_getinfo(self):
69        root = self.fs.getinfo("/", ["details"])
70        self.assertEqual(root.name, "")
71        self.assertTrue(root.is_dir)
72        self.assertEqual(root.get("details", "type"), ResourceType.directory)
73
74        bar = self.fs.getinfo("foo/bar", ["details"])
75        self.assertEqual(bar.name, "bar")
76        self.assertTrue(bar.is_dir)
77        self.assertEqual(bar.get("details", "type"), ResourceType.directory)
78
79        top = self.fs.getinfo("top.txt", ["details", "access"])
80        self.assertEqual(top.size, 12)
81        self.assertFalse(top.is_dir)
82
83        try:
84            source_syspath = self.source_fs.getsyspath("/top.txt")
85        except errors.NoSysPath:
86            pass
87        else:
88            if top.has_namespace("access"):
89                self.assertEqual(
90                    top.permissions.mode, stat.S_IMODE(os.stat(source_syspath).st_mode)
91                )
92
93        self.assertEqual(top.get("details", "type"), ResourceType.file)
94
95    def test_listdir(self):
96        self.assertEqual(
97            sorted(self.source_fs.listdir("/")), sorted(self.fs.listdir("/"))
98        )
99        for name in self.fs.listdir("/"):
100            self.assertIsInstance(name, text_type)
101        with self.assertRaises(errors.DirectoryExpected):
102            self.fs.listdir("top.txt")
103        with self.assertRaises(errors.ResourceNotFound):
104            self.fs.listdir("nothere")
105
106    def test_open(self):
107        with self.fs.open("top.txt") as f:
108            chars = []
109            while True:
110                c = f.read(2)
111                if not c:
112                    break
113                chars.append(c)
114            self.assertEqual("".join(chars), "Hello, World")
115        with self.assertRaises(errors.ResourceNotFound):
116            with self.fs.open("nothere.txt") as f:
117                pass
118        with self.assertRaises(errors.FileExpected):
119            with self.fs.open("foo") as f:
120                pass
121
122    def test_gets(self):
123        self.assertEqual(self.fs.readtext("top.txt"), "Hello, World")
124        self.assertEqual(self.fs.readtext("foo/bar/egg"), "foofoo")
125        self.assertEqual(self.fs.readbytes("top.txt"), b"Hello, World")
126        self.assertEqual(self.fs.readbytes("foo/bar/egg"), b"foofoo")
127        with self.assertRaises(errors.ResourceNotFound):
128            self.fs.readbytes("what.txt")
129
130    def test_walk_files(self):
131        source_files = sorted(walk.walk_files(self.source_fs))
132        archive_files = sorted(walk.walk_files(self.fs))
133
134        self.assertEqual(source_files, archive_files)
135
136    def test_implied_dir(self):
137        self.fs.getinfo("foo/bar")
138        self.fs.getinfo("foo")
139