// Code generated by gqlclientgen - DO NOT EDIT.

package hubsrht

import (
	"context"
	"encoding/json"
	"fmt"
	gqlclient "git.sr.ht/~emersion/gqlclient"
)

type AccessKind string

const (
	AccessKindRo AccessKind = "RO"
	AccessKindRw AccessKind = "RW"
)

type AccessScope string

const (
	AccessScopeProfile  AccessScope = "PROFILE"
	AccessScopeProjects AccessScope = "PROJECTS"
	AccessScopeLists    AccessScope = "LISTS"
	AccessScopeSources  AccessScope = "SOURCES"
	AccessScopeTrackers AccessScope = "TRACKERS"
)

type Cursor string

type Entity struct {
	CanonicalName string `json:"canonicalName"`

	// Underlying value of the GraphQL interface
	Value EntityValue `json:"-"`
}

func (base *Entity) UnmarshalJSON(b []byte) error {
	type Raw Entity
	var data struct {
		*Raw
		TypeName string `json:"__typename"`
	}
	data.Raw = (*Raw)(base)
	err := json.Unmarshal(b, &data)
	if err != nil {
		return err
	}
	switch data.TypeName {
	case "User":
		base.Value = new(User)
	case "":
		return nil
	default:
		return fmt.Errorf("gqlclient: interface Entity: unknown __typename %q", data.TypeName)
	}
	return json.Unmarshal(b, base.Value)
}

// EntityValue is one of: User
type EntityValue interface {
	isEntity()
}

// Describes the status of optional features
type Features struct {
	Lists bool `json:"lists"`
	Git   bool `json:"git"`
	Hg    bool `json:"hg"`
	Todo  bool `json:"todo"`
}

type MailingList struct {
	Rid         string         `json:"rid"`
	Linked      gqlclient.Time `json:"linked"`
	Updated     gqlclient.Time `json:"updated"`
	Owner       *Entity        `json:"owner"`
	Name        string         `json:"name"`
	Description *string        `json:"description,omitempty"`
	Visibility  Visibility     `json:"visibility"`
}

func (*MailingList) isProjectResource() {}

type MailingListCursor struct {
	Results []MailingList `json:"results"`
	Cursor  *Cursor       `json:"cursor,omitempty"`
}

type Project struct {
	Rid               string             `json:"rid"`
	Created           gqlclient.Time     `json:"created"`
	Updated           gqlclient.Time     `json:"updated"`
	Owner             *Entity            `json:"owner"`
	Name              string             `json:"name"`
	Description       *string            `json:"description,omitempty"`
	Website           *string            `json:"website,omitempty"`
	Visibility        Visibility         `json:"visibility"`
	ChecklistComplete bool               `json:"checklistComplete"`
	Tags              []string           `json:"tags"`
	MailingLists      *MailingListCursor `json:"mailingLists"`
	Sources           *SourceRepoCursor  `json:"sources"`
	Trackers          *TrackerCursor     `json:"trackers"`
	Resource          *ProjectResource   `json:"resource,omitempty"`
	MailingList       *MailingList       `json:"mailingList,omitempty"`
	Source            *SourceRepo        `json:"source,omitempty"`
	Tracker           *Tracker           `json:"tracker,omitempty"`
}

type ProjectCursor struct {
	Results []Project `json:"results"`
	Cursor  *Cursor   `json:"cursor,omitempty"`
}

type ProjectResource struct {
	Rid         string         `json:"rid"`
	Linked      gqlclient.Time `json:"linked"`
	Updated     gqlclient.Time `json:"updated"`
	Owner       *Entity        `json:"owner"`
	Name        string         `json:"name"`
	Description *string        `json:"description,omitempty"`
	Visibility  Visibility     `json:"visibility"`

	// Underlying value of the GraphQL interface
	Value ProjectResourceValue `json:"-"`
}

func (base *ProjectResource) UnmarshalJSON(b []byte) error {
	type Raw ProjectResource
	var data struct {
		*Raw
		TypeName string `json:"__typename"`
	}
	data.Raw = (*Raw)(base)
	err := json.Unmarshal(b, &data)
	if err != nil {
		return err
	}
	switch data.TypeName {
	case "MailingList":
		base.Value = new(MailingList)
	case "SourceRepo":
		base.Value = new(SourceRepo)
	case "Tracker":
		base.Value = new(Tracker)
	case "":
		return nil
	default:
		return fmt.Errorf("gqlclient: interface ProjectResource: unknown __typename %q", data.TypeName)
	}
	return json.Unmarshal(b, base.Value)
}

// ProjectResourceValue is one of: MailingList | SourceRepo | Tracker
type ProjectResourceValue interface {
	isProjectResource()
}

type RepoType string

const (
	RepoTypeGit RepoType = "GIT"
	RepoTypeHg  RepoType = "HG"
)

type SourceRepo struct {
	Rid         string         `json:"rid"`
	Linked      gqlclient.Time `json:"linked"`
	Updated     gqlclient.Time `json:"updated"`
	Owner       *Entity        `json:"owner"`
	Name        string         `json:"name"`
	Description *string        `json:"description,omitempty"`
	RepoType    RepoType       `json:"repoType"`
	Visibility  Visibility     `json:"visibility"`
}

func (*SourceRepo) isProjectResource() {}

type SourceRepoCursor struct {
	Results []SourceRepo `json:"results"`
	Cursor  *Cursor      `json:"cursor,omitempty"`
}

type Tracker struct {
	Rid         string         `json:"rid"`
	Linked      gqlclient.Time `json:"linked"`
	Updated     gqlclient.Time `json:"updated"`
	Owner       *Entity        `json:"owner"`
	Name        string         `json:"name"`
	Description *string        `json:"description,omitempty"`
	Visibility  Visibility     `json:"visibility"`
}

func (*Tracker) isProjectResource() {}

type TrackerCursor struct {
	Results []Tracker `json:"results"`
	Cursor  *Cursor   `json:"cursor,omitempty"`
}

type User struct {
	Id            int32          `json:"id"`
	CanonicalName string         `json:"canonicalName"`
	Username      string         `json:"username"`
	Project       *Project       `json:"project,omitempty"`
	Projects      *ProjectCursor `json:"projects"`
}

func (*User) isEntity() {}

type Version struct {
	Major        int32  `json:"major"`
	Minor        int32  `json:"minor"`
	Patch        int32  `json:"patch"`
	BuildVersion string `json:"buildVersion"`
	BuildDate    string `json:"buildDate"`
	// If this API version is scheduled for deprecation, this is the date on which
	// it will stop working; or null if this API version is not scheduled for
	// deprecation.
	DeprecationDate gqlclient.Time `json:"deprecationDate,omitempty"`
	// Optional features
	Features *Features `json:"features"`
}

type Visibility string

const (
	VisibilityPublic   Visibility = "PUBLIC"
	VisibilityUnlisted Visibility = "UNLISTED"
	VisibilityPrivate  Visibility = "PRIVATE"
)

func Projects(client *gqlclient.Client, ctx context.Context, cursor *Cursor) (me *User, err error) {
	op := gqlclient.NewOperation("query projects ($cursor: Cursor) {\n\tme {\n\t\tprojects(cursor: $cursor) {\n\t\t\t... projects\n\t\t}\n\t}\n}\nfragment projects on ProjectCursor {\n\tresults {\n\t\tname\n\t\tdescription\n\t\ttags\n\t\tvisibility\n\t}\n\tcursor\n}\n")
	op.Var("cursor", cursor)
	var respData struct {
		Me *User
	}
	err = client.Execute(ctx, op, &respData)
	return respData.Me, err
}

func ProjectsByUser(client *gqlclient.Client, ctx context.Context, username string, cursor *Cursor) (user *User, err error) {
	op := gqlclient.NewOperation("query projectsByUser ($username: String!, $cursor: Cursor) {\n\tuser(username: $username) {\n\t\tprojects(cursor: $cursor) {\n\t\t\t... projects\n\t\t}\n\t}\n}\nfragment projects on ProjectCursor {\n\tresults {\n\t\tname\n\t\tdescription\n\t\ttags\n\t\tvisibility\n\t}\n\tcursor\n}\n")
	op.Var("username", username)
	op.Var("cursor", cursor)
	var respData struct {
		User *User
	}
	err = client.Execute(ctx, op, &respData)
	return respData.User, err
}

func ProjectByName(client *gqlclient.Client, ctx context.Context, name string) (me *User, err error) {
	op := gqlclient.NewOperation("query projectByName ($name: String!) {\n\tme {\n\t\tproject(name: $name) {\n\t\t\t... projectDetails\n\t\t}\n\t}\n}\nfragment projectDetails on Project {\n\trid\n\tname\n\tdescription\n\twebsite\n\tvisibility\n\ttags\n\towner {\n\t\tcanonicalName\n\t}\n\tmailingLists {\n\t\tcursor\n\t\tresults {\n\t\t\trid\n\t\t\tname\n\t\t\tdescription\n\t\t\tvisibility\n\t\t}\n\t}\n\tsources {\n\t\tcursor\n\t\tresults {\n\t\t\trid\n\t\t\tname\n\t\t\trepoType\n\t\t\tdescription\n\t\t\tvisibility\n\t\t}\n\t}\n\ttrackers {\n\t\tcursor\n\t\tresults {\n\t\t\trid\n\t\t\tname\n\t\t\tdescription\n\t\t\tvisibility\n\t\t}\n\t}\n}\n")
	op.Var("name", name)
	var respData struct {
		Me *User
	}
	err = client.Execute(ctx, op, &respData)
	return respData.Me, err
}

func ProjectByUser(client *gqlclient.Client, ctx context.Context, username string, name string) (user *User, err error) {
	op := gqlclient.NewOperation("query projectByUser ($username: String!, $name: String!) {\n\tuser(username: $username) {\n\t\tproject(name: $name) {\n\t\t\t... projectDetails\n\t\t}\n\t}\n}\nfragment projectDetails on Project {\n\trid\n\tname\n\tdescription\n\twebsite\n\tvisibility\n\ttags\n\towner {\n\t\tcanonicalName\n\t}\n\tmailingLists {\n\t\tcursor\n\t\tresults {\n\t\t\trid\n\t\t\tname\n\t\t\tdescription\n\t\t\tvisibility\n\t\t}\n\t}\n\tsources {\n\t\tcursor\n\t\tresults {\n\t\t\trid\n\t\t\tname\n\t\t\trepoType\n\t\t\tdescription\n\t\t\tvisibility\n\t\t}\n\t}\n\ttrackers {\n\t\tcursor\n\t\tresults {\n\t\t\trid\n\t\t\tname\n\t\t\tdescription\n\t\t\tvisibility\n\t\t}\n\t}\n}\n")
	op.Var("username", username)
	op.Var("name", name)
	var respData struct {
		User *User
	}
	err = client.Execute(ctx, op, &respData)
	return respData.User, err
}
