##// END OF EJS Templates
help: provide help of bad alias without executing aliascmd()...
Yuya Nishihara -
r22162:7ada3467 default
parent child Browse files
Show More
@@ -1,508 +1,510 b''
1 # help.py - help data for mercurial
1 # help.py - help data for mercurial
2 #
2 #
3 # Copyright 2006 Matt Mackall <mpm@selenic.com>
3 # Copyright 2006 Matt Mackall <mpm@selenic.com>
4 #
4 #
5 # This software may be used and distributed according to the terms of the
5 # This software may be used and distributed according to the terms of the
6 # GNU General Public License version 2 or any later version.
6 # GNU General Public License version 2 or any later version.
7
7
8 from i18n import gettext, _
8 from i18n import gettext, _
9 import itertools, sys, os
9 import itertools, sys, os
10 import error
10 import error
11 import extensions, revset, fileset, templatekw, templatefilters, filemerge
11 import extensions, revset, fileset, templatekw, templatefilters, filemerge
12 import encoding, util, minirst
12 import encoding, util, minirst
13 import cmdutil
13 import cmdutil
14
14
15 def listexts(header, exts, indent=1, showdeprecated=False):
15 def listexts(header, exts, indent=1, showdeprecated=False):
16 '''return a text listing of the given extensions'''
16 '''return a text listing of the given extensions'''
17 rst = []
17 rst = []
18 if exts:
18 if exts:
19 rst.append('\n%s\n\n' % header)
19 rst.append('\n%s\n\n' % header)
20 for name, desc in sorted(exts.iteritems()):
20 for name, desc in sorted(exts.iteritems()):
21 if '(DEPRECATED)' in desc and not showdeprecated:
21 if '(DEPRECATED)' in desc and not showdeprecated:
22 continue
22 continue
23 rst.append('%s:%s: %s\n' % (' ' * indent, name, desc))
23 rst.append('%s:%s: %s\n' % (' ' * indent, name, desc))
24 return rst
24 return rst
25
25
26 def extshelp():
26 def extshelp():
27 rst = loaddoc('extensions')().splitlines(True)
27 rst = loaddoc('extensions')().splitlines(True)
28 rst.extend(listexts(
28 rst.extend(listexts(
29 _('enabled extensions:'), extensions.enabled(), showdeprecated=True))
29 _('enabled extensions:'), extensions.enabled(), showdeprecated=True))
30 rst.extend(listexts(_('disabled extensions:'), extensions.disabled()))
30 rst.extend(listexts(_('disabled extensions:'), extensions.disabled()))
31 doc = ''.join(rst)
31 doc = ''.join(rst)
32 return doc
32 return doc
33
33
34 def optrst(header, options, verbose):
34 def optrst(header, options, verbose):
35 data = []
35 data = []
36 multioccur = False
36 multioccur = False
37 for option in options:
37 for option in options:
38 if len(option) == 5:
38 if len(option) == 5:
39 shortopt, longopt, default, desc, optlabel = option
39 shortopt, longopt, default, desc, optlabel = option
40 else:
40 else:
41 shortopt, longopt, default, desc = option
41 shortopt, longopt, default, desc = option
42 optlabel = _("VALUE") # default label
42 optlabel = _("VALUE") # default label
43
43
44 if not verbose and ("DEPRECATED" in desc or _("DEPRECATED") in desc):
44 if not verbose and ("DEPRECATED" in desc or _("DEPRECATED") in desc):
45 continue
45 continue
46
46
47 so = ''
47 so = ''
48 if shortopt:
48 if shortopt:
49 so = '-' + shortopt
49 so = '-' + shortopt
50 lo = '--' + longopt
50 lo = '--' + longopt
51 if default:
51 if default:
52 desc += _(" (default: %s)") % default
52 desc += _(" (default: %s)") % default
53
53
54 if isinstance(default, list):
54 if isinstance(default, list):
55 lo += " %s [+]" % optlabel
55 lo += " %s [+]" % optlabel
56 multioccur = True
56 multioccur = True
57 elif (default is not None) and not isinstance(default, bool):
57 elif (default is not None) and not isinstance(default, bool):
58 lo += " %s" % optlabel
58 lo += " %s" % optlabel
59
59
60 data.append((so, lo, desc))
60 data.append((so, lo, desc))
61
61
62 if multioccur:
62 if multioccur:
63 header += (_(" ([+] can be repeated)"))
63 header += (_(" ([+] can be repeated)"))
64
64
65 rst = ['\n%s:\n\n' % header]
65 rst = ['\n%s:\n\n' % header]
66 rst.extend(minirst.maketable(data, 1))
66 rst.extend(minirst.maketable(data, 1))
67
67
68 return ''.join(rst)
68 return ''.join(rst)
69
69
70 def indicateomitted(rst, omitted, notomitted=None):
70 def indicateomitted(rst, omitted, notomitted=None):
71 rst.append('\n\n.. container:: omitted\n\n %s\n\n' % omitted)
71 rst.append('\n\n.. container:: omitted\n\n %s\n\n' % omitted)
72 if notomitted:
72 if notomitted:
73 rst.append('\n\n.. container:: notomitted\n\n %s\n\n' % notomitted)
73 rst.append('\n\n.. container:: notomitted\n\n %s\n\n' % notomitted)
74
74
75 def topicmatch(kw):
75 def topicmatch(kw):
76 """Return help topics matching kw.
76 """Return help topics matching kw.
77
77
78 Returns {'section': [(name, summary), ...], ...} where section is
78 Returns {'section': [(name, summary), ...], ...} where section is
79 one of topics, commands, extensions, or extensioncommands.
79 one of topics, commands, extensions, or extensioncommands.
80 """
80 """
81 kw = encoding.lower(kw)
81 kw = encoding.lower(kw)
82 def lowercontains(container):
82 def lowercontains(container):
83 return kw in encoding.lower(container) # translated in helptable
83 return kw in encoding.lower(container) # translated in helptable
84 results = {'topics': [],
84 results = {'topics': [],
85 'commands': [],
85 'commands': [],
86 'extensions': [],
86 'extensions': [],
87 'extensioncommands': [],
87 'extensioncommands': [],
88 }
88 }
89 for names, header, doc in helptable:
89 for names, header, doc in helptable:
90 if (sum(map(lowercontains, names))
90 if (sum(map(lowercontains, names))
91 or lowercontains(header)
91 or lowercontains(header)
92 or lowercontains(doc())):
92 or lowercontains(doc())):
93 results['topics'].append((names[0], header))
93 results['topics'].append((names[0], header))
94 import commands # avoid cycle
94 import commands # avoid cycle
95 for cmd, entry in commands.table.iteritems():
95 for cmd, entry in commands.table.iteritems():
96 if len(entry) == 3:
96 if len(entry) == 3:
97 summary = entry[2]
97 summary = entry[2]
98 else:
98 else:
99 summary = ''
99 summary = ''
100 # translate docs *before* searching there
100 # translate docs *before* searching there
101 docs = _(getattr(entry[0], '__doc__', None)) or ''
101 docs = _(getattr(entry[0], '__doc__', None)) or ''
102 if kw in cmd or lowercontains(summary) or lowercontains(docs):
102 if kw in cmd or lowercontains(summary) or lowercontains(docs):
103 doclines = docs.splitlines()
103 doclines = docs.splitlines()
104 if doclines:
104 if doclines:
105 summary = doclines[0]
105 summary = doclines[0]
106 cmdname = cmd.split('|')[0].lstrip('^')
106 cmdname = cmd.split('|')[0].lstrip('^')
107 results['commands'].append((cmdname, summary))
107 results['commands'].append((cmdname, summary))
108 for name, docs in itertools.chain(
108 for name, docs in itertools.chain(
109 extensions.enabled(False).iteritems(),
109 extensions.enabled(False).iteritems(),
110 extensions.disabled().iteritems()):
110 extensions.disabled().iteritems()):
111 # extensions.load ignores the UI argument
111 # extensions.load ignores the UI argument
112 mod = extensions.load(None, name, '')
112 mod = extensions.load(None, name, '')
113 name = name.split('.')[-1]
113 name = name.split('.')[-1]
114 if lowercontains(name) or lowercontains(docs):
114 if lowercontains(name) or lowercontains(docs):
115 # extension docs are already translated
115 # extension docs are already translated
116 results['extensions'].append((name, docs.splitlines()[0]))
116 results['extensions'].append((name, docs.splitlines()[0]))
117 for cmd, entry in getattr(mod, 'cmdtable', {}).iteritems():
117 for cmd, entry in getattr(mod, 'cmdtable', {}).iteritems():
118 if kw in cmd or (len(entry) > 2 and lowercontains(entry[2])):
118 if kw in cmd or (len(entry) > 2 and lowercontains(entry[2])):
119 cmdname = cmd.split('|')[0].lstrip('^')
119 cmdname = cmd.split('|')[0].lstrip('^')
120 if entry[0].__doc__:
120 if entry[0].__doc__:
121 cmddoc = gettext(entry[0].__doc__).splitlines()[0]
121 cmddoc = gettext(entry[0].__doc__).splitlines()[0]
122 else:
122 else:
123 cmddoc = _('(no help text available)')
123 cmddoc = _('(no help text available)')
124 results['extensioncommands'].append((cmdname, cmddoc))
124 results['extensioncommands'].append((cmdname, cmddoc))
125 return results
125 return results
126
126
127 def loaddoc(topic):
127 def loaddoc(topic):
128 """Return a delayed loader for help/topic.txt."""
128 """Return a delayed loader for help/topic.txt."""
129
129
130 def loader():
130 def loader():
131 if util.mainfrozen():
131 if util.mainfrozen():
132 module = sys.executable
132 module = sys.executable
133 else:
133 else:
134 module = __file__
134 module = __file__
135 base = os.path.dirname(module)
135 base = os.path.dirname(module)
136
136
137 for dir in ('.', '..'):
137 for dir in ('.', '..'):
138 docdir = os.path.join(base, dir, 'help')
138 docdir = os.path.join(base, dir, 'help')
139 if os.path.isdir(docdir):
139 if os.path.isdir(docdir):
140 break
140 break
141
141
142 path = os.path.join(docdir, topic + ".txt")
142 path = os.path.join(docdir, topic + ".txt")
143 doc = gettext(util.readfile(path))
143 doc = gettext(util.readfile(path))
144 for rewriter in helphooks.get(topic, []):
144 for rewriter in helphooks.get(topic, []):
145 doc = rewriter(topic, doc)
145 doc = rewriter(topic, doc)
146 return doc
146 return doc
147
147
148 return loader
148 return loader
149
149
150 helptable = sorted([
150 helptable = sorted([
151 (["config", "hgrc"], _("Configuration Files"), loaddoc('config')),
151 (["config", "hgrc"], _("Configuration Files"), loaddoc('config')),
152 (["dates"], _("Date Formats"), loaddoc('dates')),
152 (["dates"], _("Date Formats"), loaddoc('dates')),
153 (["patterns"], _("File Name Patterns"), loaddoc('patterns')),
153 (["patterns"], _("File Name Patterns"), loaddoc('patterns')),
154 (['environment', 'env'], _('Environment Variables'),
154 (['environment', 'env'], _('Environment Variables'),
155 loaddoc('environment')),
155 loaddoc('environment')),
156 (['revisions', 'revs'], _('Specifying Single Revisions'),
156 (['revisions', 'revs'], _('Specifying Single Revisions'),
157 loaddoc('revisions')),
157 loaddoc('revisions')),
158 (['multirevs', 'mrevs'], _('Specifying Multiple Revisions'),
158 (['multirevs', 'mrevs'], _('Specifying Multiple Revisions'),
159 loaddoc('multirevs')),
159 loaddoc('multirevs')),
160 (['revsets', 'revset'], _("Specifying Revision Sets"), loaddoc('revsets')),
160 (['revsets', 'revset'], _("Specifying Revision Sets"), loaddoc('revsets')),
161 (['filesets', 'fileset'], _("Specifying File Sets"), loaddoc('filesets')),
161 (['filesets', 'fileset'], _("Specifying File Sets"), loaddoc('filesets')),
162 (['diffs'], _('Diff Formats'), loaddoc('diffs')),
162 (['diffs'], _('Diff Formats'), loaddoc('diffs')),
163 (['merge-tools', 'mergetools'], _('Merge Tools'), loaddoc('merge-tools')),
163 (['merge-tools', 'mergetools'], _('Merge Tools'), loaddoc('merge-tools')),
164 (['templating', 'templates', 'template', 'style'], _('Template Usage'),
164 (['templating', 'templates', 'template', 'style'], _('Template Usage'),
165 loaddoc('templates')),
165 loaddoc('templates')),
166 (['urls'], _('URL Paths'), loaddoc('urls')),
166 (['urls'], _('URL Paths'), loaddoc('urls')),
167 (["extensions"], _("Using Additional Features"), extshelp),
167 (["extensions"], _("Using Additional Features"), extshelp),
168 (["subrepos", "subrepo"], _("Subrepositories"), loaddoc('subrepos')),
168 (["subrepos", "subrepo"], _("Subrepositories"), loaddoc('subrepos')),
169 (["hgweb"], _("Configuring hgweb"), loaddoc('hgweb')),
169 (["hgweb"], _("Configuring hgweb"), loaddoc('hgweb')),
170 (["glossary"], _("Glossary"), loaddoc('glossary')),
170 (["glossary"], _("Glossary"), loaddoc('glossary')),
171 (["hgignore", "ignore"], _("Syntax for Mercurial Ignore Files"),
171 (["hgignore", "ignore"], _("Syntax for Mercurial Ignore Files"),
172 loaddoc('hgignore')),
172 loaddoc('hgignore')),
173 (["phases"], _("Working with Phases"), loaddoc('phases')),
173 (["phases"], _("Working with Phases"), loaddoc('phases')),
174 ])
174 ])
175
175
176 # Map topics to lists of callable taking the current topic help and
176 # Map topics to lists of callable taking the current topic help and
177 # returning the updated version
177 # returning the updated version
178 helphooks = {}
178 helphooks = {}
179
179
180 def addtopichook(topic, rewriter):
180 def addtopichook(topic, rewriter):
181 helphooks.setdefault(topic, []).append(rewriter)
181 helphooks.setdefault(topic, []).append(rewriter)
182
182
183 def makeitemsdoc(topic, doc, marker, items):
183 def makeitemsdoc(topic, doc, marker, items):
184 """Extract docstring from the items key to function mapping, build a
184 """Extract docstring from the items key to function mapping, build a
185 .single documentation block and use it to overwrite the marker in doc
185 .single documentation block and use it to overwrite the marker in doc
186 """
186 """
187 entries = []
187 entries = []
188 for name in sorted(items):
188 for name in sorted(items):
189 text = (items[name].__doc__ or '').rstrip()
189 text = (items[name].__doc__ or '').rstrip()
190 if not text:
190 if not text:
191 continue
191 continue
192 text = gettext(text)
192 text = gettext(text)
193 lines = text.splitlines()
193 lines = text.splitlines()
194 doclines = [(lines[0])]
194 doclines = [(lines[0])]
195 for l in lines[1:]:
195 for l in lines[1:]:
196 # Stop once we find some Python doctest
196 # Stop once we find some Python doctest
197 if l.strip().startswith('>>>'):
197 if l.strip().startswith('>>>'):
198 break
198 break
199 doclines.append(' ' + l.strip())
199 doclines.append(' ' + l.strip())
200 entries.append('\n'.join(doclines))
200 entries.append('\n'.join(doclines))
201 entries = '\n\n'.join(entries)
201 entries = '\n\n'.join(entries)
202 return doc.replace(marker, entries)
202 return doc.replace(marker, entries)
203
203
204 def addtopicsymbols(topic, marker, symbols):
204 def addtopicsymbols(topic, marker, symbols):
205 def add(topic, doc):
205 def add(topic, doc):
206 return makeitemsdoc(topic, doc, marker, symbols)
206 return makeitemsdoc(topic, doc, marker, symbols)
207 addtopichook(topic, add)
207 addtopichook(topic, add)
208
208
209 addtopicsymbols('filesets', '.. predicatesmarker', fileset.symbols)
209 addtopicsymbols('filesets', '.. predicatesmarker', fileset.symbols)
210 addtopicsymbols('merge-tools', '.. internaltoolsmarker', filemerge.internals)
210 addtopicsymbols('merge-tools', '.. internaltoolsmarker', filemerge.internals)
211 addtopicsymbols('revsets', '.. predicatesmarker', revset.symbols)
211 addtopicsymbols('revsets', '.. predicatesmarker', revset.symbols)
212 addtopicsymbols('templates', '.. keywordsmarker', templatekw.dockeywords)
212 addtopicsymbols('templates', '.. keywordsmarker', templatekw.dockeywords)
213 addtopicsymbols('templates', '.. filtersmarker', templatefilters.filters)
213 addtopicsymbols('templates', '.. filtersmarker', templatefilters.filters)
214
214
215 def help_(ui, name, unknowncmd=False, full=True, **opts):
215 def help_(ui, name, unknowncmd=False, full=True, **opts):
216 '''
216 '''
217 Generate the help for 'name' as unformatted restructured text. If
217 Generate the help for 'name' as unformatted restructured text. If
218 'name' is None, describe the commands available.
218 'name' is None, describe the commands available.
219 '''
219 '''
220
220
221 import commands # avoid cycle
221 import commands # avoid cycle
222
222
223 def helpcmd(name):
223 def helpcmd(name):
224 try:
224 try:
225 aliases, entry = cmdutil.findcmd(name, commands.table,
225 aliases, entry = cmdutil.findcmd(name, commands.table,
226 strict=unknowncmd)
226 strict=unknowncmd)
227 except error.AmbiguousCommand, inst:
227 except error.AmbiguousCommand, inst:
228 # py3k fix: except vars can't be used outside the scope of the
228 # py3k fix: except vars can't be used outside the scope of the
229 # except block, nor can be used inside a lambda. python issue4617
229 # except block, nor can be used inside a lambda. python issue4617
230 prefix = inst.args[0]
230 prefix = inst.args[0]
231 select = lambda c: c.lstrip('^').startswith(prefix)
231 select = lambda c: c.lstrip('^').startswith(prefix)
232 rst = helplist(select)
232 rst = helplist(select)
233 return rst
233 return rst
234
234
235 rst = []
235 rst = []
236
236
237 # check if it's an invalid alias and display its error if it is
237 # check if it's an invalid alias and display its error if it is
238 if getattr(entry[0], 'badalias', None):
238 if getattr(entry[0], 'badalias', None):
239 if not unknowncmd:
239 rst.append(entry[0].badalias + '\n')
240 ui.pushbuffer()
240 if entry[0].unknowncmd:
241 entry[0](ui)
241 try:
242 rst.append(ui.popbuffer())
242 rst.extend(helpextcmd(entry[0].cmdname))
243 except error.UnknownCommand:
244 pass
243 return rst
245 return rst
244
246
245 # synopsis
247 # synopsis
246 if len(entry) > 2:
248 if len(entry) > 2:
247 if entry[2].startswith('hg'):
249 if entry[2].startswith('hg'):
248 rst.append("%s\n" % entry[2])
250 rst.append("%s\n" % entry[2])
249 else:
251 else:
250 rst.append('hg %s %s\n' % (aliases[0], entry[2]))
252 rst.append('hg %s %s\n' % (aliases[0], entry[2]))
251 else:
253 else:
252 rst.append('hg %s\n' % aliases[0])
254 rst.append('hg %s\n' % aliases[0])
253 # aliases
255 # aliases
254 if full and not ui.quiet and len(aliases) > 1:
256 if full and not ui.quiet and len(aliases) > 1:
255 rst.append(_("\naliases: %s\n") % ', '.join(aliases[1:]))
257 rst.append(_("\naliases: %s\n") % ', '.join(aliases[1:]))
256 rst.append('\n')
258 rst.append('\n')
257
259
258 # description
260 # description
259 doc = gettext(entry[0].__doc__)
261 doc = gettext(entry[0].__doc__)
260 if not doc:
262 if not doc:
261 doc = _("(no help text available)")
263 doc = _("(no help text available)")
262 if util.safehasattr(entry[0], 'definition'): # aliased command
264 if util.safehasattr(entry[0], 'definition'): # aliased command
263 if entry[0].definition.startswith('!'): # shell alias
265 if entry[0].definition.startswith('!'): # shell alias
264 doc = _('shell alias for::\n\n %s') % entry[0].definition[1:]
266 doc = _('shell alias for::\n\n %s') % entry[0].definition[1:]
265 else:
267 else:
266 doc = _('alias for: hg %s\n\n%s') % (entry[0].definition, doc)
268 doc = _('alias for: hg %s\n\n%s') % (entry[0].definition, doc)
267 doc = doc.splitlines(True)
269 doc = doc.splitlines(True)
268 if ui.quiet or not full:
270 if ui.quiet or not full:
269 rst.append(doc[0])
271 rst.append(doc[0])
270 else:
272 else:
271 rst.extend(doc)
273 rst.extend(doc)
272 rst.append('\n')
274 rst.append('\n')
273
275
274 # check if this command shadows a non-trivial (multi-line)
276 # check if this command shadows a non-trivial (multi-line)
275 # extension help text
277 # extension help text
276 try:
278 try:
277 mod = extensions.find(name)
279 mod = extensions.find(name)
278 doc = gettext(mod.__doc__) or ''
280 doc = gettext(mod.__doc__) or ''
279 if '\n' in doc.strip():
281 if '\n' in doc.strip():
280 msg = _('(use "hg help -e %s" to show help for '
282 msg = _('(use "hg help -e %s" to show help for '
281 'the %s extension)') % (name, name)
283 'the %s extension)') % (name, name)
282 rst.append('\n%s\n' % msg)
284 rst.append('\n%s\n' % msg)
283 except KeyError:
285 except KeyError:
284 pass
286 pass
285
287
286 # options
288 # options
287 if not ui.quiet and entry[1]:
289 if not ui.quiet and entry[1]:
288 rst.append(optrst(_("options"), entry[1], ui.verbose))
290 rst.append(optrst(_("options"), entry[1], ui.verbose))
289
291
290 if ui.verbose:
292 if ui.verbose:
291 rst.append(optrst(_("global options"),
293 rst.append(optrst(_("global options"),
292 commands.globalopts, ui.verbose))
294 commands.globalopts, ui.verbose))
293
295
294 if not ui.verbose:
296 if not ui.verbose:
295 if not full:
297 if not full:
296 rst.append(_('\n(use "hg %s -h" to show more help)\n')
298 rst.append(_('\n(use "hg %s -h" to show more help)\n')
297 % name)
299 % name)
298 elif not ui.quiet:
300 elif not ui.quiet:
299 rst.append(_('\n(some details hidden, use --verbose '
301 rst.append(_('\n(some details hidden, use --verbose '
300 'to show complete help)'))
302 'to show complete help)'))
301
303
302 return rst
304 return rst
303
305
304
306
305 def helplist(select=None):
307 def helplist(select=None):
306 # list of commands
308 # list of commands
307 if name == "shortlist":
309 if name == "shortlist":
308 header = _('basic commands:\n\n')
310 header = _('basic commands:\n\n')
309 elif name == "debug":
311 elif name == "debug":
310 header = _('debug commands (internal and unsupported):\n\n')
312 header = _('debug commands (internal and unsupported):\n\n')
311 else:
313 else:
312 header = _('list of commands:\n\n')
314 header = _('list of commands:\n\n')
313
315
314 h = {}
316 h = {}
315 cmds = {}
317 cmds = {}
316 for c, e in commands.table.iteritems():
318 for c, e in commands.table.iteritems():
317 f = c.split("|", 1)[0]
319 f = c.split("|", 1)[0]
318 if select and not select(f):
320 if select and not select(f):
319 continue
321 continue
320 if (not select and name != 'shortlist' and
322 if (not select and name != 'shortlist' and
321 e[0].__module__ != commands.__name__):
323 e[0].__module__ != commands.__name__):
322 continue
324 continue
323 if name == "shortlist" and not f.startswith("^"):
325 if name == "shortlist" and not f.startswith("^"):
324 continue
326 continue
325 f = f.lstrip("^")
327 f = f.lstrip("^")
326 if not ui.debugflag and f.startswith("debug") and name != "debug":
328 if not ui.debugflag and f.startswith("debug") and name != "debug":
327 continue
329 continue
328 doc = e[0].__doc__
330 doc = e[0].__doc__
329 if doc and 'DEPRECATED' in doc and not ui.verbose:
331 if doc and 'DEPRECATED' in doc and not ui.verbose:
330 continue
332 continue
331 doc = gettext(doc)
333 doc = gettext(doc)
332 if not doc:
334 if not doc:
333 doc = _("(no help text available)")
335 doc = _("(no help text available)")
334 h[f] = doc.splitlines()[0].rstrip()
336 h[f] = doc.splitlines()[0].rstrip()
335 cmds[f] = c.lstrip("^")
337 cmds[f] = c.lstrip("^")
336
338
337 rst = []
339 rst = []
338 if not h:
340 if not h:
339 if not ui.quiet:
341 if not ui.quiet:
340 rst.append(_('no commands defined\n'))
342 rst.append(_('no commands defined\n'))
341 return rst
343 return rst
342
344
343 if not ui.quiet:
345 if not ui.quiet:
344 rst.append(header)
346 rst.append(header)
345 fns = sorted(h)
347 fns = sorted(h)
346 for f in fns:
348 for f in fns:
347 if ui.verbose:
349 if ui.verbose:
348 commacmds = cmds[f].replace("|",", ")
350 commacmds = cmds[f].replace("|",", ")
349 rst.append(" :%s: %s\n" % (commacmds, h[f]))
351 rst.append(" :%s: %s\n" % (commacmds, h[f]))
350 else:
352 else:
351 rst.append(' :%s: %s\n' % (f, h[f]))
353 rst.append(' :%s: %s\n' % (f, h[f]))
352
354
353 if not name:
355 if not name:
354 exts = listexts(_('enabled extensions:'), extensions.enabled())
356 exts = listexts(_('enabled extensions:'), extensions.enabled())
355 if exts:
357 if exts:
356 rst.append('\n')
358 rst.append('\n')
357 rst.extend(exts)
359 rst.extend(exts)
358
360
359 rst.append(_("\nadditional help topics:\n\n"))
361 rst.append(_("\nadditional help topics:\n\n"))
360 topics = []
362 topics = []
361 for names, header, doc in helptable:
363 for names, header, doc in helptable:
362 topics.append((names[0], header))
364 topics.append((names[0], header))
363 for t, desc in topics:
365 for t, desc in topics:
364 rst.append(" :%s: %s\n" % (t, desc))
366 rst.append(" :%s: %s\n" % (t, desc))
365
367
366 if ui.quiet:
368 if ui.quiet:
367 pass
369 pass
368 elif ui.verbose:
370 elif ui.verbose:
369 rst.append('\n%s\n' % optrst(_("global options"),
371 rst.append('\n%s\n' % optrst(_("global options"),
370 commands.globalopts, ui.verbose))
372 commands.globalopts, ui.verbose))
371 if name == 'shortlist':
373 if name == 'shortlist':
372 rst.append(_('\n(use "hg help" for the full list '
374 rst.append(_('\n(use "hg help" for the full list '
373 'of commands)\n'))
375 'of commands)\n'))
374 else:
376 else:
375 if name == 'shortlist':
377 if name == 'shortlist':
376 rst.append(_('\n(use "hg help" for the full list of commands '
378 rst.append(_('\n(use "hg help" for the full list of commands '
377 'or "hg -v" for details)\n'))
379 'or "hg -v" for details)\n'))
378 elif name and not full:
380 elif name and not full:
379 rst.append(_('\n(use "hg help %s" to show the full help '
381 rst.append(_('\n(use "hg help %s" to show the full help '
380 'text)\n') % name)
382 'text)\n') % name)
381 else:
383 else:
382 rst.append(_('\n(use "hg help -v%s" to show built-in aliases '
384 rst.append(_('\n(use "hg help -v%s" to show built-in aliases '
383 'and global options)\n')
385 'and global options)\n')
384 % (name and " " + name or ""))
386 % (name and " " + name or ""))
385 return rst
387 return rst
386
388
387 def helptopic(name):
389 def helptopic(name):
388 for names, header, doc in helptable:
390 for names, header, doc in helptable:
389 if name in names:
391 if name in names:
390 break
392 break
391 else:
393 else:
392 raise error.UnknownCommand(name)
394 raise error.UnknownCommand(name)
393
395
394 rst = [minirst.section(header)]
396 rst = [minirst.section(header)]
395
397
396 # description
398 # description
397 if not doc:
399 if not doc:
398 rst.append(" %s\n" % _("(no help text available)"))
400 rst.append(" %s\n" % _("(no help text available)"))
399 if callable(doc):
401 if callable(doc):
400 rst += [" %s\n" % l for l in doc().splitlines()]
402 rst += [" %s\n" % l for l in doc().splitlines()]
401
403
402 if not ui.verbose:
404 if not ui.verbose:
403 omitted = _('(some details hidden, use --verbose'
405 omitted = _('(some details hidden, use --verbose'
404 ' to show complete help)')
406 ' to show complete help)')
405 indicateomitted(rst, omitted)
407 indicateomitted(rst, omitted)
406
408
407 try:
409 try:
408 cmdutil.findcmd(name, commands.table)
410 cmdutil.findcmd(name, commands.table)
409 rst.append(_('\nuse "hg help -c %s" to see help for '
411 rst.append(_('\nuse "hg help -c %s" to see help for '
410 'the %s command\n') % (name, name))
412 'the %s command\n') % (name, name))
411 except error.UnknownCommand:
413 except error.UnknownCommand:
412 pass
414 pass
413 return rst
415 return rst
414
416
415 def helpext(name):
417 def helpext(name):
416 try:
418 try:
417 mod = extensions.find(name)
419 mod = extensions.find(name)
418 doc = gettext(mod.__doc__) or _('no help text available')
420 doc = gettext(mod.__doc__) or _('no help text available')
419 except KeyError:
421 except KeyError:
420 mod = None
422 mod = None
421 doc = extensions.disabledext(name)
423 doc = extensions.disabledext(name)
422 if not doc:
424 if not doc:
423 raise error.UnknownCommand(name)
425 raise error.UnknownCommand(name)
424
426
425 if '\n' not in doc:
427 if '\n' not in doc:
426 head, tail = doc, ""
428 head, tail = doc, ""
427 else:
429 else:
428 head, tail = doc.split('\n', 1)
430 head, tail = doc.split('\n', 1)
429 rst = [_('%s extension - %s\n\n') % (name.split('.')[-1], head)]
431 rst = [_('%s extension - %s\n\n') % (name.split('.')[-1], head)]
430 if tail:
432 if tail:
431 rst.extend(tail.splitlines(True))
433 rst.extend(tail.splitlines(True))
432 rst.append('\n')
434 rst.append('\n')
433
435
434 if not ui.verbose:
436 if not ui.verbose:
435 omitted = _('(some details hidden, use --verbose'
437 omitted = _('(some details hidden, use --verbose'
436 ' to show complete help)')
438 ' to show complete help)')
437 indicateomitted(rst, omitted)
439 indicateomitted(rst, omitted)
438
440
439 if mod:
441 if mod:
440 try:
442 try:
441 ct = mod.cmdtable
443 ct = mod.cmdtable
442 except AttributeError:
444 except AttributeError:
443 ct = {}
445 ct = {}
444 modcmds = set([c.split('|', 1)[0] for c in ct])
446 modcmds = set([c.split('|', 1)[0] for c in ct])
445 rst.extend(helplist(modcmds.__contains__))
447 rst.extend(helplist(modcmds.__contains__))
446 else:
448 else:
447 rst.append(_('(use "hg help extensions" for information on enabling'
449 rst.append(_('(use "hg help extensions" for information on enabling'
448 ' extensions)\n'))
450 ' extensions)\n'))
449 return rst
451 return rst
450
452
451 def helpextcmd(name):
453 def helpextcmd(name):
452 cmd, ext, mod = extensions.disabledcmd(ui, name,
454 cmd, ext, mod = extensions.disabledcmd(ui, name,
453 ui.configbool('ui', 'strict'))
455 ui.configbool('ui', 'strict'))
454 doc = gettext(mod.__doc__).splitlines()[0]
456 doc = gettext(mod.__doc__).splitlines()[0]
455
457
456 rst = listexts(_("'%s' is provided by the following "
458 rst = listexts(_("'%s' is provided by the following "
457 "extension:") % cmd, {ext: doc}, indent=4)
459 "extension:") % cmd, {ext: doc}, indent=4)
458 rst.append('\n')
460 rst.append('\n')
459 rst.append(_('(use "hg help extensions" for information on enabling '
461 rst.append(_('(use "hg help extensions" for information on enabling '
460 'extensions)\n'))
462 'extensions)\n'))
461 return rst
463 return rst
462
464
463
465
464 rst = []
466 rst = []
465 kw = opts.get('keyword')
467 kw = opts.get('keyword')
466 if kw:
468 if kw:
467 matches = topicmatch(kw)
469 matches = topicmatch(kw)
468 for t, title in (('topics', _('Topics')),
470 for t, title in (('topics', _('Topics')),
469 ('commands', _('Commands')),
471 ('commands', _('Commands')),
470 ('extensions', _('Extensions')),
472 ('extensions', _('Extensions')),
471 ('extensioncommands', _('Extension Commands'))):
473 ('extensioncommands', _('Extension Commands'))):
472 if matches[t]:
474 if matches[t]:
473 rst.append('%s:\n\n' % title)
475 rst.append('%s:\n\n' % title)
474 rst.extend(minirst.maketable(sorted(matches[t]), 1))
476 rst.extend(minirst.maketable(sorted(matches[t]), 1))
475 rst.append('\n')
477 rst.append('\n')
476 if not rst:
478 if not rst:
477 msg = _('no matches')
479 msg = _('no matches')
478 hint = _('try "hg help" for a list of topics')
480 hint = _('try "hg help" for a list of topics')
479 raise util.Abort(msg, hint=hint)
481 raise util.Abort(msg, hint=hint)
480 elif name and name != 'shortlist':
482 elif name and name != 'shortlist':
481 if unknowncmd:
483 if unknowncmd:
482 queries = (helpextcmd,)
484 queries = (helpextcmd,)
483 elif opts.get('extension'):
485 elif opts.get('extension'):
484 queries = (helpext,)
486 queries = (helpext,)
485 elif opts.get('command'):
487 elif opts.get('command'):
486 queries = (helpcmd,)
488 queries = (helpcmd,)
487 else:
489 else:
488 queries = (helptopic, helpcmd, helpext, helpextcmd)
490 queries = (helptopic, helpcmd, helpext, helpextcmd)
489 for f in queries:
491 for f in queries:
490 try:
492 try:
491 rst = f(name)
493 rst = f(name)
492 break
494 break
493 except error.UnknownCommand:
495 except error.UnknownCommand:
494 pass
496 pass
495 else:
497 else:
496 if unknowncmd:
498 if unknowncmd:
497 raise error.UnknownCommand(name)
499 raise error.UnknownCommand(name)
498 else:
500 else:
499 msg = _('no such help topic: %s') % name
501 msg = _('no such help topic: %s') % name
500 hint = _('try "hg help --keyword %s"') % name
502 hint = _('try "hg help --keyword %s"') % name
501 raise util.Abort(msg, hint=hint)
503 raise util.Abort(msg, hint=hint)
502 else:
504 else:
503 # program name
505 # program name
504 if not ui.quiet:
506 if not ui.quiet:
505 rst = [_("Mercurial Distributed SCM\n"), '\n']
507 rst = [_("Mercurial Distributed SCM\n"), '\n']
506 rst.extend(helplist())
508 rst.extend(helplist())
507
509
508 return ''.join(rst)
510 return ''.join(rst)
@@ -1,515 +1,519 b''
1 $ HGFOO=BAR; export HGFOO
1 $ HGFOO=BAR; export HGFOO
2 $ cat >> $HGRCPATH <<EOF
2 $ cat >> $HGRCPATH <<EOF
3 > [alias]
3 > [alias]
4 > # should clobber ci but not commit (issue2993)
4 > # should clobber ci but not commit (issue2993)
5 > ci = version
5 > ci = version
6 > myinit = init
6 > myinit = init
7 > mycommit = commit
7 > mycommit = commit
8 > optionalrepo = showconfig alias.myinit
8 > optionalrepo = showconfig alias.myinit
9 > cleanstatus = status -c
9 > cleanstatus = status -c
10 > unknown = bargle
10 > unknown = bargle
11 > ambiguous = s
11 > ambiguous = s
12 > recursive = recursive
12 > recursive = recursive
13 > disabled = email
13 > disabled = email
14 > nodefinition =
14 > nodefinition =
15 > noclosingquotation = '
15 > noclosingquotation = '
16 > no--cwd = status --cwd elsewhere
16 > no--cwd = status --cwd elsewhere
17 > no-R = status -R elsewhere
17 > no-R = status -R elsewhere
18 > no--repo = status --repo elsewhere
18 > no--repo = status --repo elsewhere
19 > no--repository = status --repository elsewhere
19 > no--repository = status --repository elsewhere
20 > no--config = status --config a.config=1
20 > no--config = status --config a.config=1
21 > mylog = log
21 > mylog = log
22 > lognull = log -r null
22 > lognull = log -r null
23 > shortlog = log --template '{rev} {node|short} | {date|isodate}\n'
23 > shortlog = log --template '{rev} {node|short} | {date|isodate}\n'
24 > positional = log --template '{\$2} {\$1} | {date|isodate}\n'
24 > positional = log --template '{\$2} {\$1} | {date|isodate}\n'
25 > dln = lognull --debug
25 > dln = lognull --debug
26 > nousage = rollback
26 > nousage = rollback
27 > put = export -r 0 -o "\$FOO/%R.diff"
27 > put = export -r 0 -o "\$FOO/%R.diff"
28 > blank = !printf '\n'
28 > blank = !printf '\n'
29 > self = !printf '\$0\n'
29 > self = !printf '\$0\n'
30 > echoall = !printf '\$@\n'
30 > echoall = !printf '\$@\n'
31 > echo1 = !printf '\$1\n'
31 > echo1 = !printf '\$1\n'
32 > echo2 = !printf '\$2\n'
32 > echo2 = !printf '\$2\n'
33 > echo13 = !printf '\$1 \$3\n'
33 > echo13 = !printf '\$1 \$3\n'
34 > echotokens = !printf "%s\n" "\$@"
34 > echotokens = !printf "%s\n" "\$@"
35 > count = !hg log -r "\$@" --template=. | wc -c | sed -e 's/ //g'
35 > count = !hg log -r "\$@" --template=. | wc -c | sed -e 's/ //g'
36 > mcount = !hg log \$@ --template=. | wc -c | sed -e 's/ //g'
36 > mcount = !hg log \$@ --template=. | wc -c | sed -e 's/ //g'
37 > rt = root
37 > rt = root
38 > tglog = log -G --template "{rev}:{node|short}: '{desc}' {branches}\n"
38 > tglog = log -G --template "{rev}:{node|short}: '{desc}' {branches}\n"
39 > idalias = id
39 > idalias = id
40 > idaliaslong = id
40 > idaliaslong = id
41 > idaliasshell = !echo test
41 > idaliasshell = !echo test
42 > parentsshell1 = !echo one
42 > parentsshell1 = !echo one
43 > parentsshell2 = !echo two
43 > parentsshell2 = !echo two
44 > escaped1 = !printf 'test\$\$test\n'
44 > escaped1 = !printf 'test\$\$test\n'
45 > escaped2 = !sh -c 'echo "HGFOO is \$\$HGFOO"'
45 > escaped2 = !sh -c 'echo "HGFOO is \$\$HGFOO"'
46 > escaped3 = !sh -c 'echo "\$1 is \$\$\$1"'
46 > escaped3 = !sh -c 'echo "\$1 is \$\$\$1"'
47 > escaped4 = !printf '\$\$0 \$\$@\n'
47 > escaped4 = !printf '\$\$0 \$\$@\n'
48 > exit1 = !sh -c 'exit 1'
48 > exit1 = !sh -c 'exit 1'
49 >
49 >
50 > [defaults]
50 > [defaults]
51 > mylog = -q
51 > mylog = -q
52 > lognull = -q
52 > lognull = -q
53 > log = -v
53 > log = -v
54 > EOF
54 > EOF
55
55
56
56
57 basic
57 basic
58
58
59 $ hg myinit alias
59 $ hg myinit alias
60
60
61
61
62 unknown
62 unknown
63
63
64 $ hg unknown
64 $ hg unknown
65 alias 'unknown' resolves to unknown command 'bargle'
65 alias 'unknown' resolves to unknown command 'bargle'
66 [255]
66 [255]
67 $ hg help unknown
67 $ hg help unknown
68 alias 'unknown' resolves to unknown command 'bargle'
68 alias 'unknown' resolves to unknown command 'bargle'
69
69
70
70
71 ambiguous
71 ambiguous
72
72
73 $ hg ambiguous
73 $ hg ambiguous
74 alias 'ambiguous' resolves to ambiguous command 's'
74 alias 'ambiguous' resolves to ambiguous command 's'
75 [255]
75 [255]
76 $ hg help ambiguous
76 $ hg help ambiguous
77 alias 'ambiguous' resolves to ambiguous command 's'
77 alias 'ambiguous' resolves to ambiguous command 's'
78
78
79
79
80 recursive
80 recursive
81
81
82 $ hg recursive
82 $ hg recursive
83 alias 'recursive' resolves to unknown command 'recursive'
83 alias 'recursive' resolves to unknown command 'recursive'
84 [255]
84 [255]
85 $ hg help recursive
85 $ hg help recursive
86 alias 'recursive' resolves to unknown command 'recursive'
86 alias 'recursive' resolves to unknown command 'recursive'
87
87
88
88
89 disabled
89 disabled
90
90
91 $ hg disabled
91 $ hg disabled
92 alias 'disabled' resolves to unknown command 'email'
92 alias 'disabled' resolves to unknown command 'email'
93 'email' is provided by the following extension:
93 'email' is provided by the following extension:
94
94
95 patchbomb command to send changesets as (a series of) patch emails
95 patchbomb command to send changesets as (a series of) patch emails
96
96
97 (use "hg help extensions" for information on enabling extensions)
97 (use "hg help extensions" for information on enabling extensions)
98 [255]
98 [255]
99 $ hg help disabled
99 $ hg help disabled
100 alias 'disabled' resolves to unknown command 'email'
100 alias 'disabled' resolves to unknown command 'email'
101
101 'email' is provided by the following extension:
102 'email' is provided by the following extension:
102
103
103 patchbomb command to send changesets as (a series of) patch emails
104 patchbomb command to send changesets as (a series of) patch emails
104
105
105 (use "hg help extensions" for information on enabling extensions)
106 (use "hg help extensions" for information on enabling extensions)
106
107
107
108
108 no definition
109 no definition
109
110
110 $ hg nodef
111 $ hg nodef
111 no definition for alias 'nodefinition'
112 no definition for alias 'nodefinition'
112 [255]
113 [255]
113 $ hg help nodef
114 $ hg help nodef
114 no definition for alias 'nodefinition'
115 no definition for alias 'nodefinition'
115
116
116
117
117 no closing quotation
118 no closing quotation
118
119
119 $ hg noclosing
120 $ hg noclosing
120 error in definition for alias 'noclosingquotation': No closing quotation
121 error in definition for alias 'noclosingquotation': No closing quotation
121 [255]
122 [255]
122 $ hg help noclosing
123 $ hg help noclosing
123 error in definition for alias 'noclosingquotation': No closing quotation
124 error in definition for alias 'noclosingquotation': No closing quotation
124
125
125
126
126 invalid options
127 invalid options
127
128
128 $ hg no--cwd
129 $ hg no--cwd
129 error in definition for alias 'no--cwd': --cwd may only be given on the command line
130 error in definition for alias 'no--cwd': --cwd may only be given on the command line
130 [255]
131 [255]
131 $ hg help no--cwd
132 $ hg help no--cwd
132 error in definition for alias 'no--cwd': --cwd may only be given on the command line
133 error in definition for alias 'no--cwd': --cwd may only be given on the
134 command line
133 $ hg no-R
135 $ hg no-R
134 error in definition for alias 'no-R': -R may only be given on the command line
136 error in definition for alias 'no-R': -R may only be given on the command line
135 [255]
137 [255]
136 $ hg help no-R
138 $ hg help no-R
137 error in definition for alias 'no-R': -R may only be given on the command line
139 error in definition for alias 'no-R': -R may only be given on the command line
138 $ hg no--repo
140 $ hg no--repo
139 error in definition for alias 'no--repo': --repo may only be given on the command line
141 error in definition for alias 'no--repo': --repo may only be given on the command line
140 [255]
142 [255]
141 $ hg help no--repo
143 $ hg help no--repo
142 error in definition for alias 'no--repo': --repo may only be given on the command line
144 error in definition for alias 'no--repo': --repo may only be given on the
145 command line
143 $ hg no--repository
146 $ hg no--repository
144 error in definition for alias 'no--repository': --repository may only be given on the command line
147 error in definition for alias 'no--repository': --repository may only be given on the command line
145 [255]
148 [255]
146 $ hg help no--repository
149 $ hg help no--repository
147 error in definition for alias 'no--repository': --repository may only be given on the command line
150 error in definition for alias 'no--repository': --repository may only be given
151 on the command line
148 $ hg no--config
152 $ hg no--config
149 error in definition for alias 'no--config': --config may only be given on the command line
153 error in definition for alias 'no--config': --config may only be given on the command line
150 [255]
154 [255]
151
155
152 optional repository
156 optional repository
153
157
154 #if no-outer-repo
158 #if no-outer-repo
155 $ hg optionalrepo
159 $ hg optionalrepo
156 init
160 init
157 #endif
161 #endif
158 $ cd alias
162 $ cd alias
159 $ cat > .hg/hgrc <<EOF
163 $ cat > .hg/hgrc <<EOF
160 > [alias]
164 > [alias]
161 > myinit = init -q
165 > myinit = init -q
162 > EOF
166 > EOF
163 $ hg optionalrepo
167 $ hg optionalrepo
164 init -q
168 init -q
165
169
166 no usage
170 no usage
167
171
168 $ hg nousage
172 $ hg nousage
169 no rollback information available
173 no rollback information available
170 [1]
174 [1]
171
175
172 $ echo foo > foo
176 $ echo foo > foo
173 $ hg commit -Amfoo
177 $ hg commit -Amfoo
174 adding foo
178 adding foo
175
179
176
180
177 with opts
181 with opts
178
182
179 $ hg cleanst
183 $ hg cleanst
180 C foo
184 C foo
181
185
182
186
183 with opts and whitespace
187 with opts and whitespace
184
188
185 $ hg shortlog
189 $ hg shortlog
186 0 e63c23eaa88a | 1970-01-01 00:00 +0000
190 0 e63c23eaa88a | 1970-01-01 00:00 +0000
187
191
188 positional arguments
192 positional arguments
189
193
190 $ hg positional
194 $ hg positional
191 abort: too few arguments for command alias
195 abort: too few arguments for command alias
192 [255]
196 [255]
193 $ hg positional a
197 $ hg positional a
194 abort: too few arguments for command alias
198 abort: too few arguments for command alias
195 [255]
199 [255]
196 $ hg positional 'node|short' rev
200 $ hg positional 'node|short' rev
197 0 e63c23eaa88a | 1970-01-01 00:00 +0000
201 0 e63c23eaa88a | 1970-01-01 00:00 +0000
198
202
199 interaction with defaults
203 interaction with defaults
200
204
201 $ hg mylog
205 $ hg mylog
202 0:e63c23eaa88a
206 0:e63c23eaa88a
203 $ hg lognull
207 $ hg lognull
204 -1:000000000000
208 -1:000000000000
205
209
206
210
207 properly recursive
211 properly recursive
208
212
209 $ hg dln
213 $ hg dln
210 changeset: -1:0000000000000000000000000000000000000000
214 changeset: -1:0000000000000000000000000000000000000000
211 parent: -1:0000000000000000000000000000000000000000
215 parent: -1:0000000000000000000000000000000000000000
212 parent: -1:0000000000000000000000000000000000000000
216 parent: -1:0000000000000000000000000000000000000000
213 manifest: -1:0000000000000000000000000000000000000000
217 manifest: -1:0000000000000000000000000000000000000000
214 user:
218 user:
215 date: Thu Jan 01 00:00:00 1970 +0000
219 date: Thu Jan 01 00:00:00 1970 +0000
216 extra: branch=default
220 extra: branch=default
217
221
218
222
219
223
220 path expanding
224 path expanding
221
225
222 $ FOO=`pwd` hg put
226 $ FOO=`pwd` hg put
223 $ cat 0.diff
227 $ cat 0.diff
224 # HG changeset patch
228 # HG changeset patch
225 # User test
229 # User test
226 # Date 0 0
230 # Date 0 0
227 # Thu Jan 01 00:00:00 1970 +0000
231 # Thu Jan 01 00:00:00 1970 +0000
228 # Node ID e63c23eaa88ae77967edcf4ea194d31167c478b0
232 # Node ID e63c23eaa88ae77967edcf4ea194d31167c478b0
229 # Parent 0000000000000000000000000000000000000000
233 # Parent 0000000000000000000000000000000000000000
230 foo
234 foo
231
235
232 diff -r 000000000000 -r e63c23eaa88a foo
236 diff -r 000000000000 -r e63c23eaa88a foo
233 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
237 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
234 +++ b/foo Thu Jan 01 00:00:00 1970 +0000
238 +++ b/foo Thu Jan 01 00:00:00 1970 +0000
235 @@ -0,0 +1,1 @@
239 @@ -0,0 +1,1 @@
236 +foo
240 +foo
237
241
238
242
239 simple shell aliases
243 simple shell aliases
240
244
241 $ hg blank
245 $ hg blank
242
246
243 $ hg blank foo
247 $ hg blank foo
244
248
245 $ hg self
249 $ hg self
246 self
250 self
247 $ hg echoall
251 $ hg echoall
248
252
249 $ hg echoall foo
253 $ hg echoall foo
250 foo
254 foo
251 $ hg echoall 'test $2' foo
255 $ hg echoall 'test $2' foo
252 test $2 foo
256 test $2 foo
253 $ hg echoall 'test $@' foo '$@'
257 $ hg echoall 'test $@' foo '$@'
254 test $@ foo $@
258 test $@ foo $@
255 $ hg echoall 'test "$@"' foo '"$@"'
259 $ hg echoall 'test "$@"' foo '"$@"'
256 test "$@" foo "$@"
260 test "$@" foo "$@"
257 $ hg echo1 foo bar baz
261 $ hg echo1 foo bar baz
258 foo
262 foo
259 $ hg echo2 foo bar baz
263 $ hg echo2 foo bar baz
260 bar
264 bar
261 $ hg echo13 foo bar baz test
265 $ hg echo13 foo bar baz test
262 foo baz
266 foo baz
263 $ hg echo2 foo
267 $ hg echo2 foo
264
268
265 $ hg echotokens
269 $ hg echotokens
266
270
267 $ hg echotokens foo 'bar $1 baz'
271 $ hg echotokens foo 'bar $1 baz'
268 foo
272 foo
269 bar $1 baz
273 bar $1 baz
270 $ hg echotokens 'test $2' foo
274 $ hg echotokens 'test $2' foo
271 test $2
275 test $2
272 foo
276 foo
273 $ hg echotokens 'test $@' foo '$@'
277 $ hg echotokens 'test $@' foo '$@'
274 test $@
278 test $@
275 foo
279 foo
276 $@
280 $@
277 $ hg echotokens 'test "$@"' foo '"$@"'
281 $ hg echotokens 'test "$@"' foo '"$@"'
278 test "$@"
282 test "$@"
279 foo
283 foo
280 "$@"
284 "$@"
281 $ echo bar > bar
285 $ echo bar > bar
282 $ hg commit -qA -m bar
286 $ hg commit -qA -m bar
283 $ hg count .
287 $ hg count .
284 1
288 1
285 $ hg count 'branch(default)'
289 $ hg count 'branch(default)'
286 2
290 2
287 $ hg mcount -r '"branch(default)"'
291 $ hg mcount -r '"branch(default)"'
288 2
292 2
289
293
290 $ hg tglog
294 $ hg tglog
291 @ 1:042423737847: 'bar'
295 @ 1:042423737847: 'bar'
292 |
296 |
293 o 0:e63c23eaa88a: 'foo'
297 o 0:e63c23eaa88a: 'foo'
294
298
295
299
296
300
297 shadowing
301 shadowing
298
302
299 $ hg i
303 $ hg i
300 hg: command 'i' is ambiguous:
304 hg: command 'i' is ambiguous:
301 idalias idaliaslong idaliasshell identify import incoming init
305 idalias idaliaslong idaliasshell identify import incoming init
302 [255]
306 [255]
303 $ hg id
307 $ hg id
304 042423737847 tip
308 042423737847 tip
305 $ hg ida
309 $ hg ida
306 hg: command 'ida' is ambiguous:
310 hg: command 'ida' is ambiguous:
307 idalias idaliaslong idaliasshell
311 idalias idaliaslong idaliasshell
308 [255]
312 [255]
309 $ hg idalias
313 $ hg idalias
310 042423737847 tip
314 042423737847 tip
311 $ hg idaliasl
315 $ hg idaliasl
312 042423737847 tip
316 042423737847 tip
313 $ hg idaliass
317 $ hg idaliass
314 test
318 test
315 $ hg parentsshell
319 $ hg parentsshell
316 hg: command 'parentsshell' is ambiguous:
320 hg: command 'parentsshell' is ambiguous:
317 parentsshell1 parentsshell2
321 parentsshell1 parentsshell2
318 [255]
322 [255]
319 $ hg parentsshell1
323 $ hg parentsshell1
320 one
324 one
321 $ hg parentsshell2
325 $ hg parentsshell2
322 two
326 two
323
327
324
328
325 shell aliases with global options
329 shell aliases with global options
326
330
327 $ hg init sub
331 $ hg init sub
328 $ cd sub
332 $ cd sub
329 $ hg count 'branch(default)'
333 $ hg count 'branch(default)'
330 abort: unknown revision 'default'!
334 abort: unknown revision 'default'!
331 0
335 0
332 $ hg -v count 'branch(default)'
336 $ hg -v count 'branch(default)'
333 abort: unknown revision 'default'!
337 abort: unknown revision 'default'!
334 0
338 0
335 $ hg -R .. count 'branch(default)'
339 $ hg -R .. count 'branch(default)'
336 abort: unknown revision 'default'!
340 abort: unknown revision 'default'!
337 0
341 0
338 $ hg --cwd .. count 'branch(default)'
342 $ hg --cwd .. count 'branch(default)'
339 2
343 2
340 $ hg echoall --cwd ..
344 $ hg echoall --cwd ..
341
345
342
346
343
347
344 repo specific shell aliases
348 repo specific shell aliases
345
349
346 $ cat >> .hg/hgrc <<EOF
350 $ cat >> .hg/hgrc <<EOF
347 > [alias]
351 > [alias]
348 > subalias = !echo sub
352 > subalias = !echo sub
349 > EOF
353 > EOF
350 $ cat >> ../.hg/hgrc <<EOF
354 $ cat >> ../.hg/hgrc <<EOF
351 > [alias]
355 > [alias]
352 > mainalias = !echo main
356 > mainalias = !echo main
353 > EOF
357 > EOF
354
358
355
359
356 shell alias defined in current repo
360 shell alias defined in current repo
357
361
358 $ hg subalias
362 $ hg subalias
359 sub
363 sub
360 $ hg --cwd .. subalias > /dev/null
364 $ hg --cwd .. subalias > /dev/null
361 hg: unknown command 'subalias'
365 hg: unknown command 'subalias'
362 [255]
366 [255]
363 $ hg -R .. subalias > /dev/null
367 $ hg -R .. subalias > /dev/null
364 hg: unknown command 'subalias'
368 hg: unknown command 'subalias'
365 [255]
369 [255]
366
370
367
371
368 shell alias defined in other repo
372 shell alias defined in other repo
369
373
370 $ hg mainalias > /dev/null
374 $ hg mainalias > /dev/null
371 hg: unknown command 'mainalias'
375 hg: unknown command 'mainalias'
372 [255]
376 [255]
373 $ hg -R .. mainalias
377 $ hg -R .. mainalias
374 main
378 main
375 $ hg --cwd .. mainalias
379 $ hg --cwd .. mainalias
376 main
380 main
377
381
378
382
379 shell aliases with escaped $ chars
383 shell aliases with escaped $ chars
380
384
381 $ hg escaped1
385 $ hg escaped1
382 test$test
386 test$test
383 $ hg escaped2
387 $ hg escaped2
384 HGFOO is BAR
388 HGFOO is BAR
385 $ hg escaped3 HGFOO
389 $ hg escaped3 HGFOO
386 HGFOO is BAR
390 HGFOO is BAR
387 $ hg escaped4 test
391 $ hg escaped4 test
388 $0 $@
392 $0 $@
389
393
390 abbreviated name, which matches against both shell alias and the
394 abbreviated name, which matches against both shell alias and the
391 command provided extension, should be aborted.
395 command provided extension, should be aborted.
392
396
393 $ cat >> .hg/hgrc <<EOF
397 $ cat >> .hg/hgrc <<EOF
394 > [extensions]
398 > [extensions]
395 > hgext.rebase =
399 > hgext.rebase =
396 > [alias]
400 > [alias]
397 > rebate = !echo this is rebate
401 > rebate = !echo this is rebate
398 > EOF
402 > EOF
399 $ hg reba
403 $ hg reba
400 hg: command 'reba' is ambiguous:
404 hg: command 'reba' is ambiguous:
401 rebase rebate
405 rebase rebate
402 [255]
406 [255]
403 $ hg rebat
407 $ hg rebat
404 this is rebate
408 this is rebate
405
409
406 invalid arguments
410 invalid arguments
407
411
408 $ hg rt foo
412 $ hg rt foo
409 hg rt: invalid arguments
413 hg rt: invalid arguments
410 hg rt
414 hg rt
411
415
412 alias for: hg root
416 alias for: hg root
413
417
414 (use "hg rt -h" to show more help)
418 (use "hg rt -h" to show more help)
415 [255]
419 [255]
416
420
417 invalid global arguments for normal commands, aliases, and shell aliases
421 invalid global arguments for normal commands, aliases, and shell aliases
418
422
419 $ hg --invalid root
423 $ hg --invalid root
420 hg: option --invalid not recognized
424 hg: option --invalid not recognized
421 Mercurial Distributed SCM
425 Mercurial Distributed SCM
422
426
423 basic commands:
427 basic commands:
424
428
425 add add the specified files on the next commit
429 add add the specified files on the next commit
426 annotate show changeset information by line for each file
430 annotate show changeset information by line for each file
427 clone make a copy of an existing repository
431 clone make a copy of an existing repository
428 commit commit the specified files or all outstanding changes
432 commit commit the specified files or all outstanding changes
429 diff diff repository (or selected files)
433 diff diff repository (or selected files)
430 export dump the header and diffs for one or more changesets
434 export dump the header and diffs for one or more changesets
431 forget forget the specified files on the next commit
435 forget forget the specified files on the next commit
432 init create a new repository in the given directory
436 init create a new repository in the given directory
433 log show revision history of entire repository or files
437 log show revision history of entire repository or files
434 merge merge working directory with another revision
438 merge merge working directory with another revision
435 pull pull changes from the specified source
439 pull pull changes from the specified source
436 push push changes to the specified destination
440 push push changes to the specified destination
437 remove remove the specified files on the next commit
441 remove remove the specified files on the next commit
438 serve start stand-alone webserver
442 serve start stand-alone webserver
439 status show changed files in the working directory
443 status show changed files in the working directory
440 summary summarize working directory state
444 summary summarize working directory state
441 update update working directory (or switch revisions)
445 update update working directory (or switch revisions)
442
446
443 (use "hg help" for the full list of commands or "hg -v" for details)
447 (use "hg help" for the full list of commands or "hg -v" for details)
444 [255]
448 [255]
445 $ hg --invalid mylog
449 $ hg --invalid mylog
446 hg: option --invalid not recognized
450 hg: option --invalid not recognized
447 Mercurial Distributed SCM
451 Mercurial Distributed SCM
448
452
449 basic commands:
453 basic commands:
450
454
451 add add the specified files on the next commit
455 add add the specified files on the next commit
452 annotate show changeset information by line for each file
456 annotate show changeset information by line for each file
453 clone make a copy of an existing repository
457 clone make a copy of an existing repository
454 commit commit the specified files or all outstanding changes
458 commit commit the specified files or all outstanding changes
455 diff diff repository (or selected files)
459 diff diff repository (or selected files)
456 export dump the header and diffs for one or more changesets
460 export dump the header and diffs for one or more changesets
457 forget forget the specified files on the next commit
461 forget forget the specified files on the next commit
458 init create a new repository in the given directory
462 init create a new repository in the given directory
459 log show revision history of entire repository or files
463 log show revision history of entire repository or files
460 merge merge working directory with another revision
464 merge merge working directory with another revision
461 pull pull changes from the specified source
465 pull pull changes from the specified source
462 push push changes to the specified destination
466 push push changes to the specified destination
463 remove remove the specified files on the next commit
467 remove remove the specified files on the next commit
464 serve start stand-alone webserver
468 serve start stand-alone webserver
465 status show changed files in the working directory
469 status show changed files in the working directory
466 summary summarize working directory state
470 summary summarize working directory state
467 update update working directory (or switch revisions)
471 update update working directory (or switch revisions)
468
472
469 (use "hg help" for the full list of commands or "hg -v" for details)
473 (use "hg help" for the full list of commands or "hg -v" for details)
470 [255]
474 [255]
471 $ hg --invalid blank
475 $ hg --invalid blank
472 hg: option --invalid not recognized
476 hg: option --invalid not recognized
473 Mercurial Distributed SCM
477 Mercurial Distributed SCM
474
478
475 basic commands:
479 basic commands:
476
480
477 add add the specified files on the next commit
481 add add the specified files on the next commit
478 annotate show changeset information by line for each file
482 annotate show changeset information by line for each file
479 clone make a copy of an existing repository
483 clone make a copy of an existing repository
480 commit commit the specified files or all outstanding changes
484 commit commit the specified files or all outstanding changes
481 diff diff repository (or selected files)
485 diff diff repository (or selected files)
482 export dump the header and diffs for one or more changesets
486 export dump the header and diffs for one or more changesets
483 forget forget the specified files on the next commit
487 forget forget the specified files on the next commit
484 init create a new repository in the given directory
488 init create a new repository in the given directory
485 log show revision history of entire repository or files
489 log show revision history of entire repository or files
486 merge merge working directory with another revision
490 merge merge working directory with another revision
487 pull pull changes from the specified source
491 pull pull changes from the specified source
488 push push changes to the specified destination
492 push push changes to the specified destination
489 remove remove the specified files on the next commit
493 remove remove the specified files on the next commit
490 serve start stand-alone webserver
494 serve start stand-alone webserver
491 status show changed files in the working directory
495 status show changed files in the working directory
492 summary summarize working directory state
496 summary summarize working directory state
493 update update working directory (or switch revisions)
497 update update working directory (or switch revisions)
494
498
495 (use "hg help" for the full list of commands or "hg -v" for details)
499 (use "hg help" for the full list of commands or "hg -v" for details)
496 [255]
500 [255]
497
501
498 This should show id:
502 This should show id:
499
503
500 $ hg --config alias.log='id' log
504 $ hg --config alias.log='id' log
501 000000000000 tip
505 000000000000 tip
502
506
503 This shouldn't:
507 This shouldn't:
504
508
505 $ hg --config alias.log='id' history
509 $ hg --config alias.log='id' history
506
510
507 $ cd ../..
511 $ cd ../..
508
512
509 return code of command and shell aliases:
513 return code of command and shell aliases:
510
514
511 $ hg mycommit -R alias
515 $ hg mycommit -R alias
512 nothing changed
516 nothing changed
513 [1]
517 [1]
514 $ hg exit1
518 $ hg exit1
515 [1]
519 [1]
General Comments 0
You need to be logged in to leave comments. Login now