#include <boost/foreach.hpp>
using namespace isc::data;
+using namespace isc::dns;
using namespace std;
+using namespace boost;
namespace isc {
namespace datasrc {
// And put it into the vector
new_data_sources.push_back(DataSourceInfo(ds.first, ds.second,
wantCache));
+ if (wantCache) {
+ const ConstElementPtr zones(dconf->get("cache-zones"));
+ const shared_ptr<InMemoryClient>
+ cache(new_data_sources.back().cache_);
+ const DataSourceClient* const
+ client(new_data_sources.back().data_src_client_);
+ for (size_t i(0); i < zones->size(); ++i) {
+ const Name origin(zones->get(i)->stringValue());
+ const DataSourceClient::FindResult
+ zone(client->findZone(origin));
+ // TODO check it is SUCCESS
+ shared_ptr<InMemoryZoneFinder>
+ finder(new
+ InMemoryZoneFinder(zone.zone_finder->getClass(),
+ origin));
+ finder->load(*client->getIterator(origin));
+ cache->addZone(finder);
+ }
+ }
}
// If everything is OK up until now, we have the new configuration
// ready. So just put it there and let the old one die when we exit
#include <datasrc/client_list.h>
#include <datasrc/client.h>
+#include <datasrc/iterator.h>
#include <datasrc/data_source.h>
+#include <datasrc/memory_datasrc.h>
#include <dns/rrclass.h>
+#include <dns/rrttl.h>
+#include <dns/rdataclass.h>
#include <gtest/gtest.h>
Name getOrigin() const { return (origin_); }
// The rest is not to be called, so just have them
RRClass getClass() const {
- isc_throw(isc::NotImplemented, "Not implemented");
+ return (RRClass::IN());
}
shared_ptr<Context> find(const Name&, const RRType&,
const FindOptions)
private:
Name origin_;
};
+ class Iterator : public ZoneIterator {
+ public:
+ Iterator(const Name& origin) :
+ origin_(origin),
+ finished_(false),
+ soa_(new RRset(origin_, RRClass::IN(), RRType::SOA(), RRTTL(3600)))
+ {
+ // The RData here is bogus, but it is not used to anything. There
+ // just needs to be some.
+ soa_->addRdata(rdata::generic::SOA(Name::ROOT_NAME(),
+ Name::ROOT_NAME(),
+ 0, 0, 0, 0, 0));
+ }
+ virtual isc::dns::ConstRRsetPtr getNextRRset() {
+ if (finished_) {
+ return (ConstRRsetPtr());
+ } else {
+ finished_ = true;
+ return (soa_);
+ }
+ }
+ virtual isc::dns::ConstRRsetPtr getSOA() const {
+ return (soa_);
+ }
+ private:
+ const Name origin_;
+ bool finished_;
+ const isc::dns::RRsetPtr soa_;
+ };
// Constructor from a list of zones.
MockDataSourceClient(const char* zone_names[]) {
for (const char** zone(zone_names); *zone; ++zone) {
const ConstElementPtr& configuration) :
type_(type),
configuration_(configuration)
- {}
+ {
+ if (configuration_->getType() == Element::list) {
+ for (size_t i(0); i < configuration_->size(); ++i) {
+ zones.insert(Name(configuration_->get(i)->stringValue()));
+ }
+ }
+ }
virtual FindResult findZone(const Name& name) const {
if (zones.empty()) {
return (FindResult(result::NOTFOUND, ZoneFinderPtr()));
{
isc_throw(isc::NotImplemented, "Not implemented");
}
+ virtual ZoneIteratorPtr getIterator(const Name& name, bool) const {
+ return (ZoneIteratorPtr(new Iterator(name)));
+ }
const string type_;
const ConstElementPtr configuration_;
private:
checkDS(1, "type2", "{}", false);
}
+// Put some zones into the cache
+TEST_F(ListTest, cacheZones) {
+ ConstElementPtr elem(Element::fromJSON("["
+ "{"
+ " \"type\": \"type1\","
+ " \"cache-enable\": true,"
+ " \"cache-zones\": [\"example.org\", \"example.com\"],"
+ " \"params\": [\"example.org\", \"example.com\", \"exmaple.cz\"]"
+ "}]"));
+ list_->configure(*elem, true);
+ checkDS(0, "type1", "[\"example.org\", \"example.com\", \"exmaple.cz\"]",
+ true);
+
+ const shared_ptr<InMemoryClient> cache(list_->getDataSources()[0].cache_);
+ EXPECT_EQ(2, cache->getZoneCount());
+
+ EXPECT_EQ(result::SUCCESS, cache->findZone(Name("example.org")).code);
+ EXPECT_EQ(result::SUCCESS, cache->findZone(Name("example.com")).code);
+ EXPECT_EQ(result::NOTFOUND, cache->findZone(Name("example.cz")).code);
+}
+
}