fetch all posts instead of only the initial 50
This commit is contained in:
parent
1a09ba2ba9
commit
2303df7abe
|
@ -103,6 +103,7 @@ class APIRequestBuilder {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Mark single item as read, unread, saved, unsaved
|
||||||
APIRequestBuilder markItem(Item item, ItemMarkType markAs) {
|
APIRequestBuilder markItem(Item item, ItemMarkType markAs) {
|
||||||
_addArg('mark=item');
|
_addArg('mark=item');
|
||||||
_addArg('as=${markAs.name}');
|
_addArg('as=${markAs.name}');
|
||||||
|
@ -112,6 +113,22 @@ class APIRequestBuilder {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Use the `since_id` argument with the highest id of locally cached items to
|
||||||
|
/// request 50 additional items. Repeat until the items array in the response
|
||||||
|
/// is empty.
|
||||||
|
APIRequestBuilder sinceId(int id) {
|
||||||
|
_addArg('since_id=$id');
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Use the `max_id` argument with the lowest id of locally cached items (or
|
||||||
|
/// 0 initially) to request 50 previous items. Repeat until the items array
|
||||||
|
/// in the response is empty.
|
||||||
|
APIRequestBuilder maxId(int id) {
|
||||||
|
_addArg('max_id=$id');
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
/// Executes the API request and returns the JSON data
|
/// Executes the API request and returns the JSON data
|
||||||
Future<Map<String, dynamic>> fetch() async {
|
Future<Map<String, dynamic>> fetch() async {
|
||||||
if (api.apiKey == null || api.apiUrl == null) {
|
if (api.apiKey == null || api.apiUrl == null) {
|
||||||
|
@ -126,7 +143,7 @@ class APIRequestBuilder {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Executes the API request and populates the local cache with the response data
|
/// Executes the API request and populates the local cache with the response data
|
||||||
Future<void> execute() async {
|
Future<Map<String, dynamic>> execute() async {
|
||||||
final data = await fetch();
|
final data = await fetch();
|
||||||
|
|
||||||
if (data.containsKey('groups')) {
|
if (data.containsKey('groups')) {
|
||||||
|
@ -185,6 +202,8 @@ class APIRequestBuilder {
|
||||||
}
|
}
|
||||||
api.cache.items.set(_markedItem!.id, _markedItem!);
|
api.cache.items.set(_markedItem!.id, _markedItem!);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return data;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -42,6 +42,8 @@ class ObjectCache<K, T> {
|
||||||
void set(K key, T value) {
|
void set(K key, T value) {
|
||||||
_items[key] = value;
|
_items[key] = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int get size => _items.length;
|
||||||
}
|
}
|
||||||
|
|
||||||
class ItemCache extends ObjectCache<int, Item> {
|
class ItemCache extends ObjectCache<int, Item> {
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
|
|
||||||
import 'package:feet/pages/login.dart';
|
|
||||||
import 'package:feet/widgets/centered_page_hint.dart';
|
import 'package:feet/widgets/centered_page_hint.dart';
|
||||||
import 'package:feet/widgets/homepage_post.dart';
|
import 'package:feet/widgets/homepage_post.dart';
|
||||||
import 'package:feet/widgets/login_prompt.dart';
|
import 'package:feet/widgets/login_prompt.dart';
|
||||||
|
@ -10,6 +9,10 @@ import 'package:flutter/services.dart';
|
||||||
import 'package:shared_preferences/shared_preferences.dart';
|
import 'package:shared_preferences/shared_preferences.dart';
|
||||||
import 'api/api.dart';
|
import 'api/api.dart';
|
||||||
|
|
||||||
|
// Limit the maximum amount of posts to fetch so we don't wait forever when
|
||||||
|
// fetching a large list
|
||||||
|
const FETCH_MAX_POSTS = 1000;
|
||||||
|
|
||||||
void main() {
|
void main() {
|
||||||
runApp(MyApp());
|
runApp(MyApp());
|
||||||
}
|
}
|
||||||
|
@ -78,9 +81,47 @@ class MyHomePage extends StatefulWidget {
|
||||||
class _MyHomePageState extends State<MyHomePage> {
|
class _MyHomePageState extends State<MyHomePage> {
|
||||||
var _index = 0;
|
var _index = 0;
|
||||||
var _fetched = false;
|
var _fetched = false;
|
||||||
|
var _fetchedCount = 0;
|
||||||
|
var _knownPostsSize = -1;
|
||||||
|
|
||||||
Future<void> refresh() =>
|
Future<void> refresh() async {
|
||||||
widget.api.request().withFeeds().withGroups().withItems().execute();
|
widget.api.cache.clear();
|
||||||
|
|
||||||
|
print("Starting refresh");
|
||||||
|
|
||||||
|
var data = await widget.api
|
||||||
|
.request()
|
||||||
|
.withFeeds()
|
||||||
|
.withGroups()
|
||||||
|
.withItems()
|
||||||
|
.sinceId(0)
|
||||||
|
.execute();
|
||||||
|
|
||||||
|
while (
|
||||||
|
(data['items'] as List<dynamic>).isNotEmpty &&
|
||||||
|
_fetchedCount < FETCH_MAX_POSTS
|
||||||
|
) {
|
||||||
|
print("Fetching more items");
|
||||||
|
|
||||||
|
var ids = widget.api.cache.items
|
||||||
|
.getAll()
|
||||||
|
.values
|
||||||
|
.map((value) => value.id)
|
||||||
|
.toList()
|
||||||
|
..sort((a, b) => b - a);
|
||||||
|
|
||||||
|
setState(() {
|
||||||
|
_fetchedCount = ids.length;
|
||||||
|
_knownPostsSize = data['total_items'] ?? -1;
|
||||||
|
});
|
||||||
|
|
||||||
|
data =
|
||||||
|
await widget.api.request().withItems().sinceId(ids.first).execute();
|
||||||
|
|
||||||
|
print(
|
||||||
|
"Item cache size is now ${widget.api.cache.items.size} ${ids.first} ${ids.last}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
|
@ -233,8 +274,10 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||||
body: loggedIn
|
body: loggedIn
|
||||||
? (_fetched
|
? (_fetched
|
||||||
? pages[_index]
|
? pages[_index]
|
||||||
: const CenteredPageHint(
|
: CenteredPageHint(
|
||||||
icon: Icons.downloading, text: "Fetching your feeds..."))
|
icon: Icons.downloading,
|
||||||
|
text:
|
||||||
|
"Fetching your feeds...\n${_fetchedCount > 0 && _knownPostsSize > -1 ? "$_fetchedCount / $_knownPostsSize" : ""}"))
|
||||||
: Center(child: LoginPrompt(api: widget.api)),
|
: Center(child: LoginPrompt(api: widget.api)),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,7 +15,7 @@ class CenteredPageHint extends StatelessWidget {
|
||||||
padding: const EdgeInsets.all(12.0),
|
padding: const EdgeInsets.all(12.0),
|
||||||
child: Icon(icon, size: 48),
|
child: Icon(icon, size: 48),
|
||||||
),
|
),
|
||||||
Text(text),
|
Text(text, textAlign: TextAlign.center),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
|
Loading…
Reference in a new issue