[GRASS-SVN] r50024 - grass/trunk/scripts/g.extension
svn_grass at osgeo.org
svn_grass at osgeo.org
Sun Jan 1 12:25:23 EST 2012
Author: martinl
Date: 2012-01-01 09:25:23 -0800 (Sun, 01 Jan 2012)
New Revision: 50024
Modified:
grass/trunk/scripts/g.extension/g.extension.py
Log:
g.extension: initial support for toolboxes
Modified: grass/trunk/scripts/g.extension/g.extension.py
===================================================================
--- grass/trunk/scripts/g.extension/g.extension.py 2012-01-01 16:57:39 UTC (rev 50023)
+++ grass/trunk/scripts/g.extension/g.extension.py 2012-01-01 17:25:23 UTC (rev 50024)
@@ -4,7 +4,7 @@
#
# MODULE: g.extension
# AUTHOR(S): Markus Neteler
-# Pythonized by Martin Landa
+# Pythonized & upgraded for GRASS 7 by Martin Landa
# PURPOSE: Tool to download and install extensions from GRASS Addons SVN into
# local GRASS installation
# COPYRIGHT: (C) 2009-2011 by Markus Neteler, and the GRASS Development Team
@@ -100,6 +100,11 @@
#% description: Force removal when uninstalling extension (operation=remove)
#% guisection: Remove
#%end
+#%flag
+#% key: t
+#% description: Operate on toolboxes instead of single modules
+#% suppress_required: yes
+#%end
import os
import sys
@@ -151,6 +156,33 @@
# list installed extensions
def get_installed_extensions(force = False):
+ if flags['t']:
+ return get_installed_toolboxes(force)
+
+ return get_installed_modules(force)
+
+def get_installed_toolboxes(force = False):
+ fXML = os.path.join(options['prefix'], 'toolboxes.xml')
+ if not os.path.exists(fXML):
+ write_xml_toolboxes(fXML)
+
+ # read XML file
+ fo = open(fXML, 'r')
+ try:
+ tree = etree.fromstring(fo.read())
+ except:
+ os.remove(fXML)
+ write_xml_toolboxes(fXML)
+ return []
+ fo.close()
+
+ ret = list()
+ for tnode in tree.findall('toolbox'):
+ ret.append(tnode.get('code'))
+
+ return ret
+
+def get_installed_modules(force = False):
fXML = os.path.join(options['prefix'], 'modules.xml')
if not os.path.exists(fXML):
if force:
@@ -177,15 +209,75 @@
# list extensions (read XML file from grass.osgeo.org/addons)
def list_available_extensions():
- mlist = list()
+ if flags['t']:
+ grass.message(_("List of available extensions (toolboxes):"))
+ tlist = list_available_toolboxes()
+ for toolbox_code, toolbox_data in tlist.iteritems():
+ if flags['g']:
+ print 'toolbox_name=' + toolbox_data['name']
+ print 'toolbox_code=' + toolbox_code
+ else:
+ print '%s (%s)' % (toolbox_data['name'], toolbox_code)
+ if flags['c'] or flags['g']:
+ list_available_modules(toolbox_data['modules'])
+ else:
+ if toolbox_data['modules']:
+ print os.linesep.join(map(lambda x: '* ' + x, toolbox_data['modules']))
+ else:
+ grass.message(_("List of available extensions (modules):"))
+ list_available_modules()
+
+def list_available_toolboxes():
+ tdict = dict()
+ url = "http://grass.osgeo.org/addons/grass%s/toolboxes.xml" % version[0]
+ try:
+ f = urlopen(url)
+ tree = etree.fromstring(f.read())
+ for tnode in tree.findall('toolbox'):
+ mlist = list()
+ clist = list()
+ tdict[tnode.get('code')] = { 'name' : tnode.get('name'),
+ 'correlate' : clist,
+ 'modules' : mlist }
+
+ for cnode in tnode.findall('correlate'):
+ clist.append(cnode.get('name'))
+
+ for mnode in tnode.findall('task'):
+ mlist.append(mnode.get('name'))
+ except HTTPError:
+ grass.fatal(_("Unable to fetch metadata file"))
+
+ return tdict
+
+def get_toolbox_modules(name):
+ tlist = list()
+
+ url = "http://grass.osgeo.org/addons/grass%s/toolboxes.xml" % version[0]
+ try:
+ f = urlopen(url)
+ tree = etree.fromstring(f.read())
+ for tnode in tree.findall('toolbox'):
+ if name == tnode.get('code'):
+ for mnode in tnode.findall('task'):
+ tlist.append(mnode.get('name'))
+ break
+ except HTTPError:
+ grass.fatal(_("Unable to fetch metadata file"))
+
+ return tlist
+
+def list_available_modules(mlist = None):
# try to download XML metadata file first
- url = "http://grass.osgeo.org/addons/grass%s.xml" % grass.version()['version'].split('.')[0]
+ url = "http://grass.osgeo.org/addons/grass%s.xml" % version[0]
try:
f = urlopen(url)
tree = etree.fromstring(f.read())
for mnode in tree.findall('task'):
- name = mnode.get('name')
+ name = mnode.get('name').strip()
+ if mlist and name not in mlist:
+ continue
if flags['c'] or flags['g']:
desc = mnode.find('description').text
if not desc:
@@ -199,17 +291,16 @@
print 'description=' + desc
print 'keywords=' + keyw
elif flags['c']:
+ if mlist:
+ print '*',
print name + ' - ' + desc
else:
print name
except HTTPError:
- return list_available_extensions_svn()
-
- return mlist
+ list_available_extensions_svn()
# list extensions (scan SVN repo)
def list_available_extensions_svn():
- mlist = list()
grass.message(_('Fetching list of extensions from GRASS-Addons SVN (be patient)...'))
pattern = re.compile(r'(<li><a href=".+">)(.+)(</a></li>)', re.IGNORECASE)
@@ -241,14 +332,11 @@
name = sline.group(2).rstrip('/')
if name.split('.', 1)[0] == d:
print name
- mlist.append(name)
- mlist += list_wxgui_extensions()
-
- return mlist
+ # get_wxgui_extensions()
# list wxGUI extensions
-def list_wxgui_extensions(print_module = True):
+def get_wxgui_extensions():
mlist = list()
grass.debug('Fetching list of wxGUI extensions from GRASS-Addons SVN (be patient)...')
pattern = re.compile(r'(<li><a href=".+">)(.+)(</a></li>)', re.IGNORECASE)
@@ -268,10 +356,8 @@
continue
name = sline.group(2).rstrip('/')
if name not in ('..', 'Makefile'):
- if print_module:
- print name
mlist.append(name)
-
+
return mlist
def cleanup():
@@ -284,11 +370,11 @@
# write out meta-file
def write_xml_modules(name, tree = None):
fo = open(name, 'w')
- version = grass.version()['version'].split('.')[0]
fo.write('<?xml version="1.0" encoding="UTF-8"?>\n')
fo.write('<!DOCTYPE task SYSTEM "grass-addons.dtd">\n')
- fo.write('<addons version="%s">\n' % version)
-
+ fo.write('<addons version="%s">\n' % version[0])
+
+ libgisRev = grass.version()['libgis_revision']
if tree is not None:
for tnode in tree.findall('task'):
indent = 4
@@ -307,7 +393,6 @@
(' ' * indent, os.path.join(options['prefix'], fnode.text)))
indent -= 4
fo.write('%s</binary>\n' % (' ' * indent))
- libgisRev = grass.version()['libgis_revision']
fo.write('%s<libgis revision="%s" />\n' % \
(' ' * indent, libgisRev))
indent -= 4
@@ -315,18 +400,154 @@
fo.write('</addons>\n')
fo.close()
+
+def write_xml_toolboxes(name, tree = None):
+ fo = open(name, 'w')
+ fo.write('<?xml version="1.0" encoding="UTF-8"?>\n')
+ fo.write('<!DOCTYPE toolbox SYSTEM "grass-addons.dtd">\n')
+ fo.write('<addons version="%s">\n' % version[0])
+ if tree is not None:
+ for tnode in tree.findall('toolbox'):
+ indent = 4
+ fo.write('%s<toolbox name="%s" code="%s">\n' % \
+ (' ' * indent, tnode.get('name'), tnode.get('code')))
+ indent += 4
+ for cnode in tnode.findall('correlate'):
+ fo.write('%s<correlate code="%s" />\n' % \
+ (' ' * indent, tnode.get('code')))
+ for mnode in tnode.findall('task'):
+ fo.write('%s<task name="%s" />\n' % \
+ (' ' * indent, mnode.get('name')))
+ indent -= 4
+ fo.write('%s</toolbox>\n' % (' ' * indent))
-# update local meta-file when installing new extension
-def install_extension_xml():
- # read metadata from remote server
- url = "http://grass.osgeo.org/addons/grass%s.xml" % grass.version()['version'].split('.')[0]
- data = None
+ fo.write('</addons>\n')
+ fo.close()
+
+# install extension - toolbox or module
+def install_extension():
+ gisbase = os.getenv('GISBASE')
+ if not gisbase:
+ grass.fatal(_('$GISBASE not defined'))
+
+ if options['extension'] in get_installed_extensions(force = True):
+ grass.warning(_("Extension <%s> already installed. Re-installing...") % options['extension'])
+
+ if flags['t']:
+ grass.message(_("Installing toolbox <%s>...") % options['extension'])
+ mlist = get_toolbox_modules(options['extension'])
+ else:
+ mlist = [options['extension']]
+ if not mlist:
+ grass.warning(_("Nothing to install"))
+ return
+
+ ret = 0
+ for module in mlist:
+ if sys.platform == "win32":
+ ret += install_extension_win(module)
+ else:
+ ret += install_extension_other(module)
+ if len(mlist) > 1:
+ print '-' * 60
+
+ if ret != 0:
+ grass.warning(_('Installation failed, sorry. Please check above error messages.'))
+ else:
+ grass.message(_("Updating metadata file..."))
+ install_extension_xml(mlist)
+ grass.message(_("Installation of <%s> successfully finished") % options['extension'])
+
+ if not os.getenv('GRASS_ADDON_BASE'):
+ grass.warning(_('This add-on module will not function until you set the '
+ 'GRASS_ADDON_BASE environment variable (see "g.manual variables")'))
+
+
+# update local meta-file when installing new extension (toolbox / modules)
+def install_toolbox_xml(name):
+ # read metadata from remote server (toolboxes)
+ url = "http://grass.osgeo.org/addons/grass%s/toolboxes.xml" % version[0]
+ data = dict()
try:
f = urlopen(url)
tree = etree.fromstring(f.read())
+ for tnode in tree.findall('toolbox'):
+ clist = list()
+ for cnode in tnode.findall('correlate'):
+ clist.append(cnode.get('code'))
+
+ mlist = list()
+ for mnode in tnode.findall('task'):
+ mlist.append(mnode.get('name'))
+
+ code = tnode.get('code')
+ data[code] = {
+ 'name' : tnode.get('name'),
+ 'correlate' : clist,
+ 'modules' : mlist,
+ }
+ except HTTPError:
+ grass.error(_("Unable to read metadata file from the remote server"))
+
+ if not data:
+ grass.warning(_("No metadata available"))
+ return
+ if name not in data:
+ grass.warning(_("No metadata available for <%s>") % name)
+ return
+
+ fXML = os.path.join(options['prefix'], 'toolboxes.xml')
+ # create an empty file if not exists
+ if not os.path.exists(fXML):
+ write_xml_modules(fXML)
+
+ # read XML file
+ fo = open(fXML, 'r')
+ tree = etree.fromstring(fo.read())
+ fo.close()
+
+ # update tree
+ tnode = None
+ for node in tree.findall('toolbox'):
+ if node.get('code') == name:
+ tnode = node
+ break
+
+ tdata = data[name]
+ if tnode is not None:
+ # update existing node
+ for cnode in tnode.findall('correlate'):
+ tnode.remove(cnode)
+ for mnode in tnode.findall('task'):
+ tnode.remove(mnode)
+ else:
+ # create new node for task
+ tnode = etree.Element('toolbox', attrib = { 'name' : tdata['name'], 'code' : name })
+ tree.append(tnode)
+
+ for cname in tdata['correlate']:
+ cnode = etree.Element('correlate', attrib = { 'code' : cname })
+ tnode.append(cnode)
+ for tname in tdata['modules']:
+ mnode = etree.Element('task', attrib = { 'name' : tname })
+ tnode.append(mnode)
+
+ write_xml_toolboxes(fXML, tree)
+
+def install_extension_xml(mlist):
+ if len(mlist) > 1:
+ # read metadata from remote server (toolboxes)
+ install_toolbox_xml(options['extension'])
+
+ # read metadata from remote server (modules)
+ url = "http://grass.osgeo.org/addons/grass%s/modules.xml" % version[0]
+ data = {}
+ try:
+ f = urlopen(url)
+ tree = etree.fromstring(f.read())
for mnode in tree.findall('task'):
name = mnode.get('name')
- if name != options['extension']:
+ if name not in mlist:
continue
fList = list()
@@ -349,11 +570,12 @@
if not keyw:
keyw = ''
- data = { 'name' : name,
- 'desc' : desc,
- 'keyw' : keyw,
- 'files' : fList,
- }
+ data[name] = {
+ 'desc' : desc,
+ 'keyw' : keyw,
+ 'files' : fList,
+ }
+
except HTTPError:
grass.error(_("Unable to read metadata file from the remote server"))
@@ -372,52 +594,57 @@
fo.close()
# update tree
- tnode = None
- for node in tree.findall('task'):
- if node.get('name') == options['extension']:
- tnode = node
- break
+ for name in mlist:
+ tnode = None
+ for node in tree.findall('task'):
+ if node.get('name') == name:
+ tnode = node
+ break
+
+ if name not in data:
+ grass.warning(_("No metadata found for <%s>") % name)
+ continue
+
+ ndata = data[name]
+ if tnode is not None:
+ # update existing node
+ dnode = tnode.find('description')
+ if dnode is not None:
+ dnode.text = ndata['desc']
+ knode = tnode.find('keywords')
+ if knode is not None:
+ knode.text = ndata['keyw']
+ bnode = tnode.find('binary')
+ if bnode is not None:
+ tnode.remove(bnode)
+ bnode = etree.Element('binary')
+ for f in ndata['files']:
+ fnode = etree.Element('file')
+ fnode.text = f
+ bnode.append(fnode)
+ tnode.append(bnode)
+ else:
+ # create new node for task
+ tnode = etree.Element('task', attrib = { 'name' : name })
+ dnode = etree.Element('description')
+ dnode.text = ndata['desc']
+ tnode.append(dnode)
+ knode = etree.Element('keywords')
+ knode.text = ndata['keyw']
+ tnode.append(knode)
+ bnode = etree.Element('binary')
+ for f in ndata['files']:
+ fnode = etree.Element('file')
+ fnode.text = f
+ bnode.append(fnode)
+ tnode.append(bnode)
+ tree.append(tnode)
- if tnode is not None:
- # update existing node
- dnode = tnode.find('description')
- if dnode is not None:
- dnode.text = data['desc']
- knode = tnode.find('keywords')
- if knode is not None:
- knode.text = data['keyw']
- bnode = tnode.find('binary')
- if bnode is not None:
- tnode.remove(bnode)
- bnode = etree.Element('binary')
- for f in data['files']:
- fnode = etree.Element('file')
- fnode.text = f
- bnode.append(fnode)
- tnode.append(bnode)
- else:
- # create new node for task
- tnode = etree.Element('task', attrib = { 'name' : data['name'] })
- dnode = etree.Element('description')
- dnode.text = data['desc']
- tnode.append(dnode)
- knode = etree.Element('keywords')
- knode.text = data['keyw']
- tnode.append(knode)
- bnode = etree.Element('binary')
- for f in data['files']:
- fnode = etree.Element('file')
- fnode.text = f
- bnode.append(fnode)
- tnode.append(bnode)
- tree.append(tnode)
-
write_xml_modules(fXML, tree)
# install extension on MS Windows
def install_extension_win():
### TODO: do not use hardcoded url - http://wingrass.fsv.cvut.cz/grassXX/addonsX.X.X
- version = grass.version()['version'].split('.')
grass.message(_("Downloading precompiled GRASS Addons <%s>...") % options['extension'])
url = "http://wingrass.fsv.cvut.cz/grass%s%s/addons" % (version[0], version[1])
if version[2][1:] != 'svn':
@@ -451,46 +678,22 @@
return 0
-# install extension
-def install_extension():
+# install extension on other plaforms
+def install_extension_other(name):
gisbase = os.getenv('GISBASE')
- if not gisbase:
- grass.fatal(_('$GISBASE not defined'))
+ # gui_list = get_wxgui_extensions()
+ gui_list = list()
- if options['extension'] in get_installed_extensions(force = True):
- grass.warning(_("Extension <%s> already installed. Re-installing...") % options['extension'])
-
- if sys.platform == "win32":
- ret = install_extension_win()
- else:
- ret = install_extension_other()
-
- if ret != 0:
- grass.warning(_('Installation failed, sorry. Please check above error messages.'))
- else:
- grass.message(_("Updating metadata file..."))
- install_extension_xml()
- grass.message(_("Installation of <%s> successfully finished") % options['extension'])
-
- if not os.getenv('GRASS_ADDON_BASE'):
- grass.warning(_('This add-on module will not function until you set the '
- 'GRASS_ADDON_BASE environment variable (see "g.manual variables")'))
-
-# install extension on other plaforms
-def install_extension_other():
- gisbase = os.getenv('GISBASE')
- gui_list = list_wxgui_extensions(print_module = False)
-
- if options['extension'] not in gui_list:
- classchar = options['extension'].split('.', 1)[0]
+ if name not in gui_list:
+ classchar = name.split('.', 1)[0]
moduleclass = expand_module_class_name(classchar)
- url = options['svnurl'] + '/' + moduleclass + '/' + options['extension']
+ url = options['svnurl'] + '/' + moduleclass + '/' + name
else:
- url = options['svnurl'] + '/gui/wxpython/' + options['extension']
+ url = options['svnurl'] + '/gui/wxpython/' + name
if not flags['s']:
grass.fatal(_("Installation of wxGUI extension requires -%s flag.") % 's')
- grass.message(_("Fetching <%s> from GRASS-Addons SVN (be patient)...") % options['extension'])
+ grass.message(_("Fetching <%s> from GRASS-Addons SVN (be patient)...") % name)
os.chdir(tmpdir)
if grass.verbosity() <= 2:
@@ -500,15 +703,15 @@
if grass.call(['svn', 'checkout',
url], stdout = outdev) != 0:
- grass.fatal(_("GRASS Addons <%s> not found") % options['extension'])
+ grass.fatal(_("GRASS Addons <%s> not found") % name)
- dirs = { 'bin' : os.path.join(tmpdir, options['extension'], 'bin'),
- 'docs' : os.path.join(tmpdir, options['extension'], 'docs'),
- 'html' : os.path.join(tmpdir, options['extension'], 'docs', 'html'),
- 'man' : os.path.join(tmpdir, options['extension'], 'man'),
- 'man1' : os.path.join(tmpdir, options['extension'], 'man', 'man1'),
- 'scripts' : os.path.join(tmpdir, options['extension'], 'scripts'),
- 'etc' : os.path.join(tmpdir, options['extension'], 'etc'),
+ dirs = { 'bin' : os.path.join(tmpdir, name, 'bin'),
+ 'docs' : os.path.join(tmpdir, name, 'docs'),
+ 'html' : os.path.join(tmpdir, name, 'docs', 'html'),
+ 'man' : os.path.join(tmpdir, name, 'man'),
+ 'man1' : os.path.join(tmpdir, name, 'man', 'man1'),
+ 'scripts' : os.path.join(tmpdir, name, 'scripts'),
+ 'etc' : os.path.join(tmpdir, name, 'etc'),
}
makeCmd = ['make',
@@ -517,12 +720,12 @@
'HTMLDIR=%s' % dirs['html'],
'MANDIR=%s' % dirs['man1'],
'SCRIPTDIR=%s' % dirs['scripts'],
- 'ETC=%s' % os.path.join(dirs['etc'],options['extension'])
+ 'ETC=%s' % os.path.join(dirs['etc'],name)
]
installCmd = ['make',
'MODULE_TOPDIR=%s' % gisbase,
- 'ARCH_DISTDIR=%s' % os.path.join(tmpdir, options['extension']),
+ 'ARCH_DISTDIR=%s' % os.path.join(tmpdir, name),
'INST_DIR=%s' % options['prefix'],
'install'
]
@@ -534,10 +737,10 @@
sys.stderr.write(' '.join(installCmd) + '\n')
return
- os.chdir(os.path.join(tmpdir, options['extension']))
+ os.chdir(os.path.join(tmpdir, name))
grass.message(_("Compiling..."))
- if options['extension'] not in gui_list:
+ if name not in gui_list:
ret = grass.call(makeCmd,
stdout = outdev)
else:
@@ -548,7 +751,7 @@
if ret != 0:
grass.fatal(_('Compilation failed, sorry. Please check above error messages.'))
- if flags['i'] or options['extension'] in gui_list:
+ if flags['i'] or name in gui_list:
return
grass.message(_("Installing..."))
@@ -556,91 +759,86 @@
return grass.call(installCmd,
stdout = outdev)
-# update local meta-file when removing existing extension
-def remove_extension_xml():
- fXML = os.path.join(options['prefix'], 'modules.xml')
- if not os.path.exists(fXML):
- return
-
- # read XML file
- fo = open(fXML, 'r')
- tree = etree.fromstring(fo.read())
- fo.close()
-
- tnode = None
- for node in tree.findall('task'):
- if node.get('name') == options['extension']:
- tnode = node
- break
-
- if tnode is not None:
- tree.remove(tnode)
+# remove existing extension - toolbox or module
+def remove_extension(force = False):
+ if flags['t']:
+ mlist = get_toolbox_modules(options['extension'])
+ else:
+ mlist = [options['extension']]
- write_xml_modules(fXML, tree)
-
-# remove existing extension (reading XML file)
-def remove_extension(force = False):
- # try to read XML metadata file first
- fXML = os.path.join(options['prefix'], 'modules.xml')
- name = options['extension']
- if name not in get_installed_extensions():
- # try even if module does not seem to be available,
- # as the user may be trying to get rid of left over cruft
- grass.warning(_("Extension <%s> not found") % name)
-
if force:
grass.verbose(_("List of removed files:"))
else:
grass.info(_("Files to be removed (use flag 'f' to force removal):"))
- if os.path.exists(fXML):
- f = open(fXML, 'r')
- tree = etree.fromstring(f.read())
- flist = []
- for task in tree.findall('task'):
- if name == task.get('name', default = '') and \
- task.find('binary') is not None:
- for f in task.find('binary').findall('file'):
- flist.append(f.text)
-
- if flist:
- removed = False
- err = list()
- for fpath in flist:
- try:
- if force:
- grass.verbose(fpath)
- os.remove(fpath)
- removed = True
- else:
- print fpath
- except OSError:
- err.append((_("Unable to remove file '%s'") % fpath))
- if force and not removed:
- grass.fatal(_("Extension <%s> not found") % options['extension'])
-
- if err:
- for e in err:
- grass.error(e)
- else:
- remove_extension_std(force)
- else:
- remove_extension_std(force)
+ remove_modules(mlist, force)
if force:
grass.message(_("Updating metadata file..."))
- remove_extension_xml()
+ remove_extension_xml(mlist)
grass.message(_("Extension <%s> successfully uninstalled.") % options['extension'])
else:
grass.warning(_("Extension <%s> not removed.\n"
"Re-run '%s' with 'f' flag to force removal") % (options['extension'], 'g.extension'))
+# remove existing extension(s) (reading XML file)
+def remove_modules(mlist, force = False):
+ # try to read XML metadata file first
+ fXML = os.path.join(options['prefix'], 'modules.xml')
+ installed = get_installed_modules()
+
+ if os.path.exists(fXML):
+ f = open(fXML, 'r')
+ tree = etree.fromstring(f.read())
+ f.close()
+ else:
+ tree = None
+
+ for name in mlist:
+ if name not in installed:
+ # try even if module does not seem to be available,
+ # as the user may be trying to get rid of left over cruft
+ grass.warning(_("Extension <%s> not found") % name)
+
+ if tree is not None:
+ flist = []
+ for task in tree.findall('task'):
+ if name == task.get('name') and \
+ task.find('binary') is not None:
+ for f in task.find('binary').findall('file'):
+ flist.append(f.text)
+ break
+
+ if flist:
+ removed = False
+ err = list()
+ for fpath in flist:
+ try:
+ if force:
+ grass.verbose(fpath)
+ removed = True
+ os.remove(fpath)
+ else:
+ print fpath
+ except OSError:
+ err.append((_("Unable to remove file '%s'") % fpath))
+ if force and not removed:
+ grass.fatal(_("Extension <%s> not found") % name)
+
+ if err:
+ for e in err:
+ grass.error(e)
+ else:
+ remove_extension_std(name, force)
+ else:
+ remove_extension_std(name, force)
+
# remove exising extension (using standard files layout)
-def remove_extension_std(force = False):
- for fpath in [os.path.join(options['prefix'], 'bin', options['extension']),
- os.path.join(options['prefix'], 'scripts', options['extension']),
- os.path.join(options['prefix'], 'docs', 'html', options['extension'] + '.html'),
- os.path.join(options['prefix'], 'man', 'man1', options['extension'] + '.1')]:
+def remove_extension_std(name, force = False):
+ for fpath in [os.path.join(options['prefix'], 'bin', name),
+ os.path.join(options['prefix'], 'scripts', name),
+ os.path.join(options['prefix'], 'docs', 'html', name + '.html'),
+ os.path.join(options['prefix'], 'man', 'man1', name + '.1')]:
if os.path.isfile(fpath):
if force:
grass.verbose(fpath)
@@ -648,6 +846,46 @@
else:
print fpath
+# update local meta-file when removing existing extension
+def remove_toolbox_xml(name):
+ fXML = os.path.join(options['prefix'], 'toolboxes.xml')
+ if not os.path.exists(fXML):
+ return
+
+ # read XML file
+ fo = open(fXML, 'r')
+ tree = etree.fromstring(fo.read())
+ fo.close()
+
+ for node in tree.findall('toolbox'):
+ if node.get('code') != name:
+ continue
+ tree.remove(node)
+
+ write_xml_toolboxes(fXML, tree)
+
+def remove_extension_xml(modules):
+ if len(modules) > 1:
+ # update also toolboxes metadata
+ remove_toolbox_xml(options['extension'])
+
+ fXML = os.path.join(options['prefix'], 'modules.xml')
+ if not os.path.exists(fXML):
+ return
+
+ # read XML file
+ fo = open(fXML, 'r')
+ tree = etree.fromstring(fo.read())
+ fo.close()
+
+ for name in modules:
+ for node in tree.findall('task'):
+ if node.get('name') != name:
+ continue
+ tree.remove(node)
+
+ write_xml_modules(fXML, tree)
+
# check links in CSS
def check_style_files(fil):
dist_file = os.path.join(os.getenv('GISBASE'), 'docs', 'html', fil)
@@ -693,8 +931,8 @@
if not os.getenv('GRASS_ADDON_BASE'):
major_version = int(grass.version()['version'].split('.', 1)[0])
grass.warning(_("GRASS_ADDON_BASE is not defined, "
- "installing to ~/.grass%d/addons") % major_version)
- options['prefix'] = os.path.join(os.environ['HOME'], '.grass%d' % major_version, 'addons')
+ "installing to ~/.grass%s/addons") % version[0])
+ options['prefix'] = os.path.join(os.environ['HOME'], '.grass%s' % version[0], 'addons')
else:
options['prefix'] = os.environ['GRASS_ADDON_BASE']
@@ -705,15 +943,21 @@
elif flags['a']:
elist = get_installed_extensions()
if elist:
- grass.message(_("List of installed extensions:"))
+ if flags['t']:
+ grass.message(_("List of installed extensions (toolboxes):"))
+ else:
+ grass.message(_("List of installed extensions (modules):"))
sys.stdout.write('\n'.join(elist))
sys.stdout.write('\n')
else:
- grass.info(_("No extension installed"))
+ if flags['t']:
+ grass.info(_("No extension (toolbox) installed"))
+ else:
+ grass.info(_("No extension (module) installed"))
return 0
else:
if not options['extension']:
- grass.fatal(_('You need to define an extension name or use -l'))
+ grass.fatal(_('You need to define an extension name or use -l/c/g/a'))
if flags['d']:
if options['operation'] != 'add':
@@ -735,4 +979,5 @@
global tmpdir
tmpdir = grass.tempdir()
atexit.register(cleanup)
+ version = grass.version()['version'].split('.')
sys.exit(main())
More information about the grass-commit
mailing list