M .gitignore => .gitignore +1 -0
@@ 8,6 8,7 @@
.buildlog/
.history
.svn/
+.vscode/
# IntelliJ related
*.iml
M lib/main.dart => lib/main.dart +30 -10
@@ 1,5 1,8 @@
+import 'dart:html';
+
import 'package:flutter/material.dart';
import 'package:flutterflux/config.dart';
+import 'package:flutterflux/miniflux.dart';
import 'package:flutterflux/views/user_input_view.dart';
import 'package:localstorage/localstorage.dart';
@@ 37,32 40,49 @@ class MyHomePage extends StatefulWidget {
class _MyHomePageState extends State<MyHomePage> {
final LocalStorage storage = new LocalStorage(Config.IDENTIFIER_LOCALSTORAGE);
+ List<FeedEntry> unreadPosts = [];
/// Check if the user token is set.
/// If that's not the case, redirect to the config page
- void checkConfig() async {
+ Future<bool> checkConfig() async {
await storage.ready;
dynamic token = await storage.getItem(Config.IDENTIFIER_API_KEY);
+
if (token == null || token.isEmpty) {
- WidgetsBinding.instance.addPostFrameCallback((_) {
- Navigator.pushNamed(context, "/config");
- });
+ Navigator.pushNamed(context, "/config");
+ return false;
}
+ return true;
+ }
+
+ void _initUnreadPosts() async {
+ var posts = await MinifluxApi().getUnreadPosts();
+ setState(() {
+ unreadPosts = posts;
+ });
}
@override
Widget build(BuildContext context) {
- checkConfig();
+ checkConfig().then((success) {
+ if (success) {
+ _initUnreadPosts();
+ }
+ });
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
- child: Column(
- mainAxisAlignment: MainAxisAlignment.center,
- children: <Widget>[],
- ),
- ),
+ key: UniqueKey(),
+ child: ListView.builder(
+ itemCount: unreadPosts.length,
+ key: UniqueKey(),
+ itemBuilder: (BuildContext context, int index) {
+ FeedEntry entry = unreadPosts[index];
+ return Card(key: UniqueKey(), child: Text(entry.title));
+ },
+ )),
);
}
}
A lib/miniflux.dart => lib/miniflux.dart +48 -0
@@ 0,0 1,48 @@
+import 'dart:convert';
+
+import 'package:http/http.dart';
+import 'package:localstorage/localstorage.dart';
+import 'config.dart';
+import 'package:http/http.dart' as http;
+
+class FeedEntry {
+ int id;
+ String status;
+ String title;
+
+ FeedEntry({this.id, this.status, this.title});
+
+ factory FeedEntry.fromJson(Map<String, dynamic> json) {
+ return FeedEntry(
+ id: json["id"],
+ status: json["status"],
+ title: json["title"],
+ );
+ }
+}
+
+class MinifluxApi {
+ Future<List<FeedEntry>> getUnreadPosts() async {
+ final storage = new LocalStorage(Config.IDENTIFIER_LOCALSTORAGE);
+ await storage.ready;
+
+ String serverUrl = storage.getItem(Config.IDENTIFIER_SERVER_URL);
+ String apiKey = storage.getItem(Config.IDENTIFIER_API_KEY);
+
+ if (serverUrl == null ||
+ serverUrl.isEmpty ||
+ apiKey == null ||
+ apiKey.isEmpty) {
+ return [];
+ }
+ Response response = await http.get("$serverUrl/v1/entries?status=unread",
+ headers: {"X-Auth-Token": apiKey});
+ Map<String, dynamic> body = json.decode(response.body);
+ List<dynamic> rawEntries = body["entries"];
+
+ // TODO: Why the heck does rawEntries.map(...) not work here?
+ List<FeedEntry> feedEntries = [];
+ for (var entry in rawEntries) feedEntries.add(FeedEntry.fromJson(entry));
+ return feedEntries;
+ }
+}
M pubspec.lock => pubspec.lock +21 -0
@@ 81,6 81,20 @@ packages:
description: flutter
source: sdk
version: "0.0.0"
+ http:
+ dependency: "direct main"
+ description:
+ name: http
+ url: "https://pub.dartlang.org"
+ source: hosted
+ version: "0.12.2"
+ http_parser:
+ dependency: transitive
+ description:
+ name: http_parser
+ url: "https://pub.dartlang.org"
+ source: hosted
+ version: "3.1.4"
intl:
dependency: transitive
description:
@@ 151,6 165,13 @@ packages:
url: "https://pub.dartlang.org"
source: hosted
version: "0.0.4+3"
+ pedantic:
+ dependency: transitive
+ description:
+ name: pedantic
+ url: "https://pub.dartlang.org"
+ source: hosted
+ version: "1.10.0"
platform:
dependency: transitive
description:
M pubspec.yaml => pubspec.yaml +1 -0
@@ 22,6 22,7 @@ environment:
dependencies:
localstorage: ^3.0.6
+ http: ^0.12.2
flutter:
sdk: flutter