Merge lp:~bac/charms/oneiric/buildbot-slave/dynamic-relationship into lp:~yellow/charms/oneiric/buildbot-slave/trunk

Proposed by Brad Crittenden
Status: Merged
Merged at revision: 4
Proposed branch: lp:~bac/charms/oneiric/buildbot-slave/dynamic-relationship
Merge into: lp:~yellow/charms/oneiric/buildbot-slave/trunk
Diff against target: 718 lines (+496/-80)
17 files modified
.bzrignore (+3/-0)
config.setuplxc.yaml (+8/-0)
config.yaml (+38/-12)
copyright (+17/-0)
hooks/buildbot-relation-changed (+43/-26)
hooks/buildbot-relation-joined (+28/-0)
hooks/config-changed (+0/-2)
hooks/install (+91/-27)
hooks/start (+0/-5)
hooks/stop (+0/-7)
hooks/tests.py (+51/-0)
revision (+0/-1)
tests/100_buildbot-slave.config.test (+72/-0)
tests/200_buildbot-slave.test (+58/-0)
tests/config.test.yaml (+6/-0)
tests/get-unit-info (+50/-0)
tests/open-port.py (+31/-0)
To merge this branch: bzr merge lp:~bac/charms/oneiric/buildbot-slave/dynamic-relationship
Reviewer Review Type Date Requested Status
Graham Binns (community) Approve
Yellow Squad code Pending
Review via email: mp+91739@code.launchpad.net

Description of the change

Clean up. Merged Francesco's clean up branch.

The files helpers.py and local.py no longer live in the buildbot slave. The One True Version is in the buildbot master. To get access to them, in the buildbot-slave/hooks directory create a symbolic link to the version in the master. This is not ideal and is temporary until we create a branch just for them or a PPA.

To post a comment you must log in.
Revision history for this message
Graham Binns (gmb) wrote :

Thanks for putting this MP together Brad. Here's my comments / TODO list. I figure we should merge lp:~bac/charms/oneiric/buildbot-slave/dynamic-relationship into ~yellow/.../trunk and then fix these things up, so I'm going to mark the MP approved.

TODO list (slave):

[1] Pickle stuff needs removing from hooks/config-changed.
[2]

243 + if buildbot_pkg and 'buildbot-pkg' not in diff.unchanged:

I really hate this double-neg pattern. We should use:

    if buildbot_pkg and 'buildbot-pkg' in diff.added_or_changed:
        ...

(unchanged is a micro-optimisation, AIUI, but added_or_changed is so much clearer to me).

[3] Copyright info still needs to be added to every file after the #!.

[4]

IGNORE THIS POINT. I realised it was nonsense, but can't be bothered to renumber ;).

[5]

681 +from subprocess import CalledProcessError
682 +

Nit: imports not in alphabetical order.

[6]

309 +
310 +log('INSTALL HOOK:')
311 +config = get_config()
312 +
313 +bzr_ = command('bzr')
314 +
315 +buildbot_dir = config.get('installdir')
316 +

These should go in the __name__ == '__main__' block or in main().
`config` should be passed as a parameter to functions as necessary.

[7]

317 +def bzr(source, path):
318 + apt_get_install('bzr')
319 + target = tempfile.mktemp()
320 + bzr('branch', source, target)

Line 320 is going to blow up. We also have a bzr_ command defined at
line 313 for actual bzr commands. We should rename bzr() to bzr_fetch()
or something (and rename all the other fetch functions, too, come to
that).

[8]

416 +class testCommand(unittest.TestCase):

Should be TestCommand.

[9]

424 + def testArguments(self):

This may be a silly time to raise coding standards complaints, but we
seem to be sticking with PEP8 most places. Why not do it here too,
rather than using LP/Zope's hybrid standards? You just know that some
non-LP developer is going to complain about this somewhere down the
line...

[10]

459 === removed file 'revision'

Will Juju let us get away with this?

[11]

466 === added file 'tests/100_buildbot-slave.config.test'
540 === added file 'tests/200_buildbot-slave.test'

(We knew this already but) these need to be Pythonised. Also, last we
checked, they don't actually work, let alone fail.

[12]

662 === added file 'tests/helpers.py'

We probably need a better way of getting necessary helpers into tests/
than just having a copy of helpers.py there. Another symlink mebbe?

review: Approve
12. By Brad Crittenden

Changes from review. Lots of clean up.

Revision history for this message
Brad Crittenden (bac) wrote :

Changes made and pushed. Graham if you could do the merge to trunk that would be swell.

Turns out nothing in the test directory was actually using that helpers.py file, so removing it was a no brainer.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== added file '.bzrignore'
2--- .bzrignore 1970-01-01 00:00:00 +0000
3+++ .bzrignore 2012-02-07 12:39:12 +0000
4@@ -0,0 +1,3 @@
5+revision
6+hooks/helpers.py
7+hooks/local.py
8
9=== added file 'config.setuplxc.yaml'
10--- config.setuplxc.yaml 1970-01-01 00:00:00 +0000
11+++ config.setuplxc.yaml 2012-02-07 12:39:12 +0000
12@@ -0,0 +1,8 @@
13+buildbot-slave:
14+ builders: lucid_lp,lucid_db_lp
15+ script-retrieval-method: bzr_cat
16+ script-url: "http://bazaar.launchpad.net/~gmb/launchpad/neuter-setuplxc/utilities/setuplxc.py"
17+ script-path: setuplxc.py
18+ script-args: "-u launchpad-pqm -e launchpad-pqm@canonical.com -f 'Launchpad PQM' /home/launchpad-pqm/launchpad/"
19+ extra-repository: deb http://us.archive.ubuntu.com/ubuntu/ lucid main universe
20+ buildbot-pkg: buildbot/lucid
21
22=== modified file 'config.yaml'
23--- config.yaml 2012-01-30 19:09:50 +0000
24+++ config.yaml 2012-02-07 12:39:12 +0000
25@@ -1,17 +1,43 @@
26 options:
27+ script-retrieval-method:
28+ description: |
29+ How the script is retrieved. You can use bzr, brz_cat, git,
30+ mercurial or wget.
31+ type: string
32+ default: bzr
33+ script-url:
34+ description: |
35+ The url where this script lives.
36+ type: string
37+ script-path:
38+ description: |
39+ The path of the script that will be executed.
40+ type: string
41+ script-args:
42+ description: |
43+ The script arguments.
44+ type: string
45+ builders:
46+ description: |
47+ The builders that this slave should be a part of. Builders must be
48+ comma-separated.
49+ type: string
50+ buildbot-pkg:
51+ description: |
52+ The package name, possibly with versioning information, to be
53+ installed for buildbot. Example values are 'buildbot',
54+ 'buildbot/lucid', or 'buildbot=0.7.9'.
55+ type: string
56+ default: buildbot
57+ extra-repository:
58+ description: |
59+ The full line to be inserted into an apt sources.list for a repository.
60+ If called multiple times the new repository will be added but
61+ ones added previously will not be removed. An example would be:
62+ deb http://us.archive.ubuntu.com/ubuntu/ lucid main universe
63+ type: string
64 installdir:
65 description: |
66 The directory where the Buildbot slave will be installed.
67 type: string
68- default: /tmp/buildbot
69- name:
70- description: |
71- The name of this slave.
72- type: string
73- default: example-slave
74- passwd:
75- description: |
76- The password of this slave.
77- type: string
78- default: pass
79-
80+ default: /tmp/buildslave
81
82=== added file 'copyright'
83--- copyright 1970-01-01 00:00:00 +0000
84+++ copyright 2012-02-07 12:39:12 +0000
85@@ -0,0 +1,17 @@
86+Format: http://dep.debian.net/deps/dep5/
87+
88+Files: *
89+Copyright: Copyright 2012, Canonical Ltd., All Rights Reserved.
90+License: GPL-3
91+ This program is free software: you can redistribute it and/or modify
92+ it under the terms of the GNU General Public License as published by
93+ the Free Software Foundation, either version 3 of the License, or
94+ (at your option) any later version.
95+ .
96+ This program is distributed in the hope that it will be useful,
97+ but WITHOUT ANY WARRANTY; without even the implied warranty of
98+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
99+ GNU General Public License for more details.
100+ .
101+ You should have received a copy of the GNU General Public License
102+ along with this program. If not, see <http://www.gnu.org/licenses/>.
103
104=== modified file 'hooks/buildbot-relation-changed'
105--- hooks/buildbot-relation-changed 2012-01-31 01:50:27 +0000
106+++ hooks/buildbot-relation-changed 2012-02-07 12:39:12 +0000
107@@ -1,26 +1,43 @@
108-#!/bin/bash
109-# This must be renamed to the name of the relation. The goal here is to
110-# affect any change needed by relationships being formed, modified, or broken
111-# This script should be idempotent.
112-juju-log $JUJU_REMOTE_UNIT modified its settings
113-
114-BUILDBOT_DIR=`config-get installdir`
115-NAME=`config-get name`
116-PASSWD=`config-get passwd`
117-HOST=`relation-get private-address`
118-
119-juju-log "--> stop"
120-# The exit code is 0 even if the buildslave was not running.
121-buildslave stop $BUILDBOT_DIR
122-juju-log "<-- stop"
123-
124-juju-log "--> create .tac"
125-if [ -e $BUILDBOT_DIR/buildbot.tac ]; then
126- rm $BUILDBOT_DIR/buildbot.tac
127-fi
128-buildslave create-slave $BUILDBOT_DIR $HOST $NAME $PASSWD
129-juju-log "<-- create .tac"
130-
131-juju-log "--> start"
132-buildslave start $BUILDBOT_DIR
133-juju-log "<-- start"
134+#!/usr/bin/env python
135+
136+# Copyright 2012 Canonical Ltd. This software is licensed under the
137+# GNU Affero General Public License version 3 (see the file LICENSE).
138+
139+import sys
140+
141+from helpers import (
142+ get_config,
143+ log,
144+ relation_get,
145+ )
146+from local import (
147+ buildslave_start,
148+ buildslave_stop,
149+ create_slave,
150+ )
151+
152+
153+def restart_buildslave(name, passwd, host, buildbot_dir):
154+ log('Stopping buildbot slave.')
155+ buildslave_stop()
156+ log('Creating buildbot slave: {}@{} (passwd={}).'.format(
157+ name, host, passwd))
158+ create_slave(name, passwd, host=host, buildbot_dir=buildbot_dir)
159+ log('Starting buildbot slave.')
160+ return buildslave_start()
161+
162+
163+def main():
164+ name = relation_get('name')
165+ passwd = relation_get('passwd')
166+ if name and passwd:
167+ # We heard back from the master and we are ready to start.
168+ config = get_config()
169+ buildbot_dir = config.get('installdir')
170+ host = relation_get('private-address')
171+ sys.exit(restart_buildslave(name, passwd, host, buildbot_dir))
172+
173+
174+if __name__ == '__main__':
175+ log('BUILDBOT-RELATION-CHANGED HOOK:')
176+ main()
177
178=== added file 'hooks/buildbot-relation-joined'
179--- hooks/buildbot-relation-joined 1970-01-01 00:00:00 +0000
180+++ hooks/buildbot-relation-joined 2012-02-07 12:39:12 +0000
181@@ -0,0 +1,28 @@
182+#!/usr/bin/env python
183+
184+# Copyright 2012 Canonical Ltd. This software is licensed under the
185+# GNU Affero General Public License version 3 (see the file LICENSE).
186+
187+from helpers import (
188+ get_config,
189+ log,
190+ relation_set,
191+ )
192+
193+
194+def send_builders(builders):
195+ log('Sending builders to the master: {}'.format(builders))
196+ relation_set(builders=builders)
197+
198+
199+def main():
200+ config = get_config()
201+ builders = config.get('builders')
202+ if builders:
203+ # This is the first step of the handshake.
204+ send_builders(builders)
205+
206+
207+if __name__ == '__main__':
208+ log('BUILDBOT-RELATION-JOINED HOOK:')
209+ main()
210
211=== added file 'hooks/config-changed'
212--- hooks/config-changed 1970-01-01 00:00:00 +0000
213+++ hooks/config-changed 2012-02-07 12:39:12 +0000
214@@ -0,0 +1,47 @@
215+#!/usr/bin/env python
216+
217+# Copyright 2012 Canonical Ltd. This software is licensed under the
218+# GNU Affero General Public License version 3 (see the file LICENSE).
219+
220+from helpers import (
221+ apt_get_install,
222+ command,
223+ DictDiffer,
224+ get_config,
225+ install_extra_repository,
226+ log,
227+ )
228+from local import (
229+ config_json,
230+ create_slave,
231+ )
232+
233+
234+def main():
235+
236+ config = get_config()
237+ prev_config = config_json.get()
238+
239+ diff = DictDiffer(config, prev_config)
240+ log("Differences:")
241+ log(str(diff))
242+
243+ buildbot_pkg = config.get('buildbot-pkg')
244+ extra_repo = config.get('extra-repository')
245+ buildbot_dir = config.get('installdir')
246+
247+ if extra_repo and 'extra-repository' in diff.added_or_changed:
248+ install_extra_repository(extra_repo)
249+
250+ if buildbot_pkg and 'buildbot-pkg' not in diff.unchanged:
251+ log('Installing ' + buildbot_pkg)
252+ apt_get_install(buildbot_pkg)
253+ log('Creating initial buildbot slave in ' + buildbot_dir)
254+ create_slave('temporary', 'temporary', buildbot_dir=buildbot_dir)
255+
256+ config_json.set(config)
257+
258+
259+if __name__ == '__main__':
260+ log('CONFIG-CHANGED HOOK:')
261+ main()
262
263=== removed file 'hooks/config-changed'
264--- hooks/config-changed 2012-01-30 19:09:50 +0000
265+++ hooks/config-changed 1970-01-01 00:00:00 +0000
266@@ -1,2 +0,0 @@
267-#!/bin/bash
268-# Hook for handling config changes.
269
270=== modified file 'hooks/install'
271--- hooks/install 2012-01-31 01:50:27 +0000
272+++ hooks/install 2012-02-07 12:39:12 +0000
273@@ -1,27 +1,91 @@
274-#!/bin/bash
275-# Here do anything needed to install the service
276-# i.e. apt-get install -y foo or bzr branch http://myserver/mycode /srv/webroot
277-set -eux # -x for verbose logging to juju debug-log
278-
279-juju-log "--> install packages"
280-BUILDBOT_DIR=`config-get installdir`
281-apt-get install -y buildbot
282-mkdir -p $BUILDBOT_DIR
283-juju-log "<-- install packages"
284-
285-juju-log "--> create slave"
286-NAME=`config-get name`
287-PASSWD=`config-get passwd`
288-
289-# We set HOST to localhost for now because we can't get the actual host
290-# until we're joined to the buildbot-master instance.
291-HOST="localhost"
292-
293-juju-log "buildslave create-slave $BUILDBOT_DIR $HOST $NAME $PASSWD"
294-buildslave create-slave $BUILDBOT_DIR $HOST $NAME $PASSWD
295-juju-log "<-- create slave"
296-
297-# This is where we would set info/admin and info/host. Not sure what
298-# is pertinent, but the default is a bit lame in the juju case.
299-
300-# This is where we would run something like setuplxc.
301+#!/usr/bin/env python
302+
303+# Copyright 2012 Canonical Ltd. This software is licensed under the
304+# GNU Affero General Public License version 3 (see the file LICENSE).
305+
306+from helpers import (
307+ apt_get_install,
308+ command,
309+ get_config,
310+ log,
311+ run,
312+ )
313+import os
314+import shlex
315+import subprocess
316+import sys
317+import tempfile
318+
319+
320+bzr = command('bzr')
321+
322+
323+def bzr_fetch(source, path):
324+ apt_get_install('bzr')
325+ target = tempfile.mktemp()
326+ bzr('branch', source, target)
327+ return os.path.join(target, path)
328+
329+
330+def bzr_cat(source, path):
331+ apt_get_install('bzr')
332+ content = bzr('--no-plugins', 'cat', source)
333+ target = os.path.join('/tmp', path)
334+ with open(target, 'w') as f:
335+ f.write(content)
336+ return target
337+
338+
339+def wget(source, path):
340+ target = os.path.join('/tmp', path)
341+ command('wget', '-O', target, source)
342+ return target
343+
344+
345+def hg_fetch(source, target):
346+ apt_get_install('mercurial')
347+ target = tempfile.mktemp()
348+ command('hg', 'clone', source, target)
349+ return os.path.join(target, path)
350+
351+
352+def git_fetch(source, target):
353+ apt_get_install('git')
354+ target = tempfile.mktemp()
355+ command('git', 'clone', source, target)
356+ return os.path.join(target, path)
357+
358+
359+METHODS = {
360+ 'bzr': bzr_fetch,
361+ 'bzr_cat': bzr_cat,
362+ 'wget': wget,
363+ 'hg': hg_fetch,
364+ 'git': git_fetch,
365+ }
366+
367+
368+def handle_script(retrieve, url, path, args):
369+ log('Retrieving script: {}.'.format(url))
370+ script = retrieve(url, path)
371+ log('Changing script mode.')
372+ command('chmod', '+x', script)
373+ log('Executing script: {}.'.format(script))
374+ return subprocess.call([script] + shlex.split(str(args)))
375+
376+
377+def main():
378+
379+ config = get_config()
380+ method = config.get('script-retrieval-method')
381+ url = config.get('script-url')
382+ path = config.get('script-path')
383+ args = config.get('script-args')
384+ retrieve = METHODS.get(method)
385+ if retrieve and url and path:
386+ sys.exit(handle_script(retrieve, url, path, args))
387+
388+
389+if __name__ == '__main__':
390+ log('INSTALL HOOK:')
391+ main()
392
393=== removed file 'hooks/start'
394--- hooks/start 2012-01-30 19:09:50 +0000
395+++ hooks/start 1970-01-01 00:00:00 +0000
396@@ -1,5 +0,0 @@
397-#!/bin/bash
398-# Here put anything that is needed to start the service.
399-# Note that currently this is run directly after install
400-# i.e. 'service apache2 start'
401-
402
403=== removed file 'hooks/stop'
404--- hooks/stop 2012-01-30 19:09:50 +0000
405+++ hooks/stop 1970-01-01 00:00:00 +0000
406@@ -1,7 +0,0 @@
407-#!/bin/bash
408-# This will be run when the service is being torn down, allowing you to disable
409-# it in various ways..
410-# For example, if your web app uses a text file to signal to the load balancer
411-# that it is live... you could remove it and sleep for a bit to allow the load
412-# balancer to stop sending traffic.
413-# rm /srv/webroot/server-live.txt && sleep 30
414
415=== added file 'hooks/tests.py'
416--- hooks/tests.py 1970-01-01 00:00:00 +0000
417+++ hooks/tests.py 2012-02-07 12:39:12 +0000
418@@ -0,0 +1,51 @@
419+# Copyright 2012 Canonical Ltd. This software is licensed under the
420+# GNU Affero General Public License version 3 (see the file LICENSE).
421+
422+from subprocess import CalledProcessError
423+import unittest
424+
425+from helpers import command
426+
427+
428+class TestCommand(unittest.TestCase):
429+
430+ def test_simple_command(self):
431+ # Creating a simple command (ls) works and running the command
432+ # produces a string.
433+ ls = command('/bin/ls')
434+ self.assertIsInstance(ls(), str)
435+
436+ def test_arguments(self):
437+ # Arguments can be passed to commands.
438+ ls = command('/bin/ls')
439+ self.assertIn('Usage:', ls('--help'))
440+
441+ def test_missing_executable(self):
442+ # If the command does not exist, an OSError (No such file or
443+ # directory) is raised.
444+ bad = command('this command does not exist')
445+ with self.assertRaises(OSError) as info:
446+ bad()
447+ self.assertEqual(2, info.exception.errno)
448+
449+ def test_error(self):
450+ # If the command returns a non-zero exit code, an exception is raised.
451+ ls = command('/bin/ls')
452+ with self.assertRaises(CalledProcessError):
453+ ls('--not a valid switch')
454+
455+ def test_baked_in_arguments(self):
456+ # Arguments can be passed when creating the command as well as when
457+ # executing it.
458+ ll = command('/bin/ls', '-l')
459+ self.assertIn('rw', ll()) # Assumes a file is r/w in the pwd.
460+ self.assertIn('Usage:', ll('--help'))
461+
462+ def test_quoting(self):
463+ # There is no need to quote special shell characters in commands.
464+ ls = command('/bin/ls')
465+ ls('--help', '>')
466+
467+
468+if __name__ == '__main__':
469+ unittest.main()
470
471=== removed file 'revision'
472--- revision 2012-01-31 01:50:27 +0000
473+++ revision 1970-01-01 00:00:00 +0000
474@@ -1,1 +0,0 @@
475-19
476
477=== added directory 'tests'
478=== added file 'tests/100_buildbot-slave.config.test'
479--- tests/100_buildbot-slave.config.test 1970-01-01 00:00:00 +0000
480+++ tests/100_buildbot-slave.config.test 2012-02-07 12:39:12 +0000
481@@ -0,0 +1,72 @@
482+#!/bin/sh
483+
484+# Copyright 2012 Canonical Ltd. This software is licensed under the
485+# GNU Affero General Public License version 3 (see the file LICENSE).
486+
487+set -e
488+
489+teardown() {
490+ juju destroy-service buildbot-slave
491+ if [ -n "$datadir" ] ; then
492+ if [ -f $datadir/passed ]; then
493+ rm -r $datadir
494+ else
495+ echo $datadir preserved
496+ fi
497+ fi
498+}
499+trap teardown EXIT
500+
501+juju deploy --repository=$PWD/../ local:buildbot-slave
502+juju expose buildbot-slave
503+
504+for try in `seq 1 600` ; do
505+ slave_host=`juju status | tests/get-unit-info buildbot-slave public-address`
506+ if [ -z "$slave_host" ] ; then
507+ sleep 1
508+ else
509+ break
510+ fi
511+done
512+
513+if [ -z "$slave_host" ] ; then
514+ echo ERROR: status timed out
515+ exit 1
516+fi
517+
518+datadir=`mktemp -d ${TMPDIR:-/tmp}/wget.test.XXXXXXX`
519+echo INFO: datadir=$datadir
520+
521+#slave_connected=$(
522+# wget --tries=100 --timeout=6 http://$slave_host:9000 -O - \
523+# -a $datadir/wget.log | grep -q 'UP!')
524+
525+assert_is_listening() {
526+ local port=$1
527+ listening=""
528+ for try in `seq 1 10` ; do
529+ if ! nc $slave_host $port < /dev/null ; then
530+ continue
531+ fi
532+ listening="yes"
533+ break
534+ done
535+
536+ if [ -z "$listening" ] ; then
537+ echo "FAIL: not listening on port $port after 10 retries"
538+ return 1
539+ else
540+ echo "PASS: listening on port $port"
541+ return 0
542+ fi
543+}
544+
545+assert_is_listening 9000
546+
547+touch $datadir/passed
548+
549+trap - EXIT
550+teardown
551+
552+echo INFO: PASS
553+exit 0
554
555=== added file 'tests/200_buildbot-slave.test'
556--- tests/200_buildbot-slave.test 1970-01-01 00:00:00 +0000
557+++ tests/200_buildbot-slave.test 2012-02-07 12:39:12 +0000
558@@ -0,0 +1,58 @@
559+#!/bin/sh
560+
561+# Copyright 2012 Canonical Ltd. This software is licensed under the
562+# GNU Affero General Public License version 3 (see the file LICENSE).
563+
564+set -e
565+
566+teardown() {
567+ juju destroy-service buildbot-slave
568+ if [ -n "$datadir" ] ; then
569+ if [ -f $datadir/passed ]; then
570+ rm -r $datadir
571+ else
572+ echo $datadir preserved
573+ fi
574+ fi
575+}
576+trap teardown EXIT
577+
578+
579+juju deploy buildbot-master
580+juju deploy buildbot-slave
581+juju add-relation buildbot-slave buildbot-master
582+juju expose buildbot-master
583+
584+for try in `seq 1 600` ; do
585+ master_host=`juju status | tests/get-unit-info buildbot-master public-address`
586+ if [ -z "$master_host" ] ; then
587+ sleep 1
588+ else
589+ break
590+ fi
591+done
592+
593+if [ -z "$master_host" ] ; then
594+ echo ERROR: status timed out
595+ exit 1
596+fi
597+
598+datadir=`mktemp -d ${TMPDIR:-/tmp}/wget.test.XXXXXXX`
599+echo INFO: datadir=$datadir
600+
601+slave_connected=$(
602+ wget --tries=100 --timeout=6 http://$master_host:8010/buildslaves -O - \
603+ -a $datadir/wget.log | grep -q 'Idle')
604+
605+if [ -z $slave_connected ]; then
606+ echo "ERROR: The slave is not connected after 600 seconds."
607+ exit 1
608+fi
609+
610+touch $datadir/passed
611+
612+trap - EXIT
613+teardown
614+
615+echo INFO: PASS
616+exit 0
617
618=== added file 'tests/config.test.yaml'
619--- tests/config.test.yaml 1970-01-01 00:00:00 +0000
620+++ tests/config.test.yaml 2012-02-07 12:39:12 +0000
621@@ -0,0 +1,6 @@
622+buildbot-slave:
623+ installdir: /tmp/buildbot
624+ name: example-slave
625+ passwd: pass
626+ script-retrieval-method: bzr
627+ script-url: "http://bazaar.launchpad.net/~gmb/charms/oneiric/buildbot-slave/look-we-have-tests/tests/open-port.py"
628
629=== added file 'tests/get-unit-info'
630--- tests/get-unit-info 1970-01-01 00:00:00 +0000
631+++ tests/get-unit-info 2012-02-07 12:39:12 +0000
632@@ -0,0 +1,50 @@
633+#!/usr/bin/python
634+
635+# Copyright 2012 Canonical Ltd. This software is licensed under the
636+# GNU Affero General Public License version 3 (see the file LICENSE).
637+
638+# machines:
639+# 0: {dns-name: ec2-50-17-84-127.compute-1.amazonaws.com, instance-id: i-8c5c3fec}
640+# 1: {dns-name: ec2-184-73-102-113.compute-1.amazonaws.com, instance-id: i-14a2c174}
641+# 2: {dns-name: ec2-75-101-184-93.compute-1.amazonaws.com, instance-id: i-e0a2c180}
642+# services:
643+# mysql:
644+# charm: local:mysql-11
645+# relations: {db: wordpress}
646+# units:
647+# mysql/0:
648+# machine: 2
649+# relations:
650+# db: {state: up}
651+# state: started
652+# wordpress:
653+# charm: local:wordpress-31
654+# exposed: true
655+# relations: {db: mysql}
656+# units:
657+# wordpress/0:
658+# machine: 1
659+# open-ports: []
660+# relations: {}
661+# state: null
662+
663+import yaml
664+import sys
665+from subprocess import Popen, PIPE
666+
667+
668+def main():
669+ d = yaml.safe_load(Popen(['juju','status'],stdout=PIPE).stdout)
670+ srv = d.get("services", {}).get(sys.argv[1])
671+ if srv is None:
672+ return
673+ units = srv.get("units", {})
674+ if units is None:
675+ return
676+ item = units.items()[0][1].get(sys.argv[2])
677+ if item is None:
678+ return
679+ print item
680+
681+if __name__ == "__main__":
682+ main()
683
684=== added file 'tests/open-port.py'
685--- tests/open-port.py 1970-01-01 00:00:00 +0000
686+++ tests/open-port.py 2012-02-07 12:39:12 +0000
687@@ -0,0 +1,31 @@
688+#!/usr/bin/env python
689+
690+# Copyright 2012 Canonical Ltd. This software is licensed under the
691+# GNU Affero General Public License version 3 (see the file LICENSE).
692+
693+# A little python script to open a port on the buildslave so that we can
694+# test that it's actually deployed successfully.
695+
696+import subprocess
697+import SimpleHTTPServer
698+import SocketServer
699+
700+PORT = 9000
701+
702+simple_html = """
703+<html>
704+ <head>
705+ <title>Here's some HTML</title>
706+ </head>
707+ <body><p>The slave is UP!</p></body>
708+</html>
709+"""
710+
711+with open('/tmp/index.html', 'w') as index_file:
712+ index_file.write(simple_html)
713+
714+subprocess.call(['open-port', '9000/TCP'])
715+Handler = SimpleHTTPServer.SimpleHTTPRequestHandler
716+httpd = SocketServer.TCPServer(("", PORT), Handler)
717+#httpd.serve_forever()
718+print "HERE I AM!!!"

Subscribers

People subscribed via source and target branches

to all changes: