src/bin/d2/tests/d2_process_tests.sh
src/bin/d2/tests/test_data_files_config.h
src/bin/dhcp4/Makefile
- src/bin/dhcp4/spec_config.h.pre
src/bin/dhcp4/tests/Makefile
src/bin/dhcp4/tests/dhcp4_process_tests.sh
src/bin/dhcp4/tests/marker_file.h
src/bin/dhcp4/tests/test_data_files_config.h
src/bin/dhcp4/tests/test_libraries.h
src/bin/dhcp6/Makefile
- src/bin/dhcp6/spec_config.h.pre
src/bin/dhcp6/tests/Makefile
src/bin/dhcp6/tests/dhcp6_process_tests.sh
src/bin/dhcp6/tests/marker_file.h
src/lib/log/tests/severity_test.sh
src/lib/log/tests/tempdir.h
src/lib/process/Makefile
- src/lib/process/spec_config.h.pre
src/lib/process/tests/Makefile
src/lib/process/testutils/Makefile
src/lib/stats/Makefile
man_MANS = kea-dhcp-ddns.8
DISTCLEANFILES = $(man_MANS)
-EXTRA_DIST = $(man_MANS) kea-dhcp-ddns.xml dhcp-ddns.spec d2.dox
+EXTRA_DIST = $(man_MANS) kea-dhcp-ddns.xml d2.dox
EXTRA_DIST += d2_parser.yy
EXTRA_DIST += images/abstract_app_classes.svg images/add_state_model.svg
endif
kea_dhcp_ddnsdir = $(pkgdatadir)
-kea_dhcp_ddns_DATA = dhcp-ddns.spec
if GENERATE_PARSER
+++ /dev/null
-{
-"module_spec":
-{
- "module_name": "DhcpDdns",
- "module_description": "DHPC-DDNS Service",
- "config_data": [
- {
- "item_name": "ip-address",
- "item_type": "string",
- "item_optional": false,
- "item_default": "127.0.0.1"
- },
- {
- "item_name": "port",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 53001
- },
- {
- "item_name": "dns-server-timeout",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 100
- },
- {
- "item_name": "ncr-protocol",
- "item_type": "string",
- "item_optional": true,
- "item_default": "UDP"
- },
- {
- "item_name": "ncr-format",
- "item_type": "string",
- "item_optional": true,
- "item_default": "JSON"
- },
- {
- "item_name": "tsig-keys",
- "item_type": "list",
- "item_optional": true,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "tsig-key",
- "item_type": "map",
- "item_optional": false,
- "item_default": {"algorithm" : "HMAC-MD5"},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- {
- "item_name": "algorithm",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- {
- "item_name": "digest-bits",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 0
- },
- {
- "item_name": "secret",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- }]
- }
- },
- {
- "item_name": "forward-ddns",
- "item_type": "map",
- "item_optional": true,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "ddns-domains",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "ddns-domain",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- {
- "item_name": "key-name",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
-
- {
- "item_name": "dns-servers",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "dns-server",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "hostname",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "ip-address",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "port",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 53
- }]
- }
- }]
- }
- }]
- },
-
- {
- "item_name": "reverse-ddns",
- "item_type": "map",
- "item_optional": true,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "ddns-domains",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "ddns-domain",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- {
- "item_name": "key-name",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
-
- {
- "item_name": "dns-servers",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "dns-server",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "hostname",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "ip-address",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "port",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 53
- }]
- }
- }]
- }
- }]
- }],
-
- "commands": [
- {
- "command_name": "shutdown",
- "command_description": "Shuts down kea-dhcp-ddns module server.",
- "command_args": [
- {
- "item_name": "type",
- "item_type": "string",
- "item_optional": true,
- "item_default": "normal",
- "item_description": "values: normal (default), now, or drain_first"
- }
- ]
- }
- ]
- }
-}
-
#include <config.h>
-#include <config/module_spec.h>
#include <d2/d2_config.h>
#include <d2/d2_cfg_mgr.h>
#include <d2/d2_simple_parser.h>
namespace {
-/// @brief Function to create full path to the spec file
-///
-/// The full path is dependent upon the value of D2_SRC_DIR which
-/// whose value is generated from test_data_files_config.h.in
-///
-/// @param name file name to which the path should be prepended
-std::string specfile(const std::string& name) {
- return (std::string(D2_SRC_DIR) + "/" + name);
-}
-
/// @brief Function to create full path to test data file
///
/// The full path is dependent upon the value of D2_TEST_DATA_DIR which
#define SYNTAX_ERROR(a,b) ASSERT_TRUE(runConfigOrFail(a,SYNTAX_ERROR,b))
#define LOGIC_ERROR(a,b) ASSERT_TRUE(runConfigOrFail(a,LOGIC_ERROR,b))
-/// @brief Tests that the spec file is valid.
-/// Verifies that the DHCP-DDNS configuration specification file
-/// is valid.
-TEST(D2SpecTest, basicSpec) {
- ASSERT_NO_THROW(isc::config::
- moduleSpecFromFile(specfile("dhcp-ddns.spec")));
-}
-
/// @brief Tests a basic valid configuration for D2Param.
TEST_F(D2CfgMgrTest, validParamsEntry) {
// Verify that ip_address can be valid v4 address.
AM_LDFLAGS = -static
endif
-CLEANFILES = *.gcno *.gcda spec_config.h dhcp4_messages.h dhcp4_messages.cc s-messages
+CLEANFILES = *.gcno *.gcda dhcp4_messages.h dhcp4_messages.cc s-messages
man_MANS = kea-dhcp4.8
DISTCLEANFILES = $(man_MANS)
-EXTRA_DIST = $(man_MANS) kea-dhcp4.xml dhcp4.spec
+EXTRA_DIST = $(man_MANS) kea-dhcp4.xml
EXTRA_DIST += dhcp4.dox dhcp4_hooks.dox dhcp4o6.dox
EXTRA_DIST += dhcp4_parser.yy
endif
-spec_config.h: spec_config.h.pre
- $(SED) -e "s|@@LOCALSTATEDIR@@|$(localstatedir)|" spec_config.h.pre >$@
-
dhcp4_messages.h dhcp4_messages.cc: s-messages
s-messages: dhcp4_messages.mes
$(top_builddir)/src/lib/log/compiler/kea-msg-compiler $(top_srcdir)/src/bin/dhcp4/dhcp4_messages.mes
touch $@
-BUILT_SOURCES = spec_config.h dhcp4_messages.h dhcp4_messages.cc
+BUILT_SOURCES = dhcp4_messages.h dhcp4_messages.cc
# convenience archive
endif
kea_dhcp4dir = $(pkgdatadir)
-kea_dhcp4_DATA = dhcp4.spec
if GENERATE_PARSER
+++ /dev/null
-{
- "module_spec": {
- "module_name": "Dhcp4",
- "module_description": "DHCPv4 server daemon",
- "config_data": [
- {
- "item_name": "hooks-libraries",
- "item_type": "list",
- "item_optional": true,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "hooks-library-spec",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "library",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- }
- ]
- }
- },
-
- { "item_name": "interfaces-config",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "interfaces",
- "item_type": "list",
- "item_optional": false,
- "item_default": [ "*" ],
- "list_item_spec":
- {
- "item_name": "interface_name",
- "item_type": "string",
- "item_optional": false,
- "item_default": "*"
- }
- },
-
- { "item_name": "dhcp-socket-type",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- }
- ]
- },
-
- { "item_name": "expired-leases-processing",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "reclaim-timer-wait-time",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 10
- },
- {
- "item_name": "flush-reclaimed-timer-wait-time",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 25
- },
- {
- "item_name": "hold-reclaimed-time",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 3600
- },
- {
- "item_name": "max-reclaim-leases",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 100
- },
- {
- "item_name": "max-reclaim-time",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 250
- },
- {
- "item_name": "unwarned-reclaim-cycles",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 5
- }
- ]
- },
-
- { "item_name": "renew-timer",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 1000
- },
-
- { "item_name": "rebind-timer",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 2000
- },
-
- { "item_name": "valid-lifetime",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 4000
- },
-
- { "item_name": "next-server",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
-
- { "item_name": "echo-client-id",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": true
- },
-
- { "item_name": "match-client-id",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": true
- },
-
- { "item_name": "option-def",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "single-option-def",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- { "item_name": "code",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 0
- },
-
- { "item_name": "type",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- { "item_name": "array",
- "item_type": "boolean",
- "item_optional": false,
- "item_default": false
- },
-
- { "item_name": "record-types",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- { "item_name": "space",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- { "item_name": "encapsulate",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- } ]
- }
- },
-
- { "item_name": "option-data",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "single-option-data",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- { "item_name": "code",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 0
- },
- { "item_name": "data",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- { "item_name": "csv-format",
- "item_type": "boolean",
- "item_optional": false,
- "item_default": false
- },
- { "item_name": "space",
- "item_type": "string",
- "item_optional": false,
- "item_default": "dhcp4"
- } ]
- }
- },
-
- { "item_name": "lease-database",
- "item_type": "map",
- "item_optional": false,
- "item_default": {"type": "memfile"},
- "map_item_spec": [
- {
- "item_name": "type",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "user",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "host",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "password",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "persist",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": true
- },
- {
- "item_name": "lfc-interval",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 0
- },
- {
- "item_name": "readonly",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": false
- }
- ]
- },
- { "item_name": "client-classes",
- "item_type": "list",
- "item_optional": true,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "client-class",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- { "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- { "item_name": "test",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- { "item_name": "option-data",
- "item_type": "list",
- "item_optional": true,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "single-option-data",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- {
- "item_name": "code",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 0
- },
- {
- "item_name": "data",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- { "item_name": "csv-format",
- "item_type": "boolean",
- "item_optional": false,
- "item_default": false
- },
- { "item_name": "space",
- "item_type": "string",
- "item_optional": false,
- "item_default": "dhcp4"
- } ]
- }
- }
- ]
- }
- },
- { "item_name": "subnet4",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "single-subnet4",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
-
- { "item_name": "subnet",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
-
- { "item_name": "id",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 0
- },
-
- { "item_name": "renew-timer",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 1000
- },
-
- { "item_name": "rebind-timer",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 2000
- },
-
- { "item_name": "valid-lifetime",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 7200
- },
-
- { "item_name": "next-server",
- "item_type": "string",
- "item_optional": true,
- "item_default": "0.0.0.0"
- },
-
- { "item_name": "match-client-id",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": true
- },
-
- { "item_name": "pool",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "type",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- }
- },
-
- { "item_name": "client-class",
- "item_type": "string",
- "item_optional": false,
- "item_default": "",
- "item_description" : "Restricts access to this subnet to specified client class (if defined)"
- },
-
- { "item_name": "relay",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "item_description" : "Structure holding relay information.",
- "map_item_spec": [
- {
- "item_name": "ip-address",
- "item_type": "string",
- "item_optional": false,
- "item_default": "0.0.0.0",
- "item_description" : "IPv4 address of the relay (defaults to 0.0.0.0 if not specified)."
- }
- ]
- },
- { "item_name": "option-data",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "single-option-data",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- {
- "item_name": "code",
- "item_type": "integer",
- "item_optional": false,
- "item_default": 0
- },
- {
- "item_name": "data",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- { "item_name": "csv-format",
- "item_type": "boolean",
- "item_optional": false,
- "item_default": false
- },
- { "item_name": "space",
- "item_type": "string",
- "item_optional": false,
- "item_default": "dhcp4"
- } ]
- }
- },
- { "item_name": "reservations",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "reservation",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "hw-address",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "duid",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "hostname",
- "item_type": "string",
- "item_optional": false,
- "item_default": ""
- },
- {
- "item_name": "ip-address",
- "item_type": "string",
- "item_optional": false,
- "item_default": "0.0.0.0"
- },
- {
- "item_name": "next-server",
- "item_type": "string",
- "item_optional": true,
- "item_default": "0.0.0.0"
- },
- {
- "item_name": "server-hostname",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "boot-file-name",
- "item_type": "string",
- "item_optional": true,
- "item_default": ""
- },
- {
- "item_name": "client-classes",
- "item_type": "list",
- "item_optional": true,
- "item_default": [],
- "item_description": "list of reserved classes for a client",
- "list_item_spec":
- {
- "item_name": "client-class",
- "item_type": "string",
- "item_optional": false,
- "item_default": "",
- "item_description": "one of the classes reserved for a client"
- }
- } ]
- }
- },
- {
- "item_name": "reservation-mode",
- "item_type": "string",
- "item_optional": true,
- "item_default": "all",
- "item_description": "Specifies allowed host reservation types. Disabling unused modes may improve performance. Allowed values: disabled, off, out-of-pool, all"
- }
- ]
- }
- },
-
- { "item_name": "dhcp-ddns",
- "item_type": "map",
- "item_optional": false,
- "item_default": {"enable-updates": false},
- "item_description" : "Contains parameters pertaining DHCP-driven DDNS updates",
- "map_item_spec": [
- {
- "item_name": "enable-updates",
- "item_type": "boolean",
- "item_optional": false,
- "item_default": false,
- "item_description" : "Enables DDNS update processing"
- },
- {
- "item_name": "server-ip",
- "item_type": "string",
- "item_optional": true,
- "item_default": "127.0.0.1",
- "item_description" : "IP address of kea-dhcp-ddns (IPv4 or IPv6)"
- },
- {
- "item_name": "server-port",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 53001,
- "item_description" : "port number of kea-dhcp-ddns"
- },
- {
- "item_name": "sender-ip",
- "item_type": "string",
- "item_optional": true,
- "item_default": "",
- "item_description" : "IP address from which to send to kea-dhcp-ddns (IPv4 or IPv6)"
- },
- {
- "item_name": "sender-port",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 0,
- "item_description" : "port number from which to send to kea-dhcp-ddns"
- },
- {
- "item_name": "max-queue-size",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 1024,
- "item_description" : "maximum number of requests allowed in the send queue"
- },
- {
- "item_name": "ncr-protocol",
- "item_type": "string",
- "item_optional": true,
- "item_default": "UDP",
- "item_description" : "Socket protocol to use with kea-dhcp-ddns"
- },
- {
- "item_name": "ncr-format",
- "item_type": "string",
- "item_optional": true,
- "item_default": "JSON",
- "item_description" : "Format of the update request packet"
- },
- {
-
- "item_name": "always-include-fqdn",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": false,
- "item_description": "Enable always including the FQDN option in its response"
- },
- {
- "item_name": "override-no-update",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": false,
- "item_description": "Do update, even if client requested no updates with N flag"
- },
- {
- "item_name": "override-client-update",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": false,
- "item_description": "Server performs an update even if client requested delegation"
- },
- {
- "item_name": "replace-client-name",
- "item_type": "string",
- "item_optional": true,
- "item_default": "never",
- "item_description": "Should server replace the domain-name supplied by the client"
- },
- {
- "item_name": "generated-prefix",
- "item_type": "string",
- "item_optional": true,
- "item_default": "myhost",
- "item_description": "Prefix to use when generating the client's name"
- },
-
- {
- "item_name": "qualifying-suffix",
- "item_type": "string",
- "item_optional": true,
- "item_default": "",
- "item_description": "Fully qualified domain-name suffix if partial name provided by client"
- },
- ]
- },
-
- ],
- "commands": [
- {
- "command_name": "shutdown",
- "command_description": "Shuts down DHCPv4 server.",
- "command_args": [
- {
- "item_name": "pid",
- "item_type": "integer",
- "item_optional": true
- }
- ]
- },
-
- {
- "command_name": "libreload",
- "command_description": "Reloads the current hooks libraries.",
- "command_args": []
- }
-
- ]
- }
-}
+++ /dev/null
-// Copyright (C) 2011-2015 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/.
-
-#define DHCP4_SPECFILE_LOCATION "@prefix@/share/@PACKAGE@/dhcp4.spec"
#include <gtest/gtest.h>
#include <cc/command_interpreter.h>
-#include <config/module_spec.h>
#include <dhcp4/dhcp4_srv.h>
#include <dhcp4/json_config_parser.h>
#include <dhcp/option4_addrlst.h>
"}"
};
-/// @brief Prepends the given name with the DHCP4 source directory
-///
-/// @param name file name of the desired file
-/// @return string containing the absolute path of the file in the DHCP source
-/// directory.
-std::string specfile(const std::string& name) {
- return (std::string(DHCP4_SRC_DIR) + "/" + name);
-}
-
-/// @brief Tests that the spec file is valid.
-/// Verifies that the Kea DHCPv4 configuration specification file is valid.
-TEST(Dhcp4SpecTest, basicSpec) {
- (isc::config::moduleSpecFromFile(specfile("dhcp4.spec")));
- ASSERT_NO_THROW(isc::config::moduleSpecFromFile(specfile("dhcp4.spec")));
-}
-
class Dhcp4ParserTest : public ::testing::Test {
protected:
// Check that no hooks libraries are loaded. This is a pre-condition for
AM_LDFLAGS = -static
endif
-CLEANFILES = spec_config.h dhcp6_messages.h dhcp6_messages.cc s-messages
+CLEANFILES = dhcp6_messages.h dhcp6_messages.cc s-messages
man_MANS = kea-dhcp6.8
DISTCLEANFILES = $(man_MANS)
-EXTRA_DIST = $(man_MANS) kea-dhcp6.xml dhcp6.spec
+EXTRA_DIST = $(man_MANS) kea-dhcp6.xml
EXTRA_DIST += dhcp6.dox dhcp6_hooks.dox dhcp4o6.dox
EXTRA_DIST += dhcp6_parser.yy
endif
-spec_config.h: spec_config.h.pre
- $(SED) -e "s|@@LOCALSTATEDIR@@|$(localstatedir)|" spec_config.h.pre >$@
-
dhcp6_messages.h dhcp6_messages.cc: s-messages
s-messages: dhcp6_messages.mes
$(top_builddir)/src/lib/log/compiler/kea-msg-compiler $(top_srcdir)/src/bin/dhcp6/dhcp6_messages.mes
touch $@
-BUILT_SOURCES = spec_config.h dhcp6_messages.h dhcp6_messages.cc
+BUILT_SOURCES = dhcp6_messages.h dhcp6_messages.cc
# convenience archive
endif
kea_dhcp6dir = $(pkgdatadir)
-kea_dhcp6_DATA = dhcp6.spec
if GENERATE_PARSER
#include <config.h>
#include <cc/command_interpreter.h>
-#include <config/module_spec.h>
#include <dhcp/libdhcp++.h>
#include <dhcp/option6_ia.h>
#include <dhcp/iface_mgr.h>
"}"
};
-std::string specfile(const std::string& name) {
- return (std::string(DHCP6_SRC_DIR) + "/" + name);
-}
-
-/// @brief Tests that the spec file is valid.
-/// Verifies that the DHCP6 configuration specification file is valid.
-TEST(Dhcp6SpecTest, basicSpec) {
- ASSERT_NO_THROW(isc::config::
- moduleSpecFromFile(specfile("dhcp6.spec")));
-}
-
class Dhcp6ParserTest : public ::testing::Test {
protected:
// Check that no hooks libraries are loaded. This is a pre-condition for
BUILT_SOURCES = config_messages.h config_messages.cc
lib_LTLIBRARIES = libkea-cfgclient.la
-libkea_cfgclient_la_SOURCES = config_data.h config_data.cc
-libkea_cfgclient_la_SOURCES += cmds_impl.h
-libkea_cfgclient_la_SOURCES += module_spec.h module_spec.cc
+libkea_cfgclient_la_SOURCES = cmds_impl.h
libkea_cfgclient_la_SOURCES += base_command_mgr.cc base_command_mgr.h
libkea_cfgclient_la_SOURCES += client_connection.cc client_connection.h
libkea_cfgclient_la_SOURCES += command_mgr.cc command_mgr.h
command_mgr.h \
config_data.h \
config_log.h \
- hooked_command_mgr.h \
- module_spec.h
+ hooked_command_mgr.h
+++ /dev/null
-// Copyright (C) 2010-2017 Internet Systems Consortium.
-//
-// 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/module_spec.h>
-
-#include <sstream>
-#include <iostream>
-#include <fstream>
-#include <cerrno>
-
-#include <boost/foreach.hpp>
-
-// todo: add more context to thrown ModuleSpecErrors?
-
-using namespace isc::data;
-using namespace isc::config;
-
-namespace {
-//
-// Private functions
-//
-
-void
-check_leaf_item(ConstElementPtr spec, const std::string& name,
- Element::types type, bool mandatory)
-{
- if (spec->contains(name)) {
- if (type == Element::any || spec->get(name)->getType() == type) {
- return;
- } else {
- isc_throw(ModuleSpecError,
- name + " not of type " + Element::typeToName(type));
- }
- } else if (mandatory) {
- // todo: want parent item name, and perhaps some info about location
- // in list? or just catch and throw new...
- // or make this part non-throwing and check return value...
- isc_throw(ModuleSpecError, name + " missing in " + spec->str());
- }
-}
-
-void check_config_item_list(ConstElementPtr spec);
-
-void
-check_config_item(ConstElementPtr spec) {
- check_leaf_item(spec, "item_name", Element::string, true);
- check_leaf_item(spec, "item_type", Element::string, true);
- check_leaf_item(spec, "item_optional", Element::boolean, true);
- check_leaf_item(spec, "item_default",
- Element::nameToType(spec->get("item_type")->stringValue()),
- !spec->get("item_optional")->boolValue()
- );
-
- // if list, check the list specification
- if (Element::nameToType(spec->get("item_type")->stringValue()) == Element::list) {
- check_leaf_item(spec, "list_item_spec", Element::map, true);
- check_config_item(spec->get("list_item_spec"));
- }
-
- if (spec->get("item_type")->stringValue() == "map") {
- check_leaf_item(spec, "map_item_spec", Element::list, true);
- check_config_item_list(spec->get("map_item_spec"));
- } else if (spec->get("item_type")->stringValue() == "named_set") {
- check_leaf_item(spec, "named_set_item_spec", Element::map, true);
- check_config_item(spec->get("named_set_item_spec"));
- }
-}
-
-void
-check_config_item_list(ConstElementPtr spec) {
- if (spec->getType() != Element::list) {
- isc_throw(ModuleSpecError, "config_data is not a list of elements");
- }
- BOOST_FOREACH(ConstElementPtr item, spec->listValue()) {
- check_config_item(item);
- }
-}
-
-// checks whether the given element is a valid statistics specification
-// returns false if the specification is bad
-bool
-check_format(ConstElementPtr value, ConstElementPtr format_name) {
- typedef std::map<std::string, std::string> format_types;
- format_types time_formats;
- // TODO: should be added other format types if necessary
- time_formats.insert(
- format_types::value_type("date-time", "%Y-%m-%dT%H:%M:%SZ") );
- time_formats.insert(
- format_types::value_type("date", "%Y-%m-%d") );
- time_formats.insert(
- format_types::value_type("time", "%H:%M:%S") );
- BOOST_FOREACH (const format_types::value_type& f, time_formats) {
- if (format_name->stringValue() == f.first) {
- struct tm tm;
- std::vector<char> buf(32);
- memset(&tm, 0, sizeof(tm));
- // reverse check
- return (strptime(value->stringValue().c_str(),
- f.second.c_str(), &tm) != NULL
- && strftime(&buf[0], buf.size(),
- f.second.c_str(), &tm) != 0
- && strncmp(value->stringValue().c_str(),
- &buf[0], buf.size()) == 0);
- }
- }
- return (false);
-}
-
-void check_statistics_item_list(ConstElementPtr spec);
-
-void
-check_statistics_item_list(ConstElementPtr spec) {
- if (spec->getType() != Element::list) {
- isc_throw(ModuleSpecError, "statistics is not a list of elements");
- }
- BOOST_FOREACH(ConstElementPtr item, spec->listValue()) {
- check_config_item(item);
- // additional checks for statistics
- check_leaf_item(item, "item_title", Element::string, true);
- check_leaf_item(item, "item_description", Element::string, true);
- check_leaf_item(item, "item_format", Element::string, false);
- // checks name of item_format and validation of item_default
- if (item->contains("item_format")
- && item->contains("item_default")) {
- if(!check_format(item->get("item_default"),
- item->get("item_format"))) {
- isc_throw(ModuleSpecError,
- "item_default not valid type of item_format");
- }
- }
- }
-}
-
-void
-check_command(ConstElementPtr spec) {
- check_leaf_item(spec, "command_name", Element::string, true);
- check_leaf_item(spec, "command_args", Element::list, true);
- check_config_item_list(spec->get("command_args"));
-}
-
-void
-check_command_list(ConstElementPtr spec) {
- if (spec->getType() != Element::list) {
- isc_throw(ModuleSpecError, "commands is not a list of elements");
- }
- BOOST_FOREACH(ConstElementPtr item, spec->listValue()) {
- check_command(item);
- }
-}
-
-void
-check_data_specification(ConstElementPtr spec) {
- check_leaf_item(spec, "module_name", Element::string, true);
- check_leaf_item(spec, "module_description", Element::string, false);
- // config_data is not mandatory; module could just define
- // commands and have no config
- if (spec->contains("config_data")) {
- check_config_item_list(spec->get("config_data"));
- }
- if (spec->contains("commands")) {
- check_command_list(spec->get("commands"));
- }
- if (spec->contains("statistics")) {
- check_statistics_item_list(spec->get("statistics"));
- }
-}
-
-// checks whether the given element is a valid module specification
-// throws a ModuleSpecError if the specification is bad
-void
-check_module_specification(ConstElementPtr def) {
- try {
- check_data_specification(def);
- } catch (const TypeError& te) {
- isc_throw(ModuleSpecError, te.what());
- }
-}
-}
-
-namespace isc {
-namespace config {
-//
-// Public functions
-//
-
-// throw ModuleSpecError
-ModuleSpec::ModuleSpec(ConstElementPtr module_spec_element,
- const bool check)
-
-{
- module_specification = module_spec_element;
- if (check) {
- check_module_specification(module_specification);
- }
-}
-
-ConstElementPtr
-ModuleSpec::getCommandsSpec() const {
- if (module_specification->contains("commands")) {
- return (module_specification->get("commands"));
- } else {
- return (ElementPtr());
- }
-}
-
-ConstElementPtr
-ModuleSpec::getConfigSpec() const {
- if (module_specification->contains("config_data")) {
- return (module_specification->get("config_data"));
- } else {
- return (ElementPtr());
- }
-}
-
-ConstElementPtr
-ModuleSpec::getStatisticsSpec() const {
- if (module_specification->contains("statistics")) {
- return (module_specification->get("statistics"));
- } else {
- return (ElementPtr());
- }
-}
-
-const std::string
-ModuleSpec::getModuleName() const {
- return (module_specification->get("module_name")->stringValue());
-}
-
-const std::string
-ModuleSpec::getModuleDescription() const {
- if (module_specification->contains("module_description")) {
- return (module_specification->get("module_description")->stringValue());
- } else {
- return (std::string(""));
- }
-}
-
-bool
-ModuleSpec::validateConfig(ConstElementPtr data, const bool full) const {
- ConstElementPtr spec = module_specification->find("config_data");
- return (validateSpecList(spec, data, full, ElementPtr()));
-}
-
-bool
-ModuleSpec::validateStatistics(ConstElementPtr data, const bool full) const {
- ConstElementPtr spec = module_specification->find("statistics");
- return (validateSpecList(spec, data, full, ElementPtr()));
-}
-
-bool
-ModuleSpec::validateCommand(const std::string& command,
- ConstElementPtr args,
- ElementPtr errors) const
-{
- if (args->getType() != Element::map) {
- errors->add(Element::create("args for command " +
- command + " is not a map"));
- return (false);
- }
-
- ConstElementPtr commands_spec = module_specification->find("commands");
- if (!commands_spec) {
- // there are no commands according to the spec.
- errors->add(Element::create("The given module has no commands"));
- return (false);
- }
-
- BOOST_FOREACH(ConstElementPtr cur_command, commands_spec->listValue()) {
- if (cur_command->get("command_name")->stringValue() == command) {
- return (validateSpecList(cur_command->get("command_args"),
- args, true, errors));
- }
- }
-
- // this command is unknown
- errors->add(Element::create("Unknown command " + command));
- return (false);
-}
-
-bool
-ModuleSpec::validateConfig(ConstElementPtr data, const bool full,
- ElementPtr errors) const
-{
- ConstElementPtr spec = module_specification->find("config_data");
- return (validateSpecList(spec, data, full, errors));
-}
-
-bool
-ModuleSpec::validateStatistics(ConstElementPtr data, const bool full,
- ElementPtr errors) const
-{
- ConstElementPtr spec = module_specification->find("statistics");
- return (validateSpecList(spec, data, full, errors));
-}
-
-// throw JSONError and ModuleSpecError
-ModuleSpec
-moduleSpecFromFile(const std::string& file_name, const bool check)
-{
- std::ifstream file;
-
- // zero out the errno to be safe
- errno = 0;
-
- file.open(file_name.c_str());
- if (!file) {
- std::stringstream errs;
- errs << "Error opening " << file_name << ": " << strerror(errno);
- isc_throw(ModuleSpecError, errs.str());
- }
-
- ConstElementPtr module_spec_element = Element::fromJSON(file, file_name);
- if (module_spec_element->contains("module_spec")) {
- return (ModuleSpec(module_spec_element->get("module_spec"), check));
- } else {
- isc_throw(ModuleSpecError, "No module_spec in specification");
- }
-}
-
-// throw JSONError and ModuleSpecError
-ModuleSpec
-moduleSpecFromFile(std::ifstream& in, const bool check)
-{
- ConstElementPtr module_spec_element = Element::fromJSON(in);
- if (module_spec_element->contains("module_spec")) {
- return (ModuleSpec(module_spec_element->get("module_spec"), check));
- } else {
- isc_throw(ModuleSpecError, "No module_spec in specification");
- }
-}
-
-
-namespace {
-//
-// private functions
-//
-
-//
-// helper functions for validation
-//
-bool
-check_type(ConstElementPtr spec, ConstElementPtr element) {
- std::string cur_item_type;
- cur_item_type = spec->get("item_type")->stringValue();
- if (cur_item_type == "any") {
- return (true);
- }
- switch (element->getType()) {
- case Element::integer:
- return (cur_item_type == "integer");
- break;
- case Element::real:
- return (cur_item_type == "real");
- break;
- case Element::boolean:
- return (cur_item_type == "boolean");
- break;
- case Element::string:
- return (cur_item_type == "string");
- break;
- case Element::list:
- return (cur_item_type == "list");
- break;
- case Element::map:
- return (cur_item_type == "map" ||
- cur_item_type == "named_set");
- break;
- }
- return (false);
-}
-}
-
-bool
-ModuleSpec::validateItem(ConstElementPtr spec, ConstElementPtr data,
- const bool full, ElementPtr errors) const
-{
- if (!check_type(spec, data)) {
- // we should do some proper error feedback here
- // std::cout << "type mismatch; not " << spec->get("item_type") << ": " << data << std::endl;
- // std::cout << spec << std::endl;
- if (errors) {
- errors->add(Element::create("Type mismatch"));
- }
- return (false);
- }
- if (data->getType() == Element::list) {
- ConstElementPtr list_spec = spec->get("list_item_spec");
- BOOST_FOREACH(ConstElementPtr list_el, data->listValue()) {
- if (!check_type(list_spec, list_el)) {
- if (errors) {
- errors->add(Element::create("Type mismatch"));
- }
- return (false);
- }
- if (list_spec->get("item_type")->stringValue() == "map") {
- if (!validateItem(list_spec, list_el, full, errors)) {
- return (false);
- }
- }
- }
- }
- if (data->getType() == Element::map) {
- // either a normal 'map' or a 'named set' (determined by which
- // subspecification it has)
- if (spec->contains("map_item_spec")) {
- if (!validateSpecList(spec->get("map_item_spec"), data, full, errors)) {
- return (false);
- }
- } else {
- typedef std::pair<std::string, ConstElementPtr> maptype;
-
- BOOST_FOREACH(maptype m, data->mapValue()) {
- if (!validateItem(spec->get("named_set_item_spec"), m.second, full, errors)) {
- return (false);
- }
- }
- }
- }
- if (spec->contains("item_format")) {
- if (!check_format(data, spec->get("item_format"))) {
- if (errors) {
- errors->add(Element::create("Format mismatch"));
- }
- return (false);
- }
- }
- return (true);
-}
-
-// spec is a map with item_name etc, data is a map
-bool
-ModuleSpec::validateSpec(ConstElementPtr spec, ConstElementPtr data,
- const bool full, ElementPtr errors) const
-{
- std::string item_name = spec->get("item_name")->stringValue();
- bool optional = spec->get("item_optional")->boolValue();
- ConstElementPtr data_el;
- data_el = data->get(item_name);
-
- if (data_el) {
- if (!validateItem(spec, data_el, full, errors)) {
- return (false);
- }
- } else {
- if (!optional && full) {
- if (errors) {
- errors->add(Element::create("Non-optional value missing"));
- }
- return (false);
- }
- }
- return (true);
-}
-
-// spec is a list of maps, data is a map
-bool
-ModuleSpec::validateSpecList(ConstElementPtr spec, ConstElementPtr data,
- const bool full, ElementPtr errors) const
-{
- bool validated = true;
- BOOST_FOREACH(ConstElementPtr cur_spec_el, spec->listValue()) {
- if (!validateSpec(cur_spec_el, data, full, errors)) {
- validated = false;
- }
- }
-
- typedef std::pair<std::string, ConstElementPtr> maptype;
-
- BOOST_FOREACH(maptype m, data->mapValue()) {
- // Ignore 'version' as a config element
- if (m.first.compare("version") != 0) {
- bool found = false;
- BOOST_FOREACH(ConstElementPtr cur_spec_el, spec->listValue()) {
- if (cur_spec_el->get("item_name")->stringValue().compare(m.first) == 0) {
- found = true;
- }
- }
- if (!found) {
- validated = false;
- if (errors) {
- errors->add(Element::create("Unknown item " + m.first));
- }
- }
- }
- }
-
- return (validated);
-}
-
-}
-}
+++ /dev/null
-// Copyright (C) 2010-2017 Internet Systems Consortium.
-//
-// 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/.
-
-#ifndef MODULE_SPEC_H
-#define MODULE_SPEC_H 1
-
-#include <cc/data.h>
-
-#include <sstream>
-
-namespace isc { namespace config {
-
- ///
- /// A standard ModuleSpec exception that is thrown when a
- /// specification is not in the correct form.
- ///
- class ModuleSpecError : public isc::Exception {
- public:
- ModuleSpecError(const char* file, size_t line,
- const char* what = "Module specification is invalid") :
- isc::Exception(file, line, what) {}
- };
-
- ///
- /// The \c ModuleSpec class holds a data specification.
- /// Each module should have a .spec file containing the specification
- /// for configuration and commands for that module.
- /// This class holds that specification, and provides a function to
- /// validate a set of data, to see whether it conforms to the given
- /// specification
- ///
- /// The form of the specification is described in doc/ (TODO)
- ///
- class ModuleSpec {
- public:
- ModuleSpec() {};
- /// Create a \c ModuleSpec instance with the given data as
- /// the specification
- /// \param e The Element containing the data specification
- /// \param check If false, the module specification in the file
- /// is not checked to be of the correct form.
- /// \throw ModuleSpecError
- explicit ModuleSpec(isc::data::ConstElementPtr e,
- const bool check = true);
-
- /// Returns the commands part of the specification as an
- /// ElementPtr, returns an empty ElementPtr if there is none
- /// \return ElementPtr Shared pointer to the commands
- /// part of the specification
- isc::data::ConstElementPtr getCommandsSpec() const;
-
- /// Returns the configuration part of the specification as an
- /// ElementPtr
- /// \return ElementPtr Shared pointer to the configuration
- /// part of the specification
- isc::data::ConstElementPtr getConfigSpec() const;
-
- /// Returns the statistics part of the specification as an
- /// ElementPtr
- /// \return ElementPtr Shared pointer to the statistics
- /// part of the specification
- isc::data::ConstElementPtr getStatisticsSpec() const;
-
- /// Returns the full module specification as an ElementPtr
- /// \return ElementPtr Shared pointer to the specification
- isc::data::ConstElementPtr getFullSpec() const {
- return module_specification;
- }
-
- /// Returns the module name as specified by the specification
- const std::string getModuleName() const;
-
- /// Returns the module description as specified by the specification
- /// returns an empty string if there is no description
- const std::string getModuleDescription() const;
-
- // returns true if the given element conforms to this data
- // configuration specification
- /// Validates the given configuration data for this specification.
- /// \param data The base \c Element of the data to check
- /// \param full If true, all non-optional configuration parameters
- /// must be specified.
- /// \return true if the data conforms to the specification,
- /// false otherwise.
- bool validateConfig(isc::data::ConstElementPtr data,
- const bool full = false) const;
-
- // returns true if the given element conforms to this data
- // statistics specification
- /// Validates the given statistics data for this specification.
- /// \param data The base \c Element of the data to check
- /// \param full If true, all non-optional statistics parameters
- /// must be specified.
- /// \return true if the data conforms to the specification,
- /// false otherwise.
- bool validateStatistics(isc::data::ConstElementPtr data,
- const bool full = false) const;
-
- /// Validates the arguments for the given command
- ///
- /// This checks the command and argument against the
- /// specification in the module's .spec file.
- ///
- /// A command is considered valid if:
- /// - it is known (the 'command' string must have an entry in
- /// the specification)
- /// - the args is a MapElement
- /// - args contains all mandatory arguments
- /// - args does not contain unknown arguments
- /// - all arguments in args match their specification
- /// If all of these are true, this function returns \c true
- /// If not, this method returns \c false
- ///
- /// Example usage:
- /// \code
- /// ElementPtr errors = Element::createList();
- /// if (module_specification_.validateCommand(cmd_str,
- /// arg,
- /// errors)) {
- /// std::cout << "Command is valid" << std::endl;
- /// } else {
- /// std::cout << "Command is invalid: " << std::endl;
- /// BOOST_FOREACH(ConstElementPtr error,
- /// errors->listValue()) {
- /// std::cout << error->stringValue() << std::endl;
- /// }
- /// }
- /// \endcode
- ///
- /// \param command The command to validate the arguments for
- /// \param args A dict containing the command parameters
- /// \param errors An ElementPtr pointing to a ListElement. Any
- /// errors that are found are added as
- /// StringElements to this list
- /// \return true if the command is known and the parameters are correct
- /// false otherwise
- bool validateCommand(const std::string& command,
- isc::data::ConstElementPtr args,
- isc::data::ElementPtr errors) const;
-
-
- /// errors must be of type ListElement
- bool validateConfig(isc::data::ConstElementPtr data, const bool full,
- isc::data::ElementPtr errors) const;
-
- /// errors must be of type ListElement
- bool validateStatistics(isc::data::ConstElementPtr data, const bool full,
- isc::data::ElementPtr errors) const;
-
- private:
- bool validateItem(isc::data::ConstElementPtr spec,
- isc::data::ConstElementPtr data,
- const bool full,
- isc::data::ElementPtr errors) const;
- bool validateSpec(isc::data::ConstElementPtr spec,
- isc::data::ConstElementPtr data,
- const bool full,
- isc::data::ElementPtr errors) const;
- bool validateSpecList(isc::data::ConstElementPtr spec,
- isc::data::ConstElementPtr data,
- const bool full,
- isc::data::ElementPtr errors) const;
-
- isc::data::ConstElementPtr module_specification;
- };
-
- /// Creates a \c ModuleSpec instance from the contents
- /// of the file given by file_name.
- /// If check is true, and the module specification is not of
- /// the correct form, a ModuleSpecError is thrown. If the file
- /// could not be parse, a ParseError is thrown.
- /// \param file_name The file to be opened and parsed
- /// \param check If true, the module specification in the file
- /// is checked to be of the correct form
- /// \throw isc::data::JSONError and ModuleSpecError
- ModuleSpec
- moduleSpecFromFile(const std::string& file_name, const bool check = true);
-
- /// Creates a \c ModuleSpec instance from the given input
- /// stream that contains the contents of a .spec file.
- /// If check is true, and the module specification is not of
- /// the correct form, a ModuleSpecError is thrown. If the
- /// file could not be parsed, a ParseError is thrown.
- /// \param in The std::istream containing the .spec file data
- /// \param check If true, the module specification is checked
- /// to be of the correct form
- /// \throw isc::data::JSONError and ModuleSpecError
- ModuleSpec
- moduleSpecFromFile(std::ifstream& in, const bool check = true);
-} }
-
-#endif // _DATA_DEF_H
-
-// Local Variables:
-// mode: c++
-// End:
TESTS =
if HAVE_GTEST
TESTS += run_unittests
-run_unittests_SOURCES = module_spec_unittests.cc
-run_unittests_SOURCES += client_connection_unittests.cc
-run_unittests_SOURCES += config_data_unittests.cc run_unittests.cc
+run_unittests_SOURCES = client_connection_unittests.cc
+run_unittests_SOURCES += run_unittests.cc
run_unittests_SOURCES += command_mgr_unittests.cc
run_unittests_CPPFLAGS = $(AM_CPPFLAGS) $(GTEST_INCLUDES)
+++ /dev/null
-
-// Copyright (C) 2009-2015 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 <gtest/gtest.h>
-
-#include <config/tests/data_def_unittests_config.h>
-#include <config/config_data.h>
-
-#include <iostream>
-
-using namespace isc::data;
-using namespace isc::config;
-
-ConfigData
-setupSpec2() {
- ModuleSpec spec2 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec22.spec");
- return (ConfigData(spec2));
-}
-
-TEST(ConfigData, Creation) {
- ConfigData cd = setupSpec2();
- EXPECT_TRUE(true);
-}
-
-TEST(ConfigData, getValue) {
- ModuleSpec spec22 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec22.spec");
- ConfigData cd = ConfigData(spec22);
- //std::cout << "[XX] SPEC2: " << cd.getModuleSpec().getFullSpec() << std::endl;
- bool is_default;
- //ElementPtr value = cd.getValue(is_default, "item1");
- EXPECT_EQ(9, cd.getValue("value1")->intValue());
- EXPECT_EQ(9, cd.getValue(is_default, "value1")->intValue());
- EXPECT_TRUE(is_default);
- EXPECT_EQ(9.9, cd.getValue("value2")->doubleValue());
- EXPECT_EQ(9.9, cd.getValue(is_default, "value2")->doubleValue());
- EXPECT_TRUE(is_default);
- EXPECT_FALSE(cd.getValue("value3")->boolValue());
- EXPECT_FALSE(cd.getValue(is_default, "value3")->boolValue());
- EXPECT_TRUE(is_default);
- EXPECT_EQ("default_string", cd.getValue("value4")->stringValue());
- EXPECT_EQ("default_string", cd.getValue(is_default, "value4")->stringValue());
- EXPECT_TRUE(is_default);
- EXPECT_EQ("a", cd.getValue("value5")->get(0)->stringValue());
- EXPECT_EQ("a", cd.getValue(is_default, "value5")->get(0)->stringValue());
- EXPECT_TRUE(is_default);
- EXPECT_EQ("b", cd.getValue("value5")->get(1)->stringValue());
- EXPECT_EQ("b", cd.getValue(is_default, "value5")->get(1)->stringValue());
- EXPECT_EQ("b", cd.getValue(is_default, "value5/")->get(1)->stringValue());
- EXPECT_TRUE(is_default);
- EXPECT_EQ("{ }", cd.getValue("value6")->str());
- EXPECT_EQ("{ }", cd.getValue(is_default, "value6")->str());
- EXPECT_EQ("{ }", cd.getValue(is_default, "value6/")->str());
- EXPECT_TRUE(is_default);
- EXPECT_EQ("[ ]", cd.getValue("value8")->str());
- EXPECT_EQ("[ ]", cd.getDefaultValue("value8")->str());
- EXPECT_EQ("empty", cd.getValue("value8/a")->stringValue());
-
- EXPECT_THROW(cd.getValue("")->str(), DataNotFoundError);
- EXPECT_THROW(cd.getValue("/")->str(), DataNotFoundError);
- EXPECT_THROW(cd.getValue("no_such_item")->str(), DataNotFoundError);
- EXPECT_THROW(cd.getValue("value6/a")->str(), DataNotFoundError);
- EXPECT_THROW(cd.getValue("value6/no_such_item")->str(), DataNotFoundError);
- EXPECT_THROW(cd.getValue("value8/b")->str(), DataNotFoundError);
-
- ModuleSpec spec1 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec1.spec");
- ConfigData cd1 = ConfigData(spec1);
- EXPECT_THROW(cd1.getValue("anything")->str(), DataNotFoundError);
-}
-
-TEST(ConfigData, getDefaultValue) {
- ModuleSpec spec31 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec31.spec");
- ConfigData cd = ConfigData(spec31);
- EXPECT_EQ("[ ]", cd.getDefaultValue("first_list_items")->str());
- EXPECT_EQ("\"foo\"", cd.getDefaultValue("first_list_items/foo")->str());
- EXPECT_EQ("{ }", cd.getDefaultValue("first_list_items/second_list_items/map_element")->str());
- EXPECT_EQ("[ ]", cd.getDefaultValue("first_list_items/second_list_items/map_element/list1")->str());
- EXPECT_EQ("1", cd.getDefaultValue("first_list_items/second_list_items/map_element/list1/number")->str());
-
- EXPECT_THROW(cd.getDefaultValue("doesnotexist")->str(), DataNotFoundError);
- EXPECT_THROW(cd.getDefaultValue("first_list_items/second_list_items/map_element/list1/doesnotexist")->str(), DataNotFoundError);
-}
-
-
-TEST(ConfigData, setLocalConfig) {
- ModuleSpec spec2 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec2.spec");
- ConfigData cd = ConfigData(spec2);
- bool is_default;
-
- ElementPtr my_config = Element::fromJSON("{ \"item1\": 2 }");
- ElementPtr my_config2 = Element::fromJSON("{ \"item6\": { \"value1\": \"a\" } }");
-
- EXPECT_EQ("{ }", cd.getValue("item6")->str());
-
- cd.setLocalConfig(my_config);
- EXPECT_EQ(2, cd.getValue(is_default, "item1")->intValue());
- EXPECT_FALSE(is_default);
- EXPECT_EQ("{ }", cd.getValue("item6")->str());
- EXPECT_EQ(1.1, cd.getValue(is_default, "item2")->doubleValue());
- EXPECT_TRUE(is_default);
-
- cd.setLocalConfig(my_config2);
- EXPECT_EQ("{ \"value1\": \"a\" }", cd.getValue("item6")->str());
-}
-
-TEST(ConfigData, getLocalConfig) {
- ModuleSpec spec2 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec2.spec");
- ConfigData cd = ConfigData(spec2);
- EXPECT_EQ("{ }", cd.getLocalConfig()->str());
-
- ElementPtr my_config = Element::fromJSON("{ \"item1\": 2 }");
- cd.setLocalConfig(my_config);
- EXPECT_EQ("{ \"item1\": 2 }", cd.getLocalConfig()->str());
-
- ElementPtr my_config2 = Element::fromJSON("{ \"item6\": { \"value1\": \"a\" } }");
- cd.setLocalConfig(my_config2);
- EXPECT_EQ("{ \"item6\": { \"value1\": \"a\" } }", cd.getLocalConfig()->str());
-}
-
-TEST(ConfigData, getItemList) {
- ModuleSpec spec2 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec2.spec");
- ConfigData cd = ConfigData(spec2);
-
- EXPECT_EQ("[ \"item1\", \"item2\", \"item3\", \"item4\", \"item5\", \"item6\" ]", cd.getItemList()->str());
- EXPECT_EQ("[ \"item1\", \"item2\", \"item3\", \"item4\", \"item5\", \"item6/value1\", \"item6/value2\" ]", cd.getItemList("", true)->str());
- EXPECT_EQ("[ \"item6/value1\", \"item6/value2\" ]", cd.getItemList("item6")->str());
-}
-
-TEST(ConfigData, getFullConfig) {
- ModuleSpec spec2 = moduleSpecFromFile(std::string(TEST_DATA_PATH) + "/spec2.spec");
- ConfigData cd = ConfigData(spec2);
-
- EXPECT_EQ("{ \"item1\": 1, \"item2\": 1.1, \"item3\": true, \"item4\": \"test\", \"item5\": [ \"a\", \"b\" ], \"item6\": { } }", cd.getFullConfig()->str());
- ElementPtr my_config = Element::fromJSON("{ \"item1\": 2 }");
- cd.setLocalConfig(my_config);
- EXPECT_EQ("{ \"item1\": 2, \"item2\": 1.1, \"item3\": true, \"item4\": \"test\", \"item5\": [ \"a\", \"b\" ], \"item6\": { } }", cd.getFullConfig()->str());
- ElementPtr my_config2 = Element::fromJSON("{ \"item6\": { \"value1\": \"a\" } }");
- cd.setLocalConfig(my_config2);
- EXPECT_EQ("{ \"item1\": 1, \"item2\": 1.1, \"item3\": true, \"item4\": \"test\", \"item5\": [ \"a\", \"b\" ], \"item6\": { \"value1\": \"a\" } }", cd.getFullConfig()->str());
- ElementPtr my_config3 = Element::fromJSON("{ \"item6\": { \"value2\": 123 } }");
- cd.setLocalConfig(my_config3);
- EXPECT_EQ("{ \"item1\": 1, \"item2\": 1.1, \"item3\": true, \"item4\": \"test\", \"item5\": [ \"a\", \"b\" ], \"item6\": { \"value2\": 123 } }", cd.getFullConfig()->str());
-}
-
+++ /dev/null
-// Copyright (C) 2009-2015 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 <gtest/gtest.h>
-
-#include <config/module_spec.h>
-
-#include <fstream>
-
-#include <boost/foreach.hpp>
-
-#include <config/tests/data_def_unittests_config.h>
-
-using namespace isc::data;
-using namespace isc::config;
-
-std::string specfile(const std::string& name) {
- return (std::string(TEST_DATA_PATH) + "/" + name);
-}
-
-void
-moduleSpecError(const std::string& file,
- const std::string& error1,
- const std::string& error2 = "",
- const std::string& error3 = "")
-{
- EXPECT_THROW(moduleSpecFromFile(specfile(file)), ModuleSpecError);
- try {
- ModuleSpec dd = moduleSpecFromFile(specfile(file));
- } catch (const ModuleSpecError& dde) {
- std::string ddew = dde.what();
- EXPECT_EQ(error1 + error2 + error3, ddew);
- }
-}
-
-TEST(ModuleSpec, ReadingSpecfiles) {
- // Tests whether we can open specfiles and if we get the
- // right parse errors
- ModuleSpec dd = moduleSpecFromFile(specfile("spec1.spec"));
- EXPECT_EQ(dd.getFullSpec()->get("module_name")
- ->stringValue(), "Spec1");
- dd = moduleSpecFromFile(specfile("spec2.spec"));
- EXPECT_EQ(dd.getFullSpec()->get("config_data")->size(), 6);
- moduleSpecError("doesnotexist",
- "Error opening ",
- specfile("doesnotexist"),
- ": No such file or directory");
-
- dd = moduleSpecFromFile(specfile("spec2.spec"));
- EXPECT_EQ("[ { \"command_args\": [ { \"item_default\": \"\", \"item_name\": \"message\", \"item_optional\": false, \"item_type\": \"string\" } ], \"command_description\": \"Print the given message to stdout\", \"command_name\": \"print_message\" }, { \"command_args\": [ ], \"command_description\": \"Shut down Kea\", \"command_name\": \"shutdown\" } ]", dd.getCommandsSpec()->str());
- EXPECT_EQ("[ { \"item_default\": \"1970-01-01T00:00:00Z\", \"item_description\": \"A dummy date time\", \"item_format\": \"date-time\", \"item_name\": \"dummy_time\", \"item_optional\": false, \"item_title\": \"Dummy Time\", \"item_type\": \"string\" } ]", dd.getStatisticsSpec()->str());
- EXPECT_EQ("Spec2", dd.getModuleName());
- EXPECT_EQ("", dd.getModuleDescription());
-
- dd = moduleSpecFromFile(specfile("spec25.spec"));
- EXPECT_EQ("Spec25", dd.getModuleName());
- EXPECT_EQ("Just an empty module", dd.getModuleDescription());
- EXPECT_THROW(moduleSpecFromFile(specfile("spec26.spec")), ModuleSpecError);
- EXPECT_THROW(moduleSpecFromFile(specfile("spec34.spec")), ModuleSpecError);
- EXPECT_THROW(moduleSpecFromFile(specfile("spec35.spec")), ModuleSpecError);
- EXPECT_THROW(moduleSpecFromFile(specfile("spec36.spec")), ModuleSpecError);
- EXPECT_THROW(moduleSpecFromFile(specfile("spec37.spec")), ModuleSpecError);
- EXPECT_THROW(moduleSpecFromFile(specfile("spec38.spec")), ModuleSpecError);
-
- std::ifstream file;
- file.open(specfile("spec1.spec").c_str());
- dd = moduleSpecFromFile(file);
- EXPECT_EQ(dd.getFullSpec()->get("module_name")
- ->stringValue(), "Spec1");
- EXPECT_TRUE(isNull(dd.getCommandsSpec()));
- EXPECT_TRUE(isNull(dd.getStatisticsSpec()));
-
- std::ifstream file2;
- file2.open(specfile("spec8.spec").c_str());
- EXPECT_THROW(moduleSpecFromFile(file2), ModuleSpecError);
-
-}
-
-TEST(ModuleSpec, SpecfileItems) {
- moduleSpecError("spec3.spec",
- "item_name missing in { \"item_default\": 1, \"item_optional\": false, \"item_type\": \"integer\" }");
- moduleSpecError("spec4.spec",
- "item_type missing in { \"item_default\": 1, \"item_name\": \"item1\", \"item_optional\": false }");
- moduleSpecError("spec5.spec",
- "item_optional missing in { \"item_default\": 1, \"item_name\": \"item1\", \"item_type\": \"integer\" }");
- moduleSpecError("spec6.spec",
- "item_default missing in { \"item_name\": \"item1\", \"item_optional\": false, \"item_type\": \"integer\" }");
- moduleSpecError("spec9.spec",
- "item_default not of type integer");
- moduleSpecError("spec10.spec",
- "item_default not of type real");
- moduleSpecError("spec11.spec",
- "item_default not of type boolean");
- moduleSpecError("spec12.spec",
- "item_default not of type string");
- moduleSpecError("spec13.spec",
- "item_default not of type list");
- moduleSpecError("spec14.spec",
- "item_default not of type map");
- moduleSpecError("spec15.spec",
- "badname is not a valid type name");
- EXPECT_NO_THROW(moduleSpecFromFile(specfile("spec40.spec")));
-}
-
-TEST(ModuleSpec, SpecfileConfigData) {
- moduleSpecError("spec7.spec",
- "module_name missing in { }");
- moduleSpecError("spec8.spec",
- "No module_spec in specification");
- moduleSpecError("spec16.spec",
- "config_data is not a list of elements");
- moduleSpecError("spec21.spec",
- "commands is not a list of elements");
-}
-
-TEST(ModuleSpec, SpecfileStatistics) {
- moduleSpecError("spec36.spec", "item_default not valid type of item_format");
- moduleSpecError("spec37.spec", "statistics is not a list of elements");
- moduleSpecError("spec38.spec", "item_default not valid type of item_format");
-}
-
-TEST(ModuleSpec, SpecfileCommands) {
- moduleSpecError("spec17.spec",
- "command_name missing in { \"command_args\": [ { \"item_default\": \"\", \"item_name\": \"message\", \"item_optional\": false, \"item_type\": \"string\" } ], \"command_description\": \"Print the given message to stdout\" }");
- moduleSpecError("spec18.spec",
- "command_args missing in { \"command_description\": \"Print the given message to stdout\", \"command_name\": \"print_message\" }");
- moduleSpecError("spec19.spec",
- "command_args not of type list");
- moduleSpecError("spec20.spec",
- "somethingbad is not a valid type name");
-}
-
-bool
-dataTest(const ModuleSpec& dd, const std::string& data_file_name) {
- std::ifstream data_file;
-
- data_file.open(specfile(data_file_name).c_str());
- ConstElementPtr data = Element::fromJSON(data_file, data_file_name);
- data_file.close();
-
- return (dd.validateConfig(data));
-}
-
-bool
-statisticsTest(const ModuleSpec& dd, const std::string& data_file_name) {
- std::ifstream data_file;
-
- data_file.open(specfile(data_file_name).c_str());
- ConstElementPtr data = Element::fromJSON(data_file, data_file_name);
- data_file.close();
-
- return (dd.validateStatistics(data));
-}
-
-bool
-dataTestWithErrors(const ModuleSpec& dd, const std::string& data_file_name,
- ElementPtr errors)
-{
- std::ifstream data_file;
-
- data_file.open(specfile(data_file_name).c_str());
- ConstElementPtr data = Element::fromJSON(data_file, data_file_name);
- data_file.close();
-
- return (dd.validateConfig(data, true, errors));
-}
-
-bool
-statisticsTestWithErrors(const ModuleSpec& dd, const std::string& data_file_name,
- ElementPtr errors)
-{
- std::ifstream data_file;
-
- data_file.open(specfile(data_file_name).c_str());
- ConstElementPtr data = Element::fromJSON(data_file, data_file_name);
- data_file.close();
-
- return (dd.validateStatistics(data, true, errors));
-}
-
-TEST(ModuleSpec, DataValidation) {
- ModuleSpec dd = moduleSpecFromFile(specfile("spec22.spec"));
-
- EXPECT_TRUE(dataTest(dd, "data22_1.data"));
- EXPECT_FALSE(dataTest(dd, "data22_2.data"));
- EXPECT_FALSE(dataTest(dd, "data22_3.data"));
- EXPECT_FALSE(dataTest(dd, "data22_4.data"));
- EXPECT_FALSE(dataTest(dd, "data22_5.data"));
- EXPECT_TRUE(dataTest(dd, "data22_6.data"));
- EXPECT_TRUE(dataTest(dd, "data22_7.data"));
- EXPECT_FALSE(dataTest(dd, "data22_8.data"));
- EXPECT_FALSE(dataTest(dd, "data22_9.data"));
-
- // Test if "version" is allowed in config data
- // (same data as 22_7, but added "version")
- EXPECT_TRUE(dataTest(dd, "data22_10.data"));
-
- ElementPtr errors = Element::createList();
- EXPECT_FALSE(dataTestWithErrors(dd, "data22_8.data", errors));
- EXPECT_EQ("[ \"Type mismatch\" ]", errors->str());
-
- errors = Element::createList();
- EXPECT_FALSE(dataTestWithErrors(dd, "data22_9.data", errors));
- EXPECT_EQ("[ \"Unknown item value_does_not_exist\" ]", errors->str());
-}
-
-TEST(ModuleSpec, StatisticsValidation) {
- ModuleSpec dd = moduleSpecFromFile(specfile("spec33.spec"));
-
- EXPECT_TRUE(statisticsTest(dd, "data33_1.data"));
- EXPECT_FALSE(statisticsTest(dd, "data33_2.data"));
-
- ElementPtr errors = Element::createList();
- EXPECT_FALSE(statisticsTestWithErrors(dd, "data33_2.data", errors));
- EXPECT_EQ("[ \"Format mismatch\", \"Format mismatch\", \"Format mismatch\" ]", errors->str());
-
- dd = moduleSpecFromFile(specfile("spec41.spec"));
-
- EXPECT_TRUE(statisticsTest(dd, "data41_1.data"));
- EXPECT_FALSE(statisticsTest(dd, "data41_2.data"));
-
- errors = Element::createList();
- EXPECT_FALSE(statisticsTestWithErrors(dd, "data41_2.data", errors));
- EXPECT_EQ("[ \"Type mismatch\" ]", errors->str());
-}
-
-TEST(ModuleSpec, CommandValidation) {
- ModuleSpec dd = moduleSpecFromFile(specfile("spec2.spec"));
- ConstElementPtr arg = Element::fromJSON("{}");
- ElementPtr errors = Element::createList();
-
- EXPECT_TRUE(dd.validateCommand("shutdown", arg, errors));
- EXPECT_EQ(errors->size(), 0);
-
- errors = Element::createList();
- EXPECT_FALSE(dd.validateCommand("unknowncommand", arg, errors));
- EXPECT_EQ(errors->size(), 1);
- EXPECT_EQ(errors->get(0)->stringValue(), "Unknown command unknowncommand");
-
- errors = Element::createList();
- EXPECT_FALSE(dd.validateCommand("print_message", arg, errors));
- EXPECT_EQ(errors->size(), 1);
- EXPECT_EQ(errors->get(0)->stringValue(), "Non-optional value missing");
-
- errors = Element::createList();
- arg = Element::fromJSON("{ \"message\": \"Hello\" }");
- EXPECT_TRUE(dd.validateCommand("print_message", arg, errors));
- EXPECT_EQ(errors->size(), 0);
-
- errors = Element::createList();
- arg = Element::fromJSON("{ \"message\": \"Hello\", \"unknown_second_arg\": 1 }");
- EXPECT_FALSE(dd.validateCommand("print_message", arg, errors));
- EXPECT_EQ(errors->size(), 1);
- EXPECT_EQ(errors->get(0)->stringValue(), "Unknown item unknown_second_arg");
-
- errors = Element::createList();
- arg = Element::fromJSON("{ \"message\": 1 }");
- EXPECT_FALSE(dd.validateCommand("print_message", arg, errors));
- EXPECT_EQ(errors->size(), 1);
- EXPECT_EQ(errors->get(0)->stringValue(), "Type mismatch");
-
-}
-
-TEST(ModuleSpec, NamedSetValidation) {
- ModuleSpec dd = moduleSpecFromFile(specfile("spec32.spec"));
-
- ElementPtr errors = Element::createList();
- EXPECT_TRUE(dataTestWithErrors(dd, "data32_1.data", errors));
- EXPECT_FALSE(dataTest(dd, "data32_2.data"));
- EXPECT_FALSE(dataTest(dd, "data32_3.data"));
-}
-
-TEST(ModuleSpec, CheckFormat) {
-
- const std::string json_begin = "{ \"module_spec\": { \"module_name\": \"Foo\", \"statistics\": [ { \"item_name\": \"dummy_time\", \"item_type\": \"string\", \"item_optional\": true, \"item_title\": \"Dummy Time\", \"item_description\": \"A dummy date time\"";
- const std::string json_end = " } ] } }";
- std::string item_default;
- std::string item_format;
- std::vector<std::string> specs;
- ConstElementPtr el;
-
- specs.clear();
- item_default = "\"item_default\": \"2011-05-27T19:42:57Z\",";
- item_format = "\"item_format\": \"date-time\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"2011-05-27\",";
- item_format = "\"item_format\": \"date\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"19:42:57\",";
- item_format = "\"item_format\": \"time\"";
- specs.push_back("," + item_default + item_format);
-
- item_format = "\"item_format\": \"date-time\"";
- specs.push_back("," + item_format);
- item_default = "";
- item_format = "\"item_format\": \"date\"";
- specs.push_back("," + item_format);
- // cppcheck-suppress redundantAssignment
- item_default = "";
- item_format = "\"item_format\": \"time\"";
- specs.push_back("," + item_format);
-
- // cppcheck-suppress redundantAssignment
- item_default = "\"item_default\": \"a\"";
- specs.push_back("," + item_default);
- item_default = "\"item_default\": \"b\"";
- specs.push_back("," + item_default);
- item_default = "\"item_default\": \"c\"";
- specs.push_back("," + item_default);
-
- item_format = "\"item_format\": \"dummy\"";
- specs.push_back("," + item_format);
-
- specs.push_back("");
-
- BOOST_FOREACH(std::string s, specs) {
- el = Element::fromJSON(json_begin + s + json_end)->get("module_spec");
- EXPECT_NO_THROW(ModuleSpec(el, true));
- }
-
- specs.clear();
- item_default = "\"item_default\": \"2011-05-27T19:42:57Z\",";
- item_format = "\"item_format\": \"dummy\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"2011-05-27\",";
- item_format = "\"item_format\": \"dummy\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"19:42:57Z\",";
- item_format = "\"item_format\": \"dummy\"";
- specs.push_back("," + item_default + item_format);
-
- item_default = "\"item_default\": \"2011-13-99T99:99:99Z\",";
- item_format = "\"item_format\": \"date-time\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"2011-13-99\",";
- item_format = "\"item_format\": \"date\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"99:99:99Z\",";
- item_format = "\"item_format\": \"time\"";
- specs.push_back("," + item_default + item_format);
-
- item_default = "\"item_default\": \"1\",";
- item_format = "\"item_format\": \"date-time\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"1\",";
- item_format = "\"item_format\": \"date\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"1\",";
- item_format = "\"item_format\": \"time\"";
- specs.push_back("," + item_default + item_format);
-
- item_default = "\"item_default\": \"\",";
- item_format = "\"item_format\": \"date-time\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"\",";
- item_format = "\"item_format\": \"date\"";
- specs.push_back("," + item_default + item_format);
- item_default = "\"item_default\": \"\",";
- item_format = "\"item_format\": \"time\"";
- specs.push_back("," + item_default + item_format);
-
- // wrong date-time-type format not ending with "Z"
- item_default = "\"item_default\": \"2011-05-27T19:42:57\",";
- item_format = "\"item_format\": \"date-time\"";
- specs.push_back("," + item_default + item_format);
- // wrong date-type format ending with "T"
- item_default = "\"item_default\": \"2011-05-27T\",";
- item_format = "\"item_format\": \"date\"";
- specs.push_back("," + item_default + item_format);
- // wrong time-type format ending with "Z"
- item_default = "\"item_default\": \"19:42:57Z\",";
- item_format = "\"item_format\": \"time\"";
- specs.push_back("," + item_default + item_format);
-
- BOOST_FOREACH(std::string s, specs) {
- el = Element::fromJSON(json_begin + s + json_end)->get("module_spec");
- EXPECT_THROW(ModuleSpec(el, true), ModuleSpecError);
- }
-}
# Database schema creation script moved to src/bin/admin
EXTRA_DIST += database_backends.dox libdhcpsrv.dox
-# Specification file
-EXTRA_DIST += logging.spec
-
# Specify the headers for copying into the installation directory tree.
libkea_dhcpsrv_includedir = $(pkgincludedir)/dhcpsrv
libkea_dhcpsrv_include_HEADERS = \
+++ /dev/null
-{
- "module_spec": {
- "module_name": "Logging",
- "module_description": "Logging configuration",
- "config_data": [
- {
- "item_name": "loggers",
- "item_type": "list",
- "item_optional": false,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "logger",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "map_item_spec": [
- {
- "item_name": "name",
- "item_type": "string",
- "item_optional": false,
- "item_default": "kea",
- "item_description": "Logging name"
- },
-
- {
- "item_name": "output_options",
- "item_type": "list",
- "item_optional": true,
- "item_default": [],
- "list_item_spec":
- {
- "item_name": "output_option",
- "item_type": "map",
- "item_optional": false,
- "item_default": {},
- "item_description": "Options for a logging destination",
- "map_item_spec": [
- {
- "item_name": "output",
- "item_type": "string",
- "item_optional": false,
- "item_default": "stdout",
- "item_description": "Logging destination (stdout, stderr, syslog, syslog:name, file name)"
- },
-
- {
- "item_name": "maxver",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 1,
- "item_description": "Maximum number of log files in rotation"
- },
-
- {
- "item_name": "maxsize",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 204800,
- "item_description": "Maximum log file size"
- },
-
- {
- "item_name": "flush",
- "item_type": "boolean",
- "item_optional": true,
- "item_default": true,
- "item_description": "Immediate flush"
- }
- ]
- }
- },
-
- {
- "item_name": "severity",
- "item_type": "string",
- "item_optional": false,
- "item_default": "INFO",
- "item_description": "Logging severity"
- },
-
- {
- "item_name": "debuglevel",
- "item_type": "integer",
- "item_optional": true,
- "item_default": 0,
- "item_description": "Debug level (for DEBUG severity, 0..99 range)"
- }
- ]
- }
- }
- ]
- }
-}
AM_CPPFLAGS += -DTEST_DATA_BUILDDIR=\"$(abs_top_builddir)/src/lib/dhcpsrv/tests\"
AM_CPPFLAGS += -DDHCP_DATA_DIR=\"$(abs_top_builddir)/src/lib/dhcpsrv/tests\"
AM_CPPFLAGS += -DKEA_LFC_BUILD_DIR=\"$(abs_top_builddir)/src/bin/lfc\"
-AM_CPPFLAGS += -DLOGGING_SPEC_FILE=\"$(abs_top_srcdir)/src/lib/dhcpsrv/logging.spec\"
AM_CPPFLAGS += -DINSTALL_PROG=\"$(abs_top_srcdir)/install-sh\"
AM_CXXFLAGS = $(KEA_CXXFLAGS)
#include <config.h>
#include <cc/data.h>
-#include <config/module_spec.h>
#include <dhcpsrv/dhcpsrv_log.h>
#include <dhcpsrv/logging.h>
#include <exceptions/exceptions.h>
const int LoggingTest::TEST_MAX_SIZE = 204800; // Smallest without disabling rotation
const int LoggingTest::TEST_MAX_VERS = 2; // More than the default of 1
-// Tests that the spec file is valid.
-TEST_F(LoggingTest, basicSpec) {
- std::string specfile = std::string(LOGGING_SPEC_FILE);
- ASSERT_NO_THROW(isc::config::moduleSpecFromFile(specfile));
-}
-
// Checks that the constructor is able to process specified storage properly.
TEST_F(LoggingTest, constructor) {
$(top_builddir)/src/lib/log/compiler/kea-msg-compiler $(top_srcdir)/src/lib/process/process_messages.mes
touch $@
-spec_config.h: spec_config.h.pre
- $(SED) -e "s|@@LOCALSTATEDIR@@|$(localstatedir)|" spec_config.h.pre >$@
-
# Tell automake that the message files are built as part of the build process
# (so that they are built before the main library is built).
-BUILT_SOURCES = spec_config.h process_messages.h process_messages.cc
+BUILT_SOURCES = process_messages.h process_messages.cc
# Ensure that the message file is included in the distribution
EXTRA_DIST = process_messages.mes libprocess.dox
# Get rid of generated message files on a clean
-CLEANFILES = *.gcno *.gcda spec_config.h process_messages.h process_messages.cc s-messages
+CLEANFILES = *.gcno *.gcda process_messages.h process_messages.cc s-messages
lib_LTLIBRARIES = libkea-process.la
libkea_process_la_SOURCES = d_cfg_mgr.cc d_cfg_mgr.h
#include <config.h>
#include <cc/command_interpreter.h>
-#include <config/module_spec.h>
#include <exceptions/exceptions.h>
#include <dhcpsrv/parsers/dhcp_parsers.h>
#include <process/testutils/d_test_stubs.h>