blob: e57d71ed95db5aeef56fce272d0add81aa836b34 [file] [log] [blame]
Shuo Chenca329182014-03-19 18:05:18 -07001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
Davide Pesavento49f3a5f2017-09-23 01:36:33 -04002/*
Davide Pesavento9a8d7d82019-03-15 20:14:25 -04003 * Copyright (c) 2014-2019, Regents of the University of California.
Shuo Chenca329182014-03-19 18:05:18 -07004 *
5 * This file is part of NDN repo-ng (Next generation of NDN repository).
6 * See AUTHORS.md for complete list of repo-ng authors and contributors.
7 *
8 * repo-ng is free software: you can redistribute it and/or modify it under the terms
9 * of the GNU General Public License as published by the Free Software Foundation,
10 * either version 3 of the License, or (at your option) any later version.
11 *
12 * repo-ng is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
13 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
14 * PURPOSE. See the GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * repo-ng, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
18 */
19
Shuo Chenca329182014-03-19 18:05:18 -070020#include "handles/delete-handle.hpp"
weijia yuan82cf9142018-10-21 12:25:02 -070021#include "handles/write-handle.hpp"
22
Weiqi Shif0330d52014-07-09 10:54:27 -070023#include "storage/repo-storage.hpp"
weijia yuan82cf9142018-10-21 12:25:02 -070024#include "storage/sqlite-storage.hpp"
Shuo Chenca329182014-03-19 18:05:18 -070025
Junxiao Shi047a6fb2017-06-08 16:16:05 +000026#include "command-fixture.hpp"
Weiqi Shif0330d52014-07-09 10:54:27 -070027#include "../repo-storage-fixture.hpp"
Shuo Chenca329182014-03-19 18:05:18 -070028#include "../dataset-fixtures.hpp"
29
weijia yuan82cf9142018-10-21 12:25:02 -070030#include <ndn-cxx/security/command-interest-signer.hpp>
31#include <ndn-cxx/security/signing-helpers.hpp>
Shuo Chen028dcd32014-06-21 16:36:44 +080032#include <ndn-cxx/util/random.hpp>
weijia yuan82cf9142018-10-21 12:25:02 -070033#include <ndn-cxx/util/time.hpp>
Davide Pesavento49f3a5f2017-09-23 01:36:33 -040034
weijia yuan82cf9142018-10-21 12:25:02 -070035#include <boost/asio/io_service.hpp>
Davide Pesavento49f3a5f2017-09-23 01:36:33 -040036#include <boost/mpl/vector.hpp>
Shuo Chenca329182014-03-19 18:05:18 -070037#include <boost/test/unit_test.hpp>
38
39namespace repo {
40namespace tests {
41
42using ndn::time::milliseconds;
weijia yuan3aa8d2b2018-03-06 15:35:57 -080043
Davide Pesavento49f3a5f2017-09-23 01:36:33 -040044// All the test cases in this test suite should be run at once.
Shuo Chenca329182014-03-19 18:05:18 -070045BOOST_AUTO_TEST_SUITE(TestBasicCommandInsertDelete)
46
47const static uint8_t content[8] = {3, 1, 4, 1, 5, 9, 2, 6};
48
49template<class Dataset>
Junxiao Shi047a6fb2017-06-08 16:16:05 +000050class Fixture : public CommandFixture, public RepoStorageFixture, public Dataset
Shuo Chenca329182014-03-19 18:05:18 -070051{
52public:
53 Fixture()
weijia yuan82cf9142018-10-21 12:25:02 -070054 : writeHandle(repoFace, *handle, dispatcher, scheduler, validator)
55 , deleteHandle(repoFace, *handle, dispatcher, scheduler, validator)
Shuo Chenca329182014-03-19 18:05:18 -070056 , insertFace(repoFace.getIoService())
57 , deleteFace(repoFace.getIoService())
weijia yuan3aa8d2b2018-03-06 15:35:57 -080058 , signer(keyChain)
Shuo Chenca329182014-03-19 18:05:18 -070059 {
Junxiao Shi2b7b8312017-06-16 03:43:24 +000060 Name cmdPrefix("/repo/command");
61 repoFace.registerPrefix(cmdPrefix, nullptr,
62 [] (const Name& cmdPrefix, const std::string& reason) {
63 BOOST_FAIL("Command prefix registration error: " << reason);
64 });
Shuo Chenca329182014-03-19 18:05:18 -070065 }
66
Shuo Chen028dcd32014-06-21 16:36:44 +080067 void
Shuo Chenca329182014-03-19 18:05:18 -070068 scheduleInsertEvent();
69
70 void
71 scheduleDeleteEvent();
72
73 void
74 onInsertInterest(const Interest& interest);
75
76 void
77 onRegisterFailed(const std::string& reason);
78
79 void
80 delayedInterest();
81
82 void
Alexander Afanasyev42290b22017-03-09 12:58:29 -080083 onInsertData(const Interest& interest, const Data& data);
Shuo Chenca329182014-03-19 18:05:18 -070084
85 void
Alexander Afanasyev42290b22017-03-09 12:58:29 -080086 onDeleteData(const Interest& interest, const Data& data);
Shuo Chenca329182014-03-19 18:05:18 -070087
88 void
89 onInsertTimeout(const Interest& interest);
90
91 void
92 onDeleteTimeout(const Interest& interest);
93
94 void
95 sendInsertInterest(const Interest& interest);
96
97 void
98 sendDeleteInterest(const Interest& deleteInterest);
99
100 void
Shuo Chen028dcd32014-06-21 16:36:44 +0800101 checkInsertOk(const Interest& interest);
Shuo Chenca329182014-03-19 18:05:18 -0700102
103 void
Shuo Chen028dcd32014-06-21 16:36:44 +0800104 checkDeleteOk(const Interest& interest);
Shuo Chenca329182014-03-19 18:05:18 -0700105
106public:
Shuo Chenca329182014-03-19 18:05:18 -0700107 WriteHandle writeHandle;
108 DeleteHandle deleteHandle;
109 Face insertFace;
110 Face deleteFace;
Davide Pesavento9a8d7d82019-03-15 20:14:25 -0400111 std::map<Name, ndn::scheduler::EventId> insertEvents;
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800112 std::map<Name, Name> deleteNamePairs;
113 ndn::security::CommandInterestSigner signer;
Shuo Chenca329182014-03-19 18:05:18 -0700114};
115
116template<class T> void
117Fixture<T>::onInsertInterest(const Interest& interest)
118{
119 Data data(Name(interest.getName()));
120 data.setContent(content, sizeof(content));
weijia yuan82cf9142018-10-21 12:25:02 -0700121 data.setFreshnessPeriod(0_ms);
Junxiao Shi047a6fb2017-06-08 16:16:05 +0000122 keyChain.sign(data);
Shuo Chenca329182014-03-19 18:05:18 -0700123 insertFace.put(data);
Davide Pesavento9a8d7d82019-03-15 20:14:25 -0400124 auto eventIt = insertEvents.find(interest.getName());
125 if (eventIt != insertEvents.end()) {
126 eventIt->second.cancel();
127 insertEvents.erase(eventIt);
Shuo Chenca329182014-03-19 18:05:18 -0700128 }
Shuo Chen028dcd32014-06-21 16:36:44 +0800129 // schedule an event 50ms later to check whether insert is Ok
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800130 scheduler.scheduleEvent(500_ms, std::bind(&Fixture<T>::checkInsertOk, this, interest));
Shuo Chenca329182014-03-19 18:05:18 -0700131}
132
Shuo Chenca329182014-03-19 18:05:18 -0700133template<class T> void
134Fixture<T>::onRegisterFailed(const std::string& reason)
135{
136 BOOST_ERROR("ERROR: Failed to register prefix in local hub's daemon" + reason);
137}
138
139template<class T> void
140Fixture<T>::delayedInterest()
141{
142 BOOST_ERROR("Fetching interest does not come. It may be satisfied in CS or something is wrong");
143}
144
145template<class T> void
Alexander Afanasyev42290b22017-03-09 12:58:29 -0800146Fixture<T>::onInsertData(const Interest& interest, const Data& data)
Shuo Chenca329182014-03-19 18:05:18 -0700147{
148 RepoCommandResponse response;
149 response.wireDecode(data.getContent().blockFromValue());
weijia yuan82cf9142018-10-21 12:25:02 -0700150 int statusCode = response.getCode();
Shuo Chenca329182014-03-19 18:05:18 -0700151 BOOST_CHECK_EQUAL(statusCode, 100);
152}
153
154template<class T> void
Alexander Afanasyev42290b22017-03-09 12:58:29 -0800155Fixture<T>::onDeleteData(const Interest& interest, const Data& data)
Shuo Chenca329182014-03-19 18:05:18 -0700156{
157 RepoCommandResponse response;
158 response.wireDecode(data.getContent().blockFromValue());
weijia yuan82cf9142018-10-21 12:25:02 -0700159 int statusCode = response.getCode();
Shuo Chenca329182014-03-19 18:05:18 -0700160 BOOST_CHECK_EQUAL(statusCode, 200);
161
Shuo Chen028dcd32014-06-21 16:36:44 +0800162 //schedlute an event to check whether delete is Ok.
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800163 scheduler.scheduleEvent(100_ms, std::bind(&Fixture<T>::checkDeleteOk, this, interest));
Shuo Chenca329182014-03-19 18:05:18 -0700164}
165
166template<class T> void
167Fixture<T>::onInsertTimeout(const Interest& interest)
168{
Junxiao Shi2b7b8312017-06-16 03:43:24 +0000169 BOOST_ERROR("Insert command timeout");
Shuo Chenca329182014-03-19 18:05:18 -0700170}
171
172template<class T> void
173Fixture<T>::onDeleteTimeout(const Interest& interest)
174{
Junxiao Shi2b7b8312017-06-16 03:43:24 +0000175 BOOST_ERROR("Delete command timeout");
Shuo Chenca329182014-03-19 18:05:18 -0700176}
177
178template<class T> void
179Fixture<T>::sendInsertInterest(const Interest& insertInterest)
180{
181 insertFace.expressInterest(insertInterest,
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800182 std::bind(&Fixture<T>::onInsertData, this, _1, _2),
183 std::bind(&Fixture<T>::onInsertTimeout, this, _1), // Nack
184 std::bind(&Fixture<T>::onInsertTimeout, this, _1));
Shuo Chenca329182014-03-19 18:05:18 -0700185}
186
187template<class T> void
188Fixture<T>::sendDeleteInterest(const Interest& deleteInterest)
189{
190 deleteFace.expressInterest(deleteInterest,
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800191 std::bind(&Fixture<T>::onDeleteData, this, _1, _2),
192 std::bind(&Fixture<T>::onDeleteTimeout, this, _1), // Nack
193 std::bind(&Fixture<T>::onDeleteTimeout, this, _1));
Shuo Chenca329182014-03-19 18:05:18 -0700194}
195
196template<class T> void
Shuo Chen028dcd32014-06-21 16:36:44 +0800197Fixture<T>::checkInsertOk(const Interest& interest)
Shuo Chenca329182014-03-19 18:05:18 -0700198{
Shuo Chenca329182014-03-19 18:05:18 -0700199 BOOST_TEST_MESSAGE(interest);
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800200 std::shared_ptr<Data> data = handle->readData(interest);
Weiqi Shif0330d52014-07-09 10:54:27 -0700201 if (data) {
202 int rc = memcmp(data->getContent().value(), content, sizeof(content));
203 BOOST_CHECK_EQUAL(rc, 0);
204 }
205 else {
weijia yuan82cf9142018-10-21 12:25:02 -0700206 BOOST_ERROR("Check Insert Failed");
Weiqi Shif0330d52014-07-09 10:54:27 -0700207 }
Shuo Chenca329182014-03-19 18:05:18 -0700208}
209
210template<class T> void
Shuo Chen028dcd32014-06-21 16:36:44 +0800211Fixture<T>::checkDeleteOk(const Interest& interest)
Shuo Chenca329182014-03-19 18:05:18 -0700212{
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800213 std::map<Name, Name>::iterator name = deleteNamePairs.find(interest.getName());
214 BOOST_CHECK_MESSAGE(name != deleteNamePairs.end(), "Delete name not found: " << interest.getName());
215 Interest dataInterest(name->second);
216 std::shared_ptr<Data> data = handle->readData(dataInterest);
217 BOOST_CHECK(!data);
Shuo Chenca329182014-03-19 18:05:18 -0700218}
219
Shuo Chenca329182014-03-19 18:05:18 -0700220template<class T> void
221Fixture<T>::scheduleInsertEvent()
222{
223 int timeCount = 1;
224 for (typename T::DataContainer::iterator i = this->data.begin();
225 i != this->data.end(); ++i) {
226 Name insertCommandName("/repo/command/insert");
227 RepoCommandParameter insertParameter;
228 insertParameter.setName(Name((*i)->getName())
Davide Pesavento49f3a5f2017-09-23 01:36:33 -0400229 .appendNumber(ndn::random::generateWord64()));
Shuo Chenca329182014-03-19 18:05:18 -0700230 insertCommandName.append(insertParameter.wireEncode());
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800231 Interest insertInterest = signer.makeCommandInterest(insertCommandName);
weijia yuan82cf9142018-10-21 12:25:02 -0700232 // schedule a job to express insertInterest every 50ms
Shuo Chenca329182014-03-19 18:05:18 -0700233 scheduler.scheduleEvent(milliseconds(timeCount * 50 + 1000),
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800234 std::bind(&Fixture<T>::sendInsertInterest, this, insertInterest));
weijia yuan82cf9142018-10-21 12:25:02 -0700235 // schedule what to do when interest timeout
Davide Pesavento9a8d7d82019-03-15 20:14:25 -0400236 auto delayEventId = scheduler.scheduleEvent(milliseconds(5000 + timeCount * 50),
237 std::bind(&Fixture<T>::delayedInterest, this));
Shuo Chenca329182014-03-19 18:05:18 -0700238 insertEvents[insertParameter.getName()] = delayEventId;
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800239 // The delayEvent will be canceled in onInsertInterest
Shuo Chenca329182014-03-19 18:05:18 -0700240 insertFace.setInterestFilter(insertParameter.getName(),
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800241 std::bind(&Fixture<T>::onInsertInterest, this, _2),
Wentao Shang91fb4f22014-05-20 10:55:22 -0700242 ndn::RegisterPrefixSuccessCallback(),
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800243 std::bind(&Fixture<T>::onRegisterFailed, this, _2));
Shuo Chenca329182014-03-19 18:05:18 -0700244 timeCount++;
245 }
246}
247
Shuo Chenca329182014-03-19 18:05:18 -0700248template<class T> void
249Fixture<T>::scheduleDeleteEvent()
250{
251 int timeCount = 1;
252 for (typename T::DataContainer::iterator i = this->data.begin();
253 i != this->data.end(); ++i) {
254 Name deleteCommandName("/repo/command/delete");
255 RepoCommandParameter deleteParameter;
Davide Pesavento49f3a5f2017-09-23 01:36:33 -0400256 deleteParameter.setProcessId(ndn::random::generateWord64());
Shuo Chenca329182014-03-19 18:05:18 -0700257 deleteParameter.setName((*i)->getName());
258 deleteCommandName.append(deleteParameter.wireEncode());
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800259 Interest deleteInterest = signer.makeCommandInterest(deleteCommandName);
260 deleteNamePairs[deleteInterest.getName()] = (*i)->getName();
Shuo Chenca329182014-03-19 18:05:18 -0700261 scheduler.scheduleEvent(milliseconds(4000 + timeCount * 50),
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800262 std::bind(&Fixture<T>::sendDeleteInterest, this, deleteInterest));
Shuo Chenca329182014-03-19 18:05:18 -0700263 timeCount++;
264 }
265}
266
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800267using Datasets = boost::mpl::vector<BasicDataset,
268 FetchByPrefixDataset,
269 SamePrefixDataset<10>>;
Alexander Afanasyevb7e8a812014-07-23 01:36:47 -0700270
271BOOST_FIXTURE_TEST_CASE_TEMPLATE(InsertDelete, T, Datasets, Fixture<T>)
Shuo Chenca329182014-03-19 18:05:18 -0700272{
Shuo Chenca329182014-03-19 18:05:18 -0700273 // schedule events
weijia yuan3aa8d2b2018-03-06 15:35:57 -0800274 this->scheduler.scheduleEvent(0_s, std::bind(&Fixture<T>::scheduleInsertEvent, this));
275 this->scheduler.scheduleEvent(10_s, std::bind(&Fixture<T>::scheduleDeleteEvent, this));
Shuo Chenca329182014-03-19 18:05:18 -0700276
weijia yuan82cf9142018-10-21 12:25:02 -0700277 this->repoFace.processEvents(30_s);
Shuo Chenca329182014-03-19 18:05:18 -0700278}
279
280BOOST_AUTO_TEST_SUITE_END()
281
Alexander Afanasyev42290b22017-03-09 12:58:29 -0800282} // namespace tests
283} // namespace repo