Commit 369245e4 authored by Marcin Siodelski's avatar Marcin Siodelski
Browse files

[master] Merge branch 'trac5472'

parents 43a0f84c 7a6be9dd
......@@ -1716,12 +1716,14 @@ An example IPv4 lease deletion by "hw-address" looks as follows:
<command>leaseX-del</command> followed by
<command>leaseX-add</command> commands.</para>
<para>To use <command>leaseX-update</command> the lease must
be present in the lease database. If the lease is not there,
an error will be returned. Please use
<command>leaseX-add</command> to add new leases. You may
check if a lease is present using
<command>leaseX-get</command>, if needed.</para>
<para>The optional boolean parameter "force-create" specifies
if the lease should be created if it doesn't exist in the database.
It defaults to false, which indicates that the lease is not created
if it doesn't exist. In such case, an error is returned as a result
of trying to update a non-existing lease. If the "force-create" parameter
is set to true and the updated lease doesn't exist, the new lease is
created as a result of receiving the <command>leaseX-update</command>.
</para>
<para>
An example command updating IPv4 lease looks as follows:
......@@ -1731,7 +1733,8 @@ An example IPv4 lease deletion by "hw-address" looks as follows:
"ip-address": "192.0.2.1",
"hostname": "newhostname.example.org",
"hw-address": "1a:1b:1c:1d:1e:1f",
"subnet-id": 44
"subnet-id": 44,
"force-create": true
}
}</screen>
</para>
......@@ -1745,7 +1748,8 @@ An example IPv4 lease deletion by "hw-address" looks as follows:
"duid": "88:88:88:88:88:88:88:88",
"iaid": 7654321,
"hostname": "newhostname.example.org",
"subnet-id": 66
"subnet-id": 66,
"force-create": false
}
}</screen>
</para>
......
// Copyright (C) 2017 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2017-2018 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
......@@ -222,9 +222,11 @@ LeaseCmdsImpl::leaseAddHandler(CalloutHandle& handle) {
Lease4Ptr lease4;
Lease6Ptr lease6;
// This parameter is ignored for the commands adding the lease.
bool force_create = false;
if (v4) {
Lease4Parser parser;
lease4 = parser.parse(config, cmd_args_);
lease4 = parser.parse(config, cmd_args_, force_create);
// checkLeaseIntegrity(config, lease4);
......@@ -234,7 +236,7 @@ LeaseCmdsImpl::leaseAddHandler(CalloutHandle& handle) {
} else {
Lease6Parser parser;
lease6 = parser.parse(config, cmd_args_);
lease6 = parser.parse(config, cmd_args_, force_create);
// checkLeaseIntegrity(config, lease6);
......@@ -599,12 +601,19 @@ LeaseCmdsImpl::lease4UpdateHandler(CalloutHandle& handle) {
ConstSrvConfigPtr config = CfgMgr::instance().getCurrentCfg();
Lease4Ptr lease4;
Lease4Parser parser;
bool force_create = false;
// The parser does sanity checks (if the address is in scope, if
// subnet-id is valid, etc)
lease4 = parser.parse(config, cmd_args_);
lease4 = parser.parse(config, cmd_args_, force_create);
if (force_create && !LeaseMgrFactory::instance().getLease4(lease4->addr_)) {
LeaseMgrFactory::instance().addLease(lease4);
setSuccessResponse(handle, "IPv4 lease added.");
LeaseMgrFactory::instance().updateLease4(lease4);
setSuccessResponse(handle, "IPv4 lease updated.");
} else {
LeaseMgrFactory::instance().updateLease4(lease4);
setSuccessResponse(handle, "IPv4 lease updated.");
}
} catch (const std::exception& ex) {
setErrorResponse(handle, ex.what());
return (1);
......@@ -627,12 +636,19 @@ LeaseCmdsImpl::lease6UpdateHandler(CalloutHandle& handle) {
ConstSrvConfigPtr config = CfgMgr::instance().getCurrentCfg();
Lease6Ptr lease6;
Lease6Parser parser;
bool force_create = false;
// The parser does sanity checks (if the address is in scope, if
// subnet-id is valid, etc)
lease6 = parser.parse(config, cmd_args_);
LeaseMgrFactory::instance().updateLease6(lease6);
setSuccessResponse(handle, "IPv6 lease updated.");
lease6 = parser.parse(config, cmd_args_, force_create);
if (force_create && !LeaseMgrFactory::instance().getLease6(lease6->type_,
lease6->addr_)) {
LeaseMgrFactory::instance().addLease(lease6);
setSuccessResponse(handle, "IPv6 lease added.");
} else {
LeaseMgrFactory::instance().updateLease6(lease6);
setSuccessResponse(handle, "IPv6 lease updated.");
}
} catch (const std::exception& ex) {
setErrorResponse(handle, ex.what());
return (1);
......
// Copyright (C) 2017 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2017-2018 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
......@@ -227,6 +227,10 @@ public:
/// }
/// };
///
/// The optional 'force-create' boolean parameter may be specified to force
/// the lease to be created if it doesn't exist. By default, this parameter
/// is set to false, which means that the lease is not created.
///
/// @param handle Callout context - which is expected to contain the
/// update command JSON text in the "command" argument
/// @return result of the operation
......@@ -255,6 +259,10 @@ public:
/// }
/// }";
///
/// The optional 'force-create' boolean parameter may be specified to force
/// the lease to be created if it doesn't exist. By default, this parameter
/// is set to false, which means that the lease is not created.
///
/// @param handle Callout context - which is expected to contain the
/// update command JSON text in the "command" argument
/// @return result of the operation
......
// Copyright (C) 2017 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2017-2018 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
......@@ -22,7 +22,8 @@ namespace lease_cmds {
Lease4Ptr
Lease4Parser::parse(ConstSrvConfigPtr& cfg,
const ConstElementPtr& lease_info) {
const ConstElementPtr& lease_info,
bool& force_create) {
if (!lease_info) {
isc_throw(BadValue, "lease information missing");
}
......@@ -117,12 +118,21 @@ Lease4Parser::parse(ConstSrvConfigPtr& cfg,
cltt, subnet_id,
fqdn_fwd, fqdn_rev, hostname));
l->state_ = state;
// Retrieve the optional flag indicating if the lease must be created when it
// doesn't exist during the update.
force_create = false;
if (lease_info->contains("force-create")) {
force_create = getBoolean(lease_info, "force-create");
}
return (l);
}
Lease6Ptr
Lease6Parser::parse(ConstSrvConfigPtr& cfg,
const ConstElementPtr& lease_info) {
const ConstElementPtr& lease_info,
bool& force_create) {
if (!lease_info) {
isc_throw(BadValue, "lease information missing");
}
......@@ -250,6 +260,14 @@ Lease6Parser::parse(ConstSrvConfigPtr& cfg,
hwaddr_ptr, prefix_len));
l->cltt_ = cltt;
l->state_ = state;
// Retrieve the optional flag indicating if the lease must be created when it
// doesn't exist during the update.
force_create = false;
if (lease_info->contains("force-create")) {
force_create = getBoolean(lease_info, "force-create");
}
return (l);
}
......
// Copyright (C) 2017 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2017-2018 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
......@@ -40,11 +40,14 @@ public:
///
/// @param cfg Currently running config (used for sanity checks and defaults)
/// @param lease_info structure to be parsed
/// @param [out] force_create indicates if the lease should be created when it
/// doesn't exist.
/// @return A pointer to Lease4
/// @throw BadValue if any of the parameters is invalid
/// @throw DhcpConfigError if mandatory parameter is missing
virtual isc::dhcp::Lease4Ptr parse(isc::dhcp::ConstSrvConfigPtr& cfg,
const isc::data::ConstElementPtr& lease_info);
const isc::data::ConstElementPtr& lease_info,
bool& force_create);
/// @brief virtual dtor (does nothing)
virtual ~Lease4Parser() {}
......@@ -76,11 +79,14 @@ public:
///
/// @param cfg Currently running config (used for sanity checks and defaults)
/// @param lease_info structure to be parsed
/// @param [out] force_create indicates if the lease should be created when it
/// doesn't exist.
/// @return A pointer to Lease4
/// @throw BadValue if any of the parameters is invalid
/// @throw DhcpConfigError if mandatory parameter is missing
virtual isc::dhcp::Lease6Ptr parse(isc::dhcp::ConstSrvConfigPtr& cfg,
const isc::data::ConstElementPtr& lease_info);
const isc::data::ConstElementPtr& lease_info,
bool& force_create);
/// @brief virtual dtor (does nothing)
virtual ~Lease6Parser() {}
......
// Copyright (C) 2017 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2017-2018 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
......@@ -1498,6 +1498,67 @@ TEST_F(LeaseCmdsTest, Lease4Update) {
EXPECT_EQ("newhostname.example.org", l->hostname_);
}
// Check that a lease4 is created if it doesn't exist during the update.
// To trigger this behavior 'force-create' boolean parameter must be
// included in the command.
TEST_F(LeaseCmdsTest, Lease4UpdateForceCreate) {
// Initialize lease manager (false = v4, true = add a lease)
initLeaseMgr(false, false);
// Check that the lease manager pointer is there.
ASSERT_TRUE(lmptr_);
// Now send the command.
string txt =
"{\n"
" \"command\": \"lease4-update\",\n"
" \"arguments\": {"
" \"subnet-id\": 44,\n"
" \"ip-address\": \"192.0.2.1\",\n"
" \"hw-address\": \"1a:1b:1c:1d:1e:1f\",\n"
" \"hostname\": \"newhostname.example.org\","
" \"force-create\": true"
" }\n"
"}";
string exp_rsp = "IPv4 lease added.";
testCommand(txt, CONTROL_RESULT_SUCCESS, exp_rsp);
// Now check that the lease is still there.
Lease4Ptr l = lmptr_->getLease4(IOAddress("192.0.2.1"));
ASSERT_TRUE(l);
// Make sure it contains expected values..
ASSERT_TRUE(l->hwaddr_);
EXPECT_EQ("1a:1b:1c:1d:1e:1f", l->hwaddr_->toText(false));
EXPECT_EQ("newhostname.example.org", l->hostname_);
}
// Check that lease4-update correctly handles case when the 'force-create'
// parameter is explicitly set to false.
TEST_F(LeaseCmdsTest, Lease4UpdateDoNotForceCreate) {
// Initialize lease manager (false = v4, false = don't add any lease)
initLeaseMgr(false, false);
// Check that the lease manager pointer is there.
ASSERT_TRUE(lmptr_);
// Now send the command.
string txt =
"{\n"
" \"command\": \"lease4-update\",\n"
" \"arguments\": {"
" \"subnet-id\": 44,\n"
" \"ip-address\": \"192.0.2.1\",\n"
" \"hw-address\": \"1a:1b:1c:1d:1e:1f\",\n"
" \"hostname\": \"newhostname.example.org\","
" \"force-create\": false"
" }\n"
"}";
string exp_rsp = "failed to update the lease with address 192.0.2.1 - no such lease";
testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp);
}
// Test checks if lease6-update handler refuses calls with missing parameters.
TEST_F(LeaseCmdsTest, Lease6UpdateMissingParams) {
// Initialize lease manager (true = v6, true = add a lease)
......@@ -1666,6 +1727,71 @@ TEST_F(LeaseCmdsTest, Lease6UpdateNoLease) {
testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp);
}
// Check that a lease6 is created if it doesn't exist during the update.
// To trigger this behavior 'force-create' boolean parameter must be
// included in the command.
TEST_F(LeaseCmdsTest, Lease6UpdateForceCreate) {
// Initialize lease manager (true = v6, true = add a lease)
initLeaseMgr(true, false);
// Check that the lease manager pointer is there.
ASSERT_TRUE(lmptr_);
// Now send the command.
string txt =
"{\n"
" \"command\": \"lease6-update\",\n"
" \"arguments\": {"
" \"subnet-id\": 66,\n"
" \"ip-address\": \"2001:db8::1\",\n"
" \"iaid\": 7654321,\n"
" \"duid\": \"88:88:88:88:88:88:88:88\",\n"
" \"hostname\": \"newhostname.example.org\","
" \"force-create\": true"
" }\n"
"}";
string exp_rsp = "IPv6 lease added.";
testCommand(txt, CONTROL_RESULT_SUCCESS, exp_rsp);
// Now check that the lease is really there.
Lease6Ptr l = lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::1"));
ASSERT_TRUE(l);
// Make sure the lease is correct.
ASSERT_TRUE(l->duid_);
EXPECT_EQ("88:88:88:88:88:88:88:88", l->duid_->toText());
EXPECT_EQ("newhostname.example.org", l->hostname_);
EXPECT_EQ(7654321, l->iaid_);
}
// Check that lease6-update correctly handles case when the 'force-create'
// parameter is explicitly set to false.
TEST_F(LeaseCmdsTest, Lease6UpdateDoNotForceCreate) {
// Initialize lease manager (true = v6, false = don't add any lease)
initLeaseMgr(true, false);
// Check that the lease manager pointer is there.
ASSERT_TRUE(lmptr_);
// Now send the command.
string txt =
"{\n"
" \"command\": \"lease6-update\",\n"
" \"arguments\": {"
" \"subnet-id\": 66,\n"
" \"ip-address\": \"2001:db8::1\",\n"
" \"iaid\": 7654321,\n"
" \"duid\": \"88:88:88:88:88:88:88:88\",\n"
" \"hostname\": \"newhostname.example.org\","
" \"force-create\": false"
" }\n"
"}";
string exp_rsp = "failed to update the lease with address 2001:db8::1 - no such lease";
testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp);
}
// Checks that lease6-del can handle a situation when the query is
// broken (some required parameters are missing).
TEST_F(LeaseCmdsTest, Lease4DelMissingParams) {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment