diff --git a/graphql/query.graphql b/graphql/query.graphql index c01db35..47b2a5f 100644 --- a/graphql/query.graphql +++ b/graphql/query.graphql @@ -1,5 +1,5 @@ type Query { - torrents(filter: TorrentsFilter, pagination: Pagination): [Torrent!]! + torrents(filter: TorrentsFilter): [Torrent!]! fsEntry(path: String!): FsEntry } @@ -10,6 +10,7 @@ input TorrentsFilter { bytesMissing: IntFilter peersCount: IntFilter + downloading: BooleanFilter } input Pagination { diff --git a/graphql/types/torrent.graphql b/graphql/types/torrent.graphql index 10e95f6..1a16327 100644 --- a/graphql/types/torrent.graphql +++ b/graphql/types/torrent.graphql @@ -7,6 +7,9 @@ type Torrent { files: [TorrentFile!]! excludedFiles: [TorrentFile!]! peers: [TorrentPeer!]! + + # if at least one piece of the torrent is request to download and not already downloaded + downloading: Boolean! } type TorrentFile { @@ -21,4 +24,4 @@ type TorrentPeer { discovery: String! port: Int! clientName: String! -} \ No newline at end of file +} diff --git a/src/delivery/graphql/generated.go b/src/delivery/graphql/generated.go index 63e1b56..67b98c0 100644 --- a/src/delivery/graphql/generated.go +++ b/src/delivery/graphql/generated.go @@ -80,7 +80,7 @@ type ComplexityRoot struct { Query struct { FsEntry func(childComplexity int, path string) int - Torrents func(childComplexity int, filter *model.TorrentsFilter, pagination *model.Pagination) int + Torrents func(childComplexity int, filter *model.TorrentsFilter) int } ResolverFS struct { @@ -115,6 +115,7 @@ type ComplexityRoot struct { Torrent struct { BytesCompleted func(childComplexity int) int BytesMissing func(childComplexity int) int + Downloading func(childComplexity int) int ExcludedFiles func(childComplexity int) int Files func(childComplexity int) int Infohash func(childComplexity int) int @@ -166,7 +167,7 @@ type MutationResolver interface { DedupeStorage(ctx context.Context) (int64, error) } type QueryResolver interface { - Torrents(ctx context.Context, filter *model.TorrentsFilter, pagination *model.Pagination) ([]*model.Torrent, error) + Torrents(ctx context.Context, filter *model.TorrentsFilter) ([]*model.Torrent, error) FsEntry(ctx context.Context, path string) (model.FsEntry, error) } type ResolverFSResolver interface { @@ -316,7 +317,7 @@ func (e *executableSchema) Complexity(typeName, field string, childComplexity in return 0, false } - return e.complexity.Query.Torrents(childComplexity, args["filter"].(*model.TorrentsFilter), args["pagination"].(*model.Pagination)), true + return e.complexity.Query.Torrents(childComplexity, args["filter"].(*model.TorrentsFilter)), true case "ResolverFS.entries": if e.complexity.ResolverFS.Entries == nil { @@ -414,6 +415,13 @@ func (e *executableSchema) Complexity(typeName, field string, childComplexity in return e.complexity.Torrent.BytesMissing(childComplexity), true + case "Torrent.downloading": + if e.complexity.Torrent.Downloading == nil { + break + } + + return e.complexity.Torrent.Downloading(childComplexity), true + case "Torrent.excludedFiles": if e.complexity.Torrent.ExcludedFiles == nil { break @@ -731,7 +739,7 @@ type Task { } `, BuiltIn: false}, {Name: "../../../graphql/query.graphql", Input: `type Query { - torrents(filter: TorrentsFilter, pagination: Pagination): [Torrent!]! + torrents(filter: TorrentsFilter): [Torrent!]! fsEntry(path: String!): FsEntry } @@ -742,6 +750,7 @@ input TorrentsFilter { bytesMissing: IntFilter peersCount: IntFilter + downloading: BooleanFilter } input Pagination { @@ -859,6 +868,9 @@ type TorrentFileEntry implements File & FsEntry { files: [TorrentFile!]! excludedFiles: [TorrentFile!]! peers: [TorrentPeer!]! + + # if at least one piece of the torrent is request to download and not already downloaded + downloading: Boolean! } type TorrentFile { @@ -873,7 +885,8 @@ type TorrentPeer { discovery: String! port: Int! clientName: String! -}`, BuiltIn: false}, +} +`, BuiltIn: false}, } var parsedSchema = gqlparser.MustLoadSchema(sources...) @@ -986,15 +999,6 @@ func (ec *executionContext) field_Query_torrents_args(ctx context.Context, rawAr } } args["filter"] = arg0 - var arg1 *model.Pagination - if tmp, ok := rawArgs["pagination"]; ok { - ctx := graphql.WithPathContext(ctx, graphql.NewPathWithField("pagination")) - arg1, err = ec.unmarshalOPagination2ᚖgitᚗkmsignᚗruᚋroyalcatᚋtstorᚋsrcᚋdeliveryᚋgraphqlᚋmodelᚐPagination(ctx, tmp) - if err != nil { - return nil, err - } - } - args["pagination"] = arg1 return args, nil } @@ -1546,7 +1550,7 @@ func (ec *executionContext) _Query_torrents(ctx context.Context, field graphql.C }() resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { ctx = rctx // use context from middleware stack in children - return ec.resolvers.Query().Torrents(rctx, fc.Args["filter"].(*model.TorrentsFilter), fc.Args["pagination"].(*model.Pagination)) + return ec.resolvers.Query().Torrents(rctx, fc.Args["filter"].(*model.TorrentsFilter)) }) if err != nil { ec.Error(ctx, err) @@ -1587,6 +1591,8 @@ func (ec *executionContext) fieldContext_Query_torrents(ctx context.Context, fie return ec.fieldContext_Torrent_excludedFiles(ctx, field) case "peers": return ec.fieldContext_Torrent_peers(ctx, field) + case "downloading": + return ec.fieldContext_Torrent_downloading(ctx, field) } return nil, fmt.Errorf("no field named %q was found under type Torrent", field.Name) }, @@ -2683,6 +2689,50 @@ func (ec *executionContext) fieldContext_Torrent_peers(ctx context.Context, fiel return fc, nil } +func (ec *executionContext) _Torrent_downloading(ctx context.Context, field graphql.CollectedField, obj *model.Torrent) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_Torrent_downloading(ctx, field) + if err != nil { + return graphql.Null + } + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.Downloading, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.(bool) + fc.Result = res + return ec.marshalNBoolean2bool(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_Torrent_downloading(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "Torrent", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + return nil, errors.New("field of type Boolean does not have child fields") + }, + } + return fc, nil +} + func (ec *executionContext) _TorrentFS_name(ctx context.Context, field graphql.CollectedField, obj *model.TorrentFs) (ret graphql.Marshaler) { fc, err := ec.fieldContext_TorrentFS_name(ctx, field) if err != nil { @@ -2782,6 +2832,8 @@ func (ec *executionContext) fieldContext_TorrentFS_torrent(ctx context.Context, return ec.fieldContext_Torrent_excludedFiles(ctx, field) case "peers": return ec.fieldContext_Torrent_peers(ctx, field) + case "downloading": + return ec.fieldContext_Torrent_downloading(ctx, field) } return nil, fmt.Errorf("no field named %q was found under type Torrent", field.Name) }, @@ -3064,6 +3116,8 @@ func (ec *executionContext) fieldContext_TorrentFileEntry_torrent(ctx context.Co return ec.fieldContext_Torrent_excludedFiles(ctx, field) case "peers": return ec.fieldContext_Torrent_peers(ctx, field) + case "downloading": + return ec.fieldContext_Torrent_downloading(ctx, field) } return nil, fmt.Errorf("no field named %q was found under type Torrent", field.Name) }, @@ -3390,6 +3444,8 @@ func (ec *executionContext) fieldContext_TorrentProgress_torrent(ctx context.Con return ec.fieldContext_Torrent_excludedFiles(ctx, field) case "peers": return ec.fieldContext_Torrent_peers(ctx, field) + case "downloading": + return ec.fieldContext_Torrent_downloading(ctx, field) } return nil, fmt.Errorf("no field named %q was found under type Torrent", field.Name) }, @@ -5773,7 +5829,7 @@ func (ec *executionContext) unmarshalInputTorrentsFilter(ctx context.Context, ob asMap[k] = v } - fieldsInOrder := [...]string{"infohash", "name", "bytesCompleted", "bytesMissing", "peersCount"} + fieldsInOrder := [...]string{"infohash", "name", "bytesCompleted", "bytesMissing", "peersCount", "downloading"} for _, k := range fieldsInOrder { v, ok := asMap[k] if !ok { @@ -5815,6 +5871,13 @@ func (ec *executionContext) unmarshalInputTorrentsFilter(ctx context.Context, ob return it, err } it.PeersCount = data + case "downloading": + ctx := graphql.WithPathContext(ctx, graphql.NewPathWithField("downloading")) + data, err := ec.unmarshalOBooleanFilter2ᚖgitᚗkmsignᚗruᚋroyalcatᚋtstorᚋsrcᚋdeliveryᚋgraphqlᚋmodelᚐBooleanFilter(ctx, v) + if err != nil { + return it, err + } + it.Downloading = data } } @@ -6752,6 +6815,11 @@ func (ec *executionContext) _Torrent(ctx context.Context, sel ast.SelectionSet, } out.Concurrently(i, func(ctx context.Context) graphql.Marshaler { return innerFunc(ctx, out) }) + case "downloading": + out.Values[i] = ec._Torrent_downloading(ctx, field, obj) + if out.Values[i] == graphql.Null { + atomic.AddUint32(&out.Invalids, 1) + } default: panic("unknown field " + strconv.Quote(field.Name)) } @@ -8008,6 +8076,14 @@ func (ec *executionContext) marshalOBoolean2ᚖbool(ctx context.Context, sel ast return res } +func (ec *executionContext) unmarshalOBooleanFilter2ᚖgitᚗkmsignᚗruᚋroyalcatᚋtstorᚋsrcᚋdeliveryᚋgraphqlᚋmodelᚐBooleanFilter(ctx context.Context, v interface{}) (*model.BooleanFilter, error) { + if v == nil { + return nil, nil + } + res, err := ec.unmarshalInputBooleanFilter(ctx, v) + return &res, graphql.ErrorOnPath(ctx, err) +} + func (ec *executionContext) unmarshalODateTime2ᚖtimeᚐTime(ctx context.Context, v interface{}) (*time.Time, error) { if v == nil { return nil, nil @@ -8107,14 +8183,6 @@ func (ec *executionContext) marshalOMutation2ᚖgitᚗkmsignᚗruᚋroyalcatᚋt return ec._Mutation(ctx, sel) } -func (ec *executionContext) unmarshalOPagination2ᚖgitᚗkmsignᚗruᚋroyalcatᚋtstorᚋsrcᚋdeliveryᚋgraphqlᚋmodelᚐPagination(ctx context.Context, v interface{}) (*model.Pagination, error) { - if v == nil { - return nil, nil - } - res, err := ec.unmarshalInputPagination(ctx, v) - return &res, graphql.ErrorOnPath(ctx, err) -} - func (ec *executionContext) marshalOProgress2gitᚗkmsignᚗruᚋroyalcatᚋtstorᚋsrcᚋdeliveryᚋgraphqlᚋmodelᚐProgress(ctx context.Context, sel ast.SelectionSet, v model.Progress) graphql.Marshaler { if v == nil { return graphql.Null diff --git a/src/delivery/graphql/model/entry.go b/src/delivery/graphql/model/entry.go index 940e9cc..24bcf91 100644 --- a/src/delivery/graphql/model/entry.go +++ b/src/delivery/graphql/model/entry.go @@ -1,6 +1,8 @@ package model import ( + "context" + "git.kmsign.ru/royalcat/tstor/src/host/vfs" ) @@ -9,7 +11,7 @@ type FsElem interface { IsDir() bool } -func FillFsEntry(e FsElem, fs vfs.Filesystem, path string) FsEntry { +func FillFsEntry(ctx context.Context, e FsElem, fs vfs.Filesystem, path string) (FsEntry, error) { switch e.(type) { case *vfs.ArchiveFS: e := e.(*vfs.ArchiveFS) @@ -17,31 +19,35 @@ func FillFsEntry(e FsElem, fs vfs.Filesystem, path string) FsEntry { Name: e.Name(), Size: e.Size(), FS: e, - } + }, nil case *vfs.ResolverFS: e := e.(*vfs.ResolverFS) return ResolverFs{ Name: e.Name(), FS: e, - } + }, nil case *vfs.TorrentFS: e := e.(*vfs.TorrentFS) + torrent, err := MapTorrent(ctx, e.Torrent) + if err != nil { + return nil, err + } return TorrentFs{ Name: e.Name(), - Torrent: MapTorrent(e.Torrent), + Torrent: torrent, FS: e, - } + }, nil default: if e.IsDir() { return SimpleDir{ Name: e.Name(), FS: fs, Path: path, - } + }, nil } else { return SimpleFile{ Name: e.Name(), - } + }, nil } } } diff --git a/src/delivery/graphql/model/filter.go b/src/delivery/graphql/model/filter.go index 6ae7fc8..834d2ef 100644 --- a/src/delivery/graphql/model/filter.go +++ b/src/delivery/graphql/model/filter.go @@ -42,3 +42,13 @@ func (f *StringFilter) Include(v string) bool { return true } + +func (f *BooleanFilter) Include(v bool) bool { + if f == nil { + return true + } else if f.Eq != nil { + return v == *f.Eq + } + + return true +} diff --git a/src/delivery/graphql/model/mappers.go b/src/delivery/graphql/model/mappers.go index e2227e0..f0b193b 100644 --- a/src/delivery/graphql/model/mappers.go +++ b/src/delivery/graphql/model/mappers.go @@ -1,6 +1,8 @@ package model import ( + "context" + "git.kmsign.ru/royalcat/tstor/src/host/controller" "github.com/anacrolix/torrent" ) @@ -26,12 +28,25 @@ func MapPeerSource(source torrent.PeerSource) string { } } -func MapTorrent(t *controller.Torrent) *Torrent { +func MapTorrent(ctx context.Context, t *controller.Torrent) (*Torrent, error) { + downloading := false + files, err := t.Files(ctx) + if err != nil { + return nil, err + } + for _, file := range files { + if file.Priority() > torrent.PiecePriorityNone && file.BytesCompleted() < file.Length() { + downloading = true + break + } + } + return &Torrent{ Infohash: t.InfoHash(), Name: t.Name(), BytesCompleted: t.BytesCompleted(), BytesMissing: t.BytesMissing(), T: t, - } + Downloading: downloading, + }, nil } diff --git a/src/delivery/graphql/model/models_gen.go b/src/delivery/graphql/model/models_gen.go index b7f4807..2051c94 100644 --- a/src/delivery/graphql/model/models_gen.go +++ b/src/delivery/graphql/model/models_gen.go @@ -179,6 +179,7 @@ type Torrent struct { Files []*TorrentFile `json:"files"` ExcludedFiles []*TorrentFile `json:"excludedFiles"` Peers []*TorrentPeer `json:"peers"` + Downloading bool `json:"downloading"` T *controller.Torrent `json:"-"` } @@ -248,9 +249,10 @@ func (this TorrentProgress) GetCurrent() int64 { return this.Current } func (this TorrentProgress) GetTotal() int64 { return this.Total } type TorrentsFilter struct { - Infohash *StringFilter `json:"infohash,omitempty"` - Name *StringFilter `json:"name,omitempty"` - BytesCompleted *IntFilter `json:"bytesCompleted,omitempty"` - BytesMissing *IntFilter `json:"bytesMissing,omitempty"` - PeersCount *IntFilter `json:"peersCount,omitempty"` + Infohash *StringFilter `json:"infohash,omitempty"` + Name *StringFilter `json:"name,omitempty"` + BytesCompleted *IntFilter `json:"bytesCompleted,omitempty"` + BytesMissing *IntFilter `json:"bytesMissing,omitempty"` + PeersCount *IntFilter `json:"peersCount,omitempty"` + Downloading *BooleanFilter `json:"downloading,omitempty"` } diff --git a/src/delivery/graphql/resolver/fs.resolvers.go b/src/delivery/graphql/resolver/fs.resolvers.go index 999fd9b..3e180b0 100644 --- a/src/delivery/graphql/resolver/fs.resolvers.go +++ b/src/delivery/graphql/resolver/fs.resolvers.go @@ -19,7 +19,11 @@ func (r *archiveFSResolver) Entries(ctx context.Context, obj *model.ArchiveFs) ( } out := []model.FsEntry{} for _, e := range entries { - out = append(out, model.FillFsEntry(e, obj.FS, ".")) + entry, err := model.FillFsEntry(ctx, e, obj.FS, ".") + if err != nil { + return nil, err + } + out = append(out, entry) } return out, nil } @@ -32,7 +36,11 @@ func (r *resolverFSResolver) Entries(ctx context.Context, obj *model.ResolverFs) } out := []model.FsEntry{} for _, e := range entries { - out = append(out, model.FillFsEntry(e, obj.FS, ".")) + entry, err := model.FillFsEntry(ctx, e, obj.FS, ".") + if err != nil { + return nil, err + } + out = append(out, entry) } return out, nil } @@ -45,7 +53,11 @@ func (r *simpleDirResolver) Entries(ctx context.Context, obj *model.SimpleDir) ( } out := []model.FsEntry{} for _, e := range entries { - out = append(out, model.FillFsEntry(e, obj.FS, obj.Path)) + entry, err := model.FillFsEntry(ctx, e, obj.FS, obj.Path) + if err != nil { + return nil, err + } + out = append(out, entry) } return out, nil } @@ -58,7 +70,11 @@ func (r *torrentFSResolver) Entries(ctx context.Context, obj *model.TorrentFs) ( } out := []model.FsEntry{} for _, e := range entries { - out = append(out, model.FillFsEntry(e, obj.FS, ".")) + entry, err := model.FillFsEntry(ctx, e, obj.FS, ".") + if err != nil { + return nil, err + } + out = append(out, entry) } return out, nil } diff --git a/src/delivery/graphql/resolver/query.resolvers.go b/src/delivery/graphql/resolver/query.resolvers.go index 705cb65..d3d03dd 100644 --- a/src/delivery/graphql/resolver/query.resolvers.go +++ b/src/delivery/graphql/resolver/query.resolvers.go @@ -15,7 +15,7 @@ import ( ) // Torrents is the resolver for the torrents field. -func (r *queryResolver) Torrents(ctx context.Context, filter *model.TorrentsFilter, pagination *model.Pagination) ([]*model.Torrent, error) { +func (r *queryResolver) Torrents(ctx context.Context, filter *model.TorrentsFilter) ([]*model.Torrent, error) { torrents, err := r.Service.ListTorrents(ctx) if err != nil { return nil, err @@ -49,6 +49,13 @@ func (r *queryResolver) Torrents(ctx context.Context, filter *model.TorrentsFilt }) } + if filter.Downloading != nil { + filterFuncs = append(filterFuncs, func(torrent *model.Torrent) bool { + return filter.Downloading.Include( + torrent.Downloading, + ) + }) + } } filterFunc := func(torrent *model.Torrent) bool { @@ -62,7 +69,10 @@ func (r *queryResolver) Torrents(ctx context.Context, filter *model.TorrentsFilt tr := []*model.Torrent{} for _, t := range torrents { - d := model.MapTorrent(t) + d, err := model.MapTorrent(ctx, t) + if err != nil { + return nil, err + } if !filterFunc(d) { continue @@ -71,7 +81,7 @@ func (r *queryResolver) Torrents(ctx context.Context, filter *model.TorrentsFilt } slices.SortStableFunc(torrents, func(t1, t2 *controller.Torrent) int { - return strings.Compare(t1.InfoHash(), t2.InfoHash()) + return strings.Compare(t1.Name(), t2.Name()) }) return tr, nil @@ -84,7 +94,7 @@ func (r *queryResolver) FsEntry(ctx context.Context, path string) (model.FsEntry return nil, err } - return model.FillFsEntry(entry, r.VFS, path), nil + return model.FillFsEntry(ctx, entry, r.VFS, path) } // Query returns graph.QueryResolver implementation. diff --git a/src/delivery/graphql/resolver/subscription.resolvers.go b/src/delivery/graphql/resolver/subscription.resolvers.go index 7011caf..f5eb19e 100644 --- a/src/delivery/graphql/resolver/subscription.resolvers.go +++ b/src/delivery/graphql/resolver/subscription.resolvers.go @@ -32,8 +32,13 @@ func (r *subscriptionResolver) TorrentDownloadUpdates(ctx context.Context) (<-ch fmt.Println("nil torrent") continue } + torrent, err := model.MapTorrent(ctx, p.Torrent) + if err != nil { + // TODO logs + continue + } po := &model.TorrentProgress{ - Torrent: model.MapTorrent(p.Torrent), + Torrent: torrent, Current: p.Current, Total: p.Total, } diff --git a/src/delivery/http.go b/src/delivery/http.go index 52f7ff4..6074411 100644 --- a/src/delivery/http.go +++ b/src/delivery/http.go @@ -20,7 +20,7 @@ func New(fc *filecache.Cache, ss *service.Stats, s *service.Service, vfs vfs.Fil r := echo.New() r.Use( - middleware.Recover(), + // middleware.Recover(), middleware.Gzip(), middleware.Decompress(), Logger(), diff --git a/src/host/controller/torrent.go b/src/host/controller/torrent.go index 30aa6cc..9f9288f 100644 --- a/src/host/controller/torrent.go +++ b/src/host/controller/torrent.go @@ -62,9 +62,18 @@ func (s *Torrent) Files(ctx context.Context) ([]*torrent.File, error) { return nil, err } - <-s.t.GotInfo() + select { + case <-ctx.Done(): + return nil, ctx.Err() + case <-s.t.GotInfo(): + } + files := s.t.Files() files = slices.DeleteFunc(files, func(file *torrent.File) bool { + if file == nil { + return true + } + p := file.Path() if strings.Contains(p, "/.pad/") { return true diff --git a/ui/build.yaml b/ui/build.yaml index 136c524..454012b 100644 --- a/ui/build.yaml +++ b/ui/build.yaml @@ -3,6 +3,7 @@ targets: builders: graphql_codegen: options: + generatedFileHeader: "// ignore_for_file: type=lint\n" scalars: URL: type: String diff --git a/ui/lib/api/client.dart b/ui/lib/api/client.dart index d1d92e4..7b1d2a2 100644 --- a/ui/lib/api/client.dart +++ b/ui/lib/api/client.dart @@ -1,18 +1,8 @@ import 'package:flutter/foundation.dart'; import 'package:graphql/client.dart'; -final client = GraphQLClient( - link: _loggerLink.concat(HttpLink("http://localhost:4444/graphql")), - cache: GraphQLCache(store: null), - defaultPolicies: DefaultPolicies( - query: Policies( - fetch: FetchPolicy.noCache, - ), - ), -); - // final client = GraphQLClient( -// link: HttpLink("http://192.168.217.150:4444/graphql"), +// link: _loggerLink.concat(HttpLink("http://localhost:4444/graphql")), // cache: GraphQLCache(store: null), // defaultPolicies: DefaultPolicies( // query: Policies( @@ -21,6 +11,16 @@ final client = GraphQLClient( // ), // ); +final client = GraphQLClient( + link: HttpLink("http://192.168.217.150:4444/graphql"), + cache: GraphQLCache(store: null), + defaultPolicies: DefaultPolicies( + query: Policies( + fetch: FetchPolicy.noCache, + ), + ), +); + class LoggerLink extends Link { @override Stream request( diff --git a/ui/lib/api/fs_entry.graphql.dart b/ui/lib/api/fs_entry.graphql.dart index 8b047a6..9f0c455 100644 --- a/ui/lib/api/fs_entry.graphql.dart +++ b/ui/lib/api/fs_entry.graphql.dart @@ -1,4 +1,6 @@ +// ignore_for_file: type=lint import 'dart:async'; +import 'package:flutter/widgets.dart' as widgets; import 'package:gql/ast.dart'; import 'package:graphql/client.dart' as graphql; import 'package:graphql_flutter/graphql_flutter.dart' as graphql_flutter; @@ -37,14 +39,14 @@ class Fragment$File { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; + _resultData['size'] = l$size; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -64,7 +66,7 @@ class Fragment$File { if (identical(this, other)) { return true; } - if (other is! Fragment$File || runtimeType != other.runtimeType) { + if (!(other is Fragment$File) || runtimeType != other.runtimeType) { return false; } final l$name = name; @@ -163,7 +165,6 @@ class _CopyWithImpl$Fragment$File static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? size = _undefined, @@ -185,9 +186,8 @@ class _CopyWithStubImpl$Fragment$File implements CopyWith$Fragment$File { _CopyWithStubImpl$Fragment$File(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, int? size, @@ -238,7 +238,7 @@ extension ClientExtension$Fragment$File on graphql.GraphQLClient { required Map idFields, bool broadcast = true, }) => - writeFragment( + this.writeFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -253,7 +253,7 @@ extension ClientExtension$Fragment$File on graphql.GraphQLClient { required Map idFields, bool optimistic = true, }) { - final result = readFragment( + final result = this.readFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -285,25 +285,21 @@ class Fragment$File$$SimpleFile implements Fragment$File { ); } - @override final String name; - @override final int size; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; + _resultData['size'] = l$size; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -323,7 +319,7 @@ class Fragment$File$$SimpleFile implements Fragment$File { if (identical(this, other)) { return true; } - if (other is! Fragment$File$$SimpleFile || + if (!(other is Fragment$File$$SimpleFile) || runtimeType != other.runtimeType) { return false; } @@ -384,7 +380,6 @@ class _CopyWithImpl$Fragment$File$$SimpleFile static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? size = _undefined, @@ -406,9 +401,8 @@ class _CopyWithStubImpl$Fragment$File$$SimpleFile implements CopyWith$Fragment$File$$SimpleFile { _CopyWithStubImpl$Fragment$File$$SimpleFile(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, int? size, @@ -435,25 +429,21 @@ class Fragment$File$$TorrentFileEntry implements Fragment$File { ); } - @override final String name; - @override final int size; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; + _resultData['size'] = l$size; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -473,7 +463,7 @@ class Fragment$File$$TorrentFileEntry implements Fragment$File { if (identical(this, other)) { return true; } - if (other is! Fragment$File$$TorrentFileEntry || + if (!(other is Fragment$File$$TorrentFileEntry) || runtimeType != other.runtimeType) { return false; } @@ -534,7 +524,6 @@ class _CopyWithImpl$Fragment$File$$TorrentFileEntry static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? size = _undefined, @@ -556,9 +545,8 @@ class _CopyWithStubImpl$Fragment$File$$TorrentFileEntry implements CopyWith$Fragment$File$$TorrentFileEntry { _CopyWithStubImpl$Fragment$File$$TorrentFileEntry(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, int? size, @@ -593,14 +581,14 @@ class Fragment$TorrentDir { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$torrent = torrent; - resultData['torrent'] = l$torrent.toJson(); + _resultData['torrent'] = l$torrent.toJson(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -620,7 +608,7 @@ class Fragment$TorrentDir { if (identical(this, other)) { return true; } - if (other is! Fragment$TorrentDir || runtimeType != other.runtimeType) { + if (!(other is Fragment$TorrentDir) || runtimeType != other.runtimeType) { return false; } final l$name = name; @@ -680,7 +668,6 @@ class _CopyWithImpl$Fragment$TorrentDir static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? torrent = _undefined, @@ -698,7 +685,6 @@ class _CopyWithImpl$Fragment$TorrentDir : ($__typename as String), )); - @override CopyWith$Fragment$TorrentDir$torrent get torrent { final local$torrent = _instance.torrent; return CopyWith$Fragment$TorrentDir$torrent( @@ -710,9 +696,8 @@ class _CopyWithStubImpl$Fragment$TorrentDir implements CopyWith$Fragment$TorrentDir { _CopyWithStubImpl$Fragment$TorrentDir(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, Fragment$TorrentDir$torrent? torrent, @@ -720,7 +705,6 @@ class _CopyWithStubImpl$Fragment$TorrentDir }) => _res; - @override CopyWith$Fragment$TorrentDir$torrent get torrent => CopyWith$Fragment$TorrentDir$torrent.stub(_res); } @@ -810,7 +794,7 @@ extension ClientExtension$Fragment$TorrentDir on graphql.GraphQLClient { required Map idFields, bool broadcast = true, }) => - writeFragment( + this.writeFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -825,7 +809,7 @@ extension ClientExtension$Fragment$TorrentDir on graphql.GraphQLClient { required Map idFields, bool optimistic = true, }) { - final result = readFragment( + final result = this.readFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -879,20 +863,20 @@ class Fragment$TorrentDir$torrent { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$infohash = infohash; - resultData['infohash'] = l$infohash; + _resultData['infohash'] = l$infohash; final l$bytesCompleted = bytesCompleted; - resultData['bytesCompleted'] = l$bytesCompleted; + _resultData['bytesCompleted'] = l$bytesCompleted; final l$torrentFilePath = torrentFilePath; - resultData['torrentFilePath'] = l$torrentFilePath; + _resultData['torrentFilePath'] = l$torrentFilePath; final l$bytesMissing = bytesMissing; - resultData['bytesMissing'] = l$bytesMissing; + _resultData['bytesMissing'] = l$bytesMissing; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -918,7 +902,7 @@ class Fragment$TorrentDir$torrent { if (identical(this, other)) { return true; } - if (other is! Fragment$TorrentDir$torrent || + if (!(other is Fragment$TorrentDir$torrent) || runtimeType != other.runtimeType) { return false; } @@ -997,7 +981,6 @@ class _CopyWithImpl$Fragment$TorrentDir$torrent static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? infohash = _undefined, @@ -1033,9 +1016,8 @@ class _CopyWithStubImpl$Fragment$TorrentDir$torrent implements CopyWith$Fragment$TorrentDir$torrent { _CopyWithStubImpl$Fragment$TorrentDir$torrent(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? infohash, @@ -1072,14 +1054,14 @@ class Fragment$ArchiveDir { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; + _resultData['size'] = l$size; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -1099,7 +1081,7 @@ class Fragment$ArchiveDir { if (identical(this, other)) { return true; } - if (other is! Fragment$ArchiveDir || runtimeType != other.runtimeType) { + if (!(other is Fragment$ArchiveDir) || runtimeType != other.runtimeType) { return false; } final l$name = name; @@ -1158,7 +1140,6 @@ class _CopyWithImpl$Fragment$ArchiveDir static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? size = _undefined, @@ -1180,9 +1161,8 @@ class _CopyWithStubImpl$Fragment$ArchiveDir implements CopyWith$Fragment$ArchiveDir { _CopyWithStubImpl$Fragment$ArchiveDir(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, int? size, @@ -1233,7 +1213,7 @@ extension ClientExtension$Fragment$ArchiveDir on graphql.GraphQLClient { required Map idFields, bool broadcast = true, }) => - writeFragment( + this.writeFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -1248,7 +1228,7 @@ extension ClientExtension$Fragment$ArchiveDir on graphql.GraphQLClient { required Map idFields, bool optimistic = true, }) { - final result = readFragment( + final result = this.readFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -1303,12 +1283,12 @@ class Fragment$DirEntry { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -1326,7 +1306,7 @@ class Fragment$DirEntry { if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry || runtimeType != other.runtimeType) { + if (!(other is Fragment$DirEntry) || runtimeType != other.runtimeType) { return false; } final l$name = name; @@ -1468,7 +1448,6 @@ class _CopyWithImpl$Fragment$DirEntry static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? $__typename = _undefined, @@ -1487,9 +1466,8 @@ class _CopyWithStubImpl$Fragment$DirEntry implements CopyWith$Fragment$DirEntry { _CopyWithStubImpl$Fragment$DirEntry(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? $__typename, @@ -1547,7 +1525,7 @@ extension ClientExtension$Fragment$DirEntry on graphql.GraphQLClient { required Map idFields, bool broadcast = true, }) => - writeFragment( + this.writeFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -1562,7 +1540,7 @@ extension ClientExtension$Fragment$DirEntry on graphql.GraphQLClient { required Map idFields, bool optimistic = true, }) { - final result = readFragment( + final result = this.readFragment( graphql.FragmentRequest( idFields: idFields, fragment: const graphql.Fragment( @@ -1595,25 +1573,21 @@ class Fragment$DirEntry$$ArchiveFS ); } - @override final String name; - @override final int size; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; + _resultData['size'] = l$size; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -1633,7 +1607,7 @@ class Fragment$DirEntry$$ArchiveFS if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry$$ArchiveFS || + if (!(other is Fragment$DirEntry$$ArchiveFS) || runtimeType != other.runtimeType) { return false; } @@ -1694,7 +1668,6 @@ class _CopyWithImpl$Fragment$DirEntry$$ArchiveFS static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? size = _undefined, @@ -1716,9 +1689,8 @@ class _CopyWithStubImpl$Fragment$DirEntry$$ArchiveFS implements CopyWith$Fragment$DirEntry$$ArchiveFS { _CopyWithStubImpl$Fragment$DirEntry$$ArchiveFS(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, int? size, @@ -1742,20 +1714,17 @@ class Fragment$DirEntry$$ResolverFS implements Fragment$DirEntry { ); } - @override final String name; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -1773,7 +1742,7 @@ class Fragment$DirEntry$$ResolverFS implements Fragment$DirEntry { if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry$$ResolverFS || + if (!(other is Fragment$DirEntry$$ResolverFS) || runtimeType != other.runtimeType) { return false; } @@ -1828,7 +1797,6 @@ class _CopyWithImpl$Fragment$DirEntry$$ResolverFS static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? $__typename = _undefined, @@ -1847,9 +1815,8 @@ class _CopyWithStubImpl$Fragment$DirEntry$$ResolverFS implements CopyWith$Fragment$DirEntry$$ResolverFS { _CopyWithStubImpl$Fragment$DirEntry$$ResolverFS(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? $__typename, @@ -1872,20 +1839,17 @@ class Fragment$DirEntry$$SimpleDir implements Fragment$DirEntry { ); } - @override final String name; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -1903,7 +1867,7 @@ class Fragment$DirEntry$$SimpleDir implements Fragment$DirEntry { if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry$$SimpleDir || + if (!(other is Fragment$DirEntry$$SimpleDir) || runtimeType != other.runtimeType) { return false; } @@ -1958,7 +1922,6 @@ class _CopyWithImpl$Fragment$DirEntry$$SimpleDir static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? $__typename = _undefined, @@ -1977,9 +1940,8 @@ class _CopyWithStubImpl$Fragment$DirEntry$$SimpleDir implements CopyWith$Fragment$DirEntry$$SimpleDir { _CopyWithStubImpl$Fragment$DirEntry$$SimpleDir(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? $__typename, @@ -2006,25 +1968,21 @@ class Fragment$DirEntry$$SimpleFile ); } - @override final String name; - @override final int size; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; + _resultData['size'] = l$size; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -2044,7 +2002,7 @@ class Fragment$DirEntry$$SimpleFile if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry$$SimpleFile || + if (!(other is Fragment$DirEntry$$SimpleFile) || runtimeType != other.runtimeType) { return false; } @@ -2105,7 +2063,6 @@ class _CopyWithImpl$Fragment$DirEntry$$SimpleFile static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? size = _undefined, @@ -2127,9 +2084,8 @@ class _CopyWithStubImpl$Fragment$DirEntry$$SimpleFile implements CopyWith$Fragment$DirEntry$$SimpleFile { _CopyWithStubImpl$Fragment$DirEntry$$SimpleFile(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, int? size, @@ -2158,25 +2114,21 @@ class Fragment$DirEntry$$TorrentFS ); } - @override final String name; - @override final Fragment$DirEntry$$TorrentFS$torrent torrent; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$torrent = torrent; - resultData['torrent'] = l$torrent.toJson(); + _resultData['torrent'] = l$torrent.toJson(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -2196,7 +2148,7 @@ class Fragment$DirEntry$$TorrentFS if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry$$TorrentFS || + if (!(other is Fragment$DirEntry$$TorrentFS) || runtimeType != other.runtimeType) { return false; } @@ -2258,7 +2210,6 @@ class _CopyWithImpl$Fragment$DirEntry$$TorrentFS static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? torrent = _undefined, @@ -2276,7 +2227,6 @@ class _CopyWithImpl$Fragment$DirEntry$$TorrentFS : ($__typename as String), )); - @override CopyWith$Fragment$DirEntry$$TorrentFS$torrent get torrent { final local$torrent = _instance.torrent; return CopyWith$Fragment$DirEntry$$TorrentFS$torrent( @@ -2288,9 +2238,8 @@ class _CopyWithStubImpl$Fragment$DirEntry$$TorrentFS implements CopyWith$Fragment$DirEntry$$TorrentFS { _CopyWithStubImpl$Fragment$DirEntry$$TorrentFS(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, Fragment$DirEntry$$TorrentFS$torrent? torrent, @@ -2298,7 +2247,6 @@ class _CopyWithStubImpl$Fragment$DirEntry$$TorrentFS }) => _res; - @override CopyWith$Fragment$DirEntry$$TorrentFS$torrent get torrent => CopyWith$Fragment$DirEntry$$TorrentFS$torrent.stub(_res); } @@ -2332,40 +2280,33 @@ class Fragment$DirEntry$$TorrentFS$torrent ); } - @override final String name; - @override final String infohash; - @override final int bytesCompleted; - @override final String torrentFilePath; - @override final int bytesMissing; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$infohash = infohash; - resultData['infohash'] = l$infohash; + _resultData['infohash'] = l$infohash; final l$bytesCompleted = bytesCompleted; - resultData['bytesCompleted'] = l$bytesCompleted; + _resultData['bytesCompleted'] = l$bytesCompleted; final l$torrentFilePath = torrentFilePath; - resultData['torrentFilePath'] = l$torrentFilePath; + _resultData['torrentFilePath'] = l$torrentFilePath; final l$bytesMissing = bytesMissing; - resultData['bytesMissing'] = l$bytesMissing; + _resultData['bytesMissing'] = l$bytesMissing; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -2391,7 +2332,7 @@ class Fragment$DirEntry$$TorrentFS$torrent if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry$$TorrentFS$torrent || + if (!(other is Fragment$DirEntry$$TorrentFS$torrent) || runtimeType != other.runtimeType) { return false; } @@ -2471,7 +2412,6 @@ class _CopyWithImpl$Fragment$DirEntry$$TorrentFS$torrent static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? infohash = _undefined, @@ -2507,9 +2447,8 @@ class _CopyWithStubImpl$Fragment$DirEntry$$TorrentFS$torrent implements CopyWith$Fragment$DirEntry$$TorrentFS$torrent { _CopyWithStubImpl$Fragment$DirEntry$$TorrentFS$torrent(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? infohash, @@ -2541,25 +2480,21 @@ class Fragment$DirEntry$$TorrentFileEntry ); } - @override final String name; - @override final int size; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; + _resultData['size'] = l$size; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -2579,7 +2514,7 @@ class Fragment$DirEntry$$TorrentFileEntry if (identical(this, other)) { return true; } - if (other is! Fragment$DirEntry$$TorrentFileEntry || + if (!(other is Fragment$DirEntry$$TorrentFileEntry) || runtimeType != other.runtimeType) { return false; } @@ -2641,7 +2576,6 @@ class _CopyWithImpl$Fragment$DirEntry$$TorrentFileEntry static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? size = _undefined, @@ -2663,9 +2597,8 @@ class _CopyWithStubImpl$Fragment$DirEntry$$TorrentFileEntry implements CopyWith$Fragment$DirEntry$$TorrentFileEntry { _CopyWithStubImpl$Fragment$DirEntry$$TorrentFileEntry(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, int? size, @@ -2711,7 +2644,7 @@ class Variables$Query$ListDir { if (identical(this, other)) { return true; } - if (other is! Variables$Query$ListDir || + if (!(other is Variables$Query$ListDir) || runtimeType != other.runtimeType) { return false; } @@ -2755,7 +2688,6 @@ class _CopyWithImpl$Variables$Query$ListDir static const _undefined = {}; - @override TRes call({Object? path = _undefined}) => _then(Variables$Query$ListDir._({ ..._instance._$data, if (path != _undefined && path != null) 'path': (path as String), @@ -2766,9 +2698,8 @@ class _CopyWithStubImpl$Variables$Query$ListDir implements CopyWith$Variables$Query$ListDir { _CopyWithStubImpl$Variables$Query$ListDir(this._res); - final TRes _res; + TRes _res; - @override call({String? path}) => _res; } @@ -2794,12 +2725,12 @@ class Query$ListDir { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$fsEntry = fsEntry; - resultData['fsEntry'] = l$fsEntry?.toJson(); + _resultData['fsEntry'] = l$fsEntry?.toJson(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -2817,7 +2748,7 @@ class Query$ListDir { if (identical(this, other)) { return true; } - if (other is! Query$ListDir || runtimeType != other.runtimeType) { + if (!(other is Query$ListDir) || runtimeType != other.runtimeType) { return false; } final l$fsEntry = fsEntry; @@ -2870,7 +2801,6 @@ class _CopyWithImpl$Query$ListDir static const _undefined = {}; - @override TRes call({ Object? fsEntry = _undefined, Object? $__typename = _undefined, @@ -2884,7 +2814,6 @@ class _CopyWithImpl$Query$ListDir : ($__typename as String), )); - @override CopyWith$Query$ListDir$fsEntry get fsEntry { final local$fsEntry = _instance.fsEntry; return local$fsEntry == null @@ -2898,16 +2827,14 @@ class _CopyWithStubImpl$Query$ListDir implements CopyWith$Query$ListDir { _CopyWithStubImpl$Query$ListDir(this._res); - final TRes _res; + TRes _res; - @override call({ Query$ListDir$fsEntry? fsEntry, String? $__typename, }) => _res; - @override CopyWith$Query$ListDir$fsEntry get fsEntry => CopyWith$Query$ListDir$fsEntry.stub(_res); } @@ -3023,27 +2950,34 @@ typedef OnQueryComplete$Query$ListDir = FutureOr Function( class Options$Query$ListDir extends graphql.QueryOptions { Options$Query$ListDir({ - super.operationName, + String? operationName, required Variables$Query$ListDir variables, - super.fetchPolicy, - super.errorPolicy, - super.cacheRereadPolicy, + graphql.FetchPolicy? fetchPolicy, + graphql.ErrorPolicy? errorPolicy, + graphql.CacheRereadPolicy? cacheRereadPolicy, Object? optimisticResult, Query$ListDir? typedOptimisticResult, - super.pollInterval, - super.context, + Duration? pollInterval, + graphql.Context? context, OnQueryComplete$Query$ListDir? onComplete, - super.onError, + graphql.OnQueryError? onError, }) : onCompleteWithParsed = onComplete, super( variables: variables.toJson(), + operationName: operationName, + fetchPolicy: fetchPolicy, + errorPolicy: errorPolicy, + cacheRereadPolicy: cacheRereadPolicy, optimisticResult: optimisticResult ?? typedOptimisticResult?.toJson(), + pollInterval: pollInterval, + context: context, onComplete: onComplete == null ? null : (data) => onComplete( data, data == null ? null : _parserFn$Query$ListDir(data), ), + onError: onError, document: documentNodeQueryListDir, parserFn: _parserFn$Query$ListDir, ); @@ -3062,31 +2996,41 @@ class Options$Query$ListDir extends graphql.QueryOptions { class WatchOptions$Query$ListDir extends graphql.WatchQueryOptions { WatchOptions$Query$ListDir({ - super.operationName, + String? operationName, required Variables$Query$ListDir variables, - super.fetchPolicy, - super.errorPolicy, - super.cacheRereadPolicy, + graphql.FetchPolicy? fetchPolicy, + graphql.ErrorPolicy? errorPolicy, + graphql.CacheRereadPolicy? cacheRereadPolicy, Object? optimisticResult, Query$ListDir? typedOptimisticResult, - super.context, - super.pollInterval, - super.eagerlyFetchResults, - super.carryForwardDataOnException, - super.fetchResults, + graphql.Context? context, + Duration? pollInterval, + bool? eagerlyFetchResults, + bool carryForwardDataOnException = true, + bool fetchResults = false, }) : super( variables: variables.toJson(), + operationName: operationName, + fetchPolicy: fetchPolicy, + errorPolicy: errorPolicy, + cacheRereadPolicy: cacheRereadPolicy, optimisticResult: optimisticResult ?? typedOptimisticResult?.toJson(), + context: context, document: documentNodeQueryListDir, + pollInterval: pollInterval, + eagerlyFetchResults: eagerlyFetchResults, + carryForwardDataOnException: carryForwardDataOnException, + fetchResults: fetchResults, parserFn: _parserFn$Query$ListDir, ); } class FetchMoreOptions$Query$ListDir extends graphql.FetchMoreOptions { FetchMoreOptions$Query$ListDir({ - required super.updateQuery, + required graphql.UpdateQuery updateQuery, required Variables$Query$ListDir variables, }) : super( + updateQuery: updateQuery, variables: variables.toJson(), document: documentNodeQueryListDir, ); @@ -3095,18 +3039,18 @@ class FetchMoreOptions$Query$ListDir extends graphql.FetchMoreOptions { extension ClientExtension$Query$ListDir on graphql.GraphQLClient { Future> query$ListDir( Options$Query$ListDir options) async => - await query(options); + await this.query(options); graphql.ObservableQuery watchQuery$ListDir( WatchOptions$Query$ListDir options) => - watchQuery(options); + this.watchQuery(options); void writeQuery$ListDir({ required Query$ListDir data, required Variables$Query$ListDir variables, bool broadcast = true, }) => - writeQuery( + this.writeQuery( graphql.Request( - operation: const graphql.Operation(document: documentNodeQueryListDir), + operation: graphql.Operation(document: documentNodeQueryListDir), variables: variables.toJson(), ), data: data.toJson(), @@ -3116,9 +3060,9 @@ extension ClientExtension$Query$ListDir on graphql.GraphQLClient { required Variables$Query$ListDir variables, bool optimistic = true, }) { - final result = readQuery( + final result = this.readQuery( graphql.Request( - operation: const graphql.Operation(document: documentNodeQueryListDir), + operation: graphql.Operation(document: documentNodeQueryListDir), variables: variables.toJson(), ), optimistic: optimistic, @@ -3135,11 +3079,15 @@ graphql.ObservableQuery useWatchQuery$ListDir( graphql_flutter.useWatchQuery(options); class Query$ListDir$Widget extends graphql_flutter.Query { - const Query$ListDir$Widget({ - super.key, - required Options$Query$ListDir super.options, - required super.builder, - }); + Query$ListDir$Widget({ + widgets.Key? key, + required Options$Query$ListDir options, + required graphql_flutter.QueryBuilder builder, + }) : super( + key: key, + options: options, + builder: builder, + ); } class Query$ListDir$fsEntry { @@ -3183,12 +3131,12 @@ class Query$ListDir$fsEntry { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -3206,7 +3154,7 @@ class Query$ListDir$fsEntry { if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry || runtimeType != other.runtimeType) { + if (!(other is Query$ListDir$fsEntry) || runtimeType != other.runtimeType) { return false; } final l$name = name; @@ -3351,7 +3299,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? $__typename = _undefined, @@ -3370,9 +3317,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry implements CopyWith$Query$ListDir$fsEntry { _CopyWithStubImpl$Query$ListDir$fsEntry(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? $__typename, @@ -3406,27 +3352,23 @@ class Query$ListDir$fsEntry$$ArchiveFS final List entries; - @override final String $__typename; - @override final String name; - @override final int size; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$entries = entries; - resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); + _resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; + _resultData['__typename'] = l$$__typename; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$size = size; - resultData['size'] = l$size; - return resultData; + _resultData['size'] = l$size; + return _resultData; } @override @@ -3448,7 +3390,7 @@ class Query$ListDir$fsEntry$$ArchiveFS if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry$$ArchiveFS || + if (!(other is Query$ListDir$fsEntry$$ArchiveFS) || runtimeType != other.runtimeType) { return false; } @@ -3510,7 +3452,7 @@ abstract class CopyWith$Query$ListDir$fsEntry$$ArchiveFS { TRes entries( Iterable Function( Iterable>) - fn); + _fn); } class _CopyWithImpl$Query$ListDir$fsEntry$$ArchiveFS @@ -3526,7 +3468,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$ArchiveFS static const _undefined = {}; - @override TRes call({ Object? entries = _undefined, Object? $__typename = _undefined, @@ -3547,13 +3488,12 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$ArchiveFS size == _undefined || size == null ? _instance.size : (size as int), )); - @override TRes entries( Iterable Function( Iterable>) - fn) => + _fn) => call( - entries: fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( + entries: _fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( e, (i) => i, ))).toList()); @@ -3563,9 +3503,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$ArchiveFS implements CopyWith$Query$ListDir$fsEntry$$ArchiveFS { _CopyWithStubImpl$Query$ListDir$fsEntry$$ArchiveFS(this._res); - final TRes _res; + TRes _res; - @override call({ List? entries, String? $__typename, @@ -3574,8 +3513,7 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$ArchiveFS }) => _res; - @override - entries(fn) => _res; + entries(_fn) => _res; } class Query$ListDir$fsEntry$$ResolverFS implements Query$ListDir$fsEntry { @@ -3601,22 +3539,19 @@ class Query$ListDir$fsEntry$$ResolverFS implements Query$ListDir$fsEntry { final List entries; - @override final String $__typename; - @override final String name; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$entries = entries; - resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); + _resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; + _resultData['__typename'] = l$$__typename; final l$name = name; - resultData['name'] = l$name; - return resultData; + _resultData['name'] = l$name; + return _resultData; } @override @@ -3636,7 +3571,7 @@ class Query$ListDir$fsEntry$$ResolverFS implements Query$ListDir$fsEntry { if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry$$ResolverFS || + if (!(other is Query$ListDir$fsEntry$$ResolverFS) || runtimeType != other.runtimeType) { return false; } @@ -3692,7 +3627,7 @@ abstract class CopyWith$Query$ListDir$fsEntry$$ResolverFS { TRes entries( Iterable Function( Iterable>) - fn); + _fn); } class _CopyWithImpl$Query$ListDir$fsEntry$$ResolverFS @@ -3708,7 +3643,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$ResolverFS static const _undefined = {}; - @override TRes call({ Object? entries = _undefined, Object? $__typename = _undefined, @@ -3726,13 +3660,12 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$ResolverFS : (name as String), )); - @override TRes entries( Iterable Function( Iterable>) - fn) => + _fn) => call( - entries: fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( + entries: _fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( e, (i) => i, ))).toList()); @@ -3742,9 +3675,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$ResolverFS implements CopyWith$Query$ListDir$fsEntry$$ResolverFS { _CopyWithStubImpl$Query$ListDir$fsEntry$$ResolverFS(this._res); - final TRes _res; + TRes _res; - @override call({ List? entries, String? $__typename, @@ -3752,8 +3684,7 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$ResolverFS }) => _res; - @override - entries(fn) => _res; + entries(_fn) => _res; } class Query$ListDir$fsEntry$$SimpleDir implements Query$ListDir$fsEntry { @@ -3778,22 +3709,19 @@ class Query$ListDir$fsEntry$$SimpleDir implements Query$ListDir$fsEntry { final List entries; - @override final String $__typename; - @override final String name; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$entries = entries; - resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); + _resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; + _resultData['__typename'] = l$$__typename; final l$name = name; - resultData['name'] = l$name; - return resultData; + _resultData['name'] = l$name; + return _resultData; } @override @@ -3813,7 +3741,7 @@ class Query$ListDir$fsEntry$$SimpleDir implements Query$ListDir$fsEntry { if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry$$SimpleDir || + if (!(other is Query$ListDir$fsEntry$$SimpleDir) || runtimeType != other.runtimeType) { return false; } @@ -3869,7 +3797,7 @@ abstract class CopyWith$Query$ListDir$fsEntry$$SimpleDir { TRes entries( Iterable Function( Iterable>) - fn); + _fn); } class _CopyWithImpl$Query$ListDir$fsEntry$$SimpleDir @@ -3885,7 +3813,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$SimpleDir static const _undefined = {}; - @override TRes call({ Object? entries = _undefined, Object? $__typename = _undefined, @@ -3903,13 +3830,12 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$SimpleDir : (name as String), )); - @override TRes entries( Iterable Function( Iterable>) - fn) => + _fn) => call( - entries: fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( + entries: _fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( e, (i) => i, ))).toList()); @@ -3919,9 +3845,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$SimpleDir implements CopyWith$Query$ListDir$fsEntry$$SimpleDir { _CopyWithStubImpl$Query$ListDir$fsEntry$$SimpleDir(this._res); - final TRes _res; + TRes _res; - @override call({ List? entries, String? $__typename, @@ -3929,8 +3854,7 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$SimpleDir }) => _res; - @override - entries(fn) => _res; + entries(_fn) => _res; } class Query$ListDir$fsEntry$$TorrentFS @@ -3960,27 +3884,23 @@ class Query$ListDir$fsEntry$$TorrentFS final List entries; - @override final String $__typename; - @override final String name; - @override final Query$ListDir$fsEntry$$TorrentFS$torrent torrent; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$entries = entries; - resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); + _resultData['entries'] = l$entries.map((e) => e.toJson()).toList(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; + _resultData['__typename'] = l$$__typename; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$torrent = torrent; - resultData['torrent'] = l$torrent.toJson(); - return resultData; + _resultData['torrent'] = l$torrent.toJson(); + return _resultData; } @override @@ -4002,7 +3922,7 @@ class Query$ListDir$fsEntry$$TorrentFS if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry$$TorrentFS || + if (!(other is Query$ListDir$fsEntry$$TorrentFS) || runtimeType != other.runtimeType) { return false; } @@ -4064,7 +3984,7 @@ abstract class CopyWith$Query$ListDir$fsEntry$$TorrentFS { TRes entries( Iterable Function( Iterable>) - fn); + _fn); CopyWith$Query$ListDir$fsEntry$$TorrentFS$torrent get torrent; } @@ -4081,7 +4001,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$TorrentFS static const _undefined = {}; - @override TRes call({ Object? entries = _undefined, Object? $__typename = _undefined, @@ -4103,18 +4022,16 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$TorrentFS : (torrent as Query$ListDir$fsEntry$$TorrentFS$torrent), )); - @override TRes entries( Iterable Function( Iterable>) - fn) => + _fn) => call( - entries: fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( + entries: _fn(_instance.entries.map((e) => CopyWith$Fragment$DirEntry( e, (i) => i, ))).toList()); - @override CopyWith$Query$ListDir$fsEntry$$TorrentFS$torrent get torrent { final local$torrent = _instance.torrent; return CopyWith$Query$ListDir$fsEntry$$TorrentFS$torrent( @@ -4126,9 +4043,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$TorrentFS implements CopyWith$Query$ListDir$fsEntry$$TorrentFS { _CopyWithStubImpl$Query$ListDir$fsEntry$$TorrentFS(this._res); - final TRes _res; + TRes _res; - @override call({ List? entries, String? $__typename, @@ -4137,10 +4053,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$TorrentFS }) => _res; - @override - entries(fn) => _res; + entries(_fn) => _res; - @override CopyWith$Query$ListDir$fsEntry$$TorrentFS$torrent get torrent => CopyWith$Query$ListDir$fsEntry$$TorrentFS$torrent.stub(_res); } @@ -4161,20 +4075,17 @@ class Query$ListDir$fsEntry$$SimpleFile implements Query$ListDir$fsEntry { ); } - @override final String name; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -4192,7 +4103,7 @@ class Query$ListDir$fsEntry$$SimpleFile implements Query$ListDir$fsEntry { if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry$$SimpleFile || + if (!(other is Query$ListDir$fsEntry$$SimpleFile) || runtimeType != other.runtimeType) { return false; } @@ -4247,7 +4158,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$SimpleFile static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? $__typename = _undefined, @@ -4266,9 +4176,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$SimpleFile implements CopyWith$Query$ListDir$fsEntry$$SimpleFile { _CopyWithStubImpl$Query$ListDir$fsEntry$$SimpleFile(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? $__typename, @@ -4305,40 +4214,33 @@ class Query$ListDir$fsEntry$$TorrentFS$torrent ); } - @override final String name; - @override final String infohash; - @override final int bytesCompleted; - @override final String torrentFilePath; - @override final int bytesMissing; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$infohash = infohash; - resultData['infohash'] = l$infohash; + _resultData['infohash'] = l$infohash; final l$bytesCompleted = bytesCompleted; - resultData['bytesCompleted'] = l$bytesCompleted; + _resultData['bytesCompleted'] = l$bytesCompleted; final l$torrentFilePath = torrentFilePath; - resultData['torrentFilePath'] = l$torrentFilePath; + _resultData['torrentFilePath'] = l$torrentFilePath; final l$bytesMissing = bytesMissing; - resultData['bytesMissing'] = l$bytesMissing; + _resultData['bytesMissing'] = l$bytesMissing; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -4364,7 +4266,7 @@ class Query$ListDir$fsEntry$$TorrentFS$torrent if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry$$TorrentFS$torrent || + if (!(other is Query$ListDir$fsEntry$$TorrentFS$torrent) || runtimeType != other.runtimeType) { return false; } @@ -4444,7 +4346,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$TorrentFS$torrent static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? infohash = _undefined, @@ -4480,9 +4381,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$TorrentFS$torrent implements CopyWith$Query$ListDir$fsEntry$$TorrentFS$torrent { _CopyWithStubImpl$Query$ListDir$fsEntry$$TorrentFS$torrent(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? infohash, @@ -4510,20 +4410,17 @@ class Query$ListDir$fsEntry$$TorrentFileEntry implements Query$ListDir$fsEntry { ); } - @override final String name; - @override final String $__typename; - @override Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -4541,7 +4438,7 @@ class Query$ListDir$fsEntry$$TorrentFileEntry implements Query$ListDir$fsEntry { if (identical(this, other)) { return true; } - if (other is! Query$ListDir$fsEntry$$TorrentFileEntry || + if (!(other is Query$ListDir$fsEntry$$TorrentFileEntry) || runtimeType != other.runtimeType) { return false; } @@ -4597,7 +4494,6 @@ class _CopyWithImpl$Query$ListDir$fsEntry$$TorrentFileEntry static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? $__typename = _undefined, @@ -4616,9 +4512,8 @@ class _CopyWithStubImpl$Query$ListDir$fsEntry$$TorrentFileEntry implements CopyWith$Query$ListDir$fsEntry$$TorrentFileEntry { _CopyWithStubImpl$Query$ListDir$fsEntry$$TorrentFileEntry(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? $__typename, diff --git a/ui/lib/api/schema.graphql b/ui/lib/api/schema.graphql index 2d019a8..8cdc151 100644 --- a/ui/lib/api/schema.graphql +++ b/ui/lib/api/schema.graphql @@ -57,7 +57,7 @@ interface Progress { total: Int! } type Query { - torrents(filter: TorrentsFilter, pagination: Pagination): [Torrent!]! + torrents(filter: TorrentsFilter): [Torrent!]! fsEntry(path: String!): FsEntry } type ResolverFS implements Dir & FsEntry { @@ -97,6 +97,7 @@ type Torrent { files: [TorrentFile!]! excludedFiles: [TorrentFile!]! peers: [TorrentPeer!]! + downloading: Boolean! } type TorrentFS implements Dir & FsEntry { name: String! @@ -135,4 +136,5 @@ input TorrentsFilter { bytesCompleted: IntFilter bytesMissing: IntFilter peersCount: IntFilter + downloading: BooleanFilter } diff --git a/ui/lib/api/schema.graphql.dart b/ui/lib/api/schema.graphql.dart index f9e0b80..22a904f 100644 --- a/ui/lib/api/schema.graphql.dart +++ b/ui/lib/api/schema.graphql.dart @@ -1,3 +1,4 @@ +// ignore_for_file: type=lint class Input$BooleanFilter { factory Input$BooleanFilter({bool? eq}) => Input$BooleanFilter._({ if (eq != null) r'eq': eq, @@ -38,7 +39,7 @@ class Input$BooleanFilter { if (identical(this, other)) { return true; } - if (other is! Input$BooleanFilter || runtimeType != other.runtimeType) { + if (!(other is Input$BooleanFilter) || runtimeType != other.runtimeType) { return false; } final l$eq = eq; @@ -84,7 +85,6 @@ class _CopyWithImpl$Input$BooleanFilter static const _undefined = {}; - @override TRes call({Object? eq = _undefined}) => _then(Input$BooleanFilter._({ ..._instance._$data, if (eq != _undefined) 'eq': (eq as bool?), @@ -95,9 +95,8 @@ class _CopyWithStubImpl$Input$BooleanFilter implements CopyWith$Input$BooleanFilter { _CopyWithStubImpl$Input$BooleanFilter(this._res); - final TRes _res; + TRes _res; - @override call({bool? eq}) => _res; } @@ -197,7 +196,7 @@ class Input$DateTimeFilter { if (identical(this, other)) { return true; } - if (other is! Input$DateTimeFilter || runtimeType != other.runtimeType) { + if (!(other is Input$DateTimeFilter) || runtimeType != other.runtimeType) { return false; } final l$eq = eq; @@ -291,7 +290,6 @@ class _CopyWithImpl$Input$DateTimeFilter static const _undefined = {}; - @override TRes call({ Object? eq = _undefined, Object? gt = _undefined, @@ -313,9 +311,8 @@ class _CopyWithStubImpl$Input$DateTimeFilter implements CopyWith$Input$DateTimeFilter { _CopyWithStubImpl$Input$DateTimeFilter(this._res); - final TRes _res; + TRes _res; - @override call({ DateTime? eq, DateTime? gt, @@ -430,7 +427,7 @@ class Input$IntFilter { if (identical(this, other)) { return true; } - if (other is! Input$IntFilter || runtimeType != other.runtimeType) { + if (!(other is Input$IntFilter) || runtimeType != other.runtimeType) { return false; } final l$eq = eq; @@ -550,7 +547,6 @@ class _CopyWithImpl$Input$IntFilter static const _undefined = {}; - @override TRes call({ Object? eq = _undefined, Object? gt = _undefined, @@ -574,9 +570,8 @@ class _CopyWithStubImpl$Input$IntFilter implements CopyWith$Input$IntFilter { _CopyWithStubImpl$Input$IntFilter(this._res); - final TRes _res; + TRes _res; - @override call({ int? eq, int? gt, @@ -635,7 +630,7 @@ class Input$Pagination { if (identical(this, other)) { return true; } - if (other is! Input$Pagination || runtimeType != other.runtimeType) { + if (!(other is Input$Pagination) || runtimeType != other.runtimeType) { return false; } final l$offset = offset; @@ -690,7 +685,6 @@ class _CopyWithImpl$Input$Pagination static const _undefined = {}; - @override TRes call({ Object? offset = _undefined, Object? limit = _undefined, @@ -706,9 +700,8 @@ class _CopyWithStubImpl$Input$Pagination implements CopyWith$Input$Pagination { _CopyWithStubImpl$Input$Pagination(this._res); - final TRes _res; + TRes _res; - @override call({ int? offset, int? limit, @@ -784,7 +777,7 @@ class Input$StringFilter { if (identical(this, other)) { return true; } - if (other is! Input$StringFilter || runtimeType != other.runtimeType) { + if (!(other is Input$StringFilter) || runtimeType != other.runtimeType) { return false; } final l$eq = eq; @@ -871,7 +864,6 @@ class _CopyWithImpl$Input$StringFilter static const _undefined = {}; - @override TRes call({ Object? eq = _undefined, Object? substr = _undefined, @@ -889,9 +881,8 @@ class _CopyWithStubImpl$Input$StringFilter implements CopyWith$Input$StringFilter { _CopyWithStubImpl$Input$StringFilter(this._res); - final TRes _res; + TRes _res; - @override call({ String? eq, String? substr, @@ -955,7 +946,7 @@ class Input$TorrentFilter { if (identical(this, other)) { return true; } - if (other is! Input$TorrentFilter || runtimeType != other.runtimeType) { + if (!(other is Input$TorrentFilter) || runtimeType != other.runtimeType) { return false; } final l$everything = everything; @@ -1018,7 +1009,6 @@ class _CopyWithImpl$Input$TorrentFilter static const _undefined = {}; - @override TRes call({ Object? everything = _undefined, Object? infohash = _undefined, @@ -1034,9 +1024,8 @@ class _CopyWithStubImpl$Input$TorrentFilter implements CopyWith$Input$TorrentFilter { _CopyWithStubImpl$Input$TorrentFilter(this._res); - final TRes _res; + TRes _res; - @override call({ bool? everything, String? infohash, @@ -1046,22 +1035,32 @@ class _CopyWithStubImpl$Input$TorrentFilter class Input$TorrentsFilter { factory Input$TorrentsFilter({ + Input$StringFilter? infohash, Input$StringFilter? name, Input$IntFilter? bytesCompleted, Input$IntFilter? bytesMissing, Input$IntFilter? peersCount, + Input$BooleanFilter? downloading, }) => Input$TorrentsFilter._({ + if (infohash != null) r'infohash': infohash, if (name != null) r'name': name, if (bytesCompleted != null) r'bytesCompleted': bytesCompleted, if (bytesMissing != null) r'bytesMissing': bytesMissing, if (peersCount != null) r'peersCount': peersCount, + if (downloading != null) r'downloading': downloading, }); Input$TorrentsFilter._(this._$data); factory Input$TorrentsFilter.fromJson(Map data) { final result$data = {}; + if (data.containsKey('infohash')) { + final l$infohash = data['infohash']; + result$data['infohash'] = l$infohash == null + ? null + : Input$StringFilter.fromJson((l$infohash as Map)); + } if (data.containsKey('name')) { final l$name = data['name']; result$data['name'] = l$name == null @@ -1087,11 +1086,21 @@ class Input$TorrentsFilter { ? null : Input$IntFilter.fromJson((l$peersCount as Map)); } + if (data.containsKey('downloading')) { + final l$downloading = data['downloading']; + result$data['downloading'] = l$downloading == null + ? null + : Input$BooleanFilter.fromJson( + (l$downloading as Map)); + } return Input$TorrentsFilter._(result$data); } Map _$data; + Input$StringFilter? get infohash => + (_$data['infohash'] as Input$StringFilter?); + Input$StringFilter? get name => (_$data['name'] as Input$StringFilter?); Input$IntFilter? get bytesCompleted => @@ -1102,8 +1111,15 @@ class Input$TorrentsFilter { Input$IntFilter? get peersCount => (_$data['peersCount'] as Input$IntFilter?); + Input$BooleanFilter? get downloading => + (_$data['downloading'] as Input$BooleanFilter?); + Map toJson() { final result$data = {}; + if (_$data.containsKey('infohash')) { + final l$infohash = infohash; + result$data['infohash'] = l$infohash?.toJson(); + } if (_$data.containsKey('name')) { final l$name = name; result$data['name'] = l$name?.toJson(); @@ -1120,6 +1136,10 @@ class Input$TorrentsFilter { final l$peersCount = peersCount; result$data['peersCount'] = l$peersCount?.toJson(); } + if (_$data.containsKey('downloading')) { + final l$downloading = downloading; + result$data['downloading'] = l$downloading?.toJson(); + } return result$data; } @@ -1134,7 +1154,16 @@ class Input$TorrentsFilter { if (identical(this, other)) { return true; } - if (other is! Input$TorrentsFilter || runtimeType != other.runtimeType) { + if (!(other is Input$TorrentsFilter) || runtimeType != other.runtimeType) { + return false; + } + final l$infohash = infohash; + final lOther$infohash = other.infohash; + if (_$data.containsKey('infohash') != + other._$data.containsKey('infohash')) { + return false; + } + if (l$infohash != lOther$infohash) { return false; } final l$name = name; @@ -1172,20 +1201,33 @@ class Input$TorrentsFilter { if (l$peersCount != lOther$peersCount) { return false; } + final l$downloading = downloading; + final lOther$downloading = other.downloading; + if (_$data.containsKey('downloading') != + other._$data.containsKey('downloading')) { + return false; + } + if (l$downloading != lOther$downloading) { + return false; + } return true; } @override int get hashCode { + final l$infohash = infohash; final l$name = name; final l$bytesCompleted = bytesCompleted; final l$bytesMissing = bytesMissing; final l$peersCount = peersCount; + final l$downloading = downloading; return Object.hashAll([ + _$data.containsKey('infohash') ? l$infohash : const {}, _$data.containsKey('name') ? l$name : const {}, _$data.containsKey('bytesCompleted') ? l$bytesCompleted : const {}, _$data.containsKey('bytesMissing') ? l$bytesMissing : const {}, _$data.containsKey('peersCount') ? l$peersCount : const {}, + _$data.containsKey('downloading') ? l$downloading : const {}, ]); } } @@ -1200,15 +1242,19 @@ abstract class CopyWith$Input$TorrentsFilter { _CopyWithStubImpl$Input$TorrentsFilter; TRes call({ + Input$StringFilter? infohash, Input$StringFilter? name, Input$IntFilter? bytesCompleted, Input$IntFilter? bytesMissing, Input$IntFilter? peersCount, + Input$BooleanFilter? downloading, }); + CopyWith$Input$StringFilter get infohash; CopyWith$Input$StringFilter get name; CopyWith$Input$IntFilter get bytesCompleted; CopyWith$Input$IntFilter get bytesMissing; CopyWith$Input$IntFilter get peersCount; + CopyWith$Input$BooleanFilter get downloading; } class _CopyWithImpl$Input$TorrentsFilter @@ -1224,15 +1270,18 @@ class _CopyWithImpl$Input$TorrentsFilter static const _undefined = {}; - @override TRes call({ + Object? infohash = _undefined, Object? name = _undefined, Object? bytesCompleted = _undefined, Object? bytesMissing = _undefined, Object? peersCount = _undefined, + Object? downloading = _undefined, }) => _then(Input$TorrentsFilter._({ ..._instance._$data, + if (infohash != _undefined) + 'infohash': (infohash as Input$StringFilter?), if (name != _undefined) 'name': (name as Input$StringFilter?), if (bytesCompleted != _undefined) 'bytesCompleted': (bytesCompleted as Input$IntFilter?), @@ -1240,9 +1289,17 @@ class _CopyWithImpl$Input$TorrentsFilter 'bytesMissing': (bytesMissing as Input$IntFilter?), if (peersCount != _undefined) 'peersCount': (peersCount as Input$IntFilter?), + if (downloading != _undefined) + 'downloading': (downloading as Input$BooleanFilter?), })); - @override + CopyWith$Input$StringFilter get infohash { + final local$infohash = _instance.infohash; + return local$infohash == null + ? CopyWith$Input$StringFilter.stub(_then(_instance)) + : CopyWith$Input$StringFilter(local$infohash, (e) => call(infohash: e)); + } + CopyWith$Input$StringFilter get name { final local$name = _instance.name; return local$name == null @@ -1250,7 +1307,6 @@ class _CopyWithImpl$Input$TorrentsFilter : CopyWith$Input$StringFilter(local$name, (e) => call(name: e)); } - @override CopyWith$Input$IntFilter get bytesCompleted { final local$bytesCompleted = _instance.bytesCompleted; return local$bytesCompleted == null @@ -1259,7 +1315,6 @@ class _CopyWithImpl$Input$TorrentsFilter local$bytesCompleted, (e) => call(bytesCompleted: e)); } - @override CopyWith$Input$IntFilter get bytesMissing { final local$bytesMissing = _instance.bytesMissing; return local$bytesMissing == null @@ -1268,7 +1323,6 @@ class _CopyWithImpl$Input$TorrentsFilter local$bytesMissing, (e) => call(bytesMissing: e)); } - @override CopyWith$Input$IntFilter get peersCount { final local$peersCount = _instance.peersCount; return local$peersCount == null @@ -1276,38 +1330,49 @@ class _CopyWithImpl$Input$TorrentsFilter : CopyWith$Input$IntFilter( local$peersCount, (e) => call(peersCount: e)); } + + CopyWith$Input$BooleanFilter get downloading { + final local$downloading = _instance.downloading; + return local$downloading == null + ? CopyWith$Input$BooleanFilter.stub(_then(_instance)) + : CopyWith$Input$BooleanFilter( + local$downloading, (e) => call(downloading: e)); + } } class _CopyWithStubImpl$Input$TorrentsFilter implements CopyWith$Input$TorrentsFilter { _CopyWithStubImpl$Input$TorrentsFilter(this._res); - final TRes _res; + TRes _res; - @override call({ + Input$StringFilter? infohash, Input$StringFilter? name, Input$IntFilter? bytesCompleted, Input$IntFilter? bytesMissing, Input$IntFilter? peersCount, + Input$BooleanFilter? downloading, }) => _res; - @override + CopyWith$Input$StringFilter get infohash => + CopyWith$Input$StringFilter.stub(_res); + CopyWith$Input$StringFilter get name => CopyWith$Input$StringFilter.stub(_res); - @override CopyWith$Input$IntFilter get bytesCompleted => CopyWith$Input$IntFilter.stub(_res); - @override CopyWith$Input$IntFilter get bytesMissing => CopyWith$Input$IntFilter.stub(_res); - @override CopyWith$Input$IntFilter get peersCount => CopyWith$Input$IntFilter.stub(_res); + + CopyWith$Input$BooleanFilter get downloading => + CopyWith$Input$BooleanFilter.stub(_res); } enum Enum$__TypeKind { diff --git a/ui/lib/api/torrent.graphql b/ui/lib/api/torrent.graphql index 25be873..b8ef961 100644 --- a/ui/lib/api/torrent.graphql +++ b/ui/lib/api/torrent.graphql @@ -6,11 +6,20 @@ mutation MarkTorrentDownload($infohash: String!) { } } -query ListTorrents { - torrents { +query ListTorrents($downloading: Boolean) { + torrents(filter: { + downloading: { + eq: $downloading + } + }) { name infohash bytesCompleted bytesMissing + peers { + ip + downloadRate + clientName + } } } \ No newline at end of file diff --git a/ui/lib/api/torrent.graphql.dart b/ui/lib/api/torrent.graphql.dart index 8b707af..79c2263 100644 --- a/ui/lib/api/torrent.graphql.dart +++ b/ui/lib/api/torrent.graphql.dart @@ -1,3 +1,4 @@ +// ignore_for_file: type=lint import 'dart:async'; import 'package:flutter/widgets.dart' as widgets; import 'package:gql/ast.dart'; @@ -43,7 +44,7 @@ class Variables$Mutation$MarkTorrentDownload { if (identical(this, other)) { return true; } - if (other is! Variables$Mutation$MarkTorrentDownload || + if (!(other is Variables$Mutation$MarkTorrentDownload) || runtimeType != other.runtimeType) { return false; } @@ -87,7 +88,6 @@ class _CopyWithImpl$Variables$Mutation$MarkTorrentDownload static const _undefined = {}; - @override TRes call({Object? infohash = _undefined}) => _then(Variables$Mutation$MarkTorrentDownload._({ ..._instance._$data, @@ -100,9 +100,8 @@ class _CopyWithStubImpl$Variables$Mutation$MarkTorrentDownload implements CopyWith$Variables$Mutation$MarkTorrentDownload { _CopyWithStubImpl$Variables$Mutation$MarkTorrentDownload(this._res); - final TRes _res; + TRes _res; - @override call({String? infohash}) => _res; } @@ -129,12 +128,12 @@ class Mutation$MarkTorrentDownload { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$downloadTorrent = downloadTorrent; - resultData['downloadTorrent'] = l$downloadTorrent?.toJson(); + _resultData['downloadTorrent'] = l$downloadTorrent?.toJson(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -152,7 +151,7 @@ class Mutation$MarkTorrentDownload { if (identical(this, other)) { return true; } - if (other is! Mutation$MarkTorrentDownload || + if (!(other is Mutation$MarkTorrentDownload) || runtimeType != other.runtimeType) { return false; } @@ -209,7 +208,6 @@ class _CopyWithImpl$Mutation$MarkTorrentDownload static const _undefined = {}; - @override TRes call({ Object? downloadTorrent = _undefined, Object? $__typename = _undefined, @@ -224,7 +222,6 @@ class _CopyWithImpl$Mutation$MarkTorrentDownload : ($__typename as String), )); - @override CopyWith$Mutation$MarkTorrentDownload$downloadTorrent get downloadTorrent { final local$downloadTorrent = _instance.downloadTorrent; @@ -240,16 +237,14 @@ class _CopyWithStubImpl$Mutation$MarkTorrentDownload implements CopyWith$Mutation$MarkTorrentDownload { _CopyWithStubImpl$Mutation$MarkTorrentDownload(this._res); - final TRes _res; + TRes _res; - @override call({ Mutation$MarkTorrentDownload$downloadTorrent? downloadTorrent, String? $__typename, }) => _res; - @override CopyWith$Mutation$MarkTorrentDownload$downloadTorrent get downloadTorrent => CopyWith$Mutation$MarkTorrentDownload$downloadTorrent.stub(_res); @@ -336,21 +331,26 @@ typedef OnMutationCompleted$Mutation$MarkTorrentDownload = FutureOr class Options$Mutation$MarkTorrentDownload extends graphql.MutationOptions { Options$Mutation$MarkTorrentDownload({ - super.operationName, + String? operationName, required Variables$Mutation$MarkTorrentDownload variables, - super.fetchPolicy, - super.errorPolicy, - super.cacheRereadPolicy, + graphql.FetchPolicy? fetchPolicy, + graphql.ErrorPolicy? errorPolicy, + graphql.CacheRereadPolicy? cacheRereadPolicy, Object? optimisticResult, Mutation$MarkTorrentDownload? typedOptimisticResult, - super.context, + graphql.Context? context, OnMutationCompleted$Mutation$MarkTorrentDownload? onCompleted, - super.update, - super.onError, + graphql.OnMutationUpdate? update, + graphql.OnError? onError, }) : onCompletedWithParsed = onCompleted, super( variables: variables.toJson(), + operationName: operationName, + fetchPolicy: fetchPolicy, + errorPolicy: errorPolicy, + cacheRereadPolicy: cacheRereadPolicy, optimisticResult: optimisticResult ?? typedOptimisticResult?.toJson(), + context: context, onCompleted: onCompleted == null ? null : (data) => onCompleted( @@ -359,6 +359,8 @@ class Options$Mutation$MarkTorrentDownload ? null : _parserFn$Mutation$MarkTorrentDownload(data), ), + update: update, + onError: onError, document: documentNodeMutationMarkTorrentDownload, parserFn: _parserFn$Mutation$MarkTorrentDownload, ); @@ -377,22 +379,31 @@ class Options$Mutation$MarkTorrentDownload class WatchOptions$Mutation$MarkTorrentDownload extends graphql.WatchQueryOptions { WatchOptions$Mutation$MarkTorrentDownload({ - super.operationName, + String? operationName, required Variables$Mutation$MarkTorrentDownload variables, - super.fetchPolicy, - super.errorPolicy, - super.cacheRereadPolicy, + graphql.FetchPolicy? fetchPolicy, + graphql.ErrorPolicy? errorPolicy, + graphql.CacheRereadPolicy? cacheRereadPolicy, Object? optimisticResult, Mutation$MarkTorrentDownload? typedOptimisticResult, - super.context, - super.pollInterval, - super.eagerlyFetchResults, - super.carryForwardDataOnException, - super.fetchResults, + graphql.Context? context, + Duration? pollInterval, + bool? eagerlyFetchResults, + bool carryForwardDataOnException = true, + bool fetchResults = false, }) : super( variables: variables.toJson(), + operationName: operationName, + fetchPolicy: fetchPolicy, + errorPolicy: errorPolicy, + cacheRereadPolicy: cacheRereadPolicy, optimisticResult: optimisticResult ?? typedOptimisticResult?.toJson(), + context: context, document: documentNodeMutationMarkTorrentDownload, + pollInterval: pollInterval, + eagerlyFetchResults: eagerlyFetchResults, + carryForwardDataOnException: carryForwardDataOnException, + fetchResults: fetchResults, parserFn: _parserFn$Mutation$MarkTorrentDownload, ); } @@ -402,11 +413,11 @@ extension ClientExtension$Mutation$MarkTorrentDownload Future> mutate$MarkTorrentDownload( Options$Mutation$MarkTorrentDownload options) async => - await mutate(options); + await this.mutate(options); graphql.ObservableQuery watchMutation$MarkTorrentDownload( WatchOptions$Mutation$MarkTorrentDownload options) => - watchMutation(options); + this.watchMutation(options); } class Mutation$MarkTorrentDownload$HookResult { @@ -442,19 +453,24 @@ graphql.ObservableQuery class WidgetOptions$Mutation$MarkTorrentDownload extends graphql.MutationOptions { WidgetOptions$Mutation$MarkTorrentDownload({ - super.operationName, - super.fetchPolicy, - super.errorPolicy, - super.cacheRereadPolicy, + String? operationName, + graphql.FetchPolicy? fetchPolicy, + graphql.ErrorPolicy? errorPolicy, + graphql.CacheRereadPolicy? cacheRereadPolicy, Object? optimisticResult, Mutation$MarkTorrentDownload? typedOptimisticResult, - super.context, + graphql.Context? context, OnMutationCompleted$Mutation$MarkTorrentDownload? onCompleted, - super.update, - super.onError, + graphql.OnMutationUpdate? update, + graphql.OnError? onError, }) : onCompletedWithParsed = onCompleted, super( + operationName: operationName, + fetchPolicy: fetchPolicy, + errorPolicy: errorPolicy, + cacheRereadPolicy: cacheRereadPolicy, optimisticResult: optimisticResult ?? typedOptimisticResult?.toJson(), + context: context, onCompleted: onCompleted == null ? null : (data) => onCompleted( @@ -463,6 +479,8 @@ class WidgetOptions$Mutation$MarkTorrentDownload ? null : _parserFn$Mutation$MarkTorrentDownload(data), ), + update: update, + onError: onError, document: documentNodeMutationMarkTorrentDownload, parserFn: _parserFn$Mutation$MarkTorrentDownload, ); @@ -492,10 +510,11 @@ typedef Builder$Mutation$MarkTorrentDownload = widgets.Widget Function( class Mutation$MarkTorrentDownload$Widget extends graphql_flutter.Mutation { Mutation$MarkTorrentDownload$Widget({ - super.key, + widgets.Key? key, WidgetOptions$Mutation$MarkTorrentDownload? options, required Builder$Mutation$MarkTorrentDownload builder, }) : super( + key: key, options: options ?? WidgetOptions$Mutation$MarkTorrentDownload(), builder: ( run, @@ -541,12 +560,12 @@ class Mutation$MarkTorrentDownload$downloadTorrent { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$task = task; - resultData['task'] = l$task?.toJson(); + _resultData['task'] = l$task?.toJson(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -564,7 +583,7 @@ class Mutation$MarkTorrentDownload$downloadTorrent { if (identical(this, other)) { return true; } - if (other is! Mutation$MarkTorrentDownload$downloadTorrent || + if (!(other is Mutation$MarkTorrentDownload$downloadTorrent) || runtimeType != other.runtimeType) { return false; } @@ -621,7 +640,6 @@ class _CopyWithImpl$Mutation$MarkTorrentDownload$downloadTorrent static const _undefined = {}; - @override TRes call({ Object? task = _undefined, Object? $__typename = _undefined, @@ -635,7 +653,6 @@ class _CopyWithImpl$Mutation$MarkTorrentDownload$downloadTorrent : ($__typename as String), )); - @override CopyWith$Mutation$MarkTorrentDownload$downloadTorrent$task get task { final local$task = _instance.task; return local$task == null @@ -650,16 +667,14 @@ class _CopyWithStubImpl$Mutation$MarkTorrentDownload$downloadTorrent implements CopyWith$Mutation$MarkTorrentDownload$downloadTorrent { _CopyWithStubImpl$Mutation$MarkTorrentDownload$downloadTorrent(this._res); - final TRes _res; + TRes _res; - @override call({ Mutation$MarkTorrentDownload$downloadTorrent$task? task, String? $__typename, }) => _res; - @override CopyWith$Mutation$MarkTorrentDownload$downloadTorrent$task get task => CopyWith$Mutation$MarkTorrentDownload$downloadTorrent$task.stub(_res); } @@ -685,12 +700,12 @@ class Mutation$MarkTorrentDownload$downloadTorrent$task { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$id = id; - resultData['id'] = l$id; + _resultData['id'] = l$id; final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -708,7 +723,7 @@ class Mutation$MarkTorrentDownload$downloadTorrent$task { if (identical(this, other)) { return true; } - if (other is! Mutation$MarkTorrentDownload$downloadTorrent$task || + if (!(other is Mutation$MarkTorrentDownload$downloadTorrent$task) || runtimeType != other.runtimeType) { return false; } @@ -768,7 +783,6 @@ class _CopyWithImpl$Mutation$MarkTorrentDownload$downloadTorrent$task static const _undefined = {}; - @override TRes call({ Object? id = _undefined, Object? $__typename = _undefined, @@ -787,9 +801,8 @@ class _CopyWithStubImpl$Mutation$MarkTorrentDownload$downloadTorrent$task _CopyWithStubImpl$Mutation$MarkTorrentDownload$downloadTorrent$task( this._res); - final TRes _res; + TRes _res; - @override call({ String? id, String? $__typename, @@ -797,6 +810,112 @@ class _CopyWithStubImpl$Mutation$MarkTorrentDownload$downloadTorrent$task _res; } +class Variables$Query$ListTorrents { + factory Variables$Query$ListTorrents({bool? downloading}) => + Variables$Query$ListTorrents._({ + if (downloading != null) r'downloading': downloading, + }); + + Variables$Query$ListTorrents._(this._$data); + + factory Variables$Query$ListTorrents.fromJson(Map data) { + final result$data = {}; + if (data.containsKey('downloading')) { + final l$downloading = data['downloading']; + result$data['downloading'] = (l$downloading as bool?); + } + return Variables$Query$ListTorrents._(result$data); + } + + Map _$data; + + bool? get downloading => (_$data['downloading'] as bool?); + + Map toJson() { + final result$data = {}; + if (_$data.containsKey('downloading')) { + final l$downloading = downloading; + result$data['downloading'] = l$downloading; + } + return result$data; + } + + CopyWith$Variables$Query$ListTorrents + get copyWith => CopyWith$Variables$Query$ListTorrents( + this, + (i) => i, + ); + + @override + bool operator ==(Object other) { + if (identical(this, other)) { + return true; + } + if (!(other is Variables$Query$ListTorrents) || + runtimeType != other.runtimeType) { + return false; + } + final l$downloading = downloading; + final lOther$downloading = other.downloading; + if (_$data.containsKey('downloading') != + other._$data.containsKey('downloading')) { + return false; + } + if (l$downloading != lOther$downloading) { + return false; + } + return true; + } + + @override + int get hashCode { + final l$downloading = downloading; + return Object.hashAll( + [_$data.containsKey('downloading') ? l$downloading : const {}]); + } +} + +abstract class CopyWith$Variables$Query$ListTorrents { + factory CopyWith$Variables$Query$ListTorrents( + Variables$Query$ListTorrents instance, + TRes Function(Variables$Query$ListTorrents) then, + ) = _CopyWithImpl$Variables$Query$ListTorrents; + + factory CopyWith$Variables$Query$ListTorrents.stub(TRes res) = + _CopyWithStubImpl$Variables$Query$ListTorrents; + + TRes call({bool? downloading}); +} + +class _CopyWithImpl$Variables$Query$ListTorrents + implements CopyWith$Variables$Query$ListTorrents { + _CopyWithImpl$Variables$Query$ListTorrents( + this._instance, + this._then, + ); + + final Variables$Query$ListTorrents _instance; + + final TRes Function(Variables$Query$ListTorrents) _then; + + static const _undefined = {}; + + TRes call({Object? downloading = _undefined}) => + _then(Variables$Query$ListTorrents._({ + ..._instance._$data, + if (downloading != _undefined) 'downloading': (downloading as bool?), + })); +} + +class _CopyWithStubImpl$Variables$Query$ListTorrents + implements CopyWith$Variables$Query$ListTorrents { + _CopyWithStubImpl$Variables$Query$ListTorrents(this._res); + + TRes _res; + + call({bool? downloading}) => _res; +} + class Query$ListTorrents { Query$ListTorrents({ required this.torrents, @@ -820,12 +939,12 @@ class Query$ListTorrents { final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$torrents = torrents; - resultData['torrents'] = l$torrents.map((e) => e.toJson()).toList(); + _resultData['torrents'] = l$torrents.map((e) => e.toJson()).toList(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -843,7 +962,7 @@ class Query$ListTorrents { if (identical(this, other)) { return true; } - if (other is! Query$ListTorrents || runtimeType != other.runtimeType) { + if (!(other is Query$ListTorrents) || runtimeType != other.runtimeType) { return false; } final l$torrents = torrents; @@ -893,7 +1012,7 @@ abstract class CopyWith$Query$ListTorrents { Iterable< CopyWith$Query$ListTorrents$torrents< Query$ListTorrents$torrents>>) - fn); + _fn); } class _CopyWithImpl$Query$ListTorrents @@ -909,7 +1028,6 @@ class _CopyWithImpl$Query$ListTorrents static const _undefined = {}; - @override TRes call({ Object? torrents = _undefined, Object? $__typename = _undefined, @@ -923,15 +1041,14 @@ class _CopyWithImpl$Query$ListTorrents : ($__typename as String), )); - @override TRes torrents( Iterable Function( Iterable< CopyWith$Query$ListTorrents$torrents< Query$ListTorrents$torrents>>) - fn) => + _fn) => call( - torrents: fn(_instance.torrents + torrents: _fn(_instance.torrents .map((e) => CopyWith$Query$ListTorrents$torrents( e, (i) => i, @@ -942,30 +1059,53 @@ class _CopyWithStubImpl$Query$ListTorrents implements CopyWith$Query$ListTorrents { _CopyWithStubImpl$Query$ListTorrents(this._res); - final TRes _res; + TRes _res; - @override call({ List? torrents, String? $__typename, }) => _res; - @override - torrents(fn) => _res; + torrents(_fn) => _res; } const documentNodeQueryListTorrents = DocumentNode(definitions: [ OperationDefinitionNode( type: OperationType.query, name: NameNode(value: 'ListTorrents'), - variableDefinitions: [], + variableDefinitions: [ + VariableDefinitionNode( + variable: VariableNode(name: NameNode(value: 'downloading')), + type: NamedTypeNode( + name: NameNode(value: 'Boolean'), + isNonNull: false, + ), + defaultValue: DefaultValueNode(value: null), + directives: [], + ) + ], directives: [], selectionSet: SelectionSetNode(selections: [ FieldNode( name: NameNode(value: 'torrents'), alias: null, - arguments: [], + arguments: [ + ArgumentNode( + name: NameNode(value: 'filter'), + value: ObjectValueNode(fields: [ + ObjectFieldNode( + name: NameNode(value: 'downloading'), + value: ObjectValueNode(fields: [ + ObjectFieldNode( + name: NameNode(value: 'eq'), + value: VariableNode(name: NameNode(value: 'downloading')), + ) + ]), + ) + ]), + ) + ], directives: [], selectionSet: SelectionSetNode(selections: [ FieldNode( @@ -996,6 +1136,42 @@ const documentNodeQueryListTorrents = DocumentNode(definitions: [ directives: [], selectionSet: null, ), + FieldNode( + name: NameNode(value: 'peers'), + alias: null, + arguments: [], + directives: [], + selectionSet: SelectionSetNode(selections: [ + FieldNode( + name: NameNode(value: 'ip'), + alias: null, + arguments: [], + directives: [], + selectionSet: null, + ), + FieldNode( + name: NameNode(value: 'downloadRate'), + alias: null, + arguments: [], + directives: [], + selectionSet: null, + ), + FieldNode( + name: NameNode(value: 'clientName'), + alias: null, + arguments: [], + directives: [], + selectionSet: null, + ), + FieldNode( + name: NameNode(value: '__typename'), + alias: null, + arguments: [], + directives: [], + selectionSet: null, + ), + ]), + ), FieldNode( name: NameNode(value: '__typename'), alias: null, @@ -1025,25 +1201,34 @@ typedef OnQueryComplete$Query$ListTorrents = FutureOr Function( class Options$Query$ListTorrents extends graphql.QueryOptions { Options$Query$ListTorrents({ - super.operationName, - super.fetchPolicy, - super.errorPolicy, - super.cacheRereadPolicy, + String? operationName, + Variables$Query$ListTorrents? variables, + graphql.FetchPolicy? fetchPolicy, + graphql.ErrorPolicy? errorPolicy, + graphql.CacheRereadPolicy? cacheRereadPolicy, Object? optimisticResult, Query$ListTorrents? typedOptimisticResult, - super.pollInterval, - super.context, + Duration? pollInterval, + graphql.Context? context, OnQueryComplete$Query$ListTorrents? onComplete, - super.onError, + graphql.OnQueryError? onError, }) : onCompleteWithParsed = onComplete, super( + variables: variables?.toJson() ?? {}, + operationName: operationName, + fetchPolicy: fetchPolicy, + errorPolicy: errorPolicy, + cacheRereadPolicy: cacheRereadPolicy, optimisticResult: optimisticResult ?? typedOptimisticResult?.toJson(), + pollInterval: pollInterval, + context: context, onComplete: onComplete == null ? null : (data) => onComplete( data, data == null ? null : _parserFn$Query$ListTorrents(data), ), + onError: onError, document: documentNodeQueryListTorrents, parserFn: _parserFn$Query$ListTorrents, ); @@ -1062,28 +1247,42 @@ class Options$Query$ListTorrents class WatchOptions$Query$ListTorrents extends graphql.WatchQueryOptions { WatchOptions$Query$ListTorrents({ - super.operationName, - super.fetchPolicy, - super.errorPolicy, - super.cacheRereadPolicy, + String? operationName, + Variables$Query$ListTorrents? variables, + graphql.FetchPolicy? fetchPolicy, + graphql.ErrorPolicy? errorPolicy, + graphql.CacheRereadPolicy? cacheRereadPolicy, Object? optimisticResult, Query$ListTorrents? typedOptimisticResult, - super.context, - super.pollInterval, - super.eagerlyFetchResults, - super.carryForwardDataOnException, - super.fetchResults, + graphql.Context? context, + Duration? pollInterval, + bool? eagerlyFetchResults, + bool carryForwardDataOnException = true, + bool fetchResults = false, }) : super( + variables: variables?.toJson() ?? {}, + operationName: operationName, + fetchPolicy: fetchPolicy, + errorPolicy: errorPolicy, + cacheRereadPolicy: cacheRereadPolicy, optimisticResult: optimisticResult ?? typedOptimisticResult?.toJson(), + context: context, document: documentNodeQueryListTorrents, + pollInterval: pollInterval, + eagerlyFetchResults: eagerlyFetchResults, + carryForwardDataOnException: carryForwardDataOnException, + fetchResults: fetchResults, parserFn: _parserFn$Query$ListTorrents, ); } class FetchMoreOptions$Query$ListTorrents extends graphql.FetchMoreOptions { - FetchMoreOptions$Query$ListTorrents( - {required super.updateQuery}) - : super( + FetchMoreOptions$Query$ListTorrents({ + required graphql.UpdateQuery updateQuery, + Variables$Query$ListTorrents? variables, + }) : super( + updateQuery: updateQuery, + variables: variables?.toJson() ?? {}, document: documentNodeQueryListTorrents, ); } @@ -1091,26 +1290,32 @@ class FetchMoreOptions$Query$ListTorrents extends graphql.FetchMoreOptions { extension ClientExtension$Query$ListTorrents on graphql.GraphQLClient { Future> query$ListTorrents( [Options$Query$ListTorrents? options]) async => - await query(options ?? Options$Query$ListTorrents()); + await this.query(options ?? Options$Query$ListTorrents()); graphql.ObservableQuery watchQuery$ListTorrents( [WatchOptions$Query$ListTorrents? options]) => - watchQuery(options ?? WatchOptions$Query$ListTorrents()); + this.watchQuery(options ?? WatchOptions$Query$ListTorrents()); void writeQuery$ListTorrents({ required Query$ListTorrents data, + Variables$Query$ListTorrents? variables, bool broadcast = true, }) => - writeQuery( - const graphql.Request( - operation: - graphql.Operation(document: documentNodeQueryListTorrents)), + this.writeQuery( + graphql.Request( + operation: graphql.Operation(document: documentNodeQueryListTorrents), + variables: variables?.toJson() ?? const {}, + ), data: data.toJson(), broadcast: broadcast, ); - Query$ListTorrents? readQuery$ListTorrents({bool optimistic = true}) { - final result = readQuery( - const graphql.Request( - operation: - graphql.Operation(document: documentNodeQueryListTorrents)), + Query$ListTorrents? readQuery$ListTorrents({ + Variables$Query$ListTorrents? variables, + bool optimistic = true, + }) { + final result = this.readQuery( + graphql.Request( + operation: graphql.Operation(document: documentNodeQueryListTorrents), + variables: variables?.toJson() ?? const {}, + ), optimistic: optimistic, ); return result == null ? null : Query$ListTorrents.fromJson(result); @@ -1127,11 +1332,13 @@ graphql.ObservableQuery useWatchQuery$ListTorrents( class Query$ListTorrents$Widget extends graphql_flutter.Query { Query$ListTorrents$Widget({ - super.key, + widgets.Key? key, Options$Query$ListTorrents? options, - required super.builder, + required graphql_flutter.QueryBuilder builder, }) : super( + key: key, options: options ?? Options$Query$ListTorrents(), + builder: builder, ); } @@ -1141,6 +1348,7 @@ class Query$ListTorrents$torrents { required this.infohash, required this.bytesCompleted, required this.bytesMissing, + required this.peers, this.$__typename = 'Torrent', }); @@ -1149,12 +1357,17 @@ class Query$ListTorrents$torrents { final l$infohash = json['infohash']; final l$bytesCompleted = json['bytesCompleted']; final l$bytesMissing = json['bytesMissing']; + final l$peers = json['peers']; final l$$__typename = json['__typename']; return Query$ListTorrents$torrents( name: (l$name as String), infohash: (l$infohash as String), bytesCompleted: (l$bytesCompleted as int), bytesMissing: (l$bytesMissing as int), + peers: (l$peers as List) + .map((e) => Query$ListTorrents$torrents$peers.fromJson( + (e as Map))) + .toList(), $__typename: (l$$__typename as String), ); } @@ -1167,21 +1380,25 @@ class Query$ListTorrents$torrents { final int bytesMissing; + final List peers; + final String $__typename; Map toJson() { - final resultData = {}; + final _resultData = {}; final l$name = name; - resultData['name'] = l$name; + _resultData['name'] = l$name; final l$infohash = infohash; - resultData['infohash'] = l$infohash; + _resultData['infohash'] = l$infohash; final l$bytesCompleted = bytesCompleted; - resultData['bytesCompleted'] = l$bytesCompleted; + _resultData['bytesCompleted'] = l$bytesCompleted; final l$bytesMissing = bytesMissing; - resultData['bytesMissing'] = l$bytesMissing; + _resultData['bytesMissing'] = l$bytesMissing; + final l$peers = peers; + _resultData['peers'] = l$peers.map((e) => e.toJson()).toList(); final l$$__typename = $__typename; - resultData['__typename'] = l$$__typename; - return resultData; + _resultData['__typename'] = l$$__typename; + return _resultData; } @override @@ -1190,12 +1407,14 @@ class Query$ListTorrents$torrents { final l$infohash = infohash; final l$bytesCompleted = bytesCompleted; final l$bytesMissing = bytesMissing; + final l$peers = peers; final l$$__typename = $__typename; return Object.hashAll([ l$name, l$infohash, l$bytesCompleted, l$bytesMissing, + Object.hashAll(l$peers.map((v) => v)), l$$__typename, ]); } @@ -1205,7 +1424,7 @@ class Query$ListTorrents$torrents { if (identical(this, other)) { return true; } - if (other is! Query$ListTorrents$torrents || + if (!(other is Query$ListTorrents$torrents) || runtimeType != other.runtimeType) { return false; } @@ -1229,6 +1448,18 @@ class Query$ListTorrents$torrents { if (l$bytesMissing != lOther$bytesMissing) { return false; } + final l$peers = peers; + final lOther$peers = other.peers; + if (l$peers.length != lOther$peers.length) { + return false; + } + for (int i = 0; i < l$peers.length; i++) { + final l$peers$entry = l$peers[i]; + final lOther$peers$entry = lOther$peers[i]; + if (l$peers$entry != lOther$peers$entry) { + return false; + } + } final l$$__typename = $__typename; final lOther$$__typename = other.$__typename; if (l$$__typename != lOther$$__typename) { @@ -1261,8 +1492,15 @@ abstract class CopyWith$Query$ListTorrents$torrents { String? infohash, int? bytesCompleted, int? bytesMissing, + List? peers, String? $__typename, }); + TRes peers( + Iterable Function( + Iterable< + CopyWith$Query$ListTorrents$torrents$peers< + Query$ListTorrents$torrents$peers>>) + _fn); } class _CopyWithImpl$Query$ListTorrents$torrents @@ -1278,12 +1516,12 @@ class _CopyWithImpl$Query$ListTorrents$torrents static const _undefined = {}; - @override TRes call({ Object? name = _undefined, Object? infohash = _undefined, Object? bytesCompleted = _undefined, Object? bytesMissing = _undefined, + Object? peers = _undefined, Object? $__typename = _undefined, }) => _then(Query$ListTorrents$torrents( @@ -1299,24 +1537,206 @@ class _CopyWithImpl$Query$ListTorrents$torrents bytesMissing: bytesMissing == _undefined || bytesMissing == null ? _instance.bytesMissing : (bytesMissing as int), + peers: peers == _undefined || peers == null + ? _instance.peers + : (peers as List), $__typename: $__typename == _undefined || $__typename == null ? _instance.$__typename : ($__typename as String), )); + + TRes peers( + Iterable Function( + Iterable< + CopyWith$Query$ListTorrents$torrents$peers< + Query$ListTorrents$torrents$peers>>) + _fn) => + call( + peers: _fn(_instance.peers + .map((e) => CopyWith$Query$ListTorrents$torrents$peers( + e, + (i) => i, + ))).toList()); } class _CopyWithStubImpl$Query$ListTorrents$torrents implements CopyWith$Query$ListTorrents$torrents { _CopyWithStubImpl$Query$ListTorrents$torrents(this._res); - final TRes _res; + TRes _res; - @override call({ String? name, String? infohash, int? bytesCompleted, int? bytesMissing, + List? peers, + String? $__typename, + }) => + _res; + + peers(_fn) => _res; +} + +class Query$ListTorrents$torrents$peers { + Query$ListTorrents$torrents$peers({ + required this.ip, + required this.downloadRate, + required this.clientName, + this.$__typename = 'TorrentPeer', + }); + + factory Query$ListTorrents$torrents$peers.fromJson( + Map json) { + final l$ip = json['ip']; + final l$downloadRate = json['downloadRate']; + final l$clientName = json['clientName']; + final l$$__typename = json['__typename']; + return Query$ListTorrents$torrents$peers( + ip: (l$ip as String), + downloadRate: (l$downloadRate as num).toDouble(), + clientName: (l$clientName as String), + $__typename: (l$$__typename as String), + ); + } + + final String ip; + + final double downloadRate; + + final String clientName; + + final String $__typename; + + Map toJson() { + final _resultData = {}; + final l$ip = ip; + _resultData['ip'] = l$ip; + final l$downloadRate = downloadRate; + _resultData['downloadRate'] = l$downloadRate; + final l$clientName = clientName; + _resultData['clientName'] = l$clientName; + final l$$__typename = $__typename; + _resultData['__typename'] = l$$__typename; + return _resultData; + } + + @override + int get hashCode { + final l$ip = ip; + final l$downloadRate = downloadRate; + final l$clientName = clientName; + final l$$__typename = $__typename; + return Object.hashAll([ + l$ip, + l$downloadRate, + l$clientName, + l$$__typename, + ]); + } + + @override + bool operator ==(Object other) { + if (identical(this, other)) { + return true; + } + if (!(other is Query$ListTorrents$torrents$peers) || + runtimeType != other.runtimeType) { + return false; + } + final l$ip = ip; + final lOther$ip = other.ip; + if (l$ip != lOther$ip) { + return false; + } + final l$downloadRate = downloadRate; + final lOther$downloadRate = other.downloadRate; + if (l$downloadRate != lOther$downloadRate) { + return false; + } + final l$clientName = clientName; + final lOther$clientName = other.clientName; + if (l$clientName != lOther$clientName) { + return false; + } + final l$$__typename = $__typename; + final lOther$$__typename = other.$__typename; + if (l$$__typename != lOther$$__typename) { + return false; + } + return true; + } +} + +extension UtilityExtension$Query$ListTorrents$torrents$peers + on Query$ListTorrents$torrents$peers { + CopyWith$Query$ListTorrents$torrents$peers + get copyWith => CopyWith$Query$ListTorrents$torrents$peers( + this, + (i) => i, + ); +} + +abstract class CopyWith$Query$ListTorrents$torrents$peers { + factory CopyWith$Query$ListTorrents$torrents$peers( + Query$ListTorrents$torrents$peers instance, + TRes Function(Query$ListTorrents$torrents$peers) then, + ) = _CopyWithImpl$Query$ListTorrents$torrents$peers; + + factory CopyWith$Query$ListTorrents$torrents$peers.stub(TRes res) = + _CopyWithStubImpl$Query$ListTorrents$torrents$peers; + + TRes call({ + String? ip, + double? downloadRate, + String? clientName, + String? $__typename, + }); +} + +class _CopyWithImpl$Query$ListTorrents$torrents$peers + implements CopyWith$Query$ListTorrents$torrents$peers { + _CopyWithImpl$Query$ListTorrents$torrents$peers( + this._instance, + this._then, + ); + + final Query$ListTorrents$torrents$peers _instance; + + final TRes Function(Query$ListTorrents$torrents$peers) _then; + + static const _undefined = {}; + + TRes call({ + Object? ip = _undefined, + Object? downloadRate = _undefined, + Object? clientName = _undefined, + Object? $__typename = _undefined, + }) => + _then(Query$ListTorrents$torrents$peers( + ip: ip == _undefined || ip == null ? _instance.ip : (ip as String), + downloadRate: downloadRate == _undefined || downloadRate == null + ? _instance.downloadRate + : (downloadRate as double), + clientName: clientName == _undefined || clientName == null + ? _instance.clientName + : (clientName as String), + $__typename: $__typename == _undefined || $__typename == null + ? _instance.$__typename + : ($__typename as String), + )); +} + +class _CopyWithStubImpl$Query$ListTorrents$torrents$peers + implements CopyWith$Query$ListTorrents$torrents$peers { + _CopyWithStubImpl$Query$ListTorrents$torrents$peers(this._res); + + TRes _res; + + call({ + String? ip, + double? downloadRate, + String? clientName, String? $__typename, }) => _res; diff --git a/ui/lib/components/sliver_header.dart b/ui/lib/components/sliver_header.dart new file mode 100644 index 0000000..d26633e --- /dev/null +++ b/ui/lib/components/sliver_header.dart @@ -0,0 +1,91 @@ +import 'package:flutter/material.dart'; + +class HideableHeaderSliver extends StatelessWidget { + final Widget? leading; + final Widget body; + final double height; + final List? actions; + + const HideableHeaderSliver({ + super.key, + this.leading, + required this.body, + this.actions, + this.height = 150, + }); + + @override + Widget build(BuildContext context) { + return SliverPersistentHeader( + floating: true, + pinned: false, + delegate: _HideableHeaderSliverDelegate( + leading: leading, + body: body, + actions: actions, + height: height, + ), + ); + } +} + +class _HideableHeaderSliverDelegate extends SliverPersistentHeaderDelegate { + final Widget? leading; + final Widget body; + final List? actions; + final double height; + + const _HideableHeaderSliverDelegate({ + required this.leading, + required this.body, + required this.actions, + required this.height, + }); + + @override + double get maxExtent => height; + + @override + double get minExtent => height; + + @override + bool shouldRebuild(covariant SliverPersistentHeaderDelegate oldDelegate) => true; + + @override + Widget build(BuildContext context, double shrinkOffset, bool overlapsContent) { + final content = [ + if (leading != null) leading!, + Expanded(child: body), + if (actions != null && actions!.isNotEmpty) ButtonBar(children: actions!), + ]; + + final appBarTheme = AppBarTheme.of(context); + final colorScheme = Theme.of(context).colorScheme; + final onTop = (shrinkOffset == 0); + + return Material( + color: + onTop ? appBarTheme.backgroundColor ?? colorScheme.surface : colorScheme.surfaceContainer, + elevation: onTop ? 0 : appBarTheme.elevation ?? 3, + surfaceTintColor: appBarTheme.surfaceTintColor ?? colorScheme.surfaceTint, + child: ClipRect( + child: SizedBox( + height: maxExtent, + child: Column( + children: [ + const Spacer(), + Row( + children: content, + ), + const Spacer(), + const Divider( + height: 1, + thickness: 1, + ), + ], + ), + ), + ), + ); + } +} diff --git a/ui/lib/main.dart b/ui/lib/main.dart index 74d71cf..e1e204a 100644 --- a/ui/lib/main.dart +++ b/ui/lib/main.dart @@ -43,9 +43,6 @@ class _MyHomePageState extends State { @override Widget build(BuildContext context) { return Scaffold( - appBar: AppBar( - title: const Text("tStor"), - ), body: [ const FileViewScreen(), const DownloadsScreen(), diff --git a/ui/lib/screens/downloads.dart b/ui/lib/screens/downloads.dart index 2f27004..33c34b7 100644 --- a/ui/lib/screens/downloads.dart +++ b/ui/lib/screens/downloads.dart @@ -2,6 +2,7 @@ import 'package:flutter/material.dart'; import 'package:tstor_ui/api/client.dart'; import 'package:tstor_ui/api/torrent.graphql.dart'; import 'package:tstor_ui/components/download.dart'; +import 'package:tstor_ui/components/sliver_header.dart'; class DownloadsScreen extends StatefulWidget { const DownloadsScreen({super.key}); @@ -11,45 +12,98 @@ class DownloadsScreen extends StatefulWidget { } class _DownloadsScreenState extends State { + bool filterDownloading = false; + @override Widget build(BuildContext context) { return FutureBuilder( - future: client.query$ListTorrents(), + key: GlobalKey(), + future: client.query$ListTorrents(Options$Query$ListTorrents( + variables: Variables$Query$ListTorrents(downloading: filterDownloading), + )), builder: (context, snapshot) { - if (!snapshot.hasData || snapshot.data == null) { - return const Center(child: CircularProgressIndicator()); - } + final torrents = snapshot.data?.parsedData?.torrents; - final torrents = snapshot.data!.parsedData!.torrents; - - return ListView.builder( - itemCount: torrents.length, - itemBuilder: (context, index) { - final torrent = torrents[index]; - return ListTile( - title: Text(torrent.name), - subtitle: DownloadProgress( - torrent.bytesCompleted, torrent.bytesCompleted + torrent.bytesMissing), - trailing: Column( - mainAxisSize: MainAxisSize.max, - mainAxisAlignment: MainAxisAlignment.spaceAround, - children: [ - IconButton( - onPressed: () => client.mutate$MarkTorrentDownload( - Options$Mutation$MarkTorrentDownload( - variables: Variables$Mutation$MarkTorrentDownload( - infohash: torrent.infohash, - ), - ), + return NestedScrollView( + floatHeaderSlivers: true, + headerSliverBuilder: (context, innerBoxIsScrolled) => [ + HideableHeaderSliver( + height: 80, + body: Padding( + padding: const EdgeInsets.all(8.0), + child: Wrap( + spacing: 8, + runSpacing: 8, + children: [ + FilterChip( + label: const Text("Downloading"), + selected: filterDownloading, + onSelected: (value) => setState(() { + filterDownloading = value; + }), ), - icon: const Icon(Icons.download), - ) - ], + ], + ), ), - ); - }, + actions: [ + IconButton( + icon: const Icon(Icons.refresh), + onPressed: () => setState(() {}), + ), + ], + ), + ], + body: snapshot.hasData && torrents != null + ? ListView.builder( + itemCount: torrents.length, + itemBuilder: (context, index) => TorrentTile(torrent: torrents[index]), + ) + : const Center(child: CircularProgressIndicator()), ); }, ); } } + +class TorrentTile extends StatelessWidget { + final Query$ListTorrents$torrents torrent; + + const TorrentTile({super.key, required this.torrent}); + + @override + Widget build(BuildContext context) { + return ListTile( + title: Text(torrent.name), + isThreeLine: true, + subtitle: Column( + children: [ + DownloadProgress( + torrent.bytesCompleted, + torrent.bytesCompleted + torrent.bytesMissing, + ), + Row( + children: [ + Text("Peers: ${torrent.peers.length}"), + ], + ), + ], + ), + trailing: Column( + mainAxisSize: MainAxisSize.max, + mainAxisAlignment: MainAxisAlignment.spaceAround, + children: [ + IconButton( + onPressed: () => client.mutate$MarkTorrentDownload( + Options$Mutation$MarkTorrentDownload( + variables: Variables$Mutation$MarkTorrentDownload( + infohash: torrent.infohash, + ), + ), + ), + icon: const Icon(Icons.download), + ) + ], + ), + ); + } +} diff --git a/ui/lib/screens/file_view.dart b/ui/lib/screens/file_view.dart index 6e26d3c..fba634e 100644 --- a/ui/lib/screens/file_view.dart +++ b/ui/lib/screens/file_view.dart @@ -5,6 +5,7 @@ import 'package:tstor_ui/api/client.dart'; import 'package:tstor_ui/api/fs_entry.graphql.dart'; import 'package:tstor_ui/api/torrent.graphql.dart'; import 'package:tstor_ui/components/download.dart'; +import 'package:tstor_ui/components/sliver_header.dart'; import 'package:tstor_ui/font/t_icons_icons.dart'; import 'package:path/path.dart' as p; @@ -116,7 +117,7 @@ class _FileViewScreenState extends State { return CustomScrollView( slivers: [ - EntryInfoSliver(entry: entry), + EntryHeaderSliver(entry: entry), SliverList.builder( itemCount: entries.length, itemBuilder: (context, index) { @@ -214,20 +215,18 @@ class DirEntry extends StatelessWidget { } } -class EntryInfoSliver extends StatelessWidget { +class EntryHeaderSliver extends StatelessWidget { final Query$ListDir$fsEntry entry; - const EntryInfoSliver({super.key, required this.entry}); + const EntryHeaderSliver({super.key, required this.entry}); @override Widget build(BuildContext context) { switch (entry) { case Query$ListDir$fsEntry$$TorrentFS entry: final total = entry.torrent.bytesCompleted + entry.torrent.bytesMissing; - - return EntryInfoHeader( - icon: TIcons.bittorrent_bttold_logo, - title: Text(entry.torrent.name), + return HideableHeaderSliver( + leading: const Icon(TIcons.bittorrent_bttold_logo), body: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ @@ -252,101 +251,10 @@ class EntryInfoSliver extends StatelessWidget { ); default: - return EntryInfoHeader( - icon: Icons.folder, - title: Text(entry.name), + return HideableHeaderSliver( + leading: const Icon(Icons.folder), body: Text(entry.name), ); } } } - -class EntryInfoHeader extends StatelessWidget { - final IconData icon; - final Widget title; - final Widget body; - final List? actions; - - const EntryInfoHeader({ - super.key, - required this.icon, - required this.title, - required this.body, - this.actions, - }); - - @override - Widget build(BuildContext context) { - return SliverPersistentHeader( - floating: true, - pinned: false, - delegate: EntryInfoSliverHeaderDelegate(icon: icon, title: title, body: body), - ); - } -} - -class EntryInfoSliverHeaderDelegate extends SliverPersistentHeaderDelegate { - final IconData icon; - final Widget title; - final Widget body; - final List? actions; - final double size; - - const EntryInfoSliverHeaderDelegate({ - required this.icon, - required this.title, - required this.body, - this.actions, - this.size = 150, - }); - - @override - double get maxExtent => size; - - @override - double get minExtent => size; - - @override - bool shouldRebuild(covariant SliverPersistentHeaderDelegate oldDelegate) => true; - - @override - Widget build(BuildContext context, double shrinkOffset, bool overlapsContent) { - final content = [ - Icon(icon, size: 50), - Expanded(child: body), - ]; - - if (actions != null && actions!.isNotEmpty) { - content.add(ButtonBar(children: actions!)); - } - - final appBarTheme = AppBarTheme.of(context); - final colorScheme = Theme.of(context).colorScheme; - final onTop = (shrinkOffset == 0); - - return Material( - color: - onTop ? appBarTheme.backgroundColor ?? colorScheme.surface : colorScheme.surfaceContainer, - elevation: onTop ? 0 : appBarTheme.elevation ?? 3, - surfaceTintColor: appBarTheme.surfaceTintColor ?? colorScheme.surfaceTint, - child: ClipRect( - child: SizedBox( - height: maxExtent, - child: Column( - children: [ - const Spacer(), - Row( - children: content, - ), - const Spacer(), - const Divider( - height: 1, - thickness: 1, - ), - ], - ), - ), - ), - ); - } -}