Skip to content

[lldb-dap] Splitting ProtocolTypesTest into parts. #144595

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 3 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 1 addition & 2 deletions lldb/tools/lldb-dap/DAPError.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,7 @@ namespace lldb_dap {
char DAPError::ID;

DAPError::DAPError(std::string message, std::error_code EC, bool show_user,
std::optional<std::string> url,
std::optional<std::string> url_label)
std::string url, std::string url_label)
: m_message(message), m_ec(EC), m_show_user(show_user), m_url(url),
m_url_label(url_label) {}

Expand Down
12 changes: 6 additions & 6 deletions lldb/tools/lldb-dap/DAPError.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,23 +21,23 @@ class DAPError : public llvm::ErrorInfo<DAPError> {

DAPError(std::string message,
std::error_code EC = llvm::inconvertibleErrorCode(),
bool show_user = true, std::optional<std::string> url = std::nullopt,
std::optional<std::string> url_label = std::nullopt);
bool show_user = true, std::string url = "",
std::string url_label = "");

void log(llvm::raw_ostream &OS) const override;
std::error_code convertToErrorCode() const override;

const std::string &getMessage() const { return m_message; }
bool getShowUser() const { return m_show_user; }
const std::optional<std::string> &getURL() const { return m_url; }
const std::optional<std::string> &getURLLabel() const { return m_url; }
const std::string &getURL() const { return m_url; }
const std::string &getURLLabel() const { return m_url; }

private:
std::string m_message;
std::error_code m_ec;
bool m_show_user;
std::optional<std::string> m_url;
std::optional<std::string> m_url_label;
std::string m_url;
std::string m_url_label;
};

/// An error that indicates the current request handler cannot execute because
Expand Down
16 changes: 8 additions & 8 deletions lldb/tools/lldb-dap/Protocol/ProtocolBase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -180,19 +180,19 @@ bool fromJSON(json::Value const &Params, Response &R, json::Path P) {
json::Value toJSON(const ErrorMessage &EM) {
json::Object Result{{"id", EM.id}, {"format", EM.format}};

if (EM.variables) {
if (!EM.variables.empty()) {
json::Object variables;
for (auto &var : *EM.variables)
for (auto &var : EM.variables)
variables[var.first] = var.second;
Result.insert({"variables", std::move(variables)});
}
if (EM.sendTelemetry)
Result.insert({"sendTelemetry", EM.sendTelemetry});
if (EM.showUser)
Result.insert({"showUser", EM.showUser});
if (EM.url)
if (!EM.url.empty())
Result.insert({"url", EM.url});
if (EM.urlLabel)
if (!EM.urlLabel.empty())
Result.insert({"urlLabel", EM.urlLabel});

return std::move(Result);
Expand All @@ -201,10 +201,10 @@ json::Value toJSON(const ErrorMessage &EM) {
bool fromJSON(json::Value const &Params, ErrorMessage &EM, json::Path P) {
json::ObjectMapper O(Params, P);
return O && O.map("id", EM.id) && O.map("format", EM.format) &&
O.map("variables", EM.variables) &&
O.map("sendTelemetry", EM.sendTelemetry) &&
O.map("showUser", EM.showUser) && O.map("url", EM.url) &&
O.map("urlLabel", EM.urlLabel);
O.mapOptional("variables", EM.variables) &&
O.mapOptional("sendTelemetry", EM.sendTelemetry) &&
O.mapOptional("showUser", EM.showUser) &&
O.mapOptional("url", EM.url) && O.mapOptional("urlLabel", EM.urlLabel);
}

json::Value toJSON(const Event &E) {
Expand Down
6 changes: 3 additions & 3 deletions lldb/tools/lldb-dap/Protocol/ProtocolBase.h
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,7 @@ struct ErrorMessage {

/// An object used as a dictionary for looking up the variables in the format
/// string.
std::optional<std::map<std::string, std::string>> variables;
std::map<std::string, std::string> variables;

/// If true send to telemetry.
bool sendTelemetry = false;
Expand All @@ -128,10 +128,10 @@ struct ErrorMessage {
bool showUser = false;

/// A url where additional information about this message can be found.
std::optional<std::string> url;
std::string url;

/// A label that is presented to the user as the UI for opening the url.
std::optional<std::string> urlLabel;
std::string urlLabel;
};
bool fromJSON(const llvm::json::Value &, ErrorMessage &, llvm::json::Path);
llvm::json::Value toJSON(const ErrorMessage &);
Expand Down
3 changes: 3 additions & 0 deletions lldb/unittests/DAP/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,9 @@ add_lldb_unittest(DAPTests
Handler/ContinueTest.cpp
JSONUtilsTest.cpp
LLDBUtilsTest.cpp
ProtocolBaseTest.cpp
ProtocolEventsTest.cpp
ProtocolRequestsTest.cpp
ProtocolTypesTest.cpp
TestBase.cpp
VariablesTest.cpp
Expand Down
130 changes: 130 additions & 0 deletions lldb/unittests/DAP/ProtocolBaseTest.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,130 @@
//===-- ProtocolBaseTest.cpp ----------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "Protocol/ProtocolBase.h"
#include "TestingSupport/TestUtilities.h"
#include "llvm/Testing/Support/Error.h"
#include "gtest/gtest.h"

using namespace llvm;
using namespace lldb_dap;
using namespace lldb_dap::protocol;
using lldb_private::pp;
using llvm::json::parse;
using llvm::json::Value;

TEST(ProtocolBaseTest, Request) {
// Validate toJSON
EXPECT_EQ(pp(Request{/*seq=*/42, /*command=*/"hello_world",
/*arguments=*/std::nullopt}),
R"({
"command": "hello_world",
"seq": 42,
"type": "request"
})");

// Validate fromJSON
EXPECT_THAT_EXPECTED(
parse<Request>(R"({"type":"request","seq":42,"command":"hello_world"})"),
HasValue(Value(Request{/*seq=*/42, /*command=*/"hello_world",
/*arguments*/ std::nullopt})));

// Validate parsing errors
EXPECT_THAT_EXPECTED(parse<Request>(R"({})"),
FailedWithMessage("missing value at (root).type"));
EXPECT_THAT_EXPECTED(parse<Request>(R"({"type":"request"})"),
FailedWithMessage("missing value at (root).command"));
}

TEST(ProtocolBaseTest, Response) {
// Validate toJSON
EXPECT_EQ(pp(Response{/*request_seq=*/42, /*command=*/"hello_world",
/*success=*/true,
/*message=*/std::nullopt, /*body=*/std::nullopt}),
R"({
"command": "hello_world",
"request_seq": 42,
"seq": 0,
"success": true,
"type": "response"
})");

// Validate fromJSON
EXPECT_THAT_EXPECTED(
parse<Response>(
R"({"type":"response","seq":0,"request_seq":42,"command":"hello_world","success":true})"),
HasValue(
Value(Response{/*seq=*/42, /*command=*/"hello_world",
/*success=*/true,
/*message*/ std::nullopt, /*body=*/std::nullopt})));

// Validate parsing errors
EXPECT_THAT_EXPECTED(parse<Response>(R"({})"),
FailedWithMessage("missing value at (root).type"));
EXPECT_THAT_EXPECTED(parse<Response>(R"({"type":"response"})"),
FailedWithMessage("missing value at (root).seq"));
}

TEST(ProtocolBaseTest, Event) {
// Validate toJSON
EXPECT_EQ(pp(Event{/*event=*/"hello_world", /*body=*/std::nullopt}),
R"({
"event": "hello_world",
"seq": 0,
"type": "event"
})");

// Validate fromJSON
EXPECT_THAT_EXPECTED(
parse<Event>(R"({"type":"event","seq":0,"event":"hello_world"})"),
HasValue(Value(Event{/*command=*/"hello_world", /*body=*/std::nullopt})));

// Validate parsing errors
EXPECT_THAT_EXPECTED(parse<Response>(R"({})"),
FailedWithMessage("missing value at (root).type"));
}

TEST(ProtocolBaseTest, ErrorMessage) {
// Validate toJSON
EXPECT_EQ(pp(ErrorMessage{/*id=*/42,
/*format=*/"Hello world!",
/*variables=*/{{"name", "value"}},
/*sendTelemetry=*/true,
/*showUser=*/true,
/*url=*/"http://example.com/error/42",
/*urlLabel*/ "ErrorLabel"}),
R"({
"format": "Hello world!",
"id": 42,
"sendTelemetry": true,
"showUser": true,
"url": "http://example.com/error/42",
"urlLabel": "ErrorLabel",
"variables": {
"name": "value"
}
})");

// Validate fromJSON
EXPECT_THAT_EXPECTED(
parse<ErrorMessage>(
R"({"format":"Hello world!","id":42,"sendTelemetry":true,"showUser":true,"url":"http://example.com/error/42","urlLabel":"ErrorLabel","variables":{"name": "value"}})"),
HasValue(Value(ErrorMessage{/*id=*/42,
/*format=*/"Hello world!",
/*variables=*/{{"name", "value"}},
/*sendTelemetry=*/true,
/*showUser=*/true,
/*url=*/"http://example.com/error/42",
/*urlLabel*/ "ErrorLabel"})));

// Validate parsing errors
EXPECT_THAT_EXPECTED(parse<ErrorMessage>(R"({})"),
FailedWithMessage("missing value at (root).id"));
EXPECT_THAT_EXPECTED(parse<ErrorMessage>(R"({"id":42})"),
FailedWithMessage("missing value at (root).format"));
}
35 changes: 35 additions & 0 deletions lldb/unittests/DAP/ProtocolEventsTest.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
//===-- ProtocolEventsTest.cpp --------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "Protocol/ProtocolEvents.h"
#include "Protocol/ProtocolTypes.h"
#include "TestingSupport/TestUtilities.h"
#include "llvm/ADT/StringRef.h"
#include "gtest/gtest.h"

using namespace llvm;
using namespace lldb_dap::protocol;
using lldb_private::pp;

TEST(ProtocolEventsTest, CapabilitiesEventBody) {
Capabilities capabilities;
capabilities.supportedFeatures = {
eAdapterFeatureANSIStyling,
eAdapterFeatureBreakpointLocationsRequest,
};
CapabilitiesEventBody body;
body.capabilities = capabilities;
StringRef json = R"({
"capabilities": {
"supportsANSIStyling": true,
"supportsBreakpointLocationsRequest": true
}
})";
// Validate toJSON
EXPECT_EQ(json, pp(body));
}
80 changes: 80 additions & 0 deletions lldb/unittests/DAP/ProtocolRequestsTest.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
//===-- ProtocolRequestsTest.cpp ------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "Protocol/ProtocolRequests.h"
#include "Protocol/ProtocolTypes.h"
#include "TestingSupport/TestUtilities.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/Testing/Support/Error.h"
#include "gmock/gmock.h"
#include "gtest/gtest.h"
#include <optional>

using namespace llvm;
using namespace lldb_dap::protocol;
using lldb_private::pp;
using llvm::json::parse;

TEST(ProtocolRequestsTest, ThreadResponseBody) {
const ThreadsResponseBody body{{{1, "thr1"}, {2, "thr2"}}};
const StringRef json = R"({
"threads": [
{
"id": 1,
"name": "thr1"
},
{
"id": 2,
"name": "thr2"
}
]
})";
// Validate toJSON
EXPECT_EQ(json, pp(body));
}

TEST(ProtocolRequestsTest, SetExceptionBreakpointsArguments) {
EXPECT_THAT_EXPECTED(
parse<SetExceptionBreakpointsArguments>(R"({"filters":[]})"),
HasValue(testing::FieldsAre(/*filters=*/testing::IsEmpty(),
/*filterOptions=*/testing::IsEmpty())));
EXPECT_THAT_EXPECTED(
parse<SetExceptionBreakpointsArguments>(R"({"filters":["abc"]})"),
HasValue(testing::FieldsAre(/*filters=*/std::vector<std::string>{"abc"},
/*filterOptions=*/testing::IsEmpty())));
EXPECT_THAT_EXPECTED(
parse<SetExceptionBreakpointsArguments>(
R"({"filters":[],"filterOptions":[{"filterId":"abc"}]})"),
HasValue(testing::FieldsAre(
/*filters=*/testing::IsEmpty(),
/*filterOptions=*/testing::Contains(testing::FieldsAre(
/*filterId=*/"abc", /*condition=*/"", /*mode=*/"")))));

// Validate parse errors
EXPECT_THAT_EXPECTED(parse<SetExceptionBreakpointsArguments>(R"({})"),
FailedWithMessage("missing value at (root).filters"));
EXPECT_THAT_EXPECTED(
parse<SetExceptionBreakpointsArguments>(R"({"filters":false})"),
FailedWithMessage("expected array at (root).filters"));
}

TEST(ProtocolRequestsTest, SetExceptionBreakpointsResponseBody) {
SetExceptionBreakpointsResponseBody body;
Breakpoint bp;
bp.id = 12, bp.verified = true;
body.breakpoints = {bp};
EXPECT_EQ(R"({
"breakpoints": [
{
"id": 12,
"verified": true
}
]
})",
pp(body));
}
Loading
Loading