aboutsummaryrefslogtreecommitdiffstats
path: root/graphql2
diff options
context:
space:
mode:
authorMichael Muré <batolettre@gmail.com>2018-07-29 18:11:33 +0200
committerMichael Muré <batolettre@gmail.com>2018-07-29 18:51:56 +0200
commit6363518c85cbd8247a5f6507b8a1dd3903cfb71d (patch)
treeaa51652e9881196b3637247988cbd5155f42b5e2 /graphql2
parentff2fd14e3f10a7206d4ec86f07e524cfa290e0fc (diff)
downloadgit-bug-6363518c85cbd8247a5f6507b8a1dd3903cfb71d.tar.gz
relay connection working with gqlgen
Diffstat (limited to 'graphql2')
-rw-r--r--graphql2/gqlgen.yml11
-rw-r--r--graphql2/handler.go18
-rw-r--r--graphql2/relay.go39
-rw-r--r--graphql2/resolvers.go82
-rw-r--r--graphql2/resolvers/bug.go61
-rw-r--r--graphql2/resolvers/generated_graph.go (renamed from graphql2/gen/graph.go)946
-rw-r--r--graphql2/resolvers/generated_model.go (renamed from graphql2/gen/model.go)40
-rw-r--r--graphql2/resolvers/operations.go54
-rw-r--r--graphql2/resolvers/pager_bug.go225
-rw-r--r--graphql2/resolvers/pager_comment.go225
-rw-r--r--graphql2/resolvers/pager_operation.go225
-rw-r--r--graphql2/resolvers/pagers.go51
-rw-r--r--graphql2/resolvers/pagers_template.go224
-rw-r--r--graphql2/resolvers/query.go36
-rw-r--r--graphql2/resolvers/repo.go26
-rw-r--r--graphql2/resolvers/root.go53
-rw-r--r--graphql2/schema.graphql120
17 files changed, 1629 insertions, 807 deletions
diff --git a/graphql2/gqlgen.yml b/graphql2/gqlgen.yml
index 60ea0c49..d7c096bf 100644
--- a/graphql2/gqlgen.yml
+++ b/graphql2/gqlgen.yml
@@ -1,10 +1,17 @@
schema: schema.graphql
exec:
- filename: gen/graph.go
+ filename: resolvers/generated_graph.go
model:
- filename: gen/model.go
+ filename: resolvers/generated_model.go
models:
+ Repository:
+ fields:
+ bug:
+ resolver: true
+ allBugs:
+ resolver: true
+# model: github.com/MichaelMure/git-bug/graphql2/resolvers.repoResolver
Bug:
model: github.com/MichaelMure/git-bug/bug.Snapshot
Comment:
diff --git a/graphql2/handler.go b/graphql2/handler.go
new file mode 100644
index 00000000..2bf6df8c
--- /dev/null
+++ b/graphql2/handler.go
@@ -0,0 +1,18 @@
+//go:generate gorunpkg github.com/vektah/gqlgen
+
+package graphql2
+
+import (
+ "github.com/MichaelMure/git-bug/graphql2/resolvers"
+ "github.com/MichaelMure/git-bug/repository"
+ "github.com/vektah/gqlgen/handler"
+ "net/http"
+)
+
+func NewHandler(repo repository.Repo) http.Handler {
+ backend := resolvers.NewRootResolver()
+
+ backend.RegisterDefaultRepository(repo)
+
+ return handler.GraphQL(resolvers.NewExecutableSchema(backend))
+}
diff --git a/graphql2/relay.go b/graphql2/relay.go
new file mode 100644
index 00000000..b037f28b
--- /dev/null
+++ b/graphql2/relay.go
@@ -0,0 +1,39 @@
+package graphql2
+
+import (
+ "encoding/base64"
+ "strings"
+)
+
+
+type ResolvedGlobalID struct {
+ Type string `json:"type"`
+ ID string `json:"id"`
+}
+
+// Takes a type name and an ID specific to that type name, and returns a
+// "global ID" that is unique among all types.
+func ToGlobalID(ttype string, id string) string {
+ str := ttype + ":" + id
+ encStr := base64.StdEncoding.EncodeToString([]byte(str))
+ return encStr
+}
+
+// Takes the "global ID" created by toGlobalID, and returns the type name and ID
+// used to create it.
+func FromGlobalID(globalID string) *ResolvedGlobalID {
+ strID := ""
+ b, err := base64.StdEncoding.DecodeString(globalID)
+ if err == nil {
+ strID = string(b)
+ }
+ tokens := strings.Split(strID, ":")
+ if len(tokens) < 2 {
+ return nil
+ }
+ return &ResolvedGlobalID{
+ Type: tokens[0],
+ ID: tokens[1],
+ }
+}
+
diff --git a/graphql2/resolvers.go b/graphql2/resolvers.go
deleted file mode 100644
index fa47f222..00000000
--- a/graphql2/resolvers.go
+++ /dev/null
@@ -1,82 +0,0 @@
-package graphql2
-
-import (
- "context"
- "fmt"
- "github.com/MichaelMure/git-bug/bug"
- "github.com/MichaelMure/git-bug/bug/operations"
- "github.com/MichaelMure/git-bug/cache"
- "github.com/MichaelMure/git-bug/graphql2/gen"
- "time"
-)
-
-type Backend struct {
- cache cache.RootCache
-}
-
-func (*Backend) Bug_labels(ctx context.Context, obj *bug.Snapshot) ([]*bug.Label, error) {
- return obj.Labels
-}
-
-func (*Backend) LabelChangeOperation_added(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error) {
- panic("implement me")
-}
-
-func (*Backend) LabelChangeOperation_removed(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error) {
- panic("implement me")
-}
-
-func (*Backend) AddCommentOperation_date(ctx context.Context, obj *operations.AddCommentOperation) (time.Time, error) {
- return obj.Time(), nil
-}
-
-func (*Backend) Bug_status(ctx context.Context, obj *bug.Snapshot) (gen.Status, error) {
- return convertStatus(obj.Status)
-}
-
-func (*Backend) Bug_comments(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (gen.CommentConnection, error) {
- panic("implement me")
-}
-
-func (*Backend) Bug_operations(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (gen.OperationConnection, error) {
- panic("implement me")
-}
-
-func (*Backend) CreateOperation_date(ctx context.Context, obj *operations.CreateOperation) (time.Time, error) {
- return obj.Time(), nil
-}
-
-func (*Backend) LabelChangeOperation_date(ctx context.Context, obj *operations.LabelChangeOperation) (time.Time, error) {
- return obj.Time(), nil
-}
-
-func (*Backend) RootQuery_allBugs(ctx context.Context, after *string, before *string, first *int, last *int, query *string) (gen.BugConnection, error) {
- panic("implement me")
-}
-
-func (*Backend) RootQuery_bug(ctx context.Context, id string) (*bug.Snapshot, error) {
- panic("implement me")
-}
-
-func (*Backend) SetStatusOperation_date(ctx context.Context, obj *operations.SetStatusOperation) (time.Time, error) {
- return obj.Time(), nil
-}
-
-func (*Backend) SetStatusOperation_status(ctx context.Context, obj *operations.SetStatusOperation) (gen.Status, error) {
- return convertStatus(obj.Status)
-}
-
-func (*Backend) SetTitleOperation_date(ctx context.Context, obj *operations.SetTitleOperation) (time.Time, error) {
- return obj.Time(), nil
-}
-
-func convertStatus(status bug.Status) (gen.Status, error) {
- switch status {
- case bug.OpenStatus:
- return gen.StatusOpen, nil
- case bug.ClosedStatus:
- return gen.StatusClosed, nil
- }
-
- return "", fmt.Errorf("Unknown status")
-}
diff --git a/graphql2/resolvers/bug.go b/graphql2/resolvers/bug.go
new file mode 100644
index 00000000..ad6c288b
--- /dev/null
+++ b/graphql2/resolvers/bug.go
@@ -0,0 +1,61 @@
+package resolvers
+
+import (
+ "context"
+ "github.com/MichaelMure/git-bug/bug"
+ "github.com/MichaelMure/git-bug/cache"
+)
+
+type bugResolver struct {
+ cache cache.Cacher
+}
+
+func (bugResolver) Status(ctx context.Context, obj *bug.Snapshot) (Status, error) {
+ return convertStatus(obj.Status)
+}
+
+func (bugResolver) Comments(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (CommentConnection, error) {
+ var connection CommentConnection
+
+ edger := func(comment bug.Comment, offset int) Edge {
+ return CommentEdge{
+ Node: comment,
+ Cursor: offsetToCursor(offset),
+ }
+ }
+
+ edges, pageInfo, err := BugCommentPaginate(obj.Comments, edger, input)
+
+ if err != nil {
+ return connection, err
+ }
+
+ connection.Edges = edges
+ connection.PageInfo = pageInfo
+ connection.TotalCount = len(obj.Comments)
+
+ return connection, nil
+}
+
+func (bugResolver) Operations(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (OperationConnection, error) {
+ var connection OperationConnection
+
+ edger := func(op bug.Operation, offset int) Edge {
+ return OperationEdge{
+ Node: op.(OperationUnion),
+ Cursor: offsetToCursor(offset),
+ }
+ }
+
+ edges, pageInfo, err := BugOperationPaginate(obj.Operations, edger, input)
+
+ if err != nil {
+ return connection, err
+ }
+
+ connection.Edges = edges
+ connection.PageInfo = pageInfo
+ connection.TotalCount = len(obj.Operations)
+
+ return connection, nil
+}
diff --git a/graphql2/gen/graph.go b/graphql2/resolvers/generated_graph.go
index d5249dea..3d752ddc 100644
--- a/graphql2/gen/graph.go
+++ b/graphql2/resolvers/generated_graph.go
@@ -1,6 +1,6 @@
// Code generated by github.com/vektah/gqlgen, DO NOT EDIT.
-package gen
+package resolvers
import (
"bytes"
@@ -31,18 +31,19 @@ type Resolvers interface {
AddCommentOperation_date(ctx context.Context, obj *operations.AddCommentOperation) (time.Time, error)
Bug_status(ctx context.Context, obj *bug.Snapshot) (Status, error)
- Bug_labels(ctx context.Context, obj *bug.Snapshot) ([]*bug.Label, error)
- Bug_comments(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (CommentConnection, error)
- Bug_operations(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (OperationConnection, error)
+
+ Bug_comments(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (CommentConnection, error)
+ Bug_operations(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (OperationConnection, error)
CreateOperation_date(ctx context.Context, obj *operations.CreateOperation) (time.Time, error)
LabelChangeOperation_date(ctx context.Context, obj *operations.LabelChangeOperation) (time.Time, error)
- LabelChangeOperation_added(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error)
- LabelChangeOperation_removed(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error)
- RootQuery_allBugs(ctx context.Context, after *string, before *string, first *int, last *int, query *string) (BugConnection, error)
- RootQuery_bug(ctx context.Context, id string) (*bug.Snapshot, error)
+ Query_defaultRepository(ctx context.Context) (*repoResolver, error)
+ Query_repository(ctx context.Context, id string) (*repoResolver, error)
+
+ Repository_allBugs(ctx context.Context, obj *repoResolver, input ConnectionInput) (BugConnection, error)
+ Repository_bug(ctx context.Context, obj *repoResolver, prefix string) (*bug.Snapshot, error)
SetStatusOperation_date(ctx context.Context, obj *operations.SetStatusOperation) (time.Time, error)
SetStatusOperation_status(ctx context.Context, obj *operations.SetStatusOperation) (Status, error)
@@ -55,7 +56,8 @@ type ResolverRoot interface {
Bug() BugResolver
CreateOperation() CreateOperationResolver
LabelChangeOperation() LabelChangeOperationResolver
- RootQuery() RootQueryResolver
+ Query() QueryResolver
+ Repository() RepositoryResolver
SetStatusOperation() SetStatusOperationResolver
SetTitleOperation() SetTitleOperationResolver
}
@@ -64,21 +66,23 @@ type AddCommentOperationResolver interface {
}
type BugResolver interface {
Status(ctx context.Context, obj *bug.Snapshot) (Status, error)
- Labels(ctx context.Context, obj *bug.Snapshot) ([]*bug.Label, error)
- Comments(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (CommentConnection, error)
- Operations(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (OperationConnection, error)
+
+ Comments(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (CommentConnection, error)
+ Operations(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (OperationConnection, error)
}
type CreateOperationResolver interface {
Date(ctx context.Context, obj *operations.CreateOperation) (time.Time, error)
}
type LabelChangeOperationResolver interface {
Date(ctx context.Context, obj *operations.LabelChangeOperation) (time.Time, error)
- Added(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error)
- Removed(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error)
}
-type RootQueryResolver interface {
- AllBugs(ctx context.Context, after *string, before *string, first *int, last *int, query *string) (BugConnection, error)
- Bug(ctx context.Context, id string) (*bug.Snapshot, error)
+type QueryResolver interface {
+ DefaultRepository(ctx context.Context) (*repoResolver, error)
+ Repository(ctx context.Context, id string) (*repoResolver, error)
+}
+type RepositoryResolver interface {
+ AllBugs(ctx context.Context, obj *repoResolver, input ConnectionInput) (BugConnection, error)
+ Bug(ctx context.Context, obj *repoResolver, prefix string) (*bug.Snapshot, error)
}
type SetStatusOperationResolver interface {
Date(ctx context.Context, obj *operations.SetStatusOperation) (time.Time, error)
@@ -100,16 +104,12 @@ func (s shortMapper) Bug_status(ctx context.Context, obj *bug.Snapshot) (Status,
return s.r.Bug().Status(ctx, obj)
}
-func (s shortMapper) Bug_labels(ctx context.Context, obj *bug.Snapshot) ([]*bug.Label, error) {
- return s.r.Bug().Labels(ctx, obj)
+func (s shortMapper) Bug_comments(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (CommentConnection, error) {
+ return s.r.Bug().Comments(ctx, obj, input)
}
-func (s shortMapper) Bug_comments(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (CommentConnection, error) {
- return s.r.Bug().Comments(ctx, obj, after, before, first, last, query)
-}
-
-func (s shortMapper) Bug_operations(ctx context.Context, obj *bug.Snapshot, after *string, before *string, first *int, last *int, query *string) (OperationConnection, error) {
- return s.r.Bug().Operations(ctx, obj, after, before, first, last, query)
+func (s shortMapper) Bug_operations(ctx context.Context, obj *bug.Snapshot, input ConnectionInput) (OperationConnection, error) {
+ return s.r.Bug().Operations(ctx, obj, input)
}
func (s shortMapper) CreateOperation_date(ctx context.Context, obj *operations.CreateOperation) (time.Time, error) {
@@ -120,20 +120,20 @@ func (s shortMapper) LabelChangeOperation_date(ctx context.Context, obj *operati
return s.r.LabelChangeOperation().Date(ctx, obj)
}
-func (s shortMapper) LabelChangeOperation_added(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error) {
- return s.r.LabelChangeOperation().Added(ctx, obj)
+func (s shortMapper) Query_defaultRepository(ctx context.Context) (*repoResolver, error) {
+ return s.r.Query().DefaultRepository(ctx)
}
-func (s shortMapper) LabelChangeOperation_removed(ctx context.Context, obj *operations.LabelChangeOperation) ([]*bug.Label, error) {
- return s.r.LabelChangeOperation().Removed(ctx, obj)
+func (s shortMapper) Query_repository(ctx context.Context, id string) (*repoResolver, error) {
+ return s.r.Query().Repository(ctx, id)
}
-func (s shortMapper) RootQuery_allBugs(ctx context.Context, after *string, before *string, first *int, last *int, query *string) (BugConnection, error) {
- return s.r.RootQuery().AllBugs(ctx, after, before, first, last, query)
+func (s shortMapper) Repository_allBugs(ctx context.Context, obj *repoResolver, input ConnectionInput) (BugConnection, error) {
+ return s.r.Repository().AllBugs(ctx, obj, input)
}
-func (s shortMapper) RootQuery_bug(ctx context.Context, id string) (*bug.Snapshot, error) {
- return s.r.RootQuery().Bug(ctx, id)
+func (s shortMapper) Repository_bug(ctx context.Context, obj *repoResolver, prefix string) (*bug.Snapshot, error) {
+ return s.r.Repository().Bug(ctx, obj, prefix)
}
func (s shortMapper) SetStatusOperation_date(ctx context.Context, obj *operations.SetStatusOperation) (time.Time, error) {
@@ -160,7 +160,7 @@ func (e *executableSchema) Query(ctx context.Context, op *query.Operation) *grap
ec := executionContext{graphql.GetRequestContext(ctx), e.resolvers}
buf := ec.RequestMiddleware(ctx, func(ctx context.Context) []byte {
- data := ec._RootQuery(ctx, op.Selections)
+ data := ec._Query(ctx, op.Selections)
var buf bytes.Buffer
data.MarshalGQL(&buf)
return buf.Bytes()
@@ -265,7 +265,7 @@ func (ec *executionContext) _AddCommentOperation_message(ctx context.Context, fi
return graphql.MarshalString(res)
}
-var bugImplementors = []string{"Bug", "Authored", "Commentable"}
+var bugImplementors = []string{"Bug"}
// nolint: gocyclo, errcheck, gas, goconst
func (ec *executionContext) _Bug(ctx context.Context, sel []query.Selection, obj *bug.Snapshot) graphql.Marshaler {
@@ -364,124 +364,37 @@ func (ec *executionContext) _Bug_status(ctx context.Context, field graphql.Colle
}
func (ec *executionContext) _Bug_labels(ctx context.Context, field graphql.CollectedField, obj *bug.Snapshot) graphql.Marshaler {
- ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
- Object: "Bug",
- Args: nil,
- Field: field,
- })
- return graphql.Defer(func() (ret graphql.Marshaler) {
- defer func() {
- if r := recover(); r != nil {
- userErr := ec.Recover(ctx, r)
- ec.Error(ctx, userErr)
- ret = graphql.Null
- }
- }()
-
- resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
- return ec.resolvers.Bug_labels(ctx, obj)
- })
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- if resTmp == nil {
- return graphql.Null
- }
- res := resTmp.([]*bug.Label)
- arr1 := graphql.Array{}
- for idx1 := range res {
- arr1 = append(arr1, func() graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.PushIndex(idx1)
- defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return *res[idx1]
- }())
- }
- return arr1
- })
+ rctx := graphql.GetResolverContext(ctx)
+ rctx.Object = "Bug"
+ rctx.Args = nil
+ rctx.Field = field
+ rctx.PushField(field.Alias)
+ defer rctx.Pop()
+ res := obj.Labels
+ arr1 := graphql.Array{}
+ for idx1 := range res {
+ arr1 = append(arr1, func() graphql.Marshaler {
+ rctx := graphql.GetResolverContext(ctx)
+ rctx.PushIndex(idx1)
+ defer rctx.Pop()
+ return res[idx1]
+ }())
+ }
+ return arr1
}
func (ec *executionContext) _Bug_comments(ctx context.Context, field graphql.CollectedField, obj *bug.Snapshot) graphql.Marshaler {
args := map[string]interface{}{}
- var arg0 *string
- if tmp, ok := field.Args["after"]; ok {
+ var arg0 ConnectionInput
+ if tmp, ok := field.Args["input"]; ok {
var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg0 = &ptr1
- }
-
+ arg0, err = UnmarshalConnectionInput(tmp)
if err != nil {
ec.Error(ctx, err)
return graphql.Null
}
}
- args["after"] = arg0
- var arg1 *string
- if tmp, ok := field.Args["before"]; ok {
- var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg1 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["before"] = arg1
- var arg2 *int
- if tmp, ok := field.Args["first"]; ok {
- var err error
- var ptr1 int
- if tmp != nil {
- ptr1, err = graphql.UnmarshalInt(tmp)
- arg2 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["first"] = arg2
- var arg3 *int
- if tmp, ok := field.Args["last"]; ok {
- var err error
- var ptr1 int
- if tmp != nil {
- ptr1, err = graphql.UnmarshalInt(tmp)
- arg3 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["last"] = arg3
- var arg4 *string
- if tmp, ok := field.Args["query"]; ok {
- var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg4 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["query"] = arg4
+ args["input"] = arg0
ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
Object: "Bug",
Args: args,
@@ -497,7 +410,7 @@ func (ec *executionContext) _Bug_comments(ctx context.Context, field graphql.Col
}()
resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
- return ec.resolvers.Bug_comments(ctx, obj, args["after"].(*string), args["before"].(*string), args["first"].(*int), args["last"].(*int), args["query"].(*string))
+ return ec.resolvers.Bug_comments(ctx, obj, args["input"].(ConnectionInput))
})
if err != nil {
ec.Error(ctx, err)
@@ -513,81 +426,16 @@ func (ec *executionContext) _Bug_comments(ctx context.Context, field graphql.Col
func (ec *executionContext) _Bug_operations(ctx context.Context, field graphql.CollectedField, obj *bug.Snapshot) graphql.Marshaler {
args := map[string]interface{}{}
- var arg0 *string
- if tmp, ok := field.Args["after"]; ok {
- var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg0 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["after"] = arg0
- var arg1 *string
- if tmp, ok := field.Args["before"]; ok {
- var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg1 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["before"] = arg1
- var arg2 *int
- if tmp, ok := field.Args["first"]; ok {
- var err error
- var ptr1 int
- if tmp != nil {
- ptr1, err = graphql.UnmarshalInt(tmp)
- arg2 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["first"] = arg2
- var arg3 *int
- if tmp, ok := field.Args["last"]; ok {
- var err error
- var ptr1 int
- if tmp != nil {
- ptr1, err = graphql.UnmarshalInt(tmp)
- arg3 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["last"] = arg3
- var arg4 *string
- if tmp, ok := field.Args["query"]; ok {
+ var arg0 ConnectionInput
+ if tmp, ok := field.Args["input"]; ok {
var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg4 = &ptr1
- }
-
+ arg0, err = UnmarshalConnectionInput(tmp)
if err != nil {
ec.Error(ctx, err)
return graphql.Null
}
}
- args["query"] = arg4
+ args["input"] = arg0
ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
Object: "Bug",
Args: args,
@@ -603,7 +451,7 @@ func (ec *executionContext) _Bug_operations(ctx context.Context, field graphql.C
}()
resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
- return ec.resolvers.Bug_operations(ctx, obj, args["after"].(*string), args["before"].(*string), args["first"].(*int), args["last"].(*int), args["query"].(*string))
+ return ec.resolvers.Bug_operations(ctx, obj, args["input"].(ConnectionInput))
})
if err != nil {
ec.Error(ctx, err)
@@ -632,8 +480,6 @@ func (ec *executionContext) _BugConnection(ctx context.Context, sel []query.Sele
out.Values[i] = graphql.MarshalString("BugConnection")
case "edges":
out.Values[i] = ec._BugConnection_edges(ctx, field, obj)
- case "nodes":
- out.Values[i] = ec._BugConnection_nodes(ctx, field, obj)
case "pageInfo":
out.Values[i] = ec._BugConnection_pageInfo(ctx, field, obj)
case "totalCount":
@@ -669,29 +515,6 @@ func (ec *executionContext) _BugConnection_edges(ctx context.Context, field grap
return arr1
}
-func (ec *executionContext) _BugConnection_nodes(ctx context.Context, field graphql.CollectedField, obj *BugConnection) graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.Object = "BugConnection"
- rctx.Args = nil
- rctx.Field = field
- rctx.PushField(field.Alias)
- defer rctx.Pop()
- res := obj.Nodes
- arr1 := graphql.Array{}
- for idx1 := range res {
- arr1 = append(arr1, func() graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.PushIndex(idx1)
- defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return ec._Bug(ctx, field.Selections, res[idx1])
- }())
- }
- return arr1
-}
-
func (ec *executionContext) _BugConnection_pageInfo(ctx context.Context, field graphql.CollectedField, obj *BugConnection) graphql.Marshaler {
rctx := graphql.GetResolverContext(ctx)
rctx.Object = "BugConnection"
@@ -758,10 +581,7 @@ func (ec *executionContext) _BugEdge_node(ctx context.Context, field graphql.Col
rctx.PushField(field.Alias)
defer rctx.Pop()
res := obj.Node
- if res == nil {
- return graphql.Null
- }
- return ec._Bug(ctx, field.Selections, res)
+ return ec._Bug(ctx, field.Selections, &res)
}
var commentImplementors = []string{"Comment", "Authored"}
@@ -826,8 +646,6 @@ func (ec *executionContext) _CommentConnection(ctx context.Context, sel []query.
out.Values[i] = graphql.MarshalString("CommentConnection")
case "edges":
out.Values[i] = ec._CommentConnection_edges(ctx, field, obj)
- case "nodes":
- out.Values[i] = ec._CommentConnection_nodes(ctx, field, obj)
case "pageInfo":
out.Values[i] = ec._CommentConnection_pageInfo(ctx, field, obj)
case "totalCount":
@@ -854,33 +672,7 @@ func (ec *executionContext) _CommentConnection_edges(ctx context.Context, field
rctx := graphql.GetResolverContext(ctx)
rctx.PushIndex(idx1)
defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return ec._CommentEdge(ctx, field.Selections, res[idx1])
- }())
- }
- return arr1
-}
-
-func (ec *executionContext) _CommentConnection_nodes(ctx context.Context, field graphql.CollectedField, obj *CommentConnection) graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.Object = "CommentConnection"
- rctx.Args = nil
- rctx.Field = field
- rctx.PushField(field.Alias)
- defer rctx.Pop()
- res := obj.Nodes
- arr1 := graphql.Array{}
- for idx1 := range res {
- arr1 = append(arr1, func() graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.PushIndex(idx1)
- defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return ec._Comment(ctx, field.Selections, res[idx1])
+ return ec._CommentEdge(ctx, field.Selections, &res[idx1])
}())
}
return arr1
@@ -1118,87 +910,43 @@ func (ec *executionContext) _LabelChangeOperation_date(ctx context.Context, fiel
}
func (ec *executionContext) _LabelChangeOperation_added(ctx context.Context, field graphql.CollectedField, obj *operations.LabelChangeOperation) graphql.Marshaler {
- ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
- Object: "LabelChangeOperation",
- Args: nil,
- Field: field,
- })
- return graphql.Defer(func() (ret graphql.Marshaler) {
- defer func() {
- if r := recover(); r != nil {
- userErr := ec.Recover(ctx, r)
- ec.Error(ctx, userErr)
- ret = graphql.Null
- }
- }()
-
- resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
- return ec.resolvers.LabelChangeOperation_added(ctx, obj)
- })
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- if resTmp == nil {
- return graphql.Null
- }
- res := resTmp.([]*bug.Label)
- arr1 := graphql.Array{}
- for idx1 := range res {
- arr1 = append(arr1, func() graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.PushIndex(idx1)
- defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return *res[idx1]
- }())
- }
- return arr1
- })
+ rctx := graphql.GetResolverContext(ctx)
+ rctx.Object = "LabelChangeOperation"
+ rctx.Args = nil
+ rctx.Field = field
+ rctx.PushField(field.Alias)
+ defer rctx.Pop()
+ res := obj.Added
+ arr1 := graphql.Array{}
+ for idx1 := range res {
+ arr1 = append(arr1, func() graphql.Marshaler {
+ rctx := graphql.GetResolverContext(ctx)
+ rctx.PushIndex(idx1)
+ defer rctx.Pop()
+ return res[idx1]
+ }())
+ }
+ return arr1
}
func (ec *executionContext) _LabelChangeOperation_removed(ctx context.Context, field graphql.CollectedField, obj *operations.LabelChangeOperation) graphql.Marshaler {
- ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
- Object: "LabelChangeOperation",
- Args: nil,
- Field: field,
- })
- return graphql.Defer(func() (ret graphql.Marshaler) {
- defer func() {
- if r := recover(); r != nil {
- userErr := ec.Recover(ctx, r)
- ec.Error(ctx, userErr)
- ret = graphql.Null
- }
- }()
-
- resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
- return ec.resolvers.LabelChangeOperation_removed(ctx, obj)
- })
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- if resTmp == nil {
- return graphql.Null
- }
- res := resTmp.([]*bug.Label)
- arr1 := graphql.Array{}
- for idx1 := range res {
- arr1 = append(arr1, func() graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.PushIndex(idx1)
- defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return *res[idx1]
- }())
- }
- return arr1
- })
+ rctx := graphql.GetResolverContext(ctx)
+ rctx.Object = "LabelChangeOperation"
+ rctx.Args = nil
+ rctx.Field = field
+ rctx.PushField(field.Alias)
+ defer rctx.Pop()
+ res := obj.Removed
+ arr1 := graphql.Array{}
+ for idx1 := range res {
+ arr1 = append(arr1, func() graphql.Marshaler {
+ rctx := graphql.GetResolverContext(ctx)
+ rctx.PushIndex(idx1)
+ defer rctx.Pop()
+ return res[idx1]
+ }())
+ }
+ return arr1
}
var operationConnectionImplementors = []string{"OperationConnection"}
@@ -1216,8 +964,6 @@ func (ec *executionContext) _OperationConnection(ctx context.Context, sel []quer
out.Values[i] = graphql.MarshalString("OperationConnection")
case "edges":
out.Values[i] = ec._OperationConnection_edges(ctx, field, obj)
- case "nodes":
- out.Values[i] = ec._OperationConnection_nodes(ctx, field, obj)
case "pageInfo":
out.Values[i] = ec._OperationConnection_pageInfo(ctx, field, obj)
case "totalCount":
@@ -1244,33 +990,7 @@ func (ec *executionContext) _OperationConnection_edges(ctx context.Context, fiel
rctx := graphql.GetResolverContext(ctx)
rctx.PushIndex(idx1)
defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return ec._OperationEdge(ctx, field.Selections, res[idx1])
- }())
- }
- return arr1
-}
-
-func (ec *executionContext) _OperationConnection_nodes(ctx context.Context, field graphql.CollectedField, obj *OperationConnection) graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.Object = "OperationConnection"
- rctx.Args = nil
- rctx.Field = field
- rctx.PushField(field.Alias)
- defer rctx.Pop()
- res := obj.Nodes
- arr1 := graphql.Array{}
- for idx1 := range res {
- arr1 = append(arr1, func() graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.PushIndex(idx1)
- defer rctx.Pop()
- if res[idx1] == nil {
- return graphql.Null
- }
- return ec._OperationUnion(ctx, field.Selections, res[idx1])
+ return ec._OperationEdge(ctx, field.Selections, &res[idx1])
}())
}
return arr1
@@ -1362,10 +1082,6 @@ func (ec *executionContext) _PageInfo(ctx context.Context, sel []query.Selection
out.Values[i] = ec._PageInfo_hasNextPage(ctx, field, obj)
case "hasPreviousPage":
out.Values[i] = ec._PageInfo_hasPreviousPage(ctx, field, obj)
- case "startCursor":
- out.Values[i] = ec._PageInfo_startCursor(ctx, field, obj)
- case "endCursor":
- out.Values[i] = ec._PageInfo_endCursor(ctx, field, obj)
default:
panic("unknown field " + strconv.Quote(field.Name))
}
@@ -1396,34 +1112,6 @@ func (ec *executionContext) _PageInfo_hasPreviousPage(ctx context.Context, field
return graphql.MarshalBoolean(res)
}
-func (ec *executionContext) _PageInfo_startCursor(ctx context.Context, field graphql.CollectedField, obj *PageInfo) graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.Object = "PageInfo"
- rctx.Args = nil
- rctx.Field = field
- rctx.PushField(field.Alias)
- defer rctx.Pop()
- res := obj.StartCursor
- if res == nil {
- return graphql.Null
- }
- return graphql.MarshalString(*res)
-}
-
-func (ec *executionContext) _PageInfo_endCursor(ctx context.Context, field graphql.CollectedField, obj *PageInfo) graphql.Marshaler {
- rctx := graphql.GetResolverContext(ctx)
- rctx.Object = "PageInfo"
- rctx.Args = nil
- rctx.Field = field
- rctx.PushField(field.Alias)
- defer rctx.Pop()
- res := obj.EndCursor
- if res == nil {
- return graphql.Null
- }
- return graphql.MarshalString(*res)
-}
-
var personImplementors = []string{"Person"}
// nolint: gocyclo, errcheck, gas, goconst
@@ -1471,14 +1159,14 @@ func (ec *executionContext) _Person_name(ctx context.Context, field graphql.Coll
return graphql.MarshalString(res)
}
-var rootQueryImplementors = []string{"RootQuery"}
+var queryImplementors = []string{"Query"}
// nolint: gocyclo, errcheck, gas, goconst
-func (ec *executionContext) _RootQuery(ctx context.Context, sel []query.Selection) graphql.Marshaler {
- fields := graphql.CollectFields(ec.Doc, sel, rootQueryImplementors, ec.Variables)
+func (ec *executionContext) _Query(ctx context.Context, sel []query.Selection) graphql.Marshaler {
+ fields := graphql.CollectFields(ec.Doc, sel, queryImplementors, ec.Variables)
ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
- Object: "RootQuery",
+ Object: "Query",
})
out := graphql.NewOrderedMap(len(fields))
@@ -1487,15 +1175,15 @@ func (ec *executionContext) _RootQuery(ctx context.Context, sel []query.Selectio
switch field.Name {
case "__typename":
- out.Values[i] = graphql.MarshalString("RootQuery")
- case "allBugs":
- out.Values[i] = ec._RootQuery_allBugs(ctx, field)
- case "bug":
- out.Values[i] = ec._RootQuery_bug(ctx, field)
+ out.Values[i] = graphql.MarshalString("Query")
+ case "defaultRepository":
+ out.Values[i] = ec._Query_defaultRepository(ctx, field)
+ case "repository":
+ out.Values[i] = ec._Query_repository(ctx, field)
case "__schema":
- out.Values[i] = ec._RootQuery___schema(ctx, field)
+ out.Values[i] = ec._Query___schema(ctx, field)
case "__type":
- out.Values[i] = ec._RootQuery___type(ctx, field)
+ out.Values[i] = ec._Query___type(ctx, field)
default:
panic("unknown field " + strconv.Quote(field.Name))
}
@@ -1504,86 +1192,10 @@ func (ec *executionContext) _RootQuery(ctx context.Context, sel []query.Selectio
return out
}
-func (ec *executionContext) _RootQuery_allBugs(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
- args := map[string]interface{}{}
- var arg0 *string
- if tmp, ok := field.Args["after"]; ok {
- var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg0 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["after"] = arg0
- var arg1 *string
- if tmp, ok := field.Args["before"]; ok {
- var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg1 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["before"] = arg1
- var arg2 *int
- if tmp, ok := field.Args["first"]; ok {
- var err error
- var ptr1 int
- if tmp != nil {
- ptr1, err = graphql.UnmarshalInt(tmp)
- arg2 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["first"] = arg2
- var arg3 *int
- if tmp, ok := field.Args["last"]; ok {
- var err error
- var ptr1 int
- if tmp != nil {
- ptr1, err = graphql.UnmarshalInt(tmp)
- arg3 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["last"] = arg3
- var arg4 *string
- if tmp, ok := field.Args["query"]; ok {
- var err error
- var ptr1 string
- if tmp != nil {
- ptr1, err = graphql.UnmarshalString(tmp)
- arg4 = &ptr1
- }
-
- if err != nil {
- ec.Error(ctx, err)
- return graphql.Null
- }
- }
- args["query"] = arg4
+func (ec *executionContext) _Query_defaultRepository(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
- Object: "RootQuery",
- Args: args,
+ Object: "Query",
+ Args: nil,
Field: field,
})
return graphql.Defer(func() (ret graphql.Marshaler) {
@@ -1596,7 +1208,7 @@ func (ec *executionContext) _RootQuery_allBugs(ctx context.Context, field graphq
}()
resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
- return ec.resolvers.RootQuery_allBugs(ctx, args["after"].(*string), args["before"].(*string), args["first"].(*int), args["last"].(*int), args["query"].(*string))
+ return ec.resolvers.Query_defaultRepository(ctx)
})
if err != nil {
ec.Error(ctx, err)
@@ -1605,12 +1217,15 @@ func (ec *executionContext) _RootQuery_allBugs(ctx context.Context, field graphq
if resTmp == nil {
return graphql.Null
}
- res := resTmp.(BugConnection)
- return ec._BugConnection(ctx, field.Selections, &res)
+ res := resTmp.(*repoResolver)
+ if res == nil {
+ return graphql.Null
+ }
+ return ec._Repository(ctx, field.Selections, res)
})
}
-func (ec *executionContext) _RootQuery_bug(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
+func (ec *executionContext) _Query_repository(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
args := map[string]interface{}{}
var arg0 string
if tmp, ok := field.Args["id"]; ok {
@@ -1623,7 +1238,7 @@ func (ec *executionContext) _RootQuery_bug(ctx context.Context, field graphql.Co
}
args["id"] = arg0
ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
- Object: "RootQuery",
+ Object: "Query",
Args: args,
Field: field,
})
@@ -1637,7 +1252,7 @@ func (ec *executionContext) _RootQuery_bug(ctx context.Context, field graphql.Co
}()
resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
- return ec.resolvers.RootQuery_bug(ctx, args["id"].(string))
+ return ec.resolvers.Query_repository(ctx, args["id"].(string))
})
if err != nil {
ec.Error(ctx, err)
@@ -1646,17 +1261,17 @@ func (ec *executionContext) _RootQuery_bug(ctx context.Context, field graphql.Co
if resTmp == nil {
return graphql.Null
}
- res := resTmp.(*bug.Snapshot)
+ res := resTmp.(*repoResolver)
if res == nil {
return graphql.Null
}
- return ec._Bug(ctx, field.Selections, res)
+ return ec._Repository(ctx, field.Selections, res)
})
}
-func (ec *executionContext) _RootQuery___schema(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
+func (ec *executionContext) _Query___schema(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
rctx := graphql.GetResolverContext(ctx)
- rctx.Object = "RootQuery"
+ rctx.Object = "Query"
rctx.Args = nil
rctx.Field = field
rctx.PushField(field.Alias)
@@ -1668,7 +1283,7 @@ func (ec *executionContext) _RootQuery___schema(ctx context.Context, field graph
return ec.___Schema(ctx, field.Selections, res)
}
-func (ec *executionContext) _RootQuery___type(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
+func (ec *executionContext) _Query___type(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
args := map[string]interface{}{}
var arg0 string
if tmp, ok := field.Args["name"]; ok {
@@ -1681,7 +1296,7 @@ func (ec *executionContext) _RootQuery___type(ctx context.Context, field graphql
}
args["name"] = arg0
rctx := graphql.GetResolverContext(ctx)
- rctx.Object = "RootQuery"
+ rctx.Object = "Query"
rctx.Args = args
rctx.Field = field
rctx.PushField(field.Alias)
@@ -1693,6 +1308,116 @@ func (ec *executionContext) _RootQuery___type(ctx context.Context, field graphql
return ec.___Type(ctx, field.Selections, res)
}
+var repositoryImplementors = []string{"Repository"}
+
+// nolint: gocyclo, errcheck, gas, goconst
+func (ec *executionContext) _Repository(ctx context.Context, sel []query.Selection, obj *repoResolver) graphql.Marshaler {
+ fields := graphql.CollectFields(ec.Doc, sel, repositoryImplementors, ec.Variables)
+
+ out := graphql.NewOrderedMap(len(fields))
+ for i, field := range fields {
+ out.Keys[i] = field.Alias
+
+ switch field.Name {
+ case "__typename":
+ out.Values[i] = graphql.MarshalString("Repository")
+ case "allBugs":
+ out.Values[i] = ec._Repository_allBugs(ctx, field, obj)
+ case "bug":
+ out.Values[i] = ec._Repository_bug(ctx, field, obj)
+ default:
+ panic("unknown field " + strconv.Quote(field.Name))
+ }
+ }
+
+ return out
+}
+
+func (ec *executionContext) _Repository_allBugs(ctx context.Context, field graphql.CollectedField, obj *repoResolver) graphql.Marshaler {
+ args := map[string]interface{}{}
+ var arg0 ConnectionInput
+ if tmp, ok := field.Args["input"]; ok {
+ var err error
+ arg0, err = UnmarshalConnectionInput(tmp)
+ if err != nil {
+ ec.Error(ctx, err)
+ return graphql.Null
+ }
+ }
+ args["input"] = arg0
+ ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
+ Object: "Repository",
+ Args: args,
+ Field: field,
+ })
+ return graphql.Defer(func() (ret graphql.Marshaler) {
+ defer func() {
+ if r := recover(); r != nil {
+ userErr := ec.Recover(ctx, r)
+ ec.Error(ctx, userErr)
+ ret = graphql.Null
+ }
+ }()
+
+ resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
+ return ec.resolvers.Repository_allBugs(ctx, obj, args["input"].(ConnectionInput))
+ })
+ if err != nil {
+ ec.Error(ctx, err)
+ return graphql.Null
+ }
+ if resTmp == nil {
+ return graphql.Null
+ }
+ res := resTmp.(BugConnection)
+ return ec._BugConnection(ctx, field.Selections, &res)
+ })
+}
+
+func (ec *executionContext) _Repository_bug(ctx context.Context, field graphql.CollectedField, obj *repoResolver) graphql.Marshaler {
+ args := map[string]interface{}{}
+ var arg0 string
+ if tmp, ok := field.Args["prefix"]; ok {
+ var err error
+ arg0, err = graphql.UnmarshalString(tmp)
+ if err != nil {
+ ec.Error(ctx, err)
+ return graphql.Null
+ }
+ }
+ args["prefix"] = arg0
+ ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
+ Object: "Repository",
+ Args: args,
+ Field: field,
+ })
+ return graphql.Defer(func() (ret graphql.Marshaler) {
+ defer func() {
+ if r := recover(); r != nil {
+ userErr := ec.Recover(ctx, r)
+ ec.Error(ctx, userErr)
+ ret = graphql.Null
+ }
+ }()
+
+ resTmp, err := ec.ResolverMiddleware(ctx, func(ctx context.Context) (interface{}, error) {
+ return ec.resolvers.Repository_bug(ctx, obj, args["prefix"].(string))
+ })
+ if err != nil {
+ ec.Error(ctx, err)
+ return graphql.Null
+ }
+ if resTmp == nil {
+ return graphql.Null
+ }
+ res := resTmp.(*bug.Snapshot)
+ if res == nil {
+ return graphql.Null
+ }
+ return ec._Bug(ctx, field.Selections, res)
+ })
+}
+
var setStatusOperationImplementors = []string{"SetStatusOperation", "Operation", "Authored"}
// nolint: gocyclo, errcheck, gas, goconst
@@ -2588,23 +2313,6 @@ func (ec *executionContext) _Authored(ctx context.Context, sel []query.Selection
return ec._LabelChangeOperation(ctx, sel, &obj)
case *operations.LabelChangeOperation:
return ec._LabelChangeOperation(ctx, sel, obj)
- case bug.Snapshot:
- return ec._Bug(ctx, sel, &obj)
- case *bug.Snapshot:
- return ec._Bug(ctx, sel, obj)
- default:
- panic(fmt.Errorf("unexpected type %T", obj))
- }
-}
-
-func (ec *executionContext) _Commentable(ctx context.Context, sel []query.Selection, obj *Commentable) graphql.Marshaler {
- switch obj := (*obj).(type) {
- case nil:
- return graphql.Null
- case bug.Snapshot:
- return ec._Bug(ctx, sel, &obj)
- case *bug.Snapshot:
- return ec._Bug(ctx, sel, obj)
default:
panic(fmt.Errorf("unexpected type %T", obj))
}
@@ -2668,6 +2376,62 @@ func (ec *executionContext) _OperationUnion(ctx context.Context, sel []query.Sel
}
}
+func UnmarshalConnectionInput(v interface{}) (ConnectionInput, error) {
+ var it ConnectionInput
+ var asMap = v.(map[string]interface{})
+
+ for k, v := range asMap {
+ switch k {
+ case "after":
+ var err error
+ var ptr1 string
+ if v != nil {
+ ptr1, err = graphql.UnmarshalString(v)
+ it.After = &ptr1
+ }
+
+ if err != nil {
+ return it, err
+ }
+ case "before":
+ var err error
+ var ptr1 string
+ if v != nil {
+ ptr1, err = graphql.UnmarshalString(v)
+ it.Before = &ptr1
+ }
+
+ if err != nil {
+ return it, err
+ }
+ case "first":
+ var err error
+ var ptr1 int
+ if v != nil {
+ ptr1, err = graphql.UnmarshalInt(v)
+ it.First = &ptr1
+ }
+
+ if err != nil {
+ return it, err
+ }
+ case "last":
+ var err error
+ var ptr1 int
+ if v != nil {
+ ptr1, err = graphql.UnmarshalInt(v)
+ it.Last = &ptr1
+ }
+
+ if err != nil {
+ return it, err
+ }
+ }
+ }
+
+ return it, nil
+}
+
func (ec *executionContext) introspectSchema() *introspection.Schema {
return introspection.WrapSchema(parsedSchema)
}
@@ -2680,11 +2444,7 @@ func (ec *executionContext) introspectType(name string) *introspection.Type {
return introspection.WrapType(t)
}
-var parsedSchema = schema.MustParse(`schema {
- query: RootQuery
-}
-
-scalar Time
+var parsedSchema = schema.MustParse(`scalar Time
scalar Label
# Information about pagination in a connection.
@@ -2696,10 +2456,24 @@ type PageInfo {
hasPreviousPage: Boolean!
# When paginating backwards, the cursor to continue.
- startCursor: String
+# startCursor: String
# When paginating forwards, the cursor to continue.
- endCursor: String
+# endCursor: String
+}
+
+input ConnectionInput {
+ # Returns the elements in the list that come after the specified cursor.
+ after: String
+
+ # Returns the elements in the list that come before the specified cursor.
+ before: String
+
+ # Returns the first _n_ elements from the list.
+ first: Int
+
+ # Returns the last _n_ elements from the list.
+ last: Int
}
# Represents an person in a git object.
@@ -2713,8 +2487,7 @@ type Person {
type CommentConnection {
- edges: [CommentEdge]
- nodes: [Comment]
+ edges: [CommentEdge!]!
pageInfo: PageInfo!
totalCount: Int!
}
@@ -2724,23 +2497,6 @@ type CommentEdge {
node: Comment!
}
-interface Commentable {
- # A list of comments associated with the object.
- comments(
- # Returns the elements in the list that come after the specified cursor.
- after: String
-
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
- ): CommentConnection!
-}
-
# Represents a comment on a bug.
type Comment implements Authored {
# The author of this comment.
@@ -2762,15 +2518,14 @@ interface Authored {
}
type OperationConnection {
- edges: [OperationEdge]!
- nodes: [OperationUnion]!
+ edges: [OperationEdge!]!
pageInfo: PageInfo!
totalCount: Int!
}
type OperationEdge {
cursor: String!
- node: OperationUnion
+ node: OperationUnion!
}
# An operation applied to a bug.
@@ -2815,8 +2570,8 @@ type LabelChangeOperation implements Operation, Authored {
author: Person!
date: Time!
- added: [Label]!
- removed: [Label]!
+ added: [Label!]!
+ removed: [Label!]!
}
union OperationUnion =
@@ -2826,14 +2581,11 @@ union OperationUnion =
| SetStatusOperation
| LabelChangeOperation
-# The connection type for Label.
+# The connection type for Bug.
type BugConnection {
# A list of edges.
edges: [BugEdge]!
- # A list of nodes.
- nodes: [Bug]!
-
# Information to aid in pagination.
pageInfo: PageInfo!
@@ -2847,70 +2599,30 @@ type BugEdge {
cursor: String!
# The item at the end of the edge.
- node: Bug
+ node: Bug!
}
-type Bug implements Authored, Commentable {
+type Bug {
id: String!
humanId: String!
title: String!
status: Status!
# A list of labels associated with the repository.
- labels: [Label]!
-
- comments(
- # Returns the elements in the list that come after the specified cursor.
- after: String
-
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
-
- # If provided, searches comments by name and description.
- query: String
- ): CommentConnection!
+ labels: [Label!]!
- operations(
- # Returns the elements in the list that come after the specified cursor.
- after: String
+ comments(input: ConnectionInput!): CommentConnection!
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
-
- # If provided, searches operations by name and description.
- query: String
- ): OperationConnection!
+ operations(input: ConnectionInput!): OperationConnection!
}
-type RootQuery {
- allBugs(
- # Returns the elements in the list that come after the specified cursor.
- after: String
-
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
+type Repository {
+ allBugs(input: ConnectionInput!): BugConnection!
+ bug(prefix: String!): Bug
+}
- # If provided, searches labels by name and description.
- query: String
- ): BugConnection!
- bug(id: String!): Bug
+type Query {
+ defaultRepository: Repository
+ repository(id: String!): Repository
}
`)
diff --git a/graphql2/gen/model.go b/graphql2/resolvers/generated_model.go
index 7609180a..f6d78471 100644
--- a/graphql2/gen/model.go
+++ b/graphql2/resolvers/generated_model.go
@@ -1,6 +1,6 @@
// Code generated by github.com/vektah/gqlgen, DO NOT EDIT.
-package gen
+package resolvers
import (
fmt "fmt"
@@ -12,32 +12,34 @@ import (
type Authored interface{}
type BugConnection struct {
- Edges []*BugEdge `json:"edges"`
- Nodes []*bug.Snapshot `json:"nodes"`
- PageInfo PageInfo `json:"pageInfo"`
- TotalCount int `json:"totalCount"`
+ Edges []*BugEdge `json:"edges"`
+ PageInfo PageInfo `json:"pageInfo"`
+ TotalCount int `json:"totalCount"`
}
type BugEdge struct {
- Cursor string `json:"cursor"`
- Node *bug.Snapshot `json:"node"`
+ Cursor string `json:"cursor"`
+ Node bug.Snapshot `json:"node"`
}
type CommentConnection struct {
- Edges []*CommentEdge `json:"edges"`
- Nodes []*bug.Comment `json:"nodes"`
- PageInfo PageInfo `json:"pageInfo"`
- TotalCount int `json:"totalCount"`
+ Edges []CommentEdge `json:"edges"`
+ PageInfo PageInfo `json:"pageInfo"`
+ TotalCount int `json:"totalCount"`
}
type CommentEdge struct {
Cursor string `json:"cursor"`
Node bug.Comment `json:"node"`
}
-type Commentable interface{}
+type ConnectionInput struct {
+ After *string `json:"after"`
+ Before *string `json:"before"`
+ First *int `json:"first"`
+ Last *int `json:"last"`
+}
type Operation interface{}
type OperationConnection struct {
- Edges []*OperationEdge `json:"edges"`
- Nodes []*OperationUnion `json:"nodes"`
- PageInfo PageInfo `json:"pageInfo"`
- TotalCount int `json:"totalCount"`
+ Edges []OperationEdge `json:"edges"`
+ PageInfo PageInfo `json:"pageInfo"`
+ TotalCount int `json:"totalCount"`
}
type OperationEdge struct {
Cursor string `json:"cursor"`
@@ -45,10 +47,8 @@ type OperationEdge struct {
}
type OperationUnion interface{}
type PageInfo struct {
- HasNextPage bool `json:"hasNextPage"`
- HasPreviousPage bool `json:"hasPreviousPage"`
- StartCursor *string `json:"startCursor"`
- EndCursor *string `json:"endCursor"`
+ HasNextPage bool `json:"hasNextPage"`
+ HasPreviousPage bool `json:"hasPreviousPage"`
}
type Status string
diff --git a/graphql2/resolvers/operations.go b/graphql2/resolvers/operations.go
new file mode 100644
index 00000000..1279a1b4
--- /dev/null
+++ b/graphql2/resolvers/operations.go
@@ -0,0 +1,54 @@
+package resolvers
+
+import (
+ "context"
+ "fmt"
+ "github.com/MichaelMure/git-bug/bug"
+ "github.com/MichaelMure/git-bug/bug/operations"
+ "time"
+)
+
+type addCommentOperationResolver struct{}
+
+func (addCommentOperationResolver) Date(ctx context.Context, obj *operations.AddCommentOperation) (time.Time, error) {
+ return obj.Time(), nil
+}
+
+type createOperationResolver struct{}
+
+func (createOperationResolver) Date(ctx context.Context, obj *operations.CreateOperation) (time.Time, error) {
+ return obj.Time(), nil
+}
+
+type labelChangeOperation struct{}
+
+func (labelChangeOperation) Date(ctx context.Context, obj *operations.LabelChangeOperation) (time.Time, error) {
+ return obj.Time(), nil
+}
+
+type setStatusOperationResolver struct{}
+
+func (setStatusOperationResolver) Date(ctx context.Context, obj *operations.SetStatusOperation) (time.Time, error) {
+ return obj.Time(), nil
+}
+
+func (setStatusOperationResolver) Status(ctx context.Context, obj *operations.SetStatusOperation) (Status, error) {
+ return convertStatus(obj.Status)
+}
+
+type setTitleOperationResolver struct{}
+
+func (setTitleOperationResolver) Date(ctx context.Context, obj *operations.SetTitleOperation) (time.Time, error) {
+ return obj.Time(), nil
+}
+
+func convertStatus(status bug.Status) (Status, error) {
+ switch status {
+ case bug.OpenStatus:
+ return StatusOpen, nil
+ case bug.ClosedStatus:
+ return StatusClosed, nil
+ }
+
+ return "", fmt.Errorf("Unknown status")
+}
diff --git a/graphql2/resolvers/pager_bug.go b/graphql2/resolvers/pager_bug.go
new file mode 100644
index 00000000..55acfcc4
--- /dev/null
+++ b/graphql2/resolvers/pager_bug.go
@@ -0,0 +1,225 @@
+// This file was automatically generated by genny.
+// Any changes will be lost if this file is regenerated.
+// see https://github.com/cheekybits/genny
+
+package resolvers
+
+import (
+ "fmt"
+
+ "github.com/MichaelMure/git-bug/bug"
+)
+
+type BugSnapshotEdger func(value bug.Snapshot, offset int) Edge
+
+func BugSnapshotPaginate(source []bug.Snapshot, edger BugSnapshotEdger, input ConnectionInput) ([]BugEdge, PageInfo, error) {
+ var result []BugEdge
+ var pageInfo PageInfo
+
+ offset := 0
+
+ if input.After != nil {
+ for i, value := range source {
+ edge := edger(value, i)
+ if edge.GetCursor() == *input.After {
+ // remove all previous element including the "after" one
+ source = source[i+1:]
+ offset = i + 1
+ break
+ }
+ }
+ }
+
+ if input.Before != nil {
+ for i, value := range source {
+ edge := edger(value, i+offset)
+
+ if edge.GetCursor() == *input.Before {
+ // remove all after element including the "before" one
+ break
+ }
+
+ result = append(result, edge.(BugEdge))
+ }
+ } else {
+ result = make([]BugEdge, len(source))
+
+ for i, value := range source {
+ result[i] = edger(value, i+offset).(BugEdge)
+ }
+ }
+
+ if input.First != nil {
+ if *input.First < 0 {
+ return nil, PageInfo{}, fmt.Errorf("first less than zero")
+ }
+
+ if len(result) > *input.First {
+ // Slice result to be of length first by removing edges from the end
+ result = result[:*input.First]
+ pageInfo.HasNextPage = true
+ }
+ }
+
+ if input.Last != nil {
+ if *input.Last < 0 {
+ return nil, PageInfo{}, fmt.Errorf("last less than zero")
+ }
+
+ if len(result) > *input.Last {
+ // Slice result to be of length last by removing edges from the start
+ result = result[len(result)-*input.Last:]
+ pageInfo.HasPreviousPage = true
+ }
+ }
+
+ return result, pageInfo, nil
+}
+
+// Apply the before/after cursor params to the source and return an array of edges
+//func ApplyCursorToEdges(source []interface{}, edger Edger, input ConnectionInput) []Edge {
+// var result []Edge
+//
+// if input.After != nil {
+// for i, value := range source {
+// edge := edger(value)
+// if edge.Cursor() == *input.After {
+// // remove all previous element including the "after" one
+// source = source[i+1:]
+// break
+// }
+// }
+// }
+//
+// if input.Before != nil {
+// for _, value := range source {
+// edge := edger(value)
+//
+// if edge.Cursor() == *input.Before {
+// // remove all after element including the "before" one
+// break
+// }
+//
+// result = append(result, edge)
+// }
+// } else {
+// result = make([]Edge, len(source))
+//
+// for i, value := range source {
+// result[i] = edger(value)
+// }
+// }
+//
+// return result
+//}
+
+// Apply the first/last cursor params to the edges
+//func EdgesToReturn(edges []Edge, input ConnectionInput) ([]Edge, PageInfo, error) {
+// hasPreviousPage := false
+// hasNextPage := false
+//
+// if input.First != nil {
+// if *input.First < 0 {
+// return nil, nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(edges) > *input.First {
+// // Slice result to be of length first by removing edges from the end
+// edges = edges[:*input.First]
+// hasNextPage = true
+// }
+// }
+//
+// if input.Last != nil {
+// if *input.Last < 0 {
+// return nil, nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(edges) > *input.Last {
+// // Slice result to be of length last by removing edges from the start
+// edges = edges[len(edges)-*input.Last:]
+// hasPreviousPage = true
+// }
+// }
+//
+// pageInfo := PageInfo{
+// HasNextPage: hasNextPage,
+// HasPreviousPage: hasPreviousPage,
+// }
+//
+// return edges, pageInfo, nil
+//}
+
+//func EdgesToReturn(allEdges []Edge, before *cursor, after *cursor, first *int, last *int) ([]Edge, error) {
+// result := ApplyCursorToEdges(allEdges, before, after)
+//
+// if first != nil {
+// if *first < 0 {
+// return nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(result) > *first {
+// // Slice result to be of length first by removing edges from the end
+// result = result[:*first]
+// }
+// }
+//
+// if last != nil {
+// if *last < 0 {
+// return nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(result) > *last {
+// // Slice result to be of length last by removing edges from the start
+// result = result[len(result)-*last:]
+// }
+// }
+//
+// return result, nil
+//}
+
+//func ApplyCursorToEdges(allEdges []Edge, before *cursor, after *cursor) []Edge {
+// result := allEdges
+//
+// if after != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *after {
+// // remove all previous element including the "after" one
+// result = result[i+1:]
+// break
+// }
+// }
+// }
+//
+// if before != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *before {
+// // remove all after element including the "before" one
+// result = result[:i]
+// }
+// }
+// }
+//
+// return result
+//}
+
+//func HasPreviousPage(allEdges []Edge, before *cursor, after *cursor, last *int) bool {
+// if last != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *last
+// }
+//
+// // TODO: handle "after", but according to the spec it's ok to return false
+//
+// return false
+//}
+//
+//func HasNextPage(allEdges []Edge, before *cursor, after *cursor, first *int) bool {
+// if first != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *first
+// }
+//
+// // TODO: handle "before", but according to the spec it's ok to return false
+//
+// return false
diff --git a/graphql2/resolvers/pager_comment.go b/graphql2/resolvers/pager_comment.go
new file mode 100644
index 00000000..3dd11757
--- /dev/null
+++ b/graphql2/resolvers/pager_comment.go
@@ -0,0 +1,225 @@
+// This file was automatically generated by genny.
+// Any changes will be lost if this file is regenerated.
+// see https://github.com/cheekybits/genny
+
+package resolvers
+
+import (
+ "fmt"
+
+ "github.com/MichaelMure/git-bug/bug"
+)
+
+type BugCommentEdger func(value bug.Comment, offset int) Edge
+
+func BugCommentPaginate(source []bug.Comment, edger BugCommentEdger, input ConnectionInput) ([]CommentEdge, PageInfo, error) {
+ var result []CommentEdge
+ var pageInfo PageInfo
+
+ offset := 0
+
+ if input.After != nil {
+ for i, value := range source {
+ edge := edger(value, i)
+ if edge.GetCursor() == *input.After {
+ // remove all previous element including the "after" one
+ source = source[i+1:]
+ offset = i + 1
+ break
+ }
+ }
+ }
+
+ if input.Before != nil {
+ for i, value := range source {
+ edge := edger(value, i+offset)
+
+ if edge.GetCursor() == *input.Before {
+ // remove all after element including the "before" one
+ break
+ }
+
+ result = append(result, edge.(CommentEdge))
+ }
+ } else {
+ result = make([]CommentEdge, len(source))
+
+ for i, value := range source {
+ result[i] = edger(value, i+offset).(CommentEdge)
+ }
+ }
+
+ if input.First != nil {
+ if *input.First < 0 {
+ return nil, PageInfo{}, fmt.Errorf("first less than zero")
+ }
+
+ if len(result) > *input.First {
+ // Slice result to be of length first by removing edges from the end
+ result = result[:*input.First]
+ pageInfo.HasNextPage = true
+ }
+ }
+
+ if input.Last != nil {
+ if *input.Last < 0 {
+ return nil, PageInfo{}, fmt.Errorf("last less than zero")
+ }
+
+ if len(result) > *input.Last {
+ // Slice result to be of length last by removing edges from the start
+ result = result[len(result)-*input.Last:]
+ pageInfo.HasPreviousPage = true
+ }
+ }
+
+ return result, pageInfo, nil
+}
+
+// Apply the before/after cursor params to the source and return an array of edges
+//func ApplyCursorToEdges(source []interface{}, edger Edger, input ConnectionInput) []Edge {
+// var result []Edge
+//
+// if input.After != nil {
+// for i, value := range source {
+// edge := edger(value)
+// if edge.Cursor() == *input.After {
+// // remove all previous element including the "after" one
+// source = source[i+1:]
+// break
+// }
+// }
+// }
+//
+// if input.Before != nil {
+// for _, value := range source {
+// edge := edger(value)
+//
+// if edge.Cursor() == *input.Before {
+// // remove all after element including the "before" one
+// break
+// }
+//
+// result = append(result, edge)
+// }
+// } else {
+// result = make([]Edge, len(source))
+//
+// for i, value := range source {
+// result[i] = edger(value)
+// }
+// }
+//
+// return result
+//}
+
+// Apply the first/last cursor params to the edges
+//func EdgesToReturn(edges []Edge, input ConnectionInput) ([]Edge, PageInfo, error) {
+// hasPreviousPage := false
+// hasNextPage := false
+//
+// if input.First != nil {
+// if *input.First < 0 {
+// return nil, nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(edges) > *input.First {
+// // Slice result to be of length first by removing edges from the end
+// edges = edges[:*input.First]
+// hasNextPage = true
+// }
+// }
+//
+// if input.Last != nil {
+// if *input.Last < 0 {
+// return nil, nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(edges) > *input.Last {
+// // Slice result to be of length last by removing edges from the start
+// edges = edges[len(edges)-*input.Last:]
+// hasPreviousPage = true
+// }
+// }
+//
+// pageInfo := PageInfo{
+// HasNextPage: hasNextPage,
+// HasPreviousPage: hasPreviousPage,
+// }
+//
+// return edges, pageInfo, nil
+//}
+
+//func EdgesToReturn(allEdges []Edge, before *cursor, after *cursor, first *int, last *int) ([]Edge, error) {
+// result := ApplyCursorToEdges(allEdges, before, after)
+//
+// if first != nil {
+// if *first < 0 {
+// return nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(result) > *first {
+// // Slice result to be of length first by removing edges from the end
+// result = result[:*first]
+// }
+// }
+//
+// if last != nil {
+// if *last < 0 {
+// return nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(result) > *last {
+// // Slice result to be of length last by removing edges from the start
+// result = result[len(result)-*last:]
+// }
+// }
+//
+// return result, nil
+//}
+
+//func ApplyCursorToEdges(allEdges []Edge, before *cursor, after *cursor) []Edge {
+// result := allEdges
+//
+// if after != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *after {
+// // remove all previous element including the "after" one
+// result = result[i+1:]
+// break
+// }
+// }
+// }
+//
+// if before != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *before {
+// // remove all after element including the "before" one
+// result = result[:i]
+// }
+// }
+// }
+//
+// return result
+//}
+
+//func HasPreviousPage(allEdges []Edge, before *cursor, after *cursor, last *int) bool {
+// if last != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *last
+// }
+//
+// // TODO: handle "after", but according to the spec it's ok to return false
+//
+// return false
+//}
+//
+//func HasNextPage(allEdges []Edge, before *cursor, after *cursor, first *int) bool {
+// if first != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *first
+// }
+//
+// // TODO: handle "before", but according to the spec it's ok to return false
+//
+// return false
diff --git a/graphql2/resolvers/pager_operation.go b/graphql2/resolvers/pager_operation.go
new file mode 100644
index 00000000..fe4eebc2
--- /dev/null
+++ b/graphql2/resolvers/pager_operation.go
@@ -0,0 +1,225 @@
+// This file was automatically generated by genny.
+// Any changes will be lost if this file is regenerated.
+// see https://github.com/cheekybits/genny
+
+package resolvers
+
+import (
+ "fmt"
+
+ "github.com/MichaelMure/git-bug/bug"
+)
+
+type BugOperationEdger func(value bug.Operation, offset int) Edge
+
+func BugOperationPaginate(source []bug.Operation, edger BugOperationEdger, input ConnectionInput) ([]OperationEdge, PageInfo, error) {
+ var result []OperationEdge
+ var pageInfo PageInfo
+
+ offset := 0
+
+ if input.After != nil {
+ for i, value := range source {
+ edge := edger(value, i)
+ if edge.GetCursor() == *input.After {
+ // remove all previous element including the "after" one
+ source = source[i+1:]
+ offset = i + 1
+ break
+ }
+ }
+ }
+
+ if input.Before != nil {
+ for i, value := range source {
+ edge := edger(value, i+offset)
+
+ if edge.GetCursor() == *input.Before {
+ // remove all after element including the "before" one
+ break
+ }
+
+ result = append(result, edge.(OperationEdge))
+ }
+ } else {
+ result = make([]OperationEdge, len(source))
+
+ for i, value := range source {
+ result[i] = edger(value, i+offset).(OperationEdge)
+ }
+ }
+
+ if input.First != nil {
+ if *input.First < 0 {
+ return nil, PageInfo{}, fmt.Errorf("first less than zero")
+ }
+
+ if len(result) > *input.First {
+ // Slice result to be of length first by removing edges from the end
+ result = result[:*input.First]
+ pageInfo.HasNextPage = true
+ }
+ }
+
+ if input.Last != nil {
+ if *input.Last < 0 {
+ return nil, PageInfo{}, fmt.Errorf("last less than zero")
+ }
+
+ if len(result) > *input.Last {
+ // Slice result to be of length last by removing edges from the start
+ result = result[len(result)-*input.Last:]
+ pageInfo.HasPreviousPage = true
+ }
+ }
+
+ return result, pageInfo, nil
+}
+
+// Apply the before/after cursor params to the source and return an array of edges
+//func ApplyCursorToEdges(source []interface{}, edger Edger, input ConnectionInput) []Edge {
+// var result []Edge
+//
+// if input.After != nil {
+// for i, value := range source {
+// edge := edger(value)
+// if edge.Cursor() == *input.After {
+// // remove all previous element including the "after" one
+// source = source[i+1:]
+// break
+// }
+// }
+// }
+//
+// if input.Before != nil {
+// for _, value := range source {
+// edge := edger(value)
+//
+// if edge.Cursor() == *input.Before {
+// // remove all after element including the "before" one
+// break
+// }
+//
+// result = append(result, edge)
+// }
+// } else {
+// result = make([]Edge, len(source))
+//
+// for i, value := range source {
+// result[i] = edger(value)
+// }
+// }
+//
+// return result
+//}
+
+// Apply the first/last cursor params to the edges
+//func EdgesToReturn(edges []Edge, input ConnectionInput) ([]Edge, PageInfo, error) {
+// hasPreviousPage := false
+// hasNextPage := false
+//
+// if input.First != nil {
+// if *input.First < 0 {
+// return nil, nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(edges) > *input.First {
+// // Slice result to be of length first by removing edges from the end
+// edges = edges[:*input.First]
+// hasNextPage = true
+// }
+// }
+//
+// if input.Last != nil {
+// if *input.Last < 0 {
+// return nil, nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(edges) > *input.Last {
+// // Slice result to be of length last by removing edges from the start
+// edges = edges[len(edges)-*input.Last:]
+// hasPreviousPage = true
+// }
+// }
+//
+// pageInfo := PageInfo{
+// HasNextPage: hasNextPage,
+// HasPreviousPage: hasPreviousPage,
+// }
+//
+// return edges, pageInfo, nil
+//}
+
+//func EdgesToReturn(allEdges []Edge, before *cursor, after *cursor, first *int, last *int) ([]Edge, error) {
+// result := ApplyCursorToEdges(allEdges, before, after)
+//
+// if first != nil {
+// if *first < 0 {
+// return nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(result) > *first {
+// // Slice result to be of length first by removing edges from the end
+// result = result[:*first]
+// }
+// }
+//
+// if last != nil {
+// if *last < 0 {
+// return nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(result) > *last {
+// // Slice result to be of length last by removing edges from the start
+// result = result[len(result)-*last:]
+// }
+// }
+//
+// return result, nil
+//}
+
+//func ApplyCursorToEdges(allEdges []Edge, before *cursor, after *cursor) []Edge {
+// result := allEdges
+//
+// if after != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *after {
+// // remove all previous element including the "after" one
+// result = result[i+1:]
+// break
+// }
+// }
+// }
+//
+// if before != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *before {
+// // remove all after element including the "before" one
+// result = result[:i]
+// }
+// }
+// }
+//
+// return result
+//}
+
+//func HasPreviousPage(allEdges []Edge, before *cursor, after *cursor, last *int) bool {
+// if last != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *last
+// }
+//
+// // TODO: handle "after", but according to the spec it's ok to return false
+//
+// return false
+//}
+//
+//func HasNextPage(allEdges []Edge, before *cursor, after *cursor, first *int) bool {
+// if first != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *first
+// }
+//
+// // TODO: handle "before", but according to the spec it's ok to return false
+//
+// return false
diff --git a/graphql2/resolvers/pagers.go b/graphql2/resolvers/pagers.go
new file mode 100644
index 00000000..378dcdbf
--- /dev/null
+++ b/graphql2/resolvers/pagers.go
@@ -0,0 +1,51 @@
+//go:generate genny -in=pagers_template.go -out=pager_bug.go gen "NodeType=bug.Snapshot EdgeType=BugEdge"
+//go:generate genny -in=pagers_template.go -out=pager_operation.go gen "NodeType=bug.Operation EdgeType=OperationEdge"
+//go:generate genny -in=pagers_template.go -out=pager_comment.go gen "NodeType=bug.Comment EdgeType=CommentEdge"
+
+package resolvers
+
+import (
+ "encoding/base64"
+ "fmt"
+ "strconv"
+ "strings"
+)
+
+const cursorPrefix = "cursor:"
+
+type Edge interface {
+ GetCursor() string
+}
+
+// Creates the cursor string from an offset
+func offsetToCursor(offset int) string {
+ str := fmt.Sprintf("%v%v", cursorPrefix, offset)
+ return base64.StdEncoding.EncodeToString([]byte(str))
+}
+
+// Re-derives the offset from the cursor string.
+func cursorToOffset(cursor string) (int, error) {
+ str := ""
+ b, err := base64.StdEncoding.DecodeString(cursor)
+ if err == nil {
+ str = string(b)
+ }
+ str = strings.Replace(str, cursorPrefix, "", -1)
+ offset, err := strconv.Atoi(str)
+ if err != nil {
+ return 0, fmt.Errorf("Invalid cursor")
+ }
+ return offset, nil
+}
+
+func (e OperationEdge) GetCursor() string {
+ return e.Cursor
+}
+
+func (e BugEdge) GetCursor() string {
+ return e.Cursor
+}
+
+func (e CommentEdge) GetCursor() string {
+ return e.Cursor
+}
diff --git a/graphql2/resolvers/pagers_template.go b/graphql2/resolvers/pagers_template.go
new file mode 100644
index 00000000..0ca7de75
--- /dev/null
+++ b/graphql2/resolvers/pagers_template.go
@@ -0,0 +1,224 @@
+package resolvers
+
+import (
+ "fmt"
+ "github.com/cheekybits/genny/generic"
+)
+
+type NodeType generic.Type
+type EdgeType generic.Type
+
+type NodeTypeEdger func(value NodeType, offset int) Edge
+
+func NodeTypePaginate(source []NodeType, edger NodeTypeEdger, input ConnectionInput) ([]EdgeType, PageInfo, error) {
+ var result []EdgeType
+ var pageInfo PageInfo
+
+ offset := 0
+
+ if input.After != nil {
+ for i, value := range source {
+ edge := edger(value, i)
+ if edge.GetCursor() == *input.After {
+ // remove all previous element including the "after" one
+ source = source[i+1:]
+ offset = i + 1
+ break
+ }
+ }
+ }
+
+ if input.Before != nil {
+ for i, value := range source {
+ edge := edger(value, i+offset)
+
+ if edge.GetCursor() == *input.Before {
+ // remove all after element including the "before" one
+ break
+ }
+
+ result = append(result, edge.(EdgeType))
+ }
+ } else {
+ result = make([]EdgeType, len(source))
+
+ for i, value := range source {
+ result[i] = edger(value, i+offset).(EdgeType)
+ }
+ }
+
+ if input.First != nil {
+ if *input.First < 0 {
+ return nil, PageInfo{}, fmt.Errorf("first less than zero")
+ }
+
+ if len(result) > *input.First {
+ // Slice result to be of length first by removing edges from the end
+ result = result[:*input.First]
+ pageInfo.HasNextPage = true
+ }
+ }
+
+ if input.Last != nil {
+ if *input.Last < 0 {
+ return nil, PageInfo{}, fmt.Errorf("last less than zero")
+ }
+
+ if len(result) > *input.Last {
+ // Slice result to be of length last by removing edges from the start
+ result = result[len(result)-*input.Last:]
+ pageInfo.HasPreviousPage = true
+ }
+ }
+
+ return result, pageInfo, nil
+}
+
+// Apply the before/after cursor params to the source and return an array of edges
+//func ApplyCursorToEdges(source []interface{}, edger Edger, input ConnectionInput) []Edge {
+// var result []Edge
+//
+// if input.After != nil {
+// for i, value := range source {
+// edge := edger(value)
+// if edge.Cursor() == *input.After {
+// // remove all previous element including the "after" one
+// source = source[i+1:]
+// break
+// }
+// }
+// }
+//
+// if input.Before != nil {
+// for _, value := range source {
+// edge := edger(value)
+//
+// if edge.Cursor() == *input.Before {
+// // remove all after element including the "before" one
+// break
+// }
+//
+// result = append(result, edge)
+// }
+// } else {
+// result = make([]Edge, len(source))
+//
+// for i, value := range source {
+// result[i] = edger(value)
+// }
+// }
+//
+// return result
+//}
+
+// Apply the first/last cursor params to the edges
+//func EdgesToReturn(edges []Edge, input ConnectionInput) ([]Edge, PageInfo, error) {
+// hasPreviousPage := false
+// hasNextPage := false
+//
+// if input.First != nil {
+// if *input.First < 0 {
+// return nil, nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(edges) > *input.First {
+// // Slice result to be of length first by removing edges from the end
+// edges = edges[:*input.First]
+// hasNextPage = true
+// }
+// }
+//
+// if input.Last != nil {
+// if *input.Last < 0 {
+// return nil, nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(edges) > *input.Last {
+// // Slice result to be of length last by removing edges from the start
+// edges = edges[len(edges)-*input.Last:]
+// hasPreviousPage = true
+// }
+// }
+//
+// pageInfo := PageInfo{
+// HasNextPage: hasNextPage,
+// HasPreviousPage: hasPreviousPage,
+// }
+//
+// return edges, pageInfo, nil
+//}
+
+//func EdgesToReturn(allEdges []Edge, before *cursor, after *cursor, first *int, last *int) ([]Edge, error) {
+// result := ApplyCursorToEdges(allEdges, before, after)
+//
+// if first != nil {
+// if *first < 0 {
+// return nil, fmt.Errorf("first less than zero")
+// }
+//
+// if len(result) > *first {
+// // Slice result to be of length first by removing edges from the end
+// result = result[:*first]
+// }
+// }
+//
+// if last != nil {
+// if *last < 0 {
+// return nil, fmt.Errorf("last less than zero")
+// }
+//
+// if len(result) > *last {
+// // Slice result to be of length last by removing edges from the start
+// result = result[len(result)-*last:]
+// }
+// }
+//
+// return result, nil
+//}
+
+//func ApplyCursorToEdges(allEdges []Edge, before *cursor, after *cursor) []Edge {
+// result := allEdges
+//
+// if after != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *after {
+// // remove all previous element including the "after" one
+// result = result[i+1:]
+// break
+// }
+// }
+// }
+//
+// if before != nil {
+// for i, edge := range result {
+// if edge.Cursor() == *before {
+// // remove all after element including the "before" one
+// result = result[:i]
+// }
+// }
+// }
+//
+// return result
+//}
+
+//func HasPreviousPage(allEdges []Edge, before *cursor, after *cursor, last *int) bool {
+// if last != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *last
+// }
+//
+// // TODO: handle "after", but according to the spec it's ok to return false
+//
+// return false
+//}
+//
+//func HasNextPage(allEdges []Edge, before *cursor, after *cursor, first *int) bool {
+// if first != nil {
+// edges := ApplyCursorToEdges(allEdges, before, after)
+// return len(edges) > *first
+// }
+//
+// // TODO: handle "before", but according to the spec it's ok to return false
+//
+// return false
+//}
diff --git a/graphql2/resolvers/query.go b/graphql2/resolvers/query.go
new file mode 100644
index 00000000..cceca334
--- /dev/null
+++ b/graphql2/resolvers/query.go
@@ -0,0 +1,36 @@
+package resolvers
+
+import (
+ "context"
+ "github.com/MichaelMure/git-bug/cache"
+)
+
+type rootQueryResolver struct {
+ cache cache.Cacher
+}
+
+func (r rootQueryResolver) DefaultRepository(ctx context.Context) (*repoResolver, error) {
+ repo, err := r.cache.DefaultRepo()
+
+ if err != nil {
+ return nil, err
+ }
+
+ return &repoResolver{
+ cache: r.cache,
+ repo: repo,
+ }, nil
+}
+
+func (r rootQueryResolver) Repository(ctx context.Context, id string) (*repoResolver, error) {
+ repo, err := r.cache.ResolveRepo(id)
+
+ if err != nil {
+ return nil, err
+ }
+
+ return &repoResolver{
+ cache: r.cache,
+ repo: repo,
+ }, nil
+}
diff --git a/graphql2/resolvers/repo.go b/graphql2/resolvers/repo.go
new file mode 100644
index 00000000..14019b65
--- /dev/null
+++ b/graphql2/resolvers/repo.go
@@ -0,0 +1,26 @@
+package resolvers
+
+import (
+ "context"
+ "github.com/MichaelMure/git-bug/bug"
+ "github.com/MichaelMure/git-bug/cache"
+)
+
+type repoResolver struct {
+ cache cache.Cacher
+ repo cache.RepoCacher
+}
+
+func (repoResolver) AllBugs(ctx context.Context, obj *repoResolver, input ConnectionInput) (BugConnection, error) {
+ panic("implement me")
+}
+
+func (repoResolver) Bug(ctx context.Context, obj *repoResolver, prefix string) (*bug.Snapshot, error) {
+ b, err := obj.repo.ResolveBugPrefix(prefix)
+
+ if err != nil {
+ return nil, err
+ }
+
+ return b.Snapshot(), nil
+}
diff --git a/graphql2/resolvers/root.go b/graphql2/resolvers/root.go
new file mode 100644
index 00000000..e5f83060
--- /dev/null
+++ b/graphql2/resolvers/root.go
@@ -0,0 +1,53 @@
+package resolvers
+
+import (
+ "github.com/MichaelMure/git-bug/cache"
+)
+
+type RootResolver struct {
+ cache.RootCache
+}
+
+func NewRootResolver() *RootResolver {
+ return &RootResolver{
+ RootCache: cache.NewCache(),
+ }
+}
+
+func (r RootResolver) Query() QueryResolver {
+ return &rootQueryResolver{
+ cache: &r.RootCache,
+ }
+}
+
+func (RootResolver) AddCommentOperation() AddCommentOperationResolver {
+ return &addCommentOperationResolver{}
+}
+
+func (r RootResolver) Bug() BugResolver {
+ return &bugResolver{
+ cache: &r.RootCache,
+ }
+}
+
+func (RootResolver) CreateOperation() CreateOperationResolver {
+ return &createOperationResolver{}
+}
+
+func (RootResolver) LabelChangeOperation() LabelChangeOperationResolver {
+ return &labelChangeOperation{}
+}
+
+func (r RootResolver) Repository() RepositoryResolver {
+ return &repoResolver{
+ cache: &r.RootCache,
+ }
+}
+
+func (RootResolver) SetStatusOperation() SetStatusOperationResolver {
+ return &setStatusOperationResolver{}
+}
+
+func (RootResolver) SetTitleOperation() SetTitleOperationResolver {
+ return &setTitleOperationResolver{}
+}
diff --git a/graphql2/schema.graphql b/graphql2/schema.graphql
index 3c24c746..47716488 100644
--- a/graphql2/schema.graphql
+++ b/graphql2/schema.graphql
@@ -1,7 +1,3 @@
-schema {
- query: RootQuery
-}
-
scalar Time
scalar Label
@@ -14,10 +10,24 @@ type PageInfo {
hasPreviousPage: Boolean!
# When paginating backwards, the cursor to continue.
- startCursor: String
+# startCursor: String
# When paginating forwards, the cursor to continue.
- endCursor: String
+# endCursor: String
+}
+
+input ConnectionInput {
+ # Returns the elements in the list that come after the specified cursor.
+ after: String
+
+ # Returns the elements in the list that come before the specified cursor.
+ before: String
+
+ # Returns the first _n_ elements from the list.
+ first: Int
+
+ # Returns the last _n_ elements from the list.
+ last: Int
}
# Represents an person in a git object.
@@ -31,8 +41,7 @@ type Person {
type CommentConnection {
- edges: [CommentEdge]
- nodes: [Comment]
+ edges: [CommentEdge!]!
pageInfo: PageInfo!
totalCount: Int!
}
@@ -42,23 +51,6 @@ type CommentEdge {
node: Comment!
}
-interface Commentable {
- # A list of comments associated with the object.
- comments(
- # Returns the elements in the list that come after the specified cursor.
- after: String
-
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
- ): CommentConnection!
-}
-
# Represents a comment on a bug.
type Comment implements Authored {
# The author of this comment.
@@ -80,15 +72,14 @@ interface Authored {
}
type OperationConnection {
- edges: [OperationEdge]!
- nodes: [OperationUnion]!
+ edges: [OperationEdge!]!
pageInfo: PageInfo!
totalCount: Int!
}
type OperationEdge {
cursor: String!
- node: OperationUnion
+ node: OperationUnion!
}
# An operation applied to a bug.
@@ -133,8 +124,8 @@ type LabelChangeOperation implements Operation, Authored {
author: Person!
date: Time!
- added: [Label]!
- removed: [Label]!
+ added: [Label!]!
+ removed: [Label!]!
}
union OperationUnion =
@@ -144,14 +135,11 @@ union OperationUnion =
| SetStatusOperation
| LabelChangeOperation
-# The connection type for Label.
+# The connection type for Bug.
type BugConnection {
# A list of edges.
edges: [BugEdge]!
- # A list of nodes.
- nodes: [Bug]!
-
# Information to aid in pagination.
pageInfo: PageInfo!
@@ -165,69 +153,29 @@ type BugEdge {
cursor: String!
# The item at the end of the edge.
- node: Bug
+ node: Bug!
}
-type Bug implements Authored, Commentable {
+type Bug {
id: String!
humanId: String!
title: String!
status: Status!
# A list of labels associated with the repository.
- labels: [Label]!
+ labels: [Label!]!
- comments(
- # Returns the elements in the list that come after the specified cursor.
- after: String
+ comments(input: ConnectionInput!): CommentConnection!
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
-
- # If provided, searches comments by name and description.
- query: String
- ): CommentConnection!
-
- operations(
- # Returns the elements in the list that come after the specified cursor.
- after: String
-
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
-
- # If provided, searches operations by name and description.
- query: String
- ): OperationConnection!
+ operations(input: ConnectionInput!): OperationConnection!
}
-type RootQuery {
- allBugs(
- # Returns the elements in the list that come after the specified cursor.
- after: String
-
- # Returns the elements in the list that come before the specified cursor.
- before: String
-
- # Returns the first _n_ elements from the list.
- first: Int
-
- # Returns the last _n_ elements from the list.
- last: Int
+type Repository {
+ allBugs(input: ConnectionInput!): BugConnection!
+ bug(prefix: String!): Bug
+}
- # If provided, searches labels by name and description.
- query: String
- ): BugConnection!
- bug(id: String!): Bug
+type Query {
+ defaultRepository: Repository
+ repository(id: String!): Repository
}