1 # Copyright (C) 2006, Thomas Leonard
2 # See http://0install.net/0compile.html
4 import sys
, os
, __main__
5 from logging
import info
6 from xml
.dom
import minidom
, XMLNS_NAMESPACE
8 from zeroinstall
.injector
import model
, selections
9 from zeroinstall
.injector
.iface_cache
import iface_cache
10 from zeroinstall
.injector
.policy
import Policy
11 from zeroinstall
import SafeException
16 "setup [--no-prompt] [ SOURCE-URI [ DIR ] ]"
18 if args
and args
[0] == '--no-prompt':
23 if not os
.path
.isfile(ENV_FILE
):
24 raise SafeException("Run 0compile from a directory containing a '%s' file, or "
25 "specify a source URI as an argument." % ENV_FILE
)
28 interface
= buildenv
.interface
34 create_dir
= os
.path
.basename(interface
)
35 if create_dir
.endswith('.xml'):
36 create_dir
= create_dir
[:-4]
37 assert '/' not in create_dir
38 assert create_dir
is not '.'
44 raise __main__
.UsageError()
46 interface
= model
.canonical_iface_uri(args
[0])
48 if create_dir
and os
.path
.exists(create_dir
):
49 raise SafeException("Directory '%s' already exists." % create_dir
)
51 setup(interface
, create_dir
, prompt
)
53 def setup(interface
, create_dir
, prompt
):
57 gui_options
= '--offline'
59 # Prompt user to choose versions
60 if os
.spawnvp(os
.P_WAIT
, '0launch', ['0launch', gui_options
, '--source', '--download-only', interface
]):
61 raise SafeException('Failed to select source files.')
63 # Get the chosen versions
64 policy
= Policy(interface
, src
= True)
69 raise Exception('Internal error: required source components not found!')
71 root_iface
= iface_cache
.get_interface(policy
.root
)
72 impl
= policy
.implementation
[root_iface
]
73 min_version
= parse_version(impl
.metadata
.get(XMLNS_0COMPILE
+ ' min-version', None))
74 if min_version
and min_version
> parse_version(__main__
.version
):
75 raise SafeException("%s-%s requires 0compile >= %s, but we are only version %s" %
76 (root_iface
.get_name(), impl
.get_version(), format_version(min_version
), __main__
.version
))
79 if os
.path
.exists(create_dir
):
80 raise SafeException("Directory '%s' already exists." % create_dir
)
85 save_environment(policy
)
87 def save_environment(policy
):
89 if os
.path
.exists(ENV_FILE
):
90 # Don't lose existing download URL
91 download_base
= BuildEnv().download_base_url
93 sels
= selections
.Selections(policy
)
95 # Copy mappings metadata
96 for iface
, impl
in policy
.implementation
.iteritems():
97 mappings
= impl
.metadata
.get(XMLNS_0COMPILE
+ ' lib-mappings', None)
99 sels
.selections
[iface
.uri
].attrs
[XMLNS_0COMPILE
+ ' lib-mappings'] = mappings
102 root
= doc
.documentElement
104 root
.setAttributeNS(XMLNS_NAMESPACE
, 'xmlns:compile', XMLNS_0COMPILE
)
107 root
.setAttributeNS(XMLNS_0COMPILE
, 'compile:download-base-url', download_base
)
109 impl
= policy
.implementation
[iface_cache
.get_interface(policy
.root
)]
110 command
= impl
.metadata
.get(XMLNS_0COMPILE
+ ' command', None)
111 if not command
: raise SafeException("Missing 'compile:command' attribute on <implementation>.")
112 root
.setAttributeNS(XMLNS_0COMPILE
, 'compile:command', command
)
114 for name
in ['binary-main', 'binary-lib-mappings', 'metadir', 'dup-src']:
115 value
= impl
.metadata
.get(XMLNS_0COMPILE
+ ' ' + name
, None)
117 root
.setAttributeNS(XMLNS_0COMPILE
, 'compile:' + name
, value
)
119 doc
.writexml(file(ENV_FILE
, 'w'), addindent
= ' ', newl
= '\n')
121 __main__
.commands
.append(do_setup
)