all: Refactoring work with time using boost::chrono
Now the library has two clocks: time::steady_clock and
time::system_clock, following (boost|std)::chrono. In addition to
standard now() method, the library contains several helpers to convert
to/from UnixTimestamp (microsecond resolution) and IsoString (optional
microsecond resolution). The IsoString conversions use
boost::posix_time routines, since boost::chrono supports extended IO
support only starting boost version 1.52 (Boost Chrono V2).
This commit breaks compatibility with previous API. All time-related
Data/Interest calls must explicitly use time units to specify
FreshnessPeriod/InterestLifetime.
Brief usage/conversion guide:
- creation of time units does not support double/float types. If
necessary to create time unit from double, ``ndn::duration<double>`` (for
seconds) needs to be used instead. In some cases, this would also
require ``ndn::duration_cast``, if the target is not ``ndn::nanoseconds``.
- ndn::getNow, ndn::ndn_getNowMilliseconds, ndn::time::now are all
removed in favor of the now() method in a specific clock:
* time::system_clock::now();
* time::steady_clock::now();
- When necessary to convert system_clock::TimePoint to unix timestamp,
``time::toUnixTimestamp`` can be used. This method return number of
milliseconds since UNIX epoch as ``ndn::time::milliseconds`` type.
Use count() method to obtain number as an integral value.
Change-Id: Icd688bc6766e008d60c3d2888173627874526e47
Refs: #1152
diff --git a/tests-integrated/main.cpp b/tests-integrated/main.cpp
new file mode 100644
index 0000000..d43aa5a
--- /dev/null
+++ b/tests-integrated/main.cpp
@@ -0,0 +1,9 @@
+/**
+ * Copyright (C) 2013 Regents of the University of California.
+ * See COPYING for copyright and distribution information.
+ */
+
+#define BOOST_TEST_MAIN 1
+#define BOOST_TEST_DYN_LINK 1
+
+#include <boost/test/unit_test.hpp>
diff --git a/tests-integrated/test-faces.cpp b/tests-integrated/test-faces.cpp
new file mode 100644
index 0000000..03bfa9b
--- /dev/null
+++ b/tests-integrated/test-faces.cpp
@@ -0,0 +1,190 @@
+/**
+ * Copyright (C) 2013 Regents of the University of California.
+ * See COPYING for copyright and distribution information.
+ */
+
+#include <boost/test/unit_test.hpp>
+#include "face.hpp"
+#include "util/scheduler.hpp"
+
+using namespace std;
+namespace ndn {
+
+BOOST_AUTO_TEST_SUITE(TestFaces)
+
+struct FacesFixture
+{
+ FacesFixture()
+ : dataCount(0)
+ , timeoutCount(0)
+ , regPrefixId(0)
+ , inInterestCount(0)
+ , inInterestCount2(0)
+ , regFailedCount(0)
+ {
+ }
+
+ void
+ onData()
+ {
+ ++dataCount;
+ }
+
+ void
+ onTimeout()
+ {
+ ++timeoutCount;
+ }
+
+ void
+ onInterest(Face& face)
+ {
+ ++inInterestCount;
+
+ face.unsetInterestFilter(regPrefixId);
+ }
+
+ void
+ onInterest2(Face& face)
+ {
+ ++inInterestCount2;
+
+ face.unsetInterestFilter(regPrefixId2);
+ }
+
+ void
+ onRegFailed()
+ {
+ ++regFailedCount;
+ }
+
+ void
+ expressInterest(Face& face, const Name& name)
+ {
+ Interest i(name);
+ i.setInterestLifetime(time::milliseconds(50));
+ face.expressInterest(i,
+ bind(&FacesFixture::onData, this),
+ bind(&FacesFixture::onTimeout, this));
+ }
+
+ void
+ terminate(Face& face)
+ {
+ face.shutdown();
+ }
+
+ uint32_t dataCount;
+ uint32_t timeoutCount;
+
+ const RegisteredPrefixId* regPrefixId;
+ const RegisteredPrefixId* regPrefixId2;
+ uint32_t inInterestCount;
+ uint32_t inInterestCount2;
+ uint32_t regFailedCount;
+};
+
+BOOST_FIXTURE_TEST_CASE (Unix, FacesFixture)
+{
+ Face face;
+
+ face.expressInterest(Interest("/%C1.M.S.localhost/%C1.M.SRV/ndnd/KEY", time::milliseconds(1000)),
+ ptr_lib::bind(&FacesFixture::onData, this),
+ ptr_lib::bind(&FacesFixture::onTimeout, this));
+
+ BOOST_REQUIRE_NO_THROW(face.processEvents());
+
+ BOOST_CHECK_EQUAL(dataCount, 1);
+ BOOST_CHECK_EQUAL(timeoutCount, 0);
+
+ face.expressInterest(Interest("/localhost/non-existing/data/should/not/exist/anywhere", time::milliseconds(50)),
+ ptr_lib::bind(&FacesFixture::onData, this),
+ ptr_lib::bind(&FacesFixture::onTimeout, this));
+
+ BOOST_REQUIRE_NO_THROW(face.processEvents());
+
+ BOOST_CHECK_EQUAL(dataCount, 1);
+ BOOST_CHECK_EQUAL(timeoutCount, 1);
+}
+
+BOOST_FIXTURE_TEST_CASE (Tcp, FacesFixture)
+{
+ Face face("localhost");
+
+ face.expressInterest(Interest("/%C1.M.S.localhost/%C1.M.SRV/ndnd/KEY", time::milliseconds(1000)),
+ bind(&FacesFixture::onData, this),
+ bind(&FacesFixture::onTimeout, this));
+
+ BOOST_REQUIRE_NO_THROW(face.processEvents());
+
+ BOOST_CHECK_EQUAL(dataCount, 1);
+ BOOST_CHECK_EQUAL(timeoutCount, 0);
+
+ face.expressInterest(Interest("/localhost/non-existing/data/should/not/exist/anywhere", time::milliseconds(50)),
+ bind(&FacesFixture::onData, this),
+ bind(&FacesFixture::onTimeout, this));
+
+ BOOST_REQUIRE_NO_THROW(face.processEvents());
+
+ BOOST_CHECK_EQUAL(dataCount, 1);
+ BOOST_CHECK_EQUAL(timeoutCount, 1);
+}
+
+
+BOOST_FIXTURE_TEST_CASE (SetFilter, FacesFixture)
+{
+ Face face;
+ Face face2(face.ioService());
+ Scheduler scheduler(*face.ioService());
+ scheduler.scheduleEvent(time::milliseconds(300),
+ bind(&FacesFixture::terminate, this, func_lib::ref(face)));
+
+ regPrefixId = face.setInterestFilter("/Hello/World",
+ bind(&FacesFixture::onInterest, this, func_lib::ref(face)),
+ bind(&FacesFixture::onRegFailed, this));
+
+ scheduler.scheduleEvent(time::milliseconds(200),
+ bind(&FacesFixture::expressInterest, this,
+ func_lib::ref(face2), Name("/Hello/World/!")));
+
+ BOOST_REQUIRE_NO_THROW(face.processEvents());
+
+ BOOST_CHECK_EQUAL(regFailedCount, 0);
+ BOOST_CHECK_EQUAL(inInterestCount, 1);
+ BOOST_CHECK_EQUAL(timeoutCount, 1);
+ BOOST_CHECK_EQUAL(dataCount, 0);
+}
+
+BOOST_FIXTURE_TEST_CASE (SetTwoFilters, FacesFixture)
+{
+ Face face;
+ Face face2(face.ioService());
+ Scheduler scheduler(*face.ioService());
+ scheduler.scheduleEvent(time::seconds(1),
+ bind(&FacesFixture::terminate, this, func_lib::ref(face)));
+
+ regPrefixId = face.setInterestFilter("/Hello/World",
+ bind(&FacesFixture::onInterest, this, func_lib::ref(face)),
+ bind(&FacesFixture::onRegFailed, this));
+
+ regPrefixId2 = face.setInterestFilter("/Los/Angeles/Lakers",
+ bind(&FacesFixture::onInterest2, this, func_lib::ref(face)),
+ bind(&FacesFixture::onRegFailed, this));
+
+
+ scheduler.scheduleEvent(time::milliseconds(200),
+ bind(&FacesFixture::expressInterest, this,
+ func_lib::ref(face2), Name("/Hello/World/!")));
+
+ BOOST_REQUIRE_NO_THROW(face.processEvents());
+
+ BOOST_CHECK_EQUAL(regFailedCount, 0);
+ BOOST_CHECK_EQUAL(inInterestCount, 1);
+ BOOST_CHECK_EQUAL(inInterestCount2, 0);
+ BOOST_CHECK_EQUAL(timeoutCount, 1);
+ BOOST_CHECK_EQUAL(dataCount, 0);
+}
+
+BOOST_AUTO_TEST_SUITE_END()
+
+} // namespace ndn
diff --git a/tests-integrated/wscript b/tests-integrated/wscript
new file mode 100644
index 0000000..c0466cd
--- /dev/null
+++ b/tests-integrated/wscript
@@ -0,0 +1,25 @@
+# -*- Mode: python; py-indent-offset: 4; indent-tabs-mode: nil; coding: utf-8; -*-
+
+from waflib import Utils
+
+top = '..'
+
+def build(bld):
+ unittests = bld.program (
+ target="../integrated-tests",
+ features = "cxx cxxprogram",
+ source = bld.path.ant_glob(['**/*.cpp'],
+ excl = ['**/*-osx.cpp', '**/*-sqlite3.cpp']),
+ use = 'ndn-cpp-dev',
+ install_path = None,
+ )
+
+ if Utils.unversioned_sys_platform () == "darwin":
+ unittests.source += bld.path.ant_glob('**/*-osx.cpp')
+
+ # In case we want to make it optional later
+ unittests.source += bld.path.ant_glob('**/*-sqlite3.cpp')
+
+ if bld.env['WITH_PCH']:
+ unittests.pch = "test-all.hpp"
+