2 from zeroinstall
.injector
import gpg
3 from zeroinstall
import SafeException
4 from optparse
import OptionParser
7 from logging
import info
, debug
12 parser
= OptionParser(usage
="usage: %prog [options] interface")
13 parser
.add_option("--add-version", help="add a new implementation", action
='store', metavar
='VERSION')
14 parser
.add_option("--archive-url", help="add archive at this URL", action
='store', metavar
='URL')
15 parser
.add_option("--archive-file", help="local copy of archive-url", action
='store', metavar
='FILE')
16 parser
.add_option("--archive-extract", help="subdirectory of archive to extract", action
='store', metavar
='DIR')
17 parser
.add_option("-e", "--edit", help="edit with $EDITOR", action
='store_true')
18 parser
.add_option("-g", "--gpgsign", help="add a GPG signature block", action
='store_true')
19 parser
.add_option("-k", "--key", help="key to use for signing")
20 parser
.add_option("-l", "--local", help="create feed from local interface")
21 parser
.add_option("--manifest-algorithm", help="select algorithm for manifests", action
='store', metavar
='ALG')
22 parser
.add_option("--set-interface-uri", help="set interface URI", action
='store', metavar
='URI')
23 parser
.add_option("--set-id", help="set implementation ID", action
='store', metavar
='DIGEST')
24 parser
.add_option("--set-main", help="set main executable", action
='store', metavar
='EXEC')
25 parser
.add_option("--set-arch", help="set architecture", action
='store', metavar
='ARCH')
26 parser
.add_option("--set-released", help="set release date", action
='store', metavar
='DATE')
27 parser
.add_option("--set-stability", help="set stability", action
='store', metavar
='STABILITY')
28 parser
.add_option("--set-version", help="set version number", action
='store', metavar
='VERSION')
29 parser
.add_option("-s", "--stable", help="mark testing version stable", action
='store_true')
30 parser
.add_option("-x", "--xmlsign", help="add an XML signature block", action
='store_true')
31 parser
.add_option("-u", "--unsign", help="remove any signature", action
='store_true')
32 parser
.add_option("-v", "--verbose", help="more verbose output", action
='count')
33 parser
.add_option("-V", "--version", help="display version information", action
='store_true')
35 (options
, args
) = parser
.parse_args()
40 print "0publish (zero-install) " + version
41 print "Copyright (C) 2005 Thomas Leonard"
42 print "This program comes with ABSOLUTELY NO WARRANTY,"
43 print "to the extent permitted by law."
44 print "You may redistribute copies of this program"
45 print "under the terms of the GNU General Public License."
46 print "For more information about these matters, see the file named COPYING."
51 logger
= logging
.getLogger()
52 if options
.verbose
== 1:
53 logger
.setLevel(logging
.INFO
)
55 logger
.setLevel(logging
.DEBUG
)
64 ans
= raw_input(q
+ " [Y/N] ").lower()
65 if ans
in ('y', 'yes'): return True
66 if ans
in ('n', 'no'): return False
69 # Load or create the starting data...
71 if os
.path
.exists(interface
):
72 contents
= file(interface
).read()
73 data
, sign_fn
, key
= signing
.check_signature(interface
)
76 if os
.path
.exists(options
.local
):
77 data
= create
.create_from_local(options
.local
)
78 sign_fn
= signing
.sign_unsigned
83 raise Exception("File '%s' does not exist." % options
.local
)
85 if confirm("Interface file '%s' does not exist. Create it?" % interface
):
86 from create
import create
87 data
= create(interface
)
88 sign_fn
= signing
.sign_unsigned
94 debug("Original data: %s", data
)
95 info("Original signing method: %s", sign_fn
.__name
__)
96 info("Original key: %s", key
)
103 # Validate the input...
105 validator
.check(data
)
107 except validator
.InvalidInterface
, ex
:
108 print "Invalid interface: " + str(ex
)
111 ans
= raw_input("Interface is invalid. (E)dit or (A)bort?").lower()
112 if ans
in ('e', 'edit'):
113 data
= edit
.edit(data
)
114 options
.edit
= False # Don't edit twice
116 if ans
in ('a', 'abort'): sys
.exit(1)
120 sign_fn
= signing
.sign_xml
122 sign_fn
= signing
.sign_unsigned
124 sign_fn
= signing
.sign_plain
126 print "Changing key from '%s' to '%s'" % (key
, options
.key
)
128 if options
.set_interface_uri
:
130 data
= release
.set_interface_uri(data
, options
.set_interface_uri
)
131 if options
.add_version
:
133 data
= release
.add_version(data
, options
.add_version
)
134 if options
.set_id
or options
.set_version
or options
.set_released
or \
135 options
.set_stability
or options
.set_arch
or options
.set_main
:
137 data
= release
.make_release(data
, options
.set_id
,
138 options
.set_version
, options
.set_released
, options
.set_stability
,
139 options
.set_main
, options
.set_arch
)
142 data
= stable
.mark_stable(data
)
143 if options
.archive_url
:
145 data
= archive
.add_archive(data
, options
.archive_url
, options
.archive_file
, options
.archive_extract
, options
.manifest_algorithm
)
146 elif options
.archive_file
or options
.archive_extract
:
147 raise Exception('Must use --archive-uri option')
150 data
= merge
.merge(data
, options
.local
)
152 data
= edit
.edit(data
)
155 # Validate the result...
157 validator
.check(data
)
159 except validator
.InvalidInterface
, ex
:
160 print "Invalid interface: " + str(ex
)
163 ans
= raw_input("Interface is invalid. (E)dit or (A)bort?").lower()
164 if ans
in ('e', 'edit'):
165 data
= edit
.edit(data
)
167 if ans
in ('a', 'abort'): sys
.exit(1)
170 if (old_data
== data
and sign_fn
== old_sign_fn
and key
== old_key
) and not force_save
:
171 print "Interface unchanged. Not writing."
175 if not data
.endswith('\n'): data
+= '\n'
176 sign_fn(interface
, data
, key
)
178 info("Wrote '%S'", interface
)
180 if sign_fn
!= signing
.sign_unsigned
:
181 # Read it back in to find out what key we signed it with
182 # and ensure that the key has been exported
183 contents
= file(interface
).read()
184 saved_data
, saved_sign_fn
, saved_key
= signing
.check_signature(interface
)
185 assert saved_data
== data
186 assert saved_sign_fn
== sign_fn
187 signing
.export_key(os
.path
.dirname(interface
), saved_key
)
188 except SafeException
, ex
:
189 if options
.verbose
: raise
190 print >>sys
.stderr
, ex