【发布时间】:2022-01-07 09:03:08
【问题描述】:
我有一个BaseMessage 类,从中派生出几个不同的DerivedMessage 子类,并希望像这样发送它们:
class BaseMessage {
public:
virtual std::vector<uint8_t> data() const noexcept = 0;
virtual ~BaseMessage() = default;
[...]
}
class DerivedMessage : public BaseMessage {
public:
[...]
std::vector<uint8_t> data() const noexcept override { return m_data; }
private:
std::vector<uint8_t> m_data;
}
// simplified
class Tcp {
public
virtual void sendMessage(std::shared_ptr<BaseMessage> msg) { write(msg->data());}
[...]
};
class SomeClass {
public:
SomeClass(Tcp& tcp) : m_tcp(tcp) {}
void writeDataToRemote(std::shared_ptr<DerivedMessage> derived) const {
m_tcp.sendMessage(derived);
private:
Tcp m_tcp;
}
};
现在我想用 gtest 为 SomeClass 编写测试。
因此我模拟了TCP类的功能:
class MockTcp : public Tcp {
MOCK_METHOD(void, sendMessage, (std::shared_ptr<ralco::CommandMsg> msg), (override));
[...]
}
让我们假设一切都被简化到这里但可以工作。
所以在测试中,我想检查函数writeDataToRemote 中给sendMessage 的参数。
我在 StackOverflow 上阅读了有关 ::testing::SaveArg 和 ::testing::SaveArgPointee 的信息(但不在文档中)。
TEST(SomeClassTest, writesMessageToSocket){
MockTcp mockTcp;
SomeClass sc(mockTcp);
// >>>how to declare msgArg here?<<<
EXPECT_CALL(mockTcp, sendMessage(_)).Times(1).WillOnce(::testing::SaveArgPointee<0>(msgArg));
const auto derivedMsg = std::make_shared<DerivedMessage>();
sc.writeDataToRemote(derivedMsg);
// further inspection of msgArg follows
}
正如代码注释中所写,我不知道如何声明msgArg 变量,以便将其分配给sendMessage 的实际参数。使用SaveArg 时,我想我会得到一个悬空指针并按照上面的方法执行此操作会出错,因为无法复制分配消息。任何提示都表示赞赏。
【问题讨论】:
-
你已经有一个指向
derivedMsg的指针。SomeClass的实际实现是否会修改指针(即更改指向的对象)?还是只修改指向对象的内容,然后进一步传递给Tcp对象? -
在我的实际实现中,它更像是
SomeClass中的setter 函数。我传入一个值,创建一个DerivedMessage,修改数据并将其传递给sendMessage。只是想在这里简化我的示例。 -
我试图澄清一下,因为除非
SomeClass忽略它的输入并在将指针传递给Tcp之前重新分配指针(即derived = std::make_shared(something_new);),否则你已经有了测试中的指针-@987654343 @指向它。您无需将其保存在任何地方。您实际上可以验证这是否与传递给模拟 (EXPECT_CALL(mockTcp, sendMessage(derivedMsg));) 的指针相同,并且您可以检查derivedMsg的指向对象的属性。 -
很抱歉给您带来了困惑。也许我错误地过度简化了^^ 在我的真实场景中,我对传递给
sendMessage的消息一无所知,这就是为什么我需要将它分配给一个变量。实际上会是这样的 ` void writeDataToRemote(/* someDataVector*/ ) const { //construct derived // 将 someDataVector 设置为派生} ` 但这不是我的意思。
标签: c++ polymorphism smart-pointers gmock