Better exception handling in GUI.
[zeroinstall/zeroinstall-rsl.git] / tests / testreader.py
blob896c7ce4d88fbe7724cce331215efb256340a421
1 #!/usr/bin/env python2.4
2 from basetest import BaseTest
3 import sys, tempfile, os, shutil, logging
4 from StringIO import StringIO
5 import unittest
6 from logging import getLogger, DEBUG, INFO
8 sys.path.insert(0, '..')
10 from zeroinstall import NeedDownload
11 from zeroinstall.injector import model, autopolicy, gpg, iface_cache, namespaces, reader
12 from zeroinstall.support import basedir
13 import data
15 foo_iface_uri = 'http://foo'
16 bar_iface_uri = 'http://localhost/bar'
18 logger = logging.getLogger()
20 class TestReader(BaseTest):
21 def setUp(self):
22 BaseTest.setUp(self)
24 stream = tempfile.TemporaryFile()
25 stream.write(data.thomas_key)
26 stream.seek(0)
27 gpg.import_key(stream)
29 def write_with_version(self, version):
30 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
31 tmp.write(
32 """<?xml version="1.0" ?>
33 <interface last-modified="1110752708"
34 uri="%s" %s
35 xmlns="http://zero-install.sourceforge.net/2004/injector/interface">
36 <name>Foo</name>
37 <summary>Foo</summary>
38 <description>Foo</description>
39 </interface>""" % (foo_iface_uri, version))
40 tmp.flush()
41 return tmp
43 def testNoVersion(self):
44 tmp = self.write_with_version('')
45 reader.check_readable(foo_iface_uri, tmp.name)
47 def testNewEnough(self):
48 tmp = self.write_with_version('min-injector-version="0.19"')
49 reader.check_readable(foo_iface_uri, tmp.name)
51 def testTooOld(self):
52 tmp = self.write_with_version('min-injector-version="1000"')
53 try:
54 reader.check_readable(foo_iface_uri, tmp.name)
55 except reader.InvalidInterface, ex:
56 assert "1000" in str(ex)
58 def testRequiresVersion(self):
59 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
60 tmp.write(
61 """<?xml version="1.0" ?>
62 <interface last-modified="1110752708"
63 uri="%s"
64 xmlns="http://zero-install.sourceforge.net/2004/injector/interface"
65 xmlns:my='http://my/namespace'>
66 <name>Foo</name>
67 <summary>Foo</summary>
68 <description>Foo</description>
69 <group>
70 <requires interface='%s' my:foo='test'>
71 <version not-before='2.3.4' before='3.4.5'/>
72 </requires>
73 <implementation id='sha1=123' version='1'/>
74 <requires interface='%s2'/>
75 </group>
76 </interface>""" % (foo_iface_uri, bar_iface_uri, bar_iface_uri))
77 tmp.flush()
78 iface = model.Interface(foo_iface_uri)
79 reader.update(iface, tmp.name)
80 impl = iface.implementations['sha1=123']
81 assert len(impl.dependencies) == 2
82 dep = impl.dependencies[bar_iface_uri]
83 assert len(dep.restrictions) == 1
84 res = dep.restrictions[0]
85 assert res.not_before == [[2, 3, 4], 0]
86 assert res.before == [[3, 4, 5], 0]
87 dep2 = impl.dependencies[bar_iface_uri + '2']
88 assert len(dep2.restrictions) == 0
89 str(dep)
90 str(dep2)
92 assert dep.metadata.get('http://my/namespace foo') == 'test'
93 assert dep.metadata.get('http://my/namespace food', None) == None
95 def testBindings(self):
96 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
97 tmp.write(
98 """<?xml version="1.0" ?>
99 <interface xmlns="http://zero-install.sourceforge.net/2004/injector/interface">
100 <name>Foo</name>
101 <summary>Foo</summary>
102 <description>Foo</description>
103 <group>
104 <requires interface='http://example.com/foo.xml'>
105 <environment name='PATH' insert='bin'/>
106 <environment name='PATH' insert='bin' mode='prepend'/>
107 <environment name='PATH' insert='bin' default='/bin' mode='append'/>
108 <environment name='PATH' insert='bin' mode='replace'/>
109 </requires>
110 <implementation id='sha1=123' version='1'>
111 <environment name='SELF' insert='.' mode='replace'/>
112 </implementation>
113 </group>
114 </interface>""")
115 tmp.flush()
116 iface = model.Interface(foo_iface_uri)
117 reader.update(iface, tmp.name, local = True)
118 impl = iface.implementations['sha1=123']
120 assert len(impl.bindings) == 1
121 self.assertEquals(model.EnvironmentBinding.REPLACE, impl.bindings[0].mode)
123 assert len(impl.requires) == 1
124 dep = impl.requires[0]
126 assert len(dep.bindings) == 4
127 for b in dep.bindings:
128 self.assertEquals('PATH', b.name)
129 self.assertEquals('bin', b.insert)
130 self.assertEquals(model.EnvironmentBinding.PREPEND, dep.bindings[0].mode)
131 self.assertEquals(model.EnvironmentBinding.PREPEND, dep.bindings[1].mode)
132 self.assertEquals(model.EnvironmentBinding.APPEND, dep.bindings[2].mode)
133 self.assertEquals(model.EnvironmentBinding.REPLACE, dep.bindings[3].mode)
135 self.assertEquals(None, dep.bindings[1].default)
136 self.assertEquals('/bin', dep.bindings[2].default)
138 def testVersions(self):
139 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
140 tmp.write(
141 """<?xml version="1.0" ?>
142 <interface
143 uri="%s"
144 xmlns="http://zero-install.sourceforge.net/2004/injector/interface">
145 <name>Foo</name>
146 <summary>Foo</summary>
147 <description>Foo</description>
148 <implementation id='sha1=123' version='1.0-rc3' version-modifier='-pre'/>
149 </interface>""" % foo_iface_uri)
150 tmp.flush()
151 iface = model.Interface(foo_iface_uri)
152 reader.update(iface, tmp.name)
153 impl = iface.implementations['sha1=123']
154 assert impl.version == [[1, 0], -1, [3], -2]
156 def testAbsMain(self):
157 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
158 tmp.write(
159 """<?xml version="1.0" ?>
160 <interface last-modified="1110752708"
161 uri="%s"
162 xmlns="http://zero-install.sourceforge.net/2004/injector/interface">
163 <name>Foo</name>
164 <summary>Foo</summary>
165 <description>Foo</description>
166 <group main='/bin/sh'>
167 <implementation id='sha1=123' version='1'/>
168 </group>
169 </interface>""" % foo_iface_uri)
170 tmp.flush()
171 iface = model.Interface(foo_iface_uri)
172 try:
173 reader.update(iface, tmp.name)
174 assert False
175 except reader.InvalidInterface, ex:
176 assert 'main' in str(ex)
178 def testAttrs(self):
179 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
180 tmp.write(
181 """<?xml version="1.0" ?>
182 <interface last-modified="1110752708"
183 uri="%s"
184 xmlns="http://zero-install.sourceforge.net/2004/injector/interface">
185 <name>Foo</name>
186 <summary>Foo</summary>
187 <description>Foo</description>
188 <group main='bin/sh' foo='foovalue' xmlns:bobpre='http://bob' bobpre:bob='bobvalue'>
189 <implementation id='sha1=123' version='1' bobpre:bob='newbobvalue'/>
190 <implementation id='sha1=124' version='2' main='next'/>
191 </group>
192 </interface>""" % foo_iface_uri)
193 tmp.flush()
194 iface = model.Interface(foo_iface_uri)
195 reader.update(iface, tmp.name)
197 assert len(iface.implementations) == 2
199 assert iface.implementations['sha1=123'].metadata['foo'] == 'foovalue'
200 assert iface.implementations['sha1=123'].metadata['main'] == 'bin/sh'
201 assert iface.implementations['sha1=123'].metadata['http://bob bob'] == 'newbobvalue'
203 assert iface.implementations['sha1=124'].metadata['http://bob bob'] == 'bobvalue'
204 assert iface.implementations['sha1=124'].metadata['main'] == 'next'
206 def testNative(self):
207 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
208 tmp.write(
209 """<?xml version="1.0" ?>
210 <interface xmlns="http://zero-install.sourceforge.net/2004/injector/interface">
211 <name>Foo</name>
212 <summary>Foo</summary>
213 <description>Foo</description>
214 <package-implementation package='gimp'/>
215 <package-implementation package='python-bittorrent' foo='bar' main='/usr/bin/pbt'/>
216 </interface>""")
217 tmp.flush()
219 iface = model.Interface(foo_iface_uri)
220 reader.update(iface, tmp.name, True)
222 assert len(iface.implementations) == 1
224 impl = iface.implementations['package:deb:python-bittorrent:3.4.2-10']
225 assert impl.id == 'package:deb:python-bittorrent:3.4.2-10'
226 assert impl.upstream_stability == model.packaged
227 assert impl.user_stability == None
228 assert impl.requires == []
229 assert impl.main == '/usr/bin/pbt'
230 assert impl.metadata['foo'] == 'bar'
231 assert impl.feed == iface._main_feed
233 def testLang(self):
234 tmp = tempfile.NamedTemporaryFile(prefix = 'test-')
235 tmp.write(
236 """<?xml version="1.0" ?>
237 <interface xmlns="http://zero-install.sourceforge.net/2004/injector/interface">
238 <name>Foo</name>
239 <summary>Foo</summary>
240 <description>Foo</description>
241 <feed langs='fr en_GB' src='http://localhost/feed.xml'/>
242 <group>
243 <group langs='fr en_GB'>
244 <implementation id='sha1=124' version='2' langs='fr'/>
245 <implementation id='sha1=234' version='2'/>
246 </group>
247 <implementation id='sha1=345' version='2'/>
248 </group>
249 </interface>""")
250 tmp.flush()
252 iface = model.Interface(foo_iface_uri)
253 reader.update(iface, tmp.name, True)
255 assert len(iface.implementations) == 3
256 assert len(iface.feeds) == 1, iface.feeds
258 self.assertEquals('fr en_GB', iface.feeds[0].langs)
260 self.assertEquals('fr', iface.implementations['sha1=124'].langs)
261 self.assertEquals('fr en_GB', iface.implementations['sha1=234'].langs)
262 self.assertEquals(None, iface.implementations['sha1=345'].langs)
264 suite = unittest.makeSuite(TestReader)
265 if __name__ == '__main__':
266 sys.argv.append('-v')
267 unittest.main()