From 27982beec16b58cb5669f821e3c2aac68ea64d1f Mon Sep 17 00:00:00 2001 From: Junghyun Yeon Date: Mon, 2 Aug 2021 12:50:33 +0900 Subject: [PATCH] Implement ParamChecker class Implement ParamChecker class and its unittest. Change-Id: I14b26a4d3e99e8184d4059c9c14583734194b9d0 Signed-off-by: Junghyun Yeon --- CMakeLists.txt | 2 + packaging/pkgmgr-tool.spec | 1 + src/rsc-copy/CMakeLists.txt | 2 + src/rsc-copy/include/param_checker.hh | 6 + src/rsc-copy/src/param_checker.cc | 96 +++++++++++-- tests/mock/pkgmgr_info_mock.cc | 12 ++ tests/mock/pkgmgr_info_mock.h | 3 + tests/unit_tests/CMakeLists.txt | 16 ++- .../rsc-copy/src/test_param_checker.cc | 130 ++++++++++++++++++ 9 files changed, 254 insertions(+), 14 deletions(-) create mode 100644 tests/unit_tests/rsc-copy/src/test_param_checker.cc diff --git a/CMakeLists.txt b/CMakeLists.txt index 82e0da3..65798988 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -37,6 +37,8 @@ PKG_CHECK_MODULES(STORAGE_DEPS REQUIRED storage) PKG_CHECK_MODULES(SQLITE_DEPS REQUIRED sqlite3) PKG_CHECK_MODULES(SMACK_DEPS REQUIRED libsmack) +FIND_PACKAGE(Boost REQUIRED COMPONENTS system filesystem program_options iostreams) + INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/include) SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -Wl,-zdefs -pie" ) SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -fvisibility=hidden") diff --git a/packaging/pkgmgr-tool.spec b/packaging/pkgmgr-tool.spec index 8f985ad..b0ad435 100644 --- a/packaging/pkgmgr-tool.spec +++ b/packaging/pkgmgr-tool.spec @@ -11,6 +11,7 @@ Requires: unzip Requires: smack Requires: cryptsetup +BuildRequires: boost-devel BuildRequires: cmake BuildRequires: gettext-tools BuildRequires: pkgconfig(glib-2.0) diff --git a/src/rsc-copy/CMakeLists.txt b/src/rsc-copy/CMakeLists.txt index 1f6532c..d6d1cdf 100644 --- a/src/rsc-copy/CMakeLists.txt +++ b/src/rsc-copy/CMakeLists.txt @@ -10,6 +10,8 @@ APPLY_PKG_CONFIG(${TARGET_RSC_COPY} PUBLIC AUL_DEPS GLIB_DEPS BUNDLE_DEPS + Boost + PKGMGR_INFO_DEPS ) # Install diff --git a/src/rsc-copy/include/param_checker.hh b/src/rsc-copy/include/param_checker.hh index 5ab1ab5..10c5ca8 100644 --- a/src/rsc-copy/include/param_checker.hh +++ b/src/rsc-copy/include/param_checker.hh @@ -35,6 +35,12 @@ class ParamChecker { private: std::list path_info_list_; + std::string pkgid_; + uid_t uid_; + ReqType req_type_ = ReqType::REQ_TYPE_UNKNOWN; + + void SetRequestType(std::string key); + bool ValidatePkgID(); }; } // rsc_handler diff --git a/src/rsc-copy/src/param_checker.cc b/src/rsc-copy/src/param_checker.cc index caa109b..e7c6322 100644 --- a/src/rsc-copy/src/param_checker.cc +++ b/src/rsc-copy/src/param_checker.cc @@ -17,37 +17,111 @@ #include "include/param_checker.hh" -#include +#include +#include +#include +#include +#include +#include "include/logging.hh" #include "include/request_type.hh" #include "include/rsc_path_info.hh" +#include + +#include +#include + +namespace bs = boost::system; +namespace bpo = boost::program_options; + namespace rsc_handler { ParamChecker::ParamChecker(int argc, char* argv[]) { - std::cout << "ParamChecker::ParamChecker" << std::endl; + bpo::options_description options; + + options.add_options() + ("uid,u", bpo::value()->default_value(0), "user id") + ("path,p", bpo::value>()->multitoken(), + "source-destination path") + ("remove,r", bpo::value(), "remove shared resource") + ("delete,d", bpo::value(), + "delete shared resource for package") + ("copy,c", bpo::value(), "copy resource") + ("help,h", "Show this message"); + + bpo::parsed_options parsed_options = bpo::command_line_parser(argc, argv) + .options(options) + .run(); + + for (const bpo::option& o : parsed_options.options) { + if (o.string_key == "uid") { + uid_ = static_cast(std::stoi(o.value.front())); + } else if (o.string_key == "path") { + path_info_list_.emplace_back(o.value.front(), o.value.back()); + } else if (o.string_key == "copy" || + o.string_key == "delete" || + o.string_key == "remove") { + pkgid_ = o.value.front(); + SetRequestType(o.string_key); + } else if (o.string_key == "help") { + std::cout << options; + } else { + std::cout << "Invalid option : " << o.string_key << std::endl; + } + } } std::string ParamChecker::GetPkgID() const { - std::cout << "ParamChecker::GetPkgID" << std::endl; - - return "test_text"; + return pkgid_; } ReqType ParamChecker::GetRequestType() { - std::cout << "ParamChecker::GetRequestType" << std::endl; - - return ReqType::REQ_TYPE_UNKNOWN; + return req_type_; } const std::list& ParamChecker::GetPathList() const { - std::cout << "ParamChecker::GetPathList()" << std::endl; - return path_info_list_; } bool ParamChecker::Validate() { - std::cout << "ParamChecker::Validate" << std::endl; + if (uid_ == 0) { + LOG(ERROR) << "Invalid uid: " << uid_; + return false; + } + + if (req_type_ == ReqType::REQ_TYPE_UNKNOWN) { + LOG(ERROR) << "Invalid request type"; + return false; + } + + if (!ValidatePkgID()) + return false; + + if (req_type_ != ReqType::REQ_TYPE_UNINSTALL) { + if (path_info_list_.size() == 0) { + LOG(ERROR) << "Path is not given"; + return false; + } + } + + return true; +} + +void ParamChecker::SetRequestType(std::string key) { + if (key == "copy") + req_type_ = ReqType::REQ_TYPE_NEW; + else if (key == "remove") + req_type_ = ReqType::REQ_TYPE_REMOVE; + else if (key == "delete") + req_type_ = ReqType::REQ_TYPE_UNINSTALL; +} + +bool ParamChecker::ValidatePkgID() { + if (pkgid_.size() == 0) { + LOG(ERROR) << "pkgid is empty"; + return false; + } return true; } diff --git a/tests/mock/pkgmgr_info_mock.cc b/tests/mock/pkgmgr_info_mock.cc index 3177e32..2577c33 100644 --- a/tests/mock/pkgmgr_info_mock.cc +++ b/tests/mock/pkgmgr_info_mock.cc @@ -60,3 +60,15 @@ extern "C" int pkgmgrinfo_pkginfo_get_version(pkgmgrinfo_pkginfo_h handle, return MOCK_HOOK_P2(PkgMgrInfoMock, pkgmgrinfo_pkginfo_get_version, handle, version); } + +extern "C" int pkgmgrinfo_pkginfo_get_usr_pkginfo( + const char* pkgid, uid_t uid, pkgmgrinfo_pkginfo_h* handle) { + return MOCK_HOOK_P3( + PkgMgrInfoMock, pkgmgrinfo_pkginfo_get_usr_pkginfo, pkgid, uid, handle); +} + +extern "C" int pkgmgrinfo_pkginfo_destroy_pkginfo( + pkgmgrinfo_pkginfo_h handle) { + return MOCK_HOOK_P1( + PkgMgrInfoMock, pkgmgrinfo_pkginfo_destroy_pkginfo, handle); +} \ No newline at end of file diff --git a/tests/mock/pkgmgr_info_mock.h b/tests/mock/pkgmgr_info_mock.h index 7e7fae6..bbc2a67 100644 --- a/tests/mock/pkgmgr_info_mock.h +++ b/tests/mock/pkgmgr_info_mock.h @@ -40,6 +40,9 @@ class PkgMgrInfoMock : public virtual ModuleMock { MOCK_METHOD2(pkgmgrinfo_pkginfo_get_type, int(pkgmgrinfo_pkginfo_h, char**)); MOCK_METHOD2(pkgmgrinfo_pkginfo_get_version, int(pkgmgrinfo_pkginfo_h, char**)); + MOCK_METHOD3(pkgmgrinfo_pkginfo_get_usr_pkginfo, + int(const char*, uid_t, pkgmgrinfo_pkginfo_h*)); + MOCK_METHOD1(pkgmgrinfo_pkginfo_destroy_pkginfo, int(pkgmgrinfo_pkginfo_h)); }; #endif // TESTS_MOCK_PKGMGR_INFO_MOCK_H_ diff --git a/tests/unit_tests/CMakeLists.txt b/tests/unit_tests/CMakeLists.txt index 5dd2f83..37bfcb4 100644 --- a/tests/unit_tests/CMakeLists.txt +++ b/tests/unit_tests/CMakeLists.txt @@ -10,6 +10,7 @@ PKG_CHECK_MODULES(pkgmgr-tool_unittests REQUIRED libtzplatform-config libsmack sqlite3 + boost ) FOREACH(flag ${pkgmgr-tool_unittests_CFLAGS}) @@ -24,19 +25,28 @@ SET(CMAKE_CXX_FLAGS_RELEASE "-O2") ADD_DEFINITIONS("-DDB_PATH=\"${DB_PATH}\"") INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../src/pkg_upgrade/include) +INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../src/rsc-copy/) INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../) +#pkg_upgrade AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/pkg_upgrade/src PKG_UPGRADE_SRCS) +AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/../../src/pkg_upgrade/src PKG_UPGRADE_LIB_SOURCES) +LIST(REMOVE_ITEM PKG_UPGRADE_LIB_SOURCES ${CMAKE_CURRENT_SOURCE_DIR}/../../src/pkg_upgrade/src/main.cc) + +#rsc-copy AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/rsc-copy/src RSC_COPY_SRCS) -AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/../../src/pkg_upgrade/src LIB_SOURCES) -LIST(REMOVE_ITEM LIB_SOURCES ${CMAKE_CURRENT_SOURCE_DIR}/../../src/pkg_upgrade/src/main.cc) +AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/../../src/rsc-copy/src RSC_COPY_LIB_SOURCES) +LIST(REMOVE_ITEM RSC_COPY_LIB_SOURCES ${CMAKE_CURRENT_SOURCE_DIR}/../../src/rsc-copy/src/rsc_copy_main.cc) +LIST(REMOVE_ITEM RSC_COPY_LIB_SOURCES ${CMAKE_CURRENT_SOURCE_DIR}/../../src/rsc-copy/src/logging.cc) + AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/../mock MOCK_SOURCES) ADD_EXECUTABLE(${PROJECT_NAME} ${PKG_UPGRADE_SRCS} ${RSC_COPY_SRCS} ${MOCK_SOURCES} - ${LIB_SOURCES} + ${PKG_UPGRADE_LIB_SOURCES} + ${RSC_COPY_LIB_SOURCES} test_main.cc ) diff --git a/tests/unit_tests/rsc-copy/src/test_param_checker.cc b/tests/unit_tests/rsc-copy/src/test_param_checker.cc new file mode 100644 index 0000000..04d1d76 --- /dev/null +++ b/tests/unit_tests/rsc-copy/src/test_param_checker.cc @@ -0,0 +1,130 @@ +/* + * Copyright (c) 2021 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include +#include + +#include + +#include "mock/os_mock.h" +#include "mock/pkgmgr_info_mock.h" +#include "mock/test_fixture.h" +#include "include/param_checker.hh" +#include "include/request_type.hh" + +using ::testing::_; +using ::testing::DoAll; +using ::testing::Invoke; +using ::testing::Return; +using ::testing::SetArgPointee; +using ::testing::InvokeArgument; +using ::testing::SaveArg; + +using rsc_handler::ParamChecker; + +class Mocks : public ::testing::NiceMock, + public ::testing::NiceMock {}; + +class ParamCheckerTest : public TestFixture { + public: + ParamCheckerTest() : TestFixture(std::make_unique()) {} + virtual ~ParamCheckerTest() {} + + virtual void SetUp() { + EXPECT_CALL(GetMock(), pkgmgrinfo_pkginfo_get_usr_pkginfo(_, _, _)) + .WillRepeatedly(Return(0)); + EXPECT_CALL(GetMock(), pkgmgrinfo_pkginfo_destroy_pkginfo(_)) + .WillRepeatedly(Return(0)) ; + } + virtual void TearDown() {} +}; + +TEST_F(ParamCheckerTest, InvalidUIDTest) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "0", "--copy", + "org.test.targetpkgid", "-p", "srcpath", "dstpath", nullptr}; + ParamChecker checker(8, (char**)argv); + + EXPECT_EQ(checker.Validate(), false); +} + +TEST_F(ParamCheckerTest, PkgIDNotGiven) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "5001", + "-p", "srcpath", "dstpath", "--copy", "", nullptr}; + ParamChecker checker(8, (char**)argv); + + EXPECT_EQ(checker.Validate(), false); +} + +TEST_F(ParamCheckerTest, CopyRsc) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "5001", "-p", "srcpath", "dstpath", + "--copy", "org.test.targetpkgid", nullptr}; + + ParamChecker checker(8, (char**)argv); + + EXPECT_EQ(checker.Validate(), true); + EXPECT_EQ(checker.GetRequestType(), rsc_handler::ReqType::REQ_TYPE_NEW); + EXPECT_EQ(checker.GetPkgID(), "org.test.targetpkgid"); + EXPECT_EQ(checker.GetPathList().size(), 1); +} + +TEST_F(ParamCheckerTest, RemoveRsc) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "5001", "--remove", + "org.test.targetpkgid", "-p", "dstpath", nullptr}; + + ParamChecker checker(7, (char**)argv); + + EXPECT_EQ(checker.Validate(), true); + EXPECT_EQ(checker.GetRequestType(), rsc_handler::ReqType::REQ_TYPE_REMOVE); + EXPECT_EQ(checker.GetPkgID(), "org.test.targetpkgid"); + EXPECT_EQ(checker.GetPathList().size(), 1); +} + +TEST_F(ParamCheckerTest, DeleteRsc) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "5001", "--delete", + "org.test.targetpkgid", nullptr}; + + ParamChecker checker(5, (char**)argv); + + EXPECT_EQ(checker.Validate(), true); + EXPECT_EQ(checker.GetRequestType(), rsc_handler::ReqType::REQ_TYPE_UNINSTALL); + EXPECT_EQ(checker.GetPkgID(), "org.test.targetpkgid"); + EXPECT_EQ(checker.GetPathList().size(), 0); +} + +TEST_F(ParamCheckerTest, EmptyPkgID) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "5001", "--copy", + "", "-p", "srcpath", "dstpath", nullptr}; + ParamChecker checker(8,(char**)argv); + + EXPECT_EQ(checker.Validate(), false); +} + +TEST_F(ParamCheckerTest, UnknownReqType) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "5001", "-p", + "srcpath", "dstpath", nullptr}; + ParamChecker checker(6, (char**)argv); + + EXPECT_EQ(checker.Validate(), false); +} + +TEST_F(ParamCheckerTest, PathNotGiven) { + const char *argv[] = { "/bin/rsc-copy", "--uid", "5001", + "-c", "org.tizen.pathnotgiven", nullptr}; + ParamChecker checker(5, (char**)argv); + + EXPECT_EQ(checker.Validate(), false); +} -- 2.34.1