RFC: revset relation operator

Gregory Szorc gregory.szorc at gmail.com
Mon Oct 12 18:37:07 CDT 2015


On Mon, Oct 12, 2015 at 2:26 PM, Matt Mackall <mpm at selenic.com> wrote:

> On Mon, 2015-10-12 at 10:07 -0400, Augie Fackler wrote:
> > On Sun, Oct 11, 2015 at 05:45:24PM -0500, Matt Mackall wrote:
> > > It would be nice if we had a convenience syntax for finding things
> > > related to a given changeset. Currently, we have a couple of these for
> > > parents, ancestors, and descendants.
> > >
> > >  foo^  # first parent
> > >  foo^2 # second parent
> > >  foo^^ # first parent of first parent
> > >  foo~2 # same
> > >  ::foo # ancestors, inclusive
> > >  foo:: # descendants, inclusize
> > >
> > > But we have nothing directly equivalent to parents(), nor any shorthand
> > > for children(), successors(), origin(), destination(), or any other
> type
> > > of relation we may add. We'd also like a way to specify next, previous,
> > > all, all exclusive, last, etc.
> > >
> > > So my proposal[1] is to add a bracketed postfix (one of {}, [], or <>,
> > > but perhaps {} is the least bad) that looks like this:
> > >
> > >  foo{1}     # children(foo)
> > >  foo{2}     # children(children(foo))
> > >  foo{}      # defaults to 1, so children(foo)
> > >  foo{0}     # synonym for foo
> > >  foo{-1}    # parents(foo) (both of 'em)
> > >  foo{-}     # same
> > >  foo{*}     # foo:: - foo (exclusive)
> > >  foo{**}    # foo:: (inclusive)
> > >  foo{-*}    # ::foo - foo
> > >  foo{$}     # heads(foo::) aka "the last children"
> > >  foo{-4}::foo # last five changesets in a branch
> > >
> > > This makes a lot of our most common expressions shorter. To talk about
> > > other types of relations, we use a suffix character:
> > >
> > >  foo{1g}    # immediate grafts of foo
> > >  foo{-g}    # origin for grafts
> > >  foo{o}     # successor(foo)
> > >  foo{$o}    # final successor of foo
> >
> > Neat. The one-character suffix thing gives me a little pause as
> > possibly-not-entirely-self-documenting. Maybe it could be whole [a-z]
> > words, and we could allow unambiguous prefixes?
>
> s/prefixes/suffixes/, sure. Definitely makes more sense for the long
> form.
>
> I think the specific feedback I'm looking for here is how do folks feel
> about:
>
> - using {} for the operator
> - allowing empty {} to be children()
> - allowing bare "-" with no numeral
> - using * and ** (and -* and -**) for all
> - using $ (and -$) for end/last
> - suffix characters/words for relation dimension
> - any common operations I might be forgetting
>
> This is kind of a lot of new weird syntax all at once and I haven't
> completely convinced myself that it's not too horrible.
>

To be honest, my immediate reaction was this syntax was a bit complex
(although powerful!) and I was somewhat surprised to see the proposal from
you, as you are normally the one encouraging simplicity :)

The amount of things you can include inside the brackets I feel is a bit
overwhelming.

I find the numbers pretty intuitive for finding "neighbors."

I'm not a huge fan of '{-}' and '{}' because they add cognitive dissonance.
If we only accepted numbers, fine. But when you can do N things with the
syntax, now you have to remember that '-' and '' are special cases of "N."
This is starting to look like Perl's special variables.

$ for heads makes sense (if you know regular expressions).

'*' '**' and '-*' aren't very obvious. I think * is wildcard matching in
any context. And Mercurial already uses * for file matching, so I think
these are more confusion than they are worth.

If 'foo{**}' is equivalent to 'foo::' why bother?

The single letter operations are neat. But overwhelming. I /think/ I'd
rather see single letter functions instead. 'o(foo){$}' is more typing than
'foo{$o}' but for some reason it feels clearer. Perhaps it's because my
mind is trying to make a distinction between low-level DAG operations
(things I see clearly belonging in this proposed syntax) and more complex,
high-level functions (which I think are better represented as normal revset
functions). But if we're trying to advance the concepts of successors and
predecessors, I can kinda see how we'd want to push those as low-level DAG
operations (and thus suitable for {}). But I'm still not convinced the
extra clutter is worth it.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://selenic.com/pipermail/mercurial-devel/attachments/20151012/d1803aaa/attachment.html>


More information about the Mercurial-devel mailing list