Skip to content

Commit

Permalink
support for cyclic next/prev
Browse files Browse the repository at this point in the history
  • Loading branch information
Itay Donanhirsh committed Feb 7, 2021
1 parent 2aa48e2 commit de1d467
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 16 deletions.
17 changes: 13 additions & 4 deletions cmd/clutter/cmd_resolve.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import (
"fmt"

cli "github.com/urfave/cli/v2"
"go.uber.org/zap"

"github.com/cluttercode/clutter/internal/pkg/resolver"
"github.com/cluttercode/clutter/internal/pkg/scanner"
Expand All @@ -13,8 +14,8 @@ import (

var (
resolveOpts = struct {
content, loc string
prev, next bool
content, loc string
prev, next, cyclic bool
}{}

resolveCommand = cli.Command{
Expand All @@ -34,6 +35,12 @@ var (
Usage: "show only the next match after the one specified",
Destination: &resolveOpts.next,
},
&cli.BoolFlag{
Name: "cyclic",
Aliases: []string{"c"},
Usage: "make --next and --prev cyclic",
Destination: &resolveOpts.cyclic,
},
&cli.StringFlag{
Name: "loc",
Aliases: []string{"l"},
Expand Down Expand Up @@ -84,15 +91,17 @@ var (

z.Info("resolved tag")

r := resolver.ResolveList
r := func(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index, _ bool) ([]*clutterindex.Entry, error) {
return resolver.ResolveList(z, what, index)
}

if resolveOpts.next {
r = resolver.ResolveNext
} else if resolveOpts.prev {
r = resolver.ResolvePrev
}

ents, err := r(z, what, index)
ents, err := r(z, what, index, resolveOpts.cyclic)

if err != nil {
return fmt.Errorf("resolver: %w", err)
Expand Down
42 changes: 30 additions & 12 deletions internal/pkg/resolver/resolver.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,28 +8,30 @@ import (
"github.com/cluttercode/clutter/pkg/clutter/clutterindex"
)

type params struct{ next, prev, cycle, first, last bool }

func ResolveList(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index) ([]*clutterindex.Entry, error) {
return resolve(z, what, index, false, false)
return resolve(z, what, index, params{})
}

func ResolveNext(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index) ([]*clutterindex.Entry, error) {
return resolve(z, what, index, true, false)
func ResolveNext(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index, cycle bool) ([]*clutterindex.Entry, error) {
return resolve(z, what, index, params{next: true, cycle: cycle})
}

func ResolvePrev(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index) ([]*clutterindex.Entry, error) {
return resolve(z, what, index, false, true)
func ResolvePrev(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index, cycle bool) ([]*clutterindex.Entry, error) {
return resolve(z, what, index, params{prev: true, cycle: cycle})
}

func resolve(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index, next, prev bool) ([]*clutterindex.Entry, error) {
if next && prev {
func resolve(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex.Index, p params) ([]*clutterindex.Entry, error) {
if p.next && p.prev {
z.Panic("prev and next are mutually exclusive")
}

matcher := func(ent *clutterindex.Entry) bool { return what.Name == ent.Name && ent.IsReferredBy(what) }

if _, search := what.IsSearch(); search {
if prev || next {
prev, next = false, false
if p.prev || p.next {
p.prev, p.next = false, false
z.Warn("--next and --prev are ignored when resolving a search tag")
}

Expand All @@ -56,7 +58,7 @@ func resolve(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex
return nil
}

if prev {
if p.prev {
if ent.Loc == what.Loc {
if hold == nil {
z.Debugw("found what, but nothing held")
Expand All @@ -65,7 +67,7 @@ func resolve(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex

z.Debugw("found what, emit held", "ent", hold)

fmt.Println(hold.String())
ents = append(ents, hold)

return clutterindex.ErrStop
}
Expand All @@ -76,7 +78,7 @@ func resolve(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex
return nil
}

if next {
if p.next {
if hold == nil {
if ent.Loc == what.Loc {
hold = ent
Expand All @@ -95,11 +97,27 @@ func resolve(z *zap.SugaredLogger, what *clutterindex.Entry, index *clutterindex

ents = append(ents, ent)

if p.first {
return clutterindex.ErrStop
}

return nil
},
); err != nil {
return nil, fmt.Errorf("filter: %w", err)
}

if p.cycle && len(ents) == 0 {
if p.next {
return resolve(z, what, index, params{first: true})
} else if p.prev {
return resolve(z, what, index, params{last: true})
}
}

if p.last && len(ents) > 0 {
return []*clutterindex.Entry{ents[len(ents)-1]}, nil
}

return ents, nil
}
12 changes: 12 additions & 0 deletions tests/cli/resolve.clitest
Original file line number Diff line number Diff line change
Expand Up @@ -26,14 +26,26 @@ z b:2.2-10
z c:3.3-10
$ ${CLUTTER} -i index.1 r --loc a:1.1 -n
z b:2.2-10
$ ${CLUTTER} -i index.1 r --loc a:1.1 -n -c
z b:2.2-10
$ ${CLUTTER} -i index.1 r --loc a:1.1 -p
$ ${CLUTTER} -i index.1 r --loc a:1.1 -p -c
z c:3.3-10
$ ${CLUTTER} -i index.1 r --loc b:2.2 -p
z a:1.1-10
$ ${CLUTTER} -i index.1 r --loc b:2.2 -p -c
z a:1.1-10
$ ${CLUTTER} -i index.1 r --loc b:2.2 -n
z c:3.3-10
$ ${CLUTTER} -i index.1 r --loc b:2.2 -n -c
z c:3.3-10
$ ${CLUTTER} -i index.1 r --loc c:3.3 -p
z b:2.2-10
$ ${CLUTTER} -i index.1 r --loc c:3.3 -p -c
z b:2.2-10
$ ${CLUTTER} -i index.1 r --loc c:3.3 -n
$ ${CLUTTER} -i index.1 r --loc c:3.3 -n -c
z a:1.1-10
$ ${CLUTTER} -i index.1 r --loc c:3.3 -n -p; echo $?

error: --prev and --next are mutually exclusive
Expand Down

0 comments on commit de1d467

Please sign in to comment.