Skip to content

Commit ceb162a

Browse files
committed
urls [nfc]: Represent realm URL as Uri object, not String
1 parent 0b5aa67 commit ceb162a

File tree

11 files changed

+22
-23
lines changed

11 files changed

+22
-23
lines changed

lib/api/core.dart

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,9 @@ import 'package:http/http.dart' as http;
55

66
class Auth {
77
Auth({required this.realmUrl, required this.email, required this.apiKey})
8-
: assert(Uri.parse(realmUrl).query.isEmpty && Uri.parse(realmUrl).fragment.isEmpty);
8+
: assert(realmUrl.query.isEmpty && realmUrl.fragment.isEmpty);
99

10-
final String realmUrl;
10+
final Uri realmUrl;
1111
final String email;
1212
final String apiKey;
1313
}
@@ -70,8 +70,7 @@ class LiveApiConnection extends ApiConnection {
7070
@override
7171
Future<String> get(String route, Map<String, dynamic>? params) async {
7272
assert(_isOpen);
73-
final baseUrl = Uri.parse(auth.realmUrl);
74-
final url = baseUrl.replace(
73+
final url = auth.realmUrl.replace(
7574
path: "/api/v1/$route", queryParameters: encodeParameters(params));
7675
if (kDebugMode) print("GET $url");
7776
final response = await _client.get(url, headers: _headers());
@@ -85,7 +84,7 @@ class LiveApiConnection extends ApiConnection {
8584
Future<String> post(String route, Map<String, dynamic>? params) async {
8685
assert(_isOpen);
8786
final response = await _client.post(
88-
Uri.parse(auth.realmUrl).replace(path: "/api/v1/$route"),
87+
auth.realmUrl.replace(path: "/api/v1/$route"),
8988
headers: _headers(),
9089
body: encodeParameters(params));
9190
if (response.statusCode != 200) {

lib/api/route/account.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,13 +9,13 @@ part 'account.g.dart';
99

1010
/// https://zulip.com/api/fetch-api-key
1111
Future<FetchApiKeyResult> fetchApiKey({
12-
required String realmUrl,
12+
required Uri realmUrl,
1313
required String username,
1414
required String password,
1515
}) async {
1616
// TODO dedupe this part with LiveApiConnection; make this function testable
1717
final response = await http.post(
18-
Uri.parse(realmUrl).replace(path: "/api/v1/fetch_api_key"),
18+
realmUrl.replace(path: "/api/v1/fetch_api_key"),
1919
body: encodeParameters({
2020
'username': RawParameter(username),
2121
'password': RawParameter(password),

lib/api/route/messages.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ Future<SendMessageResult> sendMessage(
6969
}) async {
7070
// assert() is less verbose but would have no effect in production, I think:
7171
// https://dart.dev/guides/language/language-tour#assert
72-
if (Uri.parse(connection.auth.realmUrl).origin != 'https://chat.zulip.org') {
72+
if (connection.auth.realmUrl.origin != 'https://chat.zulip.org') {
7373
throw Exception('This binding can currently only be used on https://chat.zulip.org.');
7474
}
7575

lib/api/route/realm.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,11 +17,11 @@ part 'realm.g.dart';
1717
// See thread, and the zulip-mobile code and chat thread it links to:
1818
// https://github.com/zulip/zulip-flutter/pull/55#discussion_r1160267577
1919
Future<GetServerSettingsResult> getServerSettings({
20-
required String realmUrl,
20+
required Uri realmUrl,
2121
}) async {
2222
// TODO dedupe this part with LiveApiConnection; make this function testable
2323
final response = await http.get(
24-
Uri.parse(realmUrl).replace(path: "/api/v1/server_settings"));
24+
realmUrl.replace(path: "/api/v1/server_settings"));
2525
if (response.statusCode != 200) {
2626
throw Exception('error on GET server_settings: status ${response.statusCode}');
2727
}

lib/model/store.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -244,7 +244,7 @@ class LiveGlobalStore extends GlobalStore {
244244
/// See "Server credentials" in the project README for how to fill in the
245245
/// `credential_fixture.dart` file this requires.
246246
final Account _fixtureAccount = Account(
247-
realmUrl: credentials.realmUrl,
247+
realmUrl: Uri.parse(credentials.realmUrl),
248248
email: credentials.email,
249249
apiKey: credentials.apiKey,
250250
userId: credentials.userId,

lib/widgets/app.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ class ChooseAccountPage extends StatelessWidget {
6565
for (final (:accountId, :account) in globalStore.accountEntries)
6666
_buildAccountItem(context,
6767
accountId: accountId,
68-
title: Text(account.realmUrl),
68+
title: Text(account.realmUrl.toString()),
6969
subtitle: Text(account.email)),
7070
const SizedBox(height: 12),
7171
ElevatedButton(
@@ -103,7 +103,7 @@ class HomePage extends StatelessWidget {
103103
const SizedBox(height: 12),
104104
Text.rich(TextSpan(
105105
text: 'Connected to: ',
106-
children: [bold(store.account.realmUrl)])),
106+
children: [bold(store.account.realmUrl.toString())])),
107107
Text.rich(TextSpan(
108108
text: 'Zulip server version: ',
109109
children: [bold(store.zulipVersion)])),

lib/widgets/content.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -591,7 +591,7 @@ class RealmContentNetworkImage extends StatelessWidget {
591591
isAntiAlias: isAntiAlias,
592592

593593
// Only send the auth header to the server `auth` belongs to.
594-
headers: parsedSrc.origin == Uri.parse(auth.realmUrl).origin
594+
headers: parsedSrc.origin == auth.realmUrl.origin
595595
? authHeader(auth)
596596
: null,
597597

@@ -609,7 +609,7 @@ class RealmContentNetworkImage extends StatelessWidget {
609609
// This may dissolve when we start passing around URLs as [Uri] objects instead
610610
// of strings.
611611
String resolveUrl(String url, Account account) {
612-
final realmUrl = Uri.parse(account.realmUrl); // TODO clean this up
612+
final realmUrl = account.realmUrl;
613613
final resolved = realmUrl.resolve(url); // TODO handle if fails to parse
614614
return resolved.toString();
615615
}

lib/widgets/login.dart

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ class _AddAccountPageState extends State<AddAccountPage> {
4747
}
4848

4949
// TODO(#35): show feedback that we're working, while fetching server settings
50-
final serverSettings = await getServerSettings(realmUrl: url.toString());
50+
final serverSettings = await getServerSettings(realmUrl: url);
5151
if (context.mounted) {} // https://github.com/dart-lang/linter/issues/4007
5252
else {
5353
return;
@@ -105,7 +105,7 @@ class _EmailPasswordLoginPageState extends State<EmailPasswordLoginPage> {
105105
Future<int> _getUserId(FetchApiKeyResult fetchApiKeyResult) async {
106106
final FetchApiKeyResult(:email, :apiKey) = fetchApiKeyResult;
107107
final auth = Auth(
108-
realmUrl: widget.realmUrl.toString(), email: email, apiKey: apiKey);
108+
realmUrl: widget.realmUrl, email: email, apiKey: apiKey);
109109
final connection = LiveApiConnection(auth: auth); // TODO make this widget testable
110110
return (await getOwnUser(connection)).userId;
111111
}
@@ -124,7 +124,7 @@ class _EmailPasswordLoginPageState extends State<EmailPasswordLoginPage> {
124124
final FetchApiKeyResult result;
125125
try {
126126
result = await fetchApiKey(
127-
realmUrl: realmUrl.toString(), username: email, password: password);
127+
realmUrl: realmUrl, username: email, password: password);
128128
} on Exception catch (e) { // TODO(#37): distinguish API exceptions
129129
// TODO(#35): give feedback to user on failed login
130130
debugPrint(e.toString());
@@ -139,7 +139,7 @@ class _EmailPasswordLoginPageState extends State<EmailPasswordLoginPage> {
139139
}
140140

141141
final account = Account(
142-
realmUrl: realmUrl.toString(),
142+
realmUrl: realmUrl,
143143
email: result.email,
144144
apiKey: result.apiKey,
145145
userId: userId,

test/api/fake_api.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ import 'package:zulip/model/store.dart';
33

44
/// An [ApiConnection] that accepts and replays canned responses, for testing.
55
class FakeApiConnection extends ApiConnection {
6-
FakeApiConnection({required String realmUrl, required String email})
6+
FakeApiConnection({required Uri realmUrl, required String email})
77
: super(auth: Auth(
88
realmUrl: realmUrl, email: email, apiKey: _fakeApiKey));
99

test/api/route/messages_test.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,15 +10,15 @@ import 'route_checks.dart';
1010
void main() {
1111
test('sendMessage accepts fixture realm', () async {
1212
final connection = FakeApiConnection(
13-
realmUrl: 'https://chat.zulip.org/', email: '[email protected]');
13+
realmUrl: Uri.parse('https://chat.zulip.org/'), email: '[email protected]');
1414
connection.prepare(jsonEncode(SendMessageResult(id: 42).toJson()));
1515
check(sendMessage(connection, content: 'hello', topic: 'world'))
1616
.completes(it()..id.equals(42));
1717
});
1818

1919
test('sendMessage rejects unexpected realm', () async {
2020
final connection = FakeApiConnection(
21-
realmUrl: 'https://chat.example/', email: '[email protected]');
21+
realmUrl: Uri.parse('https://chat.example/'), email: '[email protected]');
2222
connection.prepare(jsonEncode(SendMessageResult(id: 42).toJson()));
2323
check(sendMessage(connection, content: 'hello', topic: 'world'))
2424
.throws();

0 commit comments

Comments
 (0)