feat: user organizations, fix: create,delete event (#72)

Fixes #58
This commit is contained in:
Shreyas Thirumalai 2020-04-28 22:29:01 +05:30 committed by GitHub
parent 561970ab59
commit bf5ed23971
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 167 additions and 5 deletions

View File

@ -313,3 +313,15 @@ class GithubContributorItem {
factory GithubContributorItem.fromJson(Map<String, dynamic> json) =>
_$GithubContributorItemFromJson(json);
}
@JsonSerializable(fieldRename: FieldRename.snake)
class GithubUserOrganizationItem {
int id;
String login;
String avatarUrl;
String description;
String url;
GithubUserOrganizationItem();
factory GithubUserOrganizationItem.fromJson(Map<String, dynamic> json) =>
_$GithubUserOrganizationItemFromJson(json);
}

View File

@ -440,3 +440,23 @@ Map<String, dynamic> _$GithubContributorItemToJson(
'html_url': instance.htmlUrl,
'contributions': instance.contributions,
};
GithubUserOrganizationItem _$GithubUserOrganizationItemFromJson(
Map<String, dynamic> json) {
return GithubUserOrganizationItem()
..id = json['id'] as int
..login = json['login'] as String
..avatarUrl = json['avatar_url'] as String
..description = json['description'] as String
..url = json['url'] as String;
}
Map<String, dynamic> _$GithubUserOrganizationItemToJson(
GithubUserOrganizationItem instance) =>
<String, dynamic>{
'id': instance.id,
'login': instance.login,
'avatar_url': instance.avatarUrl,
'description': instance.description,
'url': instance.url,
};

View File

@ -36,6 +36,7 @@ import 'package:git_touch/screens/gh_repo.dart';
import 'package:git_touch/screens/settings.dart';
import 'package:git_touch/screens/gh_user.dart';
import 'package:git_touch/screens/gh_users.dart';
import 'package:git_touch/screens/gh_user_organization.dart';
class RouterScreen {
String path;
@ -90,6 +91,8 @@ class GithubRouter {
return GhReposScreen(login);
case 'orgrepo':
return GhOrgReposScreen(login);
case 'organizations':
return GhUserOrganizationScreen(login);
default:
return GhUserScreen(login);
}

View File

@ -62,7 +62,6 @@ class GhUserScreen extends StatelessWidget {
final theme = Provider.of<ThemeModel>(context);
final auth = Provider.of<AuthModel>(context);
final login = p.login;
return Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: <Widget>[
@ -153,6 +152,11 @@ class GhUserScreen extends StatelessWidget {
TableView(
hasIcon: true,
items: [
TableViewItem(
leftIconData: Octicons.home,
text: Text('Organizations'),
url: '/$login?tab=organizations',
),
if (isNotNullOrEmpty(p.company))
TableViewItem(
leftIconData: Octicons.organization,

View File

@ -0,0 +1,47 @@
import 'package:flutter/material.dart';
import 'package:flutter/cupertino.dart';
import 'package:git_touch/models/github.dart';
import 'package:git_touch/scaffolds/list_stateful.dart';
import 'package:git_touch/widgets/app_bar_title.dart';
import 'package:git_touch/widgets/user_organizations.dart';
import 'package:provider/provider.dart';
import 'package:git_touch/models/auth.dart';
class GhUserOrganizationScreen extends StatelessWidget {
final String login;
GhUserOrganizationScreen(this.login);
Future<ListPayload<GithubUserOrganizationItem, int>> _query(
BuildContext context,
[int page = 1]) async {
final auth = Provider.of<AuthModel>(context);
final res =
await auth.ghClient.getJSON<List, List<GithubUserOrganizationItem>>(
'/users/$login/orgs?page=$page',
convert: (vs) =>
[for (var v in vs) GithubUserOrganizationItem.fromJson(v)],
);
return ListPayload(
cursor: page + 1,
items: res,
hasMore: res.isNotEmpty,
);
}
Widget build(BuildContext context) {
return ListStatefulScaffold<GithubUserOrganizationItem, int>(
title: AppBarTitle('Organizations'),
onRefresh: () => _query(context),
onLoadMore: (cursor) => _query(context, cursor),
itemBuilder: (v) {
final String login = v.login;
return UserOrganizationItem(
avatarUrl: v.avatarUrl,
login: v.login,
url: '/$login',
description: v.description,
);
},
);
}
}

View File

@ -308,8 +308,10 @@ class EventItem extends StatelessWidget {
return _buildItem(
context: context,
spans: <InlineSpan>[
TextSpan(text: ' created ${e.payload.refType} '),
TextSpan(text: '${e.payload.ref} at '),
TextSpan(text: ' created a ${e.payload.refType}'),
TextSpan(
text:
'${e.payload.ref == null ? '' : ' ' + e.payload.ref + 'at'} '),
_buildRepo(context),
],
);
@ -317,8 +319,10 @@ class EventItem extends StatelessWidget {
return _buildItem(
context: context,
spans: <InlineSpan>[
TextSpan(text: ' deleted ${e.payload.refType} '),
TextSpan(text: '${e.payload.ref} at '),
TextSpan(text: ' deleted the ${e.payload.refType}'),
TextSpan(
text:
'${e.payload.ref == null ? '' : ' ' + e.payload.ref + 'at'} '),
_buildRepo(context),
],
);

View File

@ -0,0 +1,72 @@
import 'package:flutter/material.dart';
import 'package:git_touch/models/theme.dart';
import 'package:git_touch/utils/utils.dart';
import 'package:git_touch/widgets/avatar.dart';
import 'package:git_touch/widgets/link.dart';
import 'package:provider/provider.dart';
class UserOrganizationItem extends StatelessWidget {
final String login;
final String avatarUrl;
final String url;
final String description;
UserOrganizationItem({
@required this.login,
@required this.avatarUrl,
@required this.url,
@required this.description,
});
@override
Widget build(BuildContext context) {
final theme = Provider.of<ThemeModel>(context);
return Link(
url: url,
child: Container(
padding: CommonStyle.padding,
child: Row(
children: <Widget>[
Avatar(url: avatarUrl, size: AvatarSize.large),
SizedBox(width: 10),
Expanded(
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Row(
children: <Widget>[
Text(
login,
style: TextStyle(
color: theme.palette.primary,
fontSize: 18,
fontWeight: FontWeight.w600,
),
),
],
),
SizedBox(height: 6),
Row(
children: <Widget>[
Expanded(
child: Text(
description,
style: TextStyle(
color: theme.palette.secondaryText,
fontSize: 16,
),
overflow: TextOverflow.visible,
),
)
],
),
],
),
)
],
),
),
);
}
}