Skip to content

Commit ed0a754

Browse files
authored
Merge pull request #285 from wravery/improve-awaitable-errors
Improve awaitable errors
2 parents 31b3312 + f170836 commit ed0a754

File tree

7 files changed

+135
-47
lines changed

7 files changed

+135
-47
lines changed

samples/proxy/client.cpp

Lines changed: 75 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@ class Query
5151
explicit Query(std::string_view host, std::string_view port, std::string_view target,
5252
int version) noexcept;
5353

54-
std::future<std::string> getRelay(std::string&& queryArg,
54+
std::future<std::optional<std::string>> getRelay(std::string&& queryArg,
5555
std::optional<std::string>&& operationNameArg,
5656
std::optional<std::string>&& variablesArg) const;
5757

@@ -73,7 +73,7 @@ Query::Query(
7373

7474
// Based on:
7575
// https://www.boost.org/doc/libs/1_82_0/libs/beast/example/http/client/awaitable/http_client_awaitable.cpp
76-
std::future<std::string> Query::getRelay(std::string&& queryArg,
76+
std::future<std::optional<std::string>> Query::getRelay(std::string&& queryArg,
7777
std::optional<std::string>&& operationNameArg, std::optional<std::string>&& variablesArg) const
7878
{
7979
response::Value payload { response::Type::Map };
@@ -99,7 +99,7 @@ std::future<std::string> Query::getRelay(std::string&& queryArg,
9999
const char* port,
100100
const char* target,
101101
int version,
102-
std::string requestBody) -> net::awaitable<std::string> {
102+
std::string requestBody) -> net::awaitable<std::optional<std::string>> {
103103
// These objects perform our I/O. They use an executor with a default completion token
104104
// of use_awaitable. This makes our code easy, but will use exceptions as the default
105105
// error handling, i.e. if the connection drops, we might see an exception.
@@ -150,7 +150,7 @@ std::future<std::string> Query::getRelay(std::string&& queryArg,
150150
throw boost::system::system_error(ec, "shutdown");
151151
}
152152

153-
co_return std::string { std::move(res.body()) };
153+
co_return std::make_optional<std::string>(std::move(res.body()));
154154
}(m_host.c_str(), m_port.c_str(), m_target.c_str(), m_version, std::move(requestBody)),
155155
net::use_future);
156156

@@ -182,8 +182,78 @@ int main(int argc, char** argv)
182182
auto serviceResponse = client::parseServiceResponse(
183183
service->resolve({ query, GetOperationName(), std::move(variables), launch }).get());
184184
auto result = client::query::relayQuery::parseResponse(std::move(serviceResponse.data));
185+
auto errors = std::move(serviceResponse.errors);
185186

186-
std::cout << result.relay << std::endl;
187+
if (result.relay)
188+
{
189+
std::cout << *result.relay << std::endl;
190+
}
191+
192+
if (!errors.empty())
193+
{
194+
std::cerr << "Errors executing query:" << std::endl << GetRequestText() << std::endl;
195+
196+
for (const auto& error : errors)
197+
{
198+
std::cerr << "Error: " << error.message;
199+
200+
if (!error.locations.empty())
201+
{
202+
bool firstLocation = true;
203+
204+
std::cerr << ", Locations: [";
205+
206+
for (const auto& location : error.locations)
207+
{
208+
if (!firstLocation)
209+
{
210+
std::cerr << ", ";
211+
}
212+
213+
firstLocation = false;
214+
215+
std::cerr << "(line: " << location.line << ", column: " << location.column
216+
<< ")";
217+
}
218+
219+
std::cerr << "]";
220+
}
221+
222+
if (!error.path.empty())
223+
{
224+
bool firstSegment = true;
225+
226+
std::cerr << ", Path: ";
227+
228+
for (const auto& segment : error.path)
229+
{
230+
std::visit(
231+
[firstSegment](const auto& value) noexcept {
232+
using _Type = std::decay_t<decltype(value)>;
233+
234+
if constexpr (std::is_same_v<std::string, _Type>)
235+
{
236+
if (!firstSegment)
237+
{
238+
std::cerr << "/";
239+
}
240+
241+
std::cerr << value;
242+
}
243+
else if constexpr (std::is_same_v<int, _Type>)
244+
{
245+
std::cerr << "[" << value << "]";
246+
}
247+
},
248+
segment);
249+
250+
firstSegment = false;
251+
}
252+
}
253+
254+
std::cerr << std::endl;
255+
}
256+
}
187257
}
188258
catch (const std::runtime_error& ex)
189259
{

samples/proxy/query/ProxyClient.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ Response parseResponse(response::Value&& response)
8383
{
8484
if (member.first == R"js(relay)js"sv)
8585
{
86-
result.relay = ModifiedResponse<std::string>::parse(std::move(member.second));
86+
result.relay = ModifiedResponse<std::string>::parse<TypeModifier::Nullable>(std::move(member.second));
8787
continue;
8888
}
8989
}

samples/proxy/query/ProxyClient.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ struct [[nodiscard]] Variables
6464

6565
struct [[nodiscard]] Response
6666
{
67-
std::string relay {};
67+
std::optional<std::string> relay {};
6868
};
6969

7070
[[nodiscard]] Response parseResponse(response::Value&& response);

samples/proxy/schema/QueryObject.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ service::AwaitableResolver Query::resolveRelay(service::ResolverParams&& params)
6565
auto result = _pimpl->getRelay(service::FieldParams(service::SelectionSetParams{ params }, std::move(directives)), std::move(argQuery), std::move(argOperationName), std::move(argVariables));
6666
resolverLock.unlock();
6767

68-
return service::ModifiedResult<std::string>::convert(std::move(result), std::move(params));
68+
return service::ModifiedResult<std::string>::convert<service::TypeModifier::Nullable>(std::move(result), std::move(params));
6969
}
7070

7171
service::AwaitableResolver Query::resolve_typename(service::ResolverParams&& params) const
@@ -92,7 +92,7 @@ service::AwaitableResolver Query::resolve_type(service::ResolverParams&& params)
9292
void AddQueryDetails(const std::shared_ptr<schema::ObjectType>& typeQuery, const std::shared_ptr<schema::Schema>& schema)
9393
{
9494
typeQuery->AddFields({
95-
schema::Field::Make(R"gql(relay)gql"sv, R"md()md"sv, std::nullopt, schema->WrapType(introspection::TypeKind::NON_NULL, schema->LookupType(R"gql(String)gql"sv)), {
95+
schema::Field::Make(R"gql(relay)gql"sv, R"md()md"sv, std::nullopt, schema->LookupType(R"gql(String)gql"sv), {
9696
schema::InputValue::Make(R"gql(query)gql"sv, R"md()md"sv, schema->WrapType(introspection::TypeKind::NON_NULL, schema->LookupType(R"gql(String)gql"sv)), R"gql()gql"sv),
9797
schema::InputValue::Make(R"gql(operationName)gql"sv, R"md()md"sv, schema->LookupType(R"gql(String)gql"sv), R"gql()gql"sv),
9898
schema::InputValue::Make(R"gql(variables)gql"sv, R"md()md"sv, schema->LookupType(R"gql(String)gql"sv), R"gql()gql"sv)

samples/proxy/schema/QueryObject.h

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -16,13 +16,13 @@ namespace methods::QueryHas {
1616
template <class TImpl>
1717
concept getRelayWithParams = requires (TImpl impl, service::FieldParams params, std::string queryArg, std::optional<std::string> operationNameArg, std::optional<std::string> variablesArg)
1818
{
19-
{ service::AwaitableScalar<std::string> { impl.getRelay(std::move(params), std::move(queryArg), std::move(operationNameArg), std::move(variablesArg)) } };
19+
{ service::AwaitableScalar<std::optional<std::string>> { impl.getRelay(std::move(params), std::move(queryArg), std::move(operationNameArg), std::move(variablesArg)) } };
2020
};
2121

2222
template <class TImpl>
2323
concept getRelay = requires (TImpl impl, std::string queryArg, std::optional<std::string> operationNameArg, std::optional<std::string> variablesArg)
2424
{
25-
{ service::AwaitableScalar<std::string> { impl.getRelay(std::move(queryArg), std::move(operationNameArg), std::move(variablesArg)) } };
25+
{ service::AwaitableScalar<std::optional<std::string>> { impl.getRelay(std::move(queryArg), std::move(operationNameArg), std::move(variablesArg)) } };
2626
};
2727

2828
template <class TImpl>
@@ -58,7 +58,7 @@ class [[nodiscard]] Query final
5858
virtual void beginSelectionSet(const service::SelectionSetParams& params) const = 0;
5959
virtual void endSelectionSet(const service::SelectionSetParams& params) const = 0;
6060

61-
[[nodiscard]] virtual service::AwaitableScalar<std::string> getRelay(service::FieldParams&& params, std::string&& queryArg, std::optional<std::string>&& operationNameArg, std::optional<std::string>&& variablesArg) const = 0;
61+
[[nodiscard]] virtual service::AwaitableScalar<std::optional<std::string>> getRelay(service::FieldParams&& params, std::string&& queryArg, std::optional<std::string>&& operationNameArg, std::optional<std::string>&& variablesArg) const = 0;
6262
};
6363

6464
template <class T>
@@ -70,7 +70,7 @@ class [[nodiscard]] Query final
7070
{
7171
}
7272

73-
[[nodiscard]] service::AwaitableScalar<std::string> getRelay(service::FieldParams&& params, std::string&& queryArg, std::optional<std::string>&& operationNameArg, std::optional<std::string>&& variablesArg) const final
73+
[[nodiscard]] service::AwaitableScalar<std::optional<std::string>> getRelay(service::FieldParams&& params, std::string&& queryArg, std::optional<std::string>&& operationNameArg, std::optional<std::string>&& variablesArg) const final
7474
{
7575
if constexpr (methods::QueryHas::getRelayWithParams<T>)
7676
{

samples/proxy/schema/schema.graphql

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,5 +2,5 @@
22
# Licensed under the MIT License.
33

44
type Query {
5-
relay(query: String!, operationName: String, variables: String): String!
5+
relay(query: String!, operationName: String, variables: String): String
66
}

0 commit comments

Comments
 (0)