Skip to content
This repository has been archived by the owner on Nov 20, 2024. It is now read-only.

Commit

Permalink
Merge #638
Browse files Browse the repository at this point in the history
638: feat: fixed for the issue (#637) r=myConsciousness a=myConsciousness

# 1. Description

<!-- Provide a description of what this PR is doing.
If you're modifying existing behavior, describe the existing behavior, how this PR is changing it,
and what motivated the change. If this is a breaking change, specify explicitly which APIs have been
changed. -->

## 1.1. Checklist

<!-- Before you create this PR confirm that it meets all requirements listed below by checking the
relevant checkboxes (`[x]`). This will ensure a smooth and quick review process. -->

- [x] The title of my PR starts with a [Conventional Commit] prefix (`fix:`, `feat:`, `docs:` etc).
- [x] I have read the [Contributor Guide] and followed the process outlined for submitting PRs.
- [x] I have updated/added tests for ALL new/updated/fixed functionality.
- [x] I have updated/added relevant documentation in `docs` and added dartdoc comments with `///`.
- [x] I have updated/added relevant examples in `examples`.

## 1.2. Breaking Change

<!-- Does your PR require users to manually update their apps to accommodate your change?

If the PR is a breaking change this should be indicated with suffix "!"  (for example, `feat!:`, `fix!:`). See [Conventional Commit] for details.
-->

- [ ] Yes, this is a breaking change.
- [x] No, this is _not_ a breaking change.

## 1.3. Related Issues

<!-- Provide a list of issues related to this PR from the [issue database].
Indicate which of these issues are resolved or fixed by this PR, i.e. Fixes #xxxx* !-->

<!-- Links -->

[issue database]: https://github.com/twitter-dart/twitter-api-v2/issues
[contributor guide]: https://github.com/twitter-dart/twitter-api-v2/blob/main/CONTRIBUTING.md
[style guide]: https://github.com/twitter-dart/twitter-api-v2/blob/main/STYLEGUIDE.md
[conventional commit]: https://conventionalcommits.org


Co-authored-by: myConsciousness <contact@shinyakato.dev>
  • Loading branch information
bors[bot] and myConsciousness authored Jan 24, 2023
2 parents 2f248ec + 09c8ea7 commit 6abe0a3
Show file tree
Hide file tree
Showing 29 changed files with 539 additions and 37 deletions.
12 changes: 12 additions & 0 deletions lib/src/core/client/stream_response.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,16 +2,28 @@
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided the conditions.

// 🌎 Project imports:
import '../../service/response/twitter_request.dart';
import '../https_status.dart';

class StreamResponse {
/// Returns the new instance of [StreamResponse].
const StreamResponse({
required this.headers,
required this.status,
required this.request,
required this.body,
});

/// The headers
final Map<String, String> headers;

/// The http status
final HttpStatus status;

/// The request that generated this response
final TwitterRequest request;

/// The body
final Stream<Map<String, dynamic>> body;
}
33 changes: 33 additions & 0 deletions lib/src/core/http_method.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
// Copyright 2023 Kato Shinya. All rights reserved.
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided the conditions.

enum HttpMethod {
/// `GET`
get('GET'),

/// `POST`
post('POST'),

/// `DELETE`
delete('DELETE'),

/// `PUT`
put('PUT');

/// The value.
final String value;

/// Returns the http method associated with [value].
static HttpMethod valueOf(final String value) {
for (final method in values) {
if (method.value == value) {
return method;
}
}

throw UnsupportedError('Unsupported value [$value].');
}

const HttpMethod(this.value);
}
153 changes: 153 additions & 0 deletions lib/src/core/https_status.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,153 @@
// Copyright 2023 Kato Shinya. All rights reserved.
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided the conditions.

enum HttpStatus {
/// The request has succeeded. The meaning of a success varies
/// depending on the HTTP method:
///
/// GET: The resource has been fetched and is transmitted in the message body.
/// HEAD: The entity headers are in the message body.
/// POST: The resource describing the result of the action is transmitted in
/// the message body.
///
/// TRACE: The message body contains the request message as received by the
/// server
///
/// https://tools.ietf.org/html/rfc7231#section-6.3.1
ok(200, 'OK'),

/// The request has succeeded and a new resource has been created
/// as a result of it. This is typically the response sent
/// after a PUT request.
///
/// https://tools.ietf.org/html/rfc7231#section-6.3.2
created(201, 'Created'),

/// There is no content to send for this request, but the headers
/// may be useful. The user-agent may update its cached headers
/// for this resource with the new ones.
///
/// https://tools.ietf.org/html/rfc7231#section-6.3.5
noContent(204, 'No Content'),

/// This response means that server could not understand
/// the request due to invalid syntax.
///
/// https://tools.ietf.org/html/rfc7231#section-6.5.1
badRequest(400, 'Bad Request'),

/// Although the HTTP standard specifies "unauthorized", semantically
/// this response means "unauthenticated". That is, the client must
/// authenticate itself to get the requested response.
///
/// https://tools.ietf.org/html/rfc7235#section-3.1
unauthorized(401, 'Unauthorized'),

/// The client does not have access rights to the content, i.e.
/// they are unauthorized, so server is rejecting to give proper response.
/// Unlike 401, the client's identity is known to the server.
///
/// https://tools.ietf.org/html/rfc7231#section-6.5.3
forbidden(403, 'Forbidden'),

/// The server can not find requested resource.
///
/// In the browser, this means the URL is not recognized.
/// In an API, this can also mean that the endpoint is valid but
/// the resource itself does not exist.
///
/// Servers may also send this response instead of 403 to hide
/// the existence of a resource from an unauthorized client.
///
/// This response code is probably the most famous one due to
/// its frequent occurrence on the web.
///
/// https://tools.ietf.org/html/rfc7231#section-6.5.4
notFound(404, 'Not Found'),

/// This response would be sent when the requested content has been
/// permanently deleted from server, with no forwarding address.
///
/// Clients are expected to remove their caches and links to the resource.
///
/// The HTTP specification intends this status code to be used for
/// "limited-time, promotional services".
///
/// APIs should not feel compelled to indicate resources that have been
/// deleted with this status code.
///
/// https://tools.ietf.org/html/rfc7231#section-6.5.9
gone(410, 'Gone'),

/// The request was well-formed but was unable to be followed
/// due to semantic errors.
///
/// https://tools.ietf.org/html/rfc2518#section-10.3
unprocessableEntity(422, 'Unprocessable Entity'),

/// The user has sent too many requests
/// in a given amount of time ("rate limiting").
///
/// https://tools.ietf.org/html/rfc6585#section-4
tooManyRequests(429, 'Too Many Requests'),

/// The server encountered an unexpected condition that prevented it
/// from fulfilling the request.
///
/// https://tools.ietf.org/html/rfc7231#section-6.6.1
internalServerError(500, 'Internal Server Error'),

/// The request method is not supported by the server and cannot be handled.
///
/// The only methods that servers are required to support (and therefore
/// that must not return this code) are GET and HEAD.
///
/// https://tools.ietf.org/html/rfc7231#section-6.6.2
notImplemented(501, 'Not Implemented'),

/// This error response means that the server, while working as a gateway
/// to get a response needed to handle the request, got an invalid response.
///
/// https://tools.ietf.org/html/rfc7231#section-6.6.3
badGateway(502, 'Bad Gateway'),

/// The server is not ready to handle the request.
///
/// Common causes are a server that is down for maintenance or that is
/// overloaded. Note that together with this response, a user-friendly page
/// explaining the problem should be sent.
///
/// This responses should be used for temporary conditions
/// and the Retry-After: HTTP header should, if possible, contain
/// the estimated time before the recovery of the service.
///
/// The webmaster must also take care about the caching-related headers
/// that are sent along with this response, as these temporary condition
/// responses should usually not be cached.
///
/// https://tools.ietf.org/html/rfc7231#section-6.6.4
serviceUnavailable(503, 'Service Unavailable');

/// The http status code.
final int code;

/// The http status message.
final String message;

/// Returns the http status of [code].
static HttpStatus valueOf(final int code) {
for (final status in values) {
if (status.code == code) {
return status;
}
}

throw UnsupportedError('Unsupported value [$code].');
}

/// Returns true if this [code] equals to passed [code], otherwise false.
bool equalsByCode(final int code) => this.code == code;

const HttpStatus(this.code, this.message);
}
8 changes: 8 additions & 0 deletions lib/src/core/service_helper.dart
Original file line number Diff line number Diff line change
Expand Up @@ -10,10 +10,13 @@ import 'package:http/http.dart' as http;
import 'package:http/http.dart';

// 🌎 Project imports:
import '../service/response/twitter_request.dart';
import 'client/client_context.dart';
import 'client/stream_request.dart';
import 'client/stream_response.dart';
import 'client/user_context.dart';
import 'http_method.dart';
import 'https_status.dart';
import 'serializable.dart';
import 'util/json_utils.dart';

Expand Down Expand Up @@ -118,6 +121,11 @@ class ServiceHelper implements Service {

return StreamResponse(
headers: streamedResponse.headers,
status: HttpStatus.valueOf(streamedResponse.statusCode),
request: TwitterRequest(
method: HttpMethod.valueOf(streamedResponse.request!.method),
url: streamedResponse.request!.url,
),
body: streamedResponse.stream.transform(converter.utf8.decoder).map(
(event) => validate != null
? validate(streamedResponse, event)
Expand Down
1 change: 1 addition & 0 deletions lib/src/service/base_media_service.dart
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,7 @@ abstract class BaseMediaService extends BaseService implements _MediaService {
}),
response.statusCode,
headers: response.headers,
request: response.request,
),
dataBuilder: dataBuilder,
);
Expand Down
Loading

0 comments on commit 6abe0a3

Please sign in to comment.