2 from basetest
import BaseTest
, TestStores
3 import sys
, os
, tempfile
4 from StringIO
import StringIO
7 sys
.path
.insert(0, '..')
8 from zeroinstall
import cmd
9 from zeroinstall
.injector
import model
, selections
, qdom
, reader
, policy
, handler
, gpg
11 mydir
= os
.path
.dirname(__file__
)
14 def __init__(self
, reply
):
20 class TestInstall(BaseTest
):
21 def run_0install(self
, args
):
22 old_stdout
= sys
.stdout
23 old_stderr
= sys
.stderr
25 sys
.stdout
= StringIO()
26 sys
.stderr
= StringIO()
29 cmd
.main(args
, config
= self
.config
)
36 except AttributeError:
38 except AssertionError:
40 except Exception as ex
:
42 out
= sys
.stdout
.getvalue()
43 err
= sys
.stderr
.getvalue()
45 err
+= str(ex
.__class
__)
47 sys
.stdout
= old_stdout
48 sys
.stderr
= old_stderr
52 out
, err
= self
.run_0install([])
53 assert out
.lower().startswith("usage:")
54 assert 'add-feed' in out
55 assert '--version' in out
58 out2
, err
= self
.run_0install(['--help'])
62 out
, err
= self
.run_0install(['--version'])
63 assert 'Thomas Leonard' in out
66 out
, err
= self
.run_0install(['foobar'])
67 assert 'Unknown sub-command' in err
, err
70 out
, err
= self
.run_0install(['select'])
71 assert out
.lower().startswith("usage:")
74 out
, err
= self
.run_0install(['select', 'Local.xml'])
76 assert 'Version: 0.1' in out
78 local_uri
= model
.canonical_iface_uri('Local.xml')
79 out
, err
= self
.run_0install(['select', 'Local.xml'])
81 assert 'Version: 0.1' in out
83 out
, err
= self
.run_0install(['select', 'Local.xml', '--xml'])
84 sels
= selections
.Selections(qdom
.parse(StringIO(str(out
))))
85 assert sels
.selections
[local_uri
].version
== '0.1'
87 out
, err
= self
.run_0install(['select', 'selections.xml'])
89 assert 'Version: 1\n' in out
90 assert '(not cached)' in out
92 def testDownload(self
):
93 out
, err
= self
.run_0install(['download'])
94 assert out
.lower().startswith("usage:")
95 assert '--show' in out
97 out
, err
= self
.run_0install(['download', 'Local.xml', '--show'])
99 assert 'Version: 0.1' in out
101 local_uri
= model
.canonical_iface_uri('Local.xml')
102 out
, err
= self
.run_0install(['download', 'Local.xml', '--xml'])
104 sels
= selections
.Selections(qdom
.parse(StringIO(str(out
))))
105 assert sels
.selections
[local_uri
].version
== '0.1'
107 out
, err
= self
.run_0install(['download', 'Local.xml', '--show', '--with-store=/foo'])
109 assert self
.config
.stores
.stores
[-1].dir == '/foo'
111 out
, err
= self
.run_0install(['download', '--offline', 'selections.xml'])
112 assert 'Would download' in err
113 self
.config
.network_use
= model
.network_full
115 self
.config
.stores
= TestStores()
116 digest
= 'sha1=3ce644dc725f1d21cfcf02562c76f375944b266a'
117 self
.config
.fetcher
.allow_download(digest
)
118 out
, err
= self
.run_0install(['download', 'Hello.xml', '--show'])
120 assert self
.config
.stores
.lookup_any([digest
]).startswith('/fake')
121 assert 'Version: 1\n' in out
123 out
, err
= self
.run_0install(['download', '--offline', 'selections.xml', '--show'])
124 assert '/fake_store' in out
125 self
.config
.network_use
= model
.network_full
127 def testDownloadSelections(self
):
128 self
.config
.stores
= TestStores()
129 digest
= 'sha1=3ce644dc725f1d21cfcf02562c76f375944b266a'
130 self
.config
.fetcher
.allow_download(digest
)
131 hello
= reader
.load_feed('Hello.xml')
132 self
.config
.fetcher
.allow_feed_download('http://example.com:8000/Hello.xml', hello
)
133 out
, err
= self
.run_0install(['download', 'selections.xml', '--show'])
135 assert self
.config
.stores
.lookup_any([digest
]).startswith('/fake')
136 assert 'Version: 1\n' in out
138 def testUpdate(self
):
139 out
, err
= self
.run_0install(['update'])
140 assert out
.lower().startswith("usage:")
141 assert '--message' in out
, out
143 # Updating a local feed with no dependencies
144 out
, err
= self
.run_0install(['update', 'Local.xml'])
146 assert 'No updates found' in out
, out
148 # Using a remote feed for the first time
149 self
.config
.stores
= TestStores()
150 binary_feed
= reader
.load_feed('Binary.xml')
151 self
.config
.fetcher
.allow_download('sha1=123')
152 self
.config
.fetcher
.allow_feed_download('http://foo/Binary.xml', binary_feed
)
153 out
, err
= self
.run_0install(['update', 'http://foo/Binary.xml'])
155 assert 'Binary.xml: new -> 1.0' in out
, out
158 self
.config
.fetcher
.allow_feed_download('http://foo/Binary.xml', binary_feed
)
159 out
, err
= self
.run_0install(['update', 'http://foo/Binary.xml'])
161 assert 'No updates found' in out
, out
163 # New binary release available.
164 new_binary_feed
= reader
.load_feed('Binary.xml')
165 new_binary_feed
.implementations
['sha1=123'].version
= model
.parse_version('1.1')
166 self
.config
.fetcher
.allow_feed_download('http://foo/Binary.xml', new_binary_feed
)
167 out
, err
= self
.run_0install(['update', 'http://foo/Binary.xml'])
169 assert 'Binary.xml: 1.0 -> 1.1' in out
, out
171 # Compiling from source for the first time.
172 source_feed
= reader
.load_feed('Source.xml')
173 compiler_feed
= reader
.load_feed('Compiler.xml')
174 self
.config
.fetcher
.allow_download('sha1=234')
175 self
.config
.fetcher
.allow_download('sha1=345')
176 self
.config
.fetcher
.allow_feed_download('http://foo/Compiler.xml', compiler_feed
)
177 self
.config
.fetcher
.allow_feed_download('http://foo/Binary.xml', binary_feed
)
178 self
.config
.fetcher
.allow_feed_download('http://foo/Source.xml', source_feed
)
179 out
, err
= self
.run_0install(['update', 'http://foo/Binary.xml', '--source'])
181 assert 'Binary.xml: new -> 1.0' in out
, out
182 assert 'Compiler.xml: new -> 1.0' in out
, out
184 # New compiler released.
185 new_compiler_feed
= reader
.load_feed('Compiler.xml')
186 new_compiler_feed
.implementations
['sha1=345'].version
= model
.parse_version('1.1')
187 self
.config
.fetcher
.allow_feed_download('http://foo/Compiler.xml', new_compiler_feed
)
188 self
.config
.fetcher
.allow_feed_download('http://foo/Binary.xml', binary_feed
)
189 self
.config
.fetcher
.allow_feed_download('http://foo/Source.xml', source_feed
)
190 out
, err
= self
.run_0install(['update', 'http://foo/Binary.xml', '--source'])
192 assert 'Compiler.xml: 1.0 -> 1.1' in out
, out
194 # A dependency disappears.
195 new_source_feed
= reader
.load_feed('Source.xml')
196 new_source_feed
.implementations
['sha1=234'].requires
= []
197 self
.config
.fetcher
.allow_feed_download('http://foo/Compiler.xml', new_compiler_feed
)
198 self
.config
.fetcher
.allow_feed_download('http://foo/Binary.xml', binary_feed
)
199 self
.config
.fetcher
.allow_feed_download('http://foo/Source.xml', new_source_feed
)
200 out
, err
= self
.run_0install(['update', 'http://foo/Binary.xml', '--source'])
202 assert 'No longer used: http://foo/Compiler.xml' in out
, out
204 def testConfig(self
):
205 out
, err
= self
.run_0install(['config', '--help'])
206 assert out
.lower().startswith("usage:")
207 assert '--console' in out
209 out
, err
= self
.run_0install(['config'])
211 assert 'full' in out
, out
212 assert 'freshness = 0' in out
, out
213 assert 'help_with_testing = False' in out
, out
215 out
, err
= self
.run_0install(['config', 'help_with_testing'])
216 assert out
== 'False\n', out
218 file_config
= policy
.load_config(handler
.Handler())
220 old_stdout
= sys
.stdout
221 sys
.stdout
= StringIO()
223 cmd
.config
.handle(file_config
, None, [name
])
224 cmd_output
= sys
.stdout
.getvalue()
226 sys
.stdout
= old_stdout
229 assert get_value('freshness') == '30d\n'
230 assert get_value('network_use') == 'full\n'
231 assert get_value('help_with_testing') == 'False\n'
233 cmd
.config
.handle(file_config
, None, ['freshness', '5m'])
234 cmd
.config
.handle(file_config
, None, ['help_with_testing', 'True'])
235 cmd
.config
.handle(file_config
, None, ['network_use', 'minimal'])
236 assert file_config
.freshness
== 5 * 60
237 assert file_config
.network_use
== model
.network_minimal
238 assert file_config
.help_with_testing
== True
240 file_config2
= policy
.load_config(handler
.Handler())
241 assert file_config2
.freshness
== 5 * 60
242 assert file_config2
.network_use
== model
.network_minimal
243 assert file_config2
.help_with_testing
== True
245 cmd
.config
.handle(file_config
, None, ['help_with_testing', 'falsE'])
246 assert file_config
.help_with_testing
== False
248 for period
in ['1s', '2d', '3.5m', '4h', '5d']:
249 secs
= cmd
.config
.TimeInterval
.parse(period
)
250 assert cmd
.config
.TimeInterval
.format(secs
) == period
252 def testAddFeed(self
):
253 binary_iface
= self
.config
.iface_cache
.get_interface('http://foo/Binary.xml')
255 out
, err
= self
.run_0install(['list-feeds', binary_iface
.uri
])
256 assert "(no feeds)" in out
, out
259 out
, err
= self
.run_0install(['add-feed'])
260 assert out
.lower().startswith("usage:")
261 assert 'NEW-FEED' in out
263 sys
.stdin
= Reply('1')
264 assert binary_iface
.extra_feeds
== []
266 out
, err
= self
.run_0install(['add-feed', 'Source.xml'])
268 assert "Add as feed for 'http://foo/Binary.xml'" in out
, out
269 assert len(binary_iface
.extra_feeds
) == 1
271 out
, err
= self
.run_0install(['list-feeds', binary_iface
.uri
])
272 assert "Source.xml" in out
275 out
, err
= self
.run_0install(['remove-feed', 'Source.xml'])
277 assert "Remove as feed for 'http://foo/Binary.xml'" in out
, out
278 assert len(binary_iface
.extra_feeds
) == 0
280 source_feed
= reader
.load_feed('Source.xml')
281 self
.config
.fetcher
.allow_feed_download('http://foo/Source.xml', source_feed
)
282 out
, err
= self
.run_0install(['add-feed', 'http://foo/Source.xml'])
284 assert 'Downloading feed; please wait' in out
, out
285 assert len(binary_iface
.extra_feeds
) == 1
287 def testImport(self
):
288 out
, err
= self
.run_0install(['import'])
289 assert out
.lower().startswith("usage:")
292 stream
= file('6FCF121BE2390E0B.gpg')
293 gpg
.import_key(stream
)
295 sys
.stdin
= Reply('Y\n')
296 out
, err
= self
.run_0install(['import', 'Hello.xml'])
298 assert 'Trusting DE937DD411906ACF7C263B396FCF121BE2390E0B for example.com:8000' in err
, out
301 out
, err
= self
.run_0install(['list', 'foo', 'bar'])
302 assert out
.lower().startswith("usage:")
303 assert 'PATTERN' in out
305 out
, err
= self
.run_0install(['list'])
307 assert '' == out
, repr(out
)
311 out
, err
= self
.run_0install(['list'])
313 assert 'http://example.com:8000/Hello.xml\n' == out
, repr(out
)
315 out
, err
= self
.run_0install(['list', 'foo'])
317 assert '' == out
, repr(out
)
319 out
, err
= self
.run_0install(['list', 'hello'])
321 assert 'http://example.com:8000/Hello.xml\n' == out
, repr(out
)
324 out
, err
= self
.run_0install(['run'])
325 assert out
.lower().startswith("usage:")
326 assert 'URI' in out
, out
328 out
, err
= self
.run_0install(['run', '--dry-run', 'runnable/Runnable.xml', '--help'])
330 assert 'arg-for-runner' in out
, out
331 assert '--help' in out
, out
333 def testDigest(self
):
334 hw
= os
.path
.join(mydir
, 'HelloWorld.tgz')
335 out
, err
= self
.run_0install(['digest', '--algorithm=sha1', hw
])
336 assert out
== 'sha1=3ce644dc725f1d21cfcf02562c76f375944b266a\n', out
339 out
, err
= self
.run_0install(['digest', hw
])
340 assert out
== 'sha1new=290eb133e146635fe37713fd58174324a16d595f\n', out
343 out
, err
= self
.run_0install(['digest', hw
, 'HelloWorld'])
344 assert out
== 'sha1new=491678c37f77fadafbaae66b13d48d237773a68f\n', out
347 tmp
= tempfile
.mkdtemp(prefix
= '0install')
348 out
, err
= self
.run_0install(['digest', tmp
])
349 assert out
== 'sha1new=da39a3ee5e6b4b0d3255bfef95601890afd80709\n', out
353 if __name__
== '__main__':