summaryrefslogtreecommitdiffstats
path: root/src/lib/hooks/tests/library_manager_collection_unittest.cc
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/hooks/tests/library_manager_collection_unittest.cc')
-rw-r--r--src/lib/hooks/tests/library_manager_collection_unittest.cc314
1 files changed, 314 insertions, 0 deletions
diff --git a/src/lib/hooks/tests/library_manager_collection_unittest.cc b/src/lib/hooks/tests/library_manager_collection_unittest.cc
new file mode 100644
index 0000000..9b30cb3
--- /dev/null
+++ b/src/lib/hooks/tests/library_manager_collection_unittest.cc
@@ -0,0 +1,314 @@
+// Copyright (C) 2013-2020 Internet Systems Consortium, Inc. ("ISC")
+//
+// This Source Code Form is subject to the terms of the Mozilla Public
+// License, v. 2.0. If a copy of the MPL was not distributed with this
+// file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+#include <config.h>
+
+#include <hooks/callout_handle.h>
+#include <hooks/callout_manager.h>
+#include <hooks/library_manager.h>
+#include <hooks/library_manager_collection.h>
+#include <hooks/libinfo.h>
+
+#include <hooks/tests/common_test_class.h>
+#include <hooks/tests/test_libraries.h>
+
+#include <boost/shared_ptr.hpp>
+#include <gtest/gtest.h>
+
+#include <algorithm>
+#include <string>
+
+
+using namespace isc;
+using namespace isc::hooks;
+using namespace std;
+
+namespace {
+
+/// @brief Library manager collection test class
+
+class LibraryManagerCollectionTest : public ::testing::Test,
+ public HooksCommonTestClass {
+private:
+
+ /// To avoid unused variable errors
+ std::string dummy(int i) {
+ if (i == 0) {
+ return (MARKER_FILE);
+ } else if (i > 0) {
+ return (LOAD_CALLOUT_LIBRARY);
+ } else {
+ return (LOAD_ERROR_CALLOUT_LIBRARY);
+ }
+ }
+};
+
+} // namespace
+
+namespace isc {
+namespace hooks {
+/// @brief Public library manager collection class
+///
+/// This is an instance of the LibraryManagerCollection class but with the
+/// protected methods made public for test purposes.
+
+class PublicLibraryManagerCollection : public LibraryManagerCollection {
+public:
+ /// @brief Constructor
+ ///
+ /// @param List of libraries that this collection will manage. The order
+ /// of the libraries is important.
+ PublicLibraryManagerCollection(const HookLibsCollection& libraries)
+ : LibraryManagerCollection(libraries) {
+ }
+
+ /// Public methods that call protected methods on the superclass.
+ using LibraryManagerCollection::unloadLibraries;
+};
+
+} // namespace hooks
+} // namespace isc
+
+namespace {
+// This is effectively the same test as for LibraryManager, but using the
+// LibraryManagerCollection object.
+
+TEST_F(LibraryManagerCollectionTest, LoadLibraries) {
+
+ // Set up the list of libraries to be loaded.
+ HookLibsCollection library_names;
+ library_names.push_back(make_pair(std::string(FULL_CALLOUT_LIBRARY),
+ data::ConstElementPtr()));
+ library_names.push_back(make_pair(std::string(BASIC_CALLOUT_LIBRARY),
+ data::ConstElementPtr()));
+
+ // Set up the library manager collection and get the callout manager we'll
+ // be using.
+ PublicLibraryManagerCollection lm_collection(library_names);
+
+ // Load the libraries.
+ EXPECT_TRUE(lm_collection.loadLibraries());
+ EXPECT_EQ(2, lm_collection.getLoadedLibraryCount());
+
+ // Execute the callouts. The first library implements the calculation.
+ //
+ // r3 = (7 * d1 - d2) * d3
+ //
+ // The last-loaded library implements the calculation
+ //
+ // r3 = (10 + d1) * d2 - d3
+ //
+ // Putting the processing for each library together in the appropriate
+ // order, we get:
+ //
+ // r3 = ((10 * d1 + d1) - d2) * d2 * d3 - d3
+ boost::shared_ptr<CalloutManager> manager =
+ lm_collection.getCalloutManager();
+ {
+ SCOPED_TRACE("Doing calculation with libraries loaded");
+ executeCallCallouts(manager, 10, 3, 33, 2, 62, 3, 183);
+ }
+
+ // Try unloading the libraries.
+ EXPECT_NO_THROW(lm_collection.unloadLibraries());
+ EXPECT_EQ(0, lm_collection.getLoadedLibraryCount());
+
+ // Re-execute the calculation - callouts can be called but as nothing
+ // happens, the result should always be -1.
+ {
+ SCOPED_TRACE("Doing calculation with libraries not loaded");
+ executeCallCallouts(manager, -1, 3, -1, 22, -1, 83, -1);
+ }
+}
+
+// This is effectively the same test as above, but with a library generating
+// an error when loaded. It is expected that no libraries will be loaded.
+
+TEST_F(LibraryManagerCollectionTest, LoadLibrariesWithError) {
+
+ // Set up the list of libraries to be loaded.
+ HookLibsCollection library_names;
+ library_names.push_back(make_pair(std::string(FULL_CALLOUT_LIBRARY),
+ data::ConstElementPtr()));
+ library_names.push_back(make_pair(std::string(INCORRECT_VERSION_LIBRARY),
+ data::ConstElementPtr()));
+ library_names.push_back(make_pair(std::string(BASIC_CALLOUT_LIBRARY),
+ data::ConstElementPtr()));
+
+ // Set up the library manager collection and get the callout manager we'll
+ // be using.
+ PublicLibraryManagerCollection lm_collection(library_names);
+
+ // Load the libraries. We expect a failure status to be returned as
+ // one of the libraries failed to load.
+ EXPECT_FALSE(lm_collection.loadLibraries());
+
+ // Expect no libraries were loaded.
+ EXPECT_EQ(0, lm_collection.getLoadedLibraryCount());
+}
+
+// Check that everything works even with no libraries loaded.
+
+TEST_F(LibraryManagerCollectionTest, NoLibrariesLoaded) {
+ // Set up the list of libraries to be loaded.
+ HookLibsCollection library_names;
+
+ // Set up the library manager collection and get the callout manager we'll
+ // be using.
+ LibraryManagerCollection lm_collection(library_names);
+ EXPECT_TRUE(lm_collection.loadLibraries());
+ EXPECT_EQ(0, lm_collection.getLoadedLibraryCount());
+ boost::shared_ptr<CalloutManager> manager =
+ lm_collection.getCalloutManager();
+
+ // Execute the calculation - callouts can be called but as nothing
+ // happens, the result should always be -1.
+ executeCallCallouts(manager, -1, 3, -1, 22, -1, 83, -1);
+}
+
+// Check that we can get the names of the libraries.
+
+TEST_F(LibraryManagerCollectionTest, LibraryNames) {
+
+ // Set up the list of libraries to be loaded.
+ HookLibsCollection libraries;
+ libraries.push_back(make_pair(std::string(FULL_CALLOUT_LIBRARY),
+ data::ConstElementPtr()));
+ libraries.push_back(make_pair(std::string(BASIC_CALLOUT_LIBRARY),
+ data::ConstElementPtr()));
+
+ // Set up the library manager collection and get the callout manager we'll
+ // be using.
+ PublicLibraryManagerCollection lm_collection(libraries);
+
+ // Check the names before the libraries are loaded.
+ std::vector<std::string> collection_names = lm_collection.getLibraryNames();
+ EXPECT_TRUE(extractNames(libraries) == collection_names);
+
+ // Load the libraries and check the names again.
+ EXPECT_TRUE(lm_collection.loadLibraries());
+ EXPECT_EQ(2, lm_collection.getLoadedLibraryCount());
+ collection_names = lm_collection.getLibraryNames();
+ EXPECT_TRUE(extractNames(libraries) == collection_names);
+}
+
+// Test the library validation function.
+
+TEST_F(LibraryManagerCollectionTest, validateLibraries) {
+ // Vector of libraries that failed validation
+ std::vector<std::string> failed;
+
+ // Test different vectors of libraries.
+
+ // No libraries should return a success.
+ std::vector<std::string> libraries;
+
+ failed = LibraryManagerCollection::validateLibraries(libraries);
+ EXPECT_TRUE(failed.empty());
+
+ // Single valid library should validate.
+ libraries.clear();
+ libraries.push_back(BASIC_CALLOUT_LIBRARY);
+
+ failed = LibraryManagerCollection::validateLibraries(libraries);
+ EXPECT_TRUE(failed.empty());
+
+ // Multiple valid libraries should succeed.
+ libraries.clear();
+ libraries.push_back(BASIC_CALLOUT_LIBRARY);
+ libraries.push_back(FULL_CALLOUT_LIBRARY);
+ libraries.push_back(UNLOAD_CALLOUT_LIBRARY);
+ libraries.push_back(CALLOUT_PARAMS_LIBRARY);
+
+ failed = LibraryManagerCollection::validateLibraries(libraries);
+ EXPECT_TRUE(failed.empty());
+
+ // Single invalid library should fail.
+ libraries.clear();
+ libraries.push_back(NOT_PRESENT_LIBRARY);
+
+ failed = LibraryManagerCollection::validateLibraries(libraries);
+ EXPECT_TRUE(failed == libraries);
+
+ // Multiple invalid libraries should fail.
+ libraries.clear();
+ libraries.push_back(INCORRECT_VERSION_LIBRARY);
+ libraries.push_back(NO_VERSION_LIBRARY);
+ libraries.push_back(FRAMEWORK_EXCEPTION_LIBRARY);
+
+ failed = LibraryManagerCollection::validateLibraries(libraries);
+ EXPECT_TRUE(failed == libraries);
+
+ // Combination of valid and invalid (first one valid) should fail.
+ libraries.clear();
+ libraries.push_back(FULL_CALLOUT_LIBRARY);
+ libraries.push_back(INCORRECT_VERSION_LIBRARY);
+ libraries.push_back(NO_VERSION_LIBRARY);
+
+ std::vector<std::string> expected_failures;
+ expected_failures.push_back(INCORRECT_VERSION_LIBRARY);
+ expected_failures.push_back(NO_VERSION_LIBRARY);
+
+ failed = LibraryManagerCollection::validateLibraries(libraries);
+ EXPECT_TRUE(failed == expected_failures);
+
+ // Combination of valid and invalid (first one invalid) should fail.
+ libraries.clear();
+ libraries.push_back(NO_VERSION_LIBRARY);
+ libraries.push_back(FULL_CALLOUT_LIBRARY);
+ libraries.push_back(INCORRECT_VERSION_LIBRARY);
+
+ expected_failures.clear();
+ expected_failures.push_back(NO_VERSION_LIBRARY);
+ expected_failures.push_back(INCORRECT_VERSION_LIBRARY);
+
+ failed = LibraryManagerCollection::validateLibraries(libraries);
+ EXPECT_TRUE(failed == expected_failures);
+}
+
+// This test verifies if getLibraryNames and getLibraryInfo are returning
+// expected values if there are no libraries configured.
+TEST_F(LibraryManagerCollectionTest, libraryGetEmpty) {
+
+ HookLibsCollection empty;
+ boost::shared_ptr<LibraryManagerCollection> mgr;
+
+ // Instantiate library manager collection with no libraries
+ EXPECT_NO_THROW(mgr.reset(new LibraryManagerCollection(empty)));
+
+ // Check that getLibraryInfo returns empty list properly.
+ HookLibsCollection returned = mgr->getLibraryInfo();
+ EXPECT_TRUE(returned.empty());
+
+ // Check that getLibraryNames return empty list, too.
+ vector<string> names(3, "rubbish"); // just put something in it.
+ EXPECT_NO_THROW(names = mgr->getLibraryNames());
+ EXPECT_TRUE(names.empty());
+}
+
+// This test verifies if getLibraryNames and getLibraryInfo are returning
+// expected values when there are libraries configured.
+TEST_F(LibraryManagerCollectionTest, libraryGet) {
+ using namespace data;
+
+ HookLibsCollection libs;
+ ElementPtr param1(Element::fromJSON("{ \"param1\": \"foo\" }"));
+ ElementPtr param2(Element::fromJSON("{ \"param2\": \"bar\" }"));
+ libs.push_back(make_pair("libone", param1));
+ libs.push_back(make_pair("libtwo", param2));
+
+ boost::shared_ptr<LibraryManagerCollection> mgr;
+ EXPECT_NO_THROW(mgr.reset(new LibraryManagerCollection(libs)));
+ EXPECT_TRUE(libs == mgr->getLibraryInfo());
+
+ vector<string> exp_names;
+ exp_names.push_back("libone");
+ exp_names.push_back("libtwo");
+
+ EXPECT_TRUE(exp_names == mgr->getLibraryNames());
+}
+
+} // Anonymous namespace