<?xml version="1.0" encoding="UTF-8" ?>
<rss version="2.0"><channel><title>designate-specs</title><link>https://specs.openstack.org/openstack/designate-specs</link><description /><language>en</language><copyright>2026, OpenStack Foundation</copyright><item><title>Asynchronous Zone Import/Export</title><link>https://specs.openstack.org/openstack/designate-specs/specs/liberty/async-import-export.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="asynchronous-zone-import-export"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/async-import-export"&gt;https://blueprints.launchpad.net/designate/+spec/async-import-export&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Large zone imports have the potential to take a lot longer than the
typically allowed time for API responses. Parsing large zone files, and inserting
the necessary records scales linearly with the amount of records that need to be
imported.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;The API for Zone imports needs to be changed to be asynchronous. This would involve
a new database table for zone import “statuses”, and a more robust system for managing
the parsing and insertion of the zone data. Exporting zones will also return to the v2 API.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;section id="get-v2-zones-tasks-imports"&gt;
&lt;h4&gt;GET /v2/zones/tasks/imports&lt;/h4&gt;
&lt;p&gt;This allows the user to view the statuses of their zone import requests. If the import has
completed successfully, they can get the zone id and a link to the zone.&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

HTTP/1.1 200 OK
Content-Type: application/json; charset=UTF-8
Location: /v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66

{
  "imports": [
      {
        "id": "cddda8f0-f558-11e3-a3ac-0800200c9a66",
        "zone_id": "agqm44f0-s638-15e3-f4d3-1893572c9a67",
        "status": "SUCCESS",
        "links":{
            "self": "http://127.0.0.1:9001/v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66",
            "href": "http://127.0.0.1:9001/v2/zones/agqm44f0-s638-15e3-f4d3-1893572c9a67"
      },
      {
        "id": "addda8f0-f558-11e3-a3ac-0800200c9a66",
        "zone_id": "qgqm44f0-s638-15e3-f4d3-1893572c9a67",
        "status": "SUCCESS",
        "links":{
            "self": "http://127.0.0.1:9001/v2/zones/tasks/import/addda8f0-f558-11e3-a3ac-0800200c9a66",
            "href": "http://127.0.0.1:9001/v2/zones/qgqm44f0-s638-15e3-f4d3-1893572c9a67"
      }
  ]
}
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="post-v2-zones-tasks-imports"&gt;
&lt;h4&gt;POST /v2/zones/tasks/imports&lt;/h4&gt;
&lt;p&gt;This creates a request to import a zone. The zone data is passed via the request body,
and the Content-Type header must be set to ‘text/dns’.&lt;/p&gt;
&lt;p&gt;This returns an id for the import request, for the user to query.&lt;/p&gt;
&lt;div class="highlight-text notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;POST /v2/zones/tasks/import HTTP/1.1
Accept: application/json
Content-Type: text/dns

$ORIGIN example.com.
example.com. 42 IN SOA ns.example.com. nsadmin.example.com. 42 42 42 42 42
example.com. 42 IN NS ns.example.com.
example.com. 42 IN MX 10 mail.example.com.
ns.example.com. 42 IN A 10.0.0.1
mail.example.com. 42 IN A 10.0.0.2

HTTP/1.1 201 Accepted
Content-Type: application/json; charset=UTF-8
Location: /v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66

{
    "id": "cddda8f0-f558-11e3-a3ac-0800200c9a66",
    "zone_id": null,
    "status": "PENDING",
    "links":{
        "self": "http://127.0.0.1:9001/v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66"
    }
}
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-v2-zones-tasks-imports-id"&gt;
&lt;h4&gt;GET /v2/zones/tasks/imports/&amp;lt;id&amp;gt;&lt;/h4&gt;
&lt;p&gt;This allows the user to view the status of their zone import request. If the import has
completed successfully, they can get the zone id and a link to the zone.&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

HTTP/1.1 200 OK
Content-Type: application/json; charset=UTF-8
Location: /v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66

{
    "id": "cddda8f0-f558-11e3-a3ac-0800200c9a66",
    "zone_id": "agqm44f0-s638-15e3-f4d3-1893572c9a67",
    "status": "SUCCESS",
    "links":{
        "self": "http://127.0.0.1:9001/v2/zones/tasks/import/cddda8f0-f558-11e3-a3ac-0800200c9a66",
        "href": "http://127.0.0.1:9001/v2/zones/agqm44f0-s638-15e3-f4d3-1893572c9a67"
    }
}
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-v2-zones-id"&gt;
&lt;h4&gt;GET /v2/zones/&amp;lt;id&amp;gt;&lt;/h4&gt;
&lt;p&gt;This request, with the header “Accept:text/dns” exports the zone in DNS zonefile format to the user.&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/cddda8f0-f558-11e3-a3ac-0800200c9a66&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;text/dns&lt;/span&gt;

HTTP/1.1 200 OK
Content-Type: text/dns; charset=UTF-8
Location: /v2/zones/cddda8f0-f558-11e3-a3ac-0800200c9a66

HTTP/1.1 200 OK
Content-Type: text/dns

$ORIGIN example.com.
$TTL 42
example.com. IN SOA ns.designate.com. nsadmin.example.com. (
    1394213803 ; serial
    3600 ; refresh
    600 ; retry
    86400 ; expire
    3600 ; minimum
)
example.com. IN NS ns.designate.com.
example.com.  IN MX 10 mail.example.com.
ns.example.com.  IN A  10.0.0.1
mail.example.com.  IN A  10.0.0.2
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;section id="create-import-domain-body"&gt;
&lt;h4&gt;create_import_domain(body)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;body&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Unserialized request data from the API request&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;1. Create an entry in the zone_imports table to track the request with status
PENDING.
2. Kicks off a thread to _import_domain with the request body.
3. Returns a zone_import object.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="get-import-domain-id"&gt;
&lt;h4&gt;get_import_domain(id)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;import_id&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The id of the zone import&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;1. Calls storage.find_import to get a specific zone_import record from the
zone_imports table.
2. Returns the zone_import object&lt;/p&gt;
&lt;/section&gt;
&lt;section id="find-import-domains-context"&gt;
&lt;h4&gt;find_import_domains(context)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Context to be passed to storage.find_imports&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;1. Calls off to the storage.find_imports to find all the zone imports for a
tenant.
2. Returns the zone_import_list object&lt;/p&gt;
&lt;/section&gt;
&lt;section id="delete-import-domain-id"&gt;
&lt;h4&gt;delete_import_domain(id)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;import_id&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The id of the zone import&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;1. Calls off to storage.delete_zone_import to delete the zone import record from
the zone_imports table.&lt;/p&gt;
&lt;section id="import-domain-body"&gt;
&lt;h5&gt;_import_domain(body)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;body&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Unserialized request data from the API request&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;zone_import&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;zone_import object from the original request&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;1. Tries to use dnspython’s from_text method to convert the zone into a dnspython
object. If that doesn’t work, updates the zone_import object in storage to ERROR
to indicate that the zone could not be imported.
2. Converts the dnspython zone to a Designate domain object.
3. Calls central.create_domain with the converted object.
4. Takes the return object’s id and updates the zone_import object in storage
with the new zone_id and updates the status of the import to COMPLETE, or similar.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;A new table for zone import records will be added, along with the boilerplate
get, set, delete, update methods.&lt;/p&gt;
&lt;section id="new-table-zone-imports"&gt;
&lt;h4&gt;New Table - zone_imports&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Row&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Primary key&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;zone_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Zone id when the import completes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ENUM&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;One of [COMPLETE, PENDING, ERROR]&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;message&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A message letting the user know why
their import failed. For example:
“Malformed zonefile”, “Complete”&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;New DesignateObjects for the Imports will have be created, ZoneImport, ZoneImportList.&lt;/p&gt;
&lt;p&gt;Exporting zones will also return to the v2 API, but should remain relatively unchanged.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;Instead of creating a new zone_import table and object, it may be possible
to create an empty domain object and call central._create_domain_in_storage
and make an empty domain that is then updated with the result of the import.
Only then could the call to the pool manager be made.&lt;/p&gt;
&lt;p&gt;This might make the code simpler. But provides very little in the way of
letting the user know that their import failed.
You could add a status like MALFORMED_ZONEFILE or something, but that
would still require the user to delete the zone before they tried again.
Unless you soft-delete the zone when it fails and modify the default
find_domains criterion to find zones that have been deleted only if they
have that status.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;tim-simmons-t&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Liberty-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Implement the database table, migration.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement the storage methods.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement the central methods.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Fix the API to use the new code.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Move the APIs back into the v2 namespace&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 23 Mar 2026 00:00:00 </pubDate></item><item><title>TSIG Signing for Worker Poll and Notify Messages</title><link>https://specs.openstack.org/openstack/designate-specs/specs/2026.2/worker-tsig-poll-notify.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="tsig-signing-for-worker-poll-and-notify-messages"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://bugs.launchpad.net/designate/+bug/2142614"&gt;https://bugs.launchpad.net/designate/+bug/2142614&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Designate’s worker service sends unsigned DNS NOTIFY and SOA poll queries to
backend nameservers. In split-horizon DNS deployments using BIND views, this
causes zone management failures because BIND uses TSIG keys to route requests
to the correct view.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;When Designate manages zones across multiple BIND views (split-horizon DNS),
each view is typically configured to accept queries and notifications based
on match criteria such as source IP (match-clients), destination IP
(match-destinations), or TSIG key. One option is to use TSIG keys, where
BIND determines which view a DNS message belongs to by verifying the
signature.&lt;/p&gt;
&lt;p&gt;Currently, Designate’s MDNS service supports TSIG for AXFR (zone transfer)
responses — BIND can successfully pull zone data from MDNS using TSIG-signed
transfers. However, the worker service sends two types of DNS messages that
are completely unsigned:&lt;/p&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;NOTIFY messages&lt;/strong&gt;: After creating or updating a zone on a backend target,
the worker sends a DNS NOTIFY to tell the nameserver to initiate an AXFR.
Without TSIG, BIND either rejects the NOTIFY or routes it to the default
(“any”) view if configured, which may be the wrong view.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;SOA poll queries&lt;/strong&gt;: After a zone change, the worker polls nameservers by
sending SOA queries to verify the zone serial has been updated. Without
TSIG, the SOA query hits the wrong view, returns the wrong serial (or
NXDOMAIN), and the zone transitions to ERROR status.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;This means that while Designate can technically create zones in BIND backends
with view-based split-horizon, the zones inevitably transition to ERROR
because the worker cannot properly notify or verify them.&lt;/p&gt;
&lt;p&gt;The infrastructure to support TSIG signing partially exists:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;The &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;TsigKey&lt;/span&gt;&lt;/code&gt; object model stores TSIG key name, algorithm, and secret&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PoolTarget&lt;/span&gt;&lt;/code&gt; object has a &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; field&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;MDNS already uses TSIG for signing AXFR responses&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;dnspython provides &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;Message.use_tsig()&lt;/span&gt;&lt;/code&gt; for signing outgoing queries&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;However, &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PoolNameserver&lt;/span&gt;&lt;/code&gt; (used for polling) has no TSIG reference, and the
worker’s &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;dnsutils.notify()&lt;/span&gt;&lt;/code&gt; / &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;dnsutils.soa_query()&lt;/span&gt;&lt;/code&gt; functions have no
TSIG support.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Add TSIG signing support to the worker’s NOTIFY and SOA poll messages, keyed
by the pool target and nameserver configuration.&lt;/p&gt;
&lt;section id="dnsutils-changes"&gt;
&lt;h3&gt;dnsutils Changes&lt;/h3&gt;
&lt;p&gt;Extend &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;prepare_dns_message()&lt;/span&gt;&lt;/code&gt;, &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;notify()&lt;/span&gt;&lt;/code&gt;, &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;soa_query()&lt;/span&gt;&lt;/code&gt;, and
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;send_dns_message()&lt;/span&gt;&lt;/code&gt; to optionally accept TSIG parameters and sign
outgoing DNS messages.&lt;/p&gt;
&lt;p&gt;When a TSIG key is provided, the DNS message is signed using dnspython’s
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;Message.use_tsig()&lt;/span&gt;&lt;/code&gt; before being sent. This applies to both UDP and TCP
transport.&lt;/p&gt;
&lt;p&gt;The TSIG parameters (key name, secret, algorithm) are resolved from the
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;TsigKey&lt;/span&gt;&lt;/code&gt; object referenced by the pool target or nameserver’s
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="worker-changes"&gt;
&lt;h3&gt;Worker Changes&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;SendNotify&lt;/strong&gt;: The &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;SendNotify&lt;/span&gt;&lt;/code&gt; task already receives the pool &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;target&lt;/span&gt;&lt;/code&gt;
object. When &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;target.tsigkey_id&lt;/span&gt;&lt;/code&gt; is set, the task looks up the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;TsigKey&lt;/span&gt;&lt;/code&gt;
from storage and passes the TSIG parameters to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;dnsutils.notify()&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;PollForZone&lt;/strong&gt;: The &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PollForZone&lt;/span&gt;&lt;/code&gt; task receives a &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PoolNameserver&lt;/span&gt;&lt;/code&gt;.
With the addition of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PoolNameserver&lt;/span&gt;&lt;/code&gt; (see below), the
task looks up the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;TsigKey&lt;/span&gt;&lt;/code&gt; from storage and passes the TSIG parameters
to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;dnsutils.soa_query()&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;ZonePoller&lt;/strong&gt;: Passes the context to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PollForZone&lt;/span&gt;&lt;/code&gt; so it can look up TSIG
keys from storage.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;None. TSIG keys are configured via pool YAML and the existing TSIG key API.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;Add &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; column to the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;pool_nameservers&lt;/span&gt;&lt;/code&gt; table.&lt;/p&gt;
&lt;section id="altered-table-pool-nameservers"&gt;
&lt;h4&gt;Altered Table - pool_nameservers&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Row&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;tsigkey_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;This mirrors the existing &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; column on &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;pool_targets&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;A database migration will add this nullable column with a default of NULL,
which preserves backwards compatibility — existing deployments without TSIG
continue to work with unsigned queries.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="pool-configuration-changes"&gt;
&lt;h3&gt;Pool Configuration Changes&lt;/h3&gt;
&lt;p&gt;The pool YAML schema is extended to allow &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; on nameservers,
consistent with the existing support on targets:&lt;/p&gt;
&lt;div class="highlight-yaml notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;internal-view-pool&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;Pool for BIND internal view&lt;/span&gt;

&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;nameservers&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.1&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;53&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;tsigkey_id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;4a1a4e28-2b4e-4b2a-8b0a-3c4d5e6f7a8b&lt;/span&gt;

&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;targets&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;bind9&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;BIND9 internal view&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;tsigkey_id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;4a1a4e28-2b4e-4b2a-8b0a-3c4d5e6f7a8b&lt;/span&gt;

&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;masters&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.10&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;5354&lt;/span&gt;

&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;options&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.1&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;53&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;rndc_host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.1&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;rndc_port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;953&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;rndc_key_file&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;/etc/bind/rndc.key&lt;/span&gt;

&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;external-view-pool&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;Pool for BIND external view&lt;/span&gt;

&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;nameservers&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.1&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;53&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;tsigkey_id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;9b8c7d6e-5f4a-3b2c-1d0e-a9b8c7d6e5f4&lt;/span&gt;

&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;targets&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;bind9&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;BIND9 external view&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;tsigkey_id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;9b8c7d6e-5f4a-3b2c-1d0e-a9b8c7d6e5f4&lt;/span&gt;

&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;masters&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p p-Indicator"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.10&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;5354&lt;/span&gt;

&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;options&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.1&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;53&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;rndc_host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;192.0.2.1&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;rndc_port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;953&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;rndc_key_file&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l l-Scalar l-Scalar-Plain"&gt;/etc/bind/rndc.key&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;In this configuration, both pools point to the same physical BIND server
(192.0.2.1), but use different TSIG keys to route to different views. The
nameserver and target for the same view typically share the same TSIG key.&lt;/p&gt;
&lt;p&gt;The TSIG keys must be created beforehand via the Designate TSIG key API with
scope &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;POOL&lt;/span&gt;&lt;/code&gt; and the corresponding pool’s resource_id.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;PoolNameserver object&lt;/strong&gt;: Add &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; field (UUIDFields, nullable).&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Pool update command&lt;/strong&gt;: &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-manage&lt;/span&gt; &lt;span class="pre"&gt;pool&lt;/span&gt; &lt;span class="pre"&gt;update&lt;/span&gt;&lt;/code&gt; already reads pool
YAML and updates pool objects. It must handle the new &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; field on
nameservers, same as it already does for targets.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;TSIG key on pool (not target/nameserver)&lt;/strong&gt;: Use a single TSIG key per
pool instead of per-target and per-nameserver. Simpler, but doesn’t work
when a pool has multiple targets or nameservers that each require their
own key (e.g., multiple BIND servers with distinct TSIG keys). Keeping
TSIG per-target and per-nameserver is consistent with the existing
target-level &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; and gives operators full control.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Derive nameserver TSIG from target TSIG&lt;/strong&gt;: Instead of adding
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; to nameservers, infer the TSIG key from the target that
shares the same host. This avoids a schema change but creates a fragile
implicit coupling — the pool data model has no explicit relationship
between targets and nameservers, so matching would require comparing
hosts across different schemas (nameserver &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;host&lt;/span&gt;&lt;/code&gt; vs. target
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;options.host&lt;/span&gt;&lt;/code&gt;), with the risk of ambiguous or missing matches.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Configuration file options&lt;/strong&gt;: Add TSIG key name/secret/algorithm as
worker configuration options (e.g., &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;[service:worker]&lt;/span&gt; &lt;span class="pre"&gt;tsig_key_name&lt;/span&gt;&lt;/code&gt;).
This would apply a single TSIG key to all poll/notify messages globally,
which doesn’t work for multi-pool split-horizon deployments where each pool
needs a different key.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Omer Schwartz (oschwart)&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;2026.2 (Hibiscus)&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Add &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PoolNameserver&lt;/span&gt;&lt;/code&gt; object model&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Database migration: add &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; column to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;pool_nameservers&lt;/span&gt;&lt;/code&gt; table&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Extend &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;dnsutils.notify()&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;dnsutils.soa_query()&lt;/span&gt;&lt;/code&gt; to accept and
apply TSIG parameters&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Update &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;SendNotify&lt;/span&gt;&lt;/code&gt; to look up and use TSIG key from target&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Update &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;PollForZone&lt;/span&gt;&lt;/code&gt; / &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;ZonePoller&lt;/span&gt;&lt;/code&gt; to look up and use TSIG key from
nameserver&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Update &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-manage&lt;/span&gt; &lt;span class="pre"&gt;pool&lt;/span&gt; &lt;span class="pre"&gt;update&lt;/span&gt;&lt;/code&gt; to handle nameserver &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Unit and functional tests&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Documentation: pool configuration guide for split-horizon with TSIG&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;None. All required libraries (dnspython TSIG support) and infrastructure
(TsigKey model, PoolTarget.tsigkey_id) already exist.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="upgrade-implications"&gt;
&lt;h2&gt;Upgrade Implications&lt;/h2&gt;
&lt;p&gt;A database migration adds the nullable &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tsigkey_id&lt;/span&gt;&lt;/code&gt; column to
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;pool_nameservers&lt;/span&gt;&lt;/code&gt;. Existing deployments are unaffected — the column
defaults to NULL, and when no TSIG key is configured, the worker continues
to send unsigned messages as it does today. No changes to existing pool YAML
files are required.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 17 Mar 2026 00:00:00 </pubDate></item><item><title>Zone Attributes Support for Zone Import</title><link>https://specs.openstack.org/openstack/designate-specs/specs/2026.2/zone-import-attributes.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="zone-attributes-support-for-zone-import"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://bugs.launchpad.net/designate/+bug/1690184"&gt;https://bugs.launchpad.net/designate/+bug/1690184&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Zone import currently does not support specifying zone attributes. This means
zones imported via &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;POST&lt;/span&gt; &lt;span class="pre"&gt;/v2/zones/tasks/imports&lt;/span&gt;&lt;/code&gt; are always scheduled to the
default pool. With the deprecation of pool management APIs, zone attributes are
the primary mechanism for controlling pool assignment during zone creation. Zone
import should support the same attributes that zone creation does, so that
imported zones can be scheduled to the correct pool.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;When creating a zone via &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;POST&lt;/span&gt; &lt;span class="pre"&gt;/v2/zones&lt;/span&gt;&lt;/code&gt;, users can specify &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;attributes&lt;/span&gt;&lt;/code&gt;
in the JSON body to influence pool scheduling. For example:&lt;/p&gt;
&lt;div class="highlight-json notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"example.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"email"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"admin@example.com"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"attributes"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nt"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"794ccc2c-d751-44fe-b57f-8894c9f5c842"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;The pool scheduler uses these attributes to match the zone to the appropriate
pool. However, zone import (&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;POST&lt;/span&gt; &lt;span class="pre"&gt;/v2/zones/tasks/imports&lt;/span&gt;&lt;/code&gt;) only accepts a
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;text/dns&lt;/span&gt;&lt;/code&gt; body containing the raw zonefile. There is no way to pass zone
attributes, so imported zones always land in the default pool.&lt;/p&gt;
&lt;p&gt;This is a significant limitation for operators managing multiple pools. The
available workarounds are cumbersome: one option is to import each zone into
the default pool and then use &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zone&lt;/span&gt; &lt;span class="pre"&gt;pool&lt;/span&gt; &lt;span class="pre"&gt;move&lt;/span&gt;&lt;/code&gt; to relocate each zone
individually to the correct pool — a tedious per-zone process. Another option
is to skip import entirely, create each zone via &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;POST&lt;/span&gt; &lt;span class="pre"&gt;/v2/zones&lt;/span&gt;&lt;/code&gt; with the
desired attributes, and then populate it with records through the API — which
defeats the purpose of having a zonefile-based import. With pool management
APIs deprecated, this gap becomes even more critical, as attributes are now the
standard way to control pool assignment.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Extend the zone import endpoint to optionally accept &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; as a
content type, in addition to the existing &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;text/dns&lt;/span&gt;&lt;/code&gt;. When the request body
is JSON, it may include both the zonefile content and zone attributes:&lt;/p&gt;
&lt;div class="highlight-json notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"zonefile"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"$ORIGIN example.com.\n$TTL 3600\n..."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"attributes"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nt"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"794ccc2c-d751-44fe-b57f-8894c9f5c842"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;The attributes are passed through to the zone object before creation, using
the same code path as &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;POST&lt;/span&gt; &lt;span class="pre"&gt;/v2/zones&lt;/span&gt;&lt;/code&gt;. This means pool scheduling,
validation, and attribute storage all work identically to normal zone creation.&lt;/p&gt;
&lt;p&gt;When no attributes are provided, or when the request uses &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;text/dns&lt;/span&gt;&lt;/code&gt;, the
behavior is unchanged — the zone is scheduled to the default pool as it is
today. This makes the change fully backwards compatible.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;section id="post-v2-zones-tasks-imports"&gt;
&lt;h4&gt;POST /v2/zones/tasks/imports&lt;/h4&gt;
&lt;p&gt;The endpoint currently accepts only &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;text/dns&lt;/span&gt;&lt;/code&gt;. This change adds
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; as an accepted content type.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Existing behavior (unchanged):&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Request:&lt;/p&gt;
&lt;div class="highlight-text notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;POST /v2/zones/tasks/imports HTTP/1.1
Content-Type: text/dns

$ORIGIN example.com.
$TTL 3600
example.com. IN SOA ns1.example.com. admin.example.com. (
    2024101401 3600 900 1209600 300 )
example.com. IN NS ns1.example.com.
example.com. IN A 192.0.2.1
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;Response:&lt;/p&gt;
&lt;div class="highlight-text notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;HTTP/1.1 202 Accepted
Content-Type: application/json

{
    "id": "074e2e30-8748-11e4-a4a2-08002783c8f3",
    "status": "PENDING",
    "message": null,
    "zone_id": null,
    "links": {
        "self": "/v2/zones/tasks/imports/074e2e30-8748-11e4-a4a2-08002783c8f3"
    }
}
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;New behavior (with attributes):&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Request:&lt;/p&gt;
&lt;div class="highlight-text notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;POST /v2/zones/tasks/imports HTTP/1.1
Content-Type: application/json

{
    "zonefile": "$ORIGIN example.com.\n$TTL 3600\nexample.com. IN SOA ...",
    "attributes": {
        "pool_id": "794ccc2c-d751-44fe-b57f-8894c9f5c842"
    }
}
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;Response:&lt;/p&gt;
&lt;div class="highlight-text notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;HTTP/1.1 202 Accepted
Content-Type: application/json

{
    "id": "074e2e30-8748-11e4-a4a2-08002783c8f3",
    "status": "PENDING",
    "message": null,
    "zone_id": null,
    "links": {
        "self": "/v2/zones/tasks/imports/074e2e30-8748-11e4-a4a2-08002783c8f3"
    }
}
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;JSON body parameters:&lt;/strong&gt;&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Parameter&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Required&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;zonefile&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The zonefile content as a string (same
format as the text/dns body).&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;attributes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Zone attributes as key-value pairs. Accepts
the same attributes as zone creation (e.g.
pool_id, scope).&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;&lt;strong&gt;Error cases:&lt;/strong&gt;&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; body missing &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zonefile&lt;/span&gt;&lt;/code&gt; field: &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;400&lt;/span&gt; &lt;span class="pre"&gt;Bad&lt;/span&gt; &lt;span class="pre"&gt;Request&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Invalid attributes (e.g. referencing non-existent pool): handled during zone
creation, reported in the zone import status as &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;ERROR&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;The &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;create_zone_import&lt;/span&gt;&lt;/code&gt; method in central will accept an optional
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zone_attributes&lt;/span&gt;&lt;/code&gt; dict parameter. This is passed through to
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;_import_zone&lt;/span&gt;&lt;/code&gt;, which sets the attributes on the zone object before calling
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;create_zone&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;The attributes are parsed using the existing &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;ZoneAttributeListAPIv2Adapter&lt;/span&gt;&lt;/code&gt;,
the same adapter used by zone creation. This ensures consistent validation and
behavior.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;None. Zone attributes are already stored via the existing zone creation flow.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;python-designateclient&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;The &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;openstack&lt;/span&gt; &lt;span class="pre"&gt;zone&lt;/span&gt; &lt;span class="pre"&gt;import&lt;/span&gt; &lt;span class="pre"&gt;create&lt;/span&gt;&lt;/code&gt; command will accept an optional
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;--attributes&lt;/span&gt;&lt;/code&gt; flag using the same &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;key:value&lt;/span&gt;&lt;/code&gt; format as
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;openstack&lt;/span&gt; &lt;span class="pre"&gt;zone&lt;/span&gt; &lt;span class="pre"&gt;create&lt;/span&gt;&lt;/code&gt;:&lt;/p&gt;
&lt;div class="highlight-bash notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;openstack&lt;span class="w"&gt; &lt;/span&gt;zone&lt;span class="w"&gt; &lt;/span&gt;import&lt;span class="w"&gt; &lt;/span&gt;create&lt;span class="w"&gt; &lt;/span&gt;/path/to/zonefile&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="se"&gt;\&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;--attributes&lt;span class="w"&gt; &lt;/span&gt;pool_id:794ccc2c-d751-44fe-b57f-8894c9f5c842
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;When &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;--attributes&lt;/span&gt;&lt;/code&gt; is provided, the client sends the request as
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; with the zonefile content and attributes in the body.
When &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;--attributes&lt;/span&gt;&lt;/code&gt; is omitted, the client sends &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;text/dns&lt;/span&gt;&lt;/code&gt; as it does
today.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;openstacksdk&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Update the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;ZoneImport&lt;/span&gt;&lt;/code&gt; resource in openstacksdk to support the new
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; content type and zone attributes.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;designate-tempest-plugin&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;API tests covering:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Zone import with attributes (verify pool assignment)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Zone import with &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; content type&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Zone import without attributes (backwards compatibility)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Zone import with invalid attributes (error handling)&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;api-ref&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Update the zone import API reference documentation to describe the new
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; content type and the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;attributes&lt;/span&gt;&lt;/code&gt; parameter.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;Several alternatives were considered:&lt;/p&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Custom HTTP header (X-Designate-Zone-Attributes)&lt;/strong&gt;: Pass attributes as a
custom header. This was prototyped in
&lt;a class="reference external" href="https://review.opendev.org/c/openstack/designate/+/932323"&gt;https://review.opendev.org/c/openstack/designate/+/932323&lt;/a&gt; but rejected
because headers are not easily discoverable in API documentation, require
fragile string-to-JSON parsing, and need CORS configuration changes.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Query parameters&lt;/strong&gt;: Pass attributes as query parameters (e.g.
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;?attributes=pool_id:uuid&lt;/span&gt;&lt;/code&gt;). Simple for a single attribute but becomes
unwieldy with many attributes and is inconsistent with how zone creation
accepts them.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Two-step process&lt;/strong&gt;: Import the zone, then update attributes via PATCH.
Not viable because pool scheduling happens at creation time — the zone
would already be assigned to the wrong pool.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;The JSON body approach was chosen because it reuses the exact same attribute
format as zone creation, scales to any number of attributes, and is easy to
document and discover.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Omer Schwartz (oschwart)&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;2026.2 (Hibiscus)&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Designate: extend zone import endpoint to accept &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Designate: pass attributes through central to zone creation&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Designate: unit and functional tests&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;python-designateclient: add &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;--attributes&lt;/span&gt;&lt;/code&gt; flag to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zone&lt;/span&gt; &lt;span class="pre"&gt;import&lt;/span&gt; &lt;span class="pre"&gt;create&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;openstacksdk: update &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;ZoneImport&lt;/span&gt;&lt;/code&gt; resource to support attributes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;designate-tempest-plugin: API tests for zone import with attributes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;api-ref: document new content type and attributes parameter&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;None. This feature builds entirely on existing zone attribute and pool
scheduling infrastructure.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="upgrade-implications"&gt;
&lt;h2&gt;Upgrade Implications&lt;/h2&gt;
&lt;p&gt;None. The change is backwards compatible. Existing &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;text/dns&lt;/span&gt;&lt;/code&gt; requests
continue to work unchanged. The new &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;application/json&lt;/span&gt;&lt;/code&gt; content type is
opt-in.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 17 Mar 2026 00:00:00 </pubDate></item><item><title>Catalog Zones</title><link>https://specs.openstack.org/openstack/designate-specs/specs/antelope/catalog-zones.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="catalog-zones"&gt;

&lt;blockquote&gt;
&lt;div&gt;&lt;p&gt;DNS Catalog Zones is a method in which a catalog of zones is
represented as a regular DNS zone, and transferred using DNS zone
transfers. As zones are added to or removed from the catalog zone, the
changes are propagated to the secondary nameservers in the normal way.
The secondary nameservers then add/remove/modify the zones they serve
in accordance with the changes to the zone.&lt;/p&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;p&gt;(&lt;a class="reference external" href="https://zones.cat/"&gt;https://zones.cat/&lt;/a&gt;)&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Currently Designate does not provide a list of zones for secondary
nameservers to consume and to be provisioned from. Rather Designate
manually creates, modifies and deleted every zone one by one via a
call to a management tooling like BIND’s &lt;cite&gt;rndc&lt;/cite&gt;. This mechanism has
scaling issues for large number of domains being added and maintained
on secondary server and a slow convergence in case of new servers being
added to the server pool.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Support for providing &lt;cite&gt;catalog zones&lt;/cite&gt; should be added to Designate.&lt;/p&gt;
&lt;p&gt;In essence &lt;cite&gt;catalog zones&lt;/cite&gt; provide easy provisioning capabilities of
lists of zones on secondary servers via AXFR from a special zone,
the &lt;cite&gt;catalog&lt;/cite&gt;.&lt;/p&gt;
&lt;p&gt;The below links explain the catalog zone feature, use cases and
data model:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://zones.cat/"&gt;https://zones.cat/&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://kb.isc.org/docs/aa-01401"&gt;https://kb.isc.org/docs/aa-01401&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://datatracker.ietf.org/doc/draft-ietf-dnsop-dns-catalog-zones/"&gt;https://datatracker.ietf.org/doc/draft-ietf-dnsop-dns-catalog-zones/&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;There already is support in BIND9, Knot and other major DNS servers like
PowerDNS or NSD to consume &lt;cite&gt;catalog zones&lt;/cite&gt;, all of them are backends
Designate supports:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;BIND (&amp;gt;=9.11) &lt;a class="reference external" href="https://bind9.readthedocs.io/en/latest/chapter6.html#catalog-zones"&gt;https://bind9.readthedocs.io/en/latest/chapter6.html#catalog-zones&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Knot (&amp;gt;=3.0) &lt;a class="reference external" href="https://www.knot-dns.cz/docs/3.0/html/configuration.html#catalog-zones"&gt;https://www.knot-dns.cz/docs/3.0/html/configuration.html#catalog-zones&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;NSD &lt;a class="reference external" href="https://github.com/IETF-Hackathon/NSDCatZ"&gt;https://github.com/IETF-Hackathon/NSDCatZ&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;PowerDNS &lt;a class="reference external" href="https://github.com/PowerDNS/powercatz/"&gt;https://github.com/PowerDNS/powercatz/&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Apart from improving on performance and resilience of the provisioning
in general, supporting &lt;cite&gt;catalog zones&lt;/cite&gt; also enables Designate to support
other backend implementationsas secondary DNS servers without the
requirement for dedicated drivers.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;The Pool object (and maybe adapters) will need to updated to include the new
pool settings required for creating a catalog zone. See the &lt;a class="reference internal" href="#other-changes"&gt;Other Changes&lt;/a&gt;
section for details of these settings.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Central must be updated to increment the pool catalog zone serial number
when a zone is created, updated, or deleted in the associated pool. It must
also trigger a NOTIFY to the nameservers in the affected pool.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Central and/or the workers must be updated to not directly create the zones
on the backend DNS servers if the pool has a catalog zone configured.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;The zone database schema will need to be updated to add a new “type” of
CATALOG to indicate that this zone is a catalog zone.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The existing zone “version” field can be used to track the catalog zone
“Schema Version” which is required to be present in a TXT record for the
zone. As of this spec, the version must be “2”.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The catalog zone will not have an associated tenant_id.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A new storage query will need to be created that merges the zone SOA and NS
records with a the list of zone PTR records for the catalog.&lt;/p&gt;
&lt;ol class="loweralpha simple"&gt;
&lt;li&gt;&lt;p&gt;The zone records returned for the catalog will use the zone ID as the
“unique ID” for the zone PTR record in the catalog.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Storage create_pool and update_pool will need to be updated to create the
catalog zone for the pool when the proper settings are included in the
pools.yaml. See the &lt;a class="reference internal" href="#other-changes"&gt;Other Changes&lt;/a&gt; section for details of these settings.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Storage create_pool and update_pool will need to be updated to create or
update the catalog zone TSIG key record in the database when one is
provided in the pools.yaml “catalog_zone_tsig_key” setting.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Storage create_pool and update_pool will need to be updated to capture the
catalog zone attributes in the existing pool_attributes table. See the
&lt;a class="reference internal" href="#other-changes"&gt;Other Changes&lt;/a&gt; section for details of these settings.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;The pool definition will next to be extended to add an optional section
“catalog_zone”.&lt;/p&gt;
&lt;ol class="loweralpha simple"&gt;
&lt;li&gt;&lt;p&gt;A “catalog_zone_fqdn” key/value will be added below the “catalog_zone”
parent. This will be a required field if “catalog_zone” is specified. It
will be validated to ensure it is a valid Fully Qualified Domain Name
(fqdn).&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A “catalog_zone_refresh” key/value will be added below the “catalog_zone”
parent. This is an optional setting that will use a default of 60
(seconds) if the parameter is not specified. This value will be validated
to be in the range of 0 to 2147483647 as with other zones.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A “catalog_zone_tsig_key” key/value will be added below the “catalog_zone”
parent. This setting is optional, but will be highly recommended in the
documentation for this feature. It will be validated the same way TSIG
keys are validated in the API.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A “catalog_zone_tsig_algorithm” key/value will be added below the
“catalog_zone” parent. This setting must be specified if a
“catalog_zone_tsig_key” is specified. It will be validated the same way
the TSIG algorithm is validated in the API.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Documentation must be created for setting up catalog zones.&lt;/p&gt;
&lt;ol class="loweralpha simple"&gt;
&lt;li&gt;&lt;p&gt;It must include a security warning and guide to adding a TSIG key to the
catalog zone.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;When the catalog zone is created by a pools.yaml pool creation, only one
NS record will be created for the zone. It must contain “invalid.” as the
NSDNAME as recommended in the catalog zone specification.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The catalog zone SOA record fields: RETRY and EXPIRE will be defined the
same way other Designate zones are defined.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Tests must be updated to cover this new capability.&lt;/p&gt;
&lt;ol class="loweralpha simple"&gt;
&lt;li&gt;&lt;p&gt;This should include tests that validate that non-admin users cannot see
the catalog zones.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A release note must be created for the feature.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="other-notes"&gt;
&lt;h3&gt;Other Notes&lt;/h3&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;This spec does not include creating “masters” records in the catalog zone.
This extension does not seem to be finalized at this time and it does not
currently support alternate port numbers. This could be added at a future
time.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;This spec does not include allowing backend drivers to configure the catalog
zones on the backend DNS servers. This could be added at a future time.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The catalog zone TSIG key is included in the pools.yaml as opposed to
created via the API to ensure the zone is protected as soon as possible and
to facilitate future patches that may create the catalog zone consumer on
the backend DNS servers automatically.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;The primary alternative to implementing “catalog zones” is the current
mechanism used by the Designate worker to manage zones on the backend name
servers.
Examples of this are: for BIND, rndc zone management; for PowerDNS, the
HTTP API.&lt;/p&gt;
&lt;p&gt;Providing the means to allow backends to pull a list of their zones
first of all provides an alternative or addition to the explicit
configuration of backends by the worker and their drivers.&lt;/p&gt;
&lt;p&gt;While there is the Designate API available to fetch zone data for other
means of provisioning backends, the catalog zone provides a common and
agreed interface to make this data available via AXFR and to various DNS
servers.&lt;/p&gt;
&lt;p&gt;There is no real alterative to providing a catalog zone, as it is a
distinct data model and protocol to be then provided by Designate.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Christian Rohmann &lt;a class="reference external" href="https://launchpad.net/~christian-rohmann"&gt;https://launchpad.net/~christian-rohmann&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;IRC Nick Name:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;crohmann&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;/section&gt;
&lt;section id="upgrade-implications"&gt;
&lt;h2&gt;Upgrade Implications&lt;/h2&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Fri, 08 Jul 2022 00:00:00 </pubDate></item><item><title>Designate Zone Pool Move</title><link>https://specs.openstack.org/openstack/designate-specs/specs/antelope/zone-pool-move.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="designate-zone-pool-move"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/zone-move"&gt;https://blueprints.launchpad.net/designate/+spec/zone-move&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Zone move is an important feature that possibly eliminates the problem observed
with zone export-import.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Assume, zone is currently located in pool A, but has to move to pool B. (for example
pool B is another, new DNS provider).&lt;/p&gt;
&lt;p&gt;Currently, Designate only allows you to create zone export (will be a Bind-format
single file with all the records of the zone) and zone import. So, a zone can be
exported from one pool; deleted from pool A; and imported into another pool B.&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;The problem is that the zone has to be deleted in this process and imported.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Large zone imports (20-30k records) can take a couple of hours as Designate
creates all records one by one.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Therefore, it is problematic to move a zone between the pools/backends without any
hacks. At the point when the zone is deleted, but not imported, any DNS queries to
Designate-MDNS from the backend will not work.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Introduce a new admin-only command in designate &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zone&lt;/span&gt; &lt;span class="pre"&gt;pool&lt;/span&gt; &lt;span class="pre"&gt;move&lt;/span&gt;&lt;/code&gt;. The command works
as below:&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;openstack zone pool move zone_id_or_name –pool_id=AN_ID_OF_POOL_B&lt;/strong&gt;&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;The designate service should update zone pool_id property similar to other zone
properties. The updated pool_id will be reflected in the designate DB. If the
command is invoked without pool_id paramter, the designate reschedule the zone
and move it to a different pool if appropriate. For example, user can move
their zone up to a higher tier of service by updating an attribute and then
calling move will cause attribute scheduler to select appropriate pool.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;After DB update, designate will create copy of zone (can also be called as clone)
except it should not create new db entry for the clone zone. The clone zone will
be created on target pool backend servers i.e. pool B.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The zone transfer(AXFR/IXFR) will happen and the zone on pool B gets synced with
the designate DB.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;At this point zone still exists in pool A. It can be removed after the administrator
has changed the settings manually at domain registrar. This is a manual process.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The above proposed change eliminates the zone export as well as zone delete steps.
Thus, speed up the import of large zone to the target pool.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;The zone move will be triggered via the V2 API.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Example zone pool move request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;POST&lt;/span&gt; &lt;span class="nn"&gt;http://192.168.1.47/dns/v2/zones/52f42b9e-c48b-43e2-af01-180e8ed33cd0/tasks/pool_move&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Host&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;127.0.0.1:9001&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"794ccc2c-d751-44fe-b57f-8894c9f5c842"&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;Central will update the pool_id of the zone for which move is requested. The updated
pool_id will be written to DB. Central will then clone the zone and then create new clone
zone in target pool backend servers.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kiran Pawar (kpdev in Gerrit)&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Fri, 04 Jun 2021 00:00:00 </pubDate></item><item><title>A Worker Model for Designate</title><link>https://specs.openstack.org/openstack/designate-specs/specs/newton/worker-model.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="a-worker-model-for-designate"&gt;

&lt;p&gt;Thesis: Gratuitous unnecessary complexity exists within the Designate
code, and in the operation of Designate as a service. Making Designate
a producer-worker type of project will vastly simplify the development
and operation, and align it more to the true nature of the service it
provides (DNS).&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-pool-manager&lt;/span&gt;&lt;/code&gt; does a reasonably good job at pushing Create/Delete
changes out to nameservers, but the process gets a bit less shiny after that.&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Polling to see if state is live is done via asynchronous and synchronous RPC
with another component.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Cache usage is a mess (storing mutliple keys, keeping one key around forever,
storing a different key for each type of operation).&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Periodic Sync/Recovery are very unreliable as the number of changes grows.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The update_status and logic for calculating consensus is heavy-handed, too
eager, and too complex.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The state machine is very foggy, and the logic for updating status that gets
pushed into central is obfuscated.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Pool Managers are tied to one pool&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager&lt;/span&gt;&lt;/code&gt; does a good job at executing periodic timers for the
zones it manages. However:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;One zone-manager process is responsible for a certain set of zones, if the
operations for that set of zones gets heavy, a single zone manager process
could become overwhelmed.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;We rely on &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tooz&lt;/span&gt;&lt;/code&gt; to manage the extremely delicate task of ensuring
balance and coverage of all zones by zone manager processes.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Certain work (export) that’s in the critical path of operations has already
crept into the component that wasn’t really meant for that. As a substitute
for proper workers, the zone-manager is looking like the current answer.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; is a DNS server written in Python. It works well for small
amounts of traffic, but as traffic grows, we may realize that we need it to be
more specialized, as a DNS server written in Python should be. The logic for
sending NOTIFYs and polling of changes seems less likely to belong in mdns in
the future. If those bits were removed, &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; could be rewritten
to make use of a better tool for the problem.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;A change to the underlying architecture of executing actual work on DNS servers
and the running of other tasks. Essentially, removing
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-pool-manager&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager&lt;/span&gt;&lt;/code&gt;, replacing them with
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt; (names up for debate) and
removing certain logic from &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt;. All of the actual “work” would
be put in the scalable &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; process, which has work produced
by the API/Central, and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt;. &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; gets back
to it’s roots, and only answers AXFRs. Callbacks over queues that don’t involve
the API are eliminated, simplifying the code in all components that deal with
DNS servers.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;No changes&lt;/strong&gt; to the API or Database are required, with minimal changes to
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-central&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;To the end user, the results of this change would be relatively simple:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Scalability limited only by DNS servers, datastores, and queues. If at any
point Designate starts to slow down in some aspect, unless there’s an issue
with those services listed above, the problem can be solved by throwing more
Designate processes at the problem.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Fault tolerance. One or more Designate processes dying would be inivisible
in almost every case. An operator wouldn’t have to fear a certain process
dying, because no one process handles responsiblities others will not, as long
as there is a minimal amount of redundancy.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Simplicity. The Designate architecture becomes much cleaner and easier to
understand. The questions of “what is the difference between pool-manager and
zone-manager” and “what’s synchronous and asynchronous” become less muddy,
or disappear altogether.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Operationally, this opens the door for simpler scenarios for small
deployments where a customer need only scale a couple components (even on
the same machine) to get more performance. You could even go so far as to
deploy app nodes that only shared datastore (db, cache) and had their own
designate components and queues.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;section id="architectural-changes"&gt;
&lt;h3&gt;Architectural Changes&lt;/h3&gt;
&lt;p&gt;These are the services that would remain present:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-api&lt;/span&gt;&lt;/code&gt; - To receive JSON and parse it for Designate&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-central&lt;/span&gt;&lt;/code&gt; - To do validation/storage of zone/record data and
send CRUD tasks to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; - To &lt;strong&gt;only&lt;/strong&gt; perfrom AXFRs from Designate’s database&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; - Any and all tasks that Designate needs to
produce state on nameservers&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt; - To run periodic/timed jobs, and produce work
for &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; that is out the normal path of API operations.
For example: Periodic recovery.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Other necessary components:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Queue - Usually RabbitMQ&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Database - Usually MySQL&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Cache - (encouraged, although not necessary) Memcached, MySQL, Redis&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tooz&lt;/span&gt;&lt;/code&gt; backend (Zookeeper, Memcahed, Redis)&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Services/components that are no longer required:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-pool-manager&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="designate-worker"&gt;
&lt;h3&gt;Designate Worker&lt;/h3&gt;
&lt;p&gt;The scope of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;’s duties are essentially any and all tasks
that Designate needs to take action to perform. For example:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Create, Update, and Delete zones on pool targets via backend plugins&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Poll that the change is live&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Update a cache with the serial number for a zone/target&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Emit zone-exists events for billing&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Flatten Alias Records&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Clean up deleted zones&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Importing/Exporting zones&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Many more&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The service essentially exposes a vast RPCAPI that contains &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tasks&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;An important difference to Designate’s current model is that all
of these tasks do not call back. They are all fire-and-forget tasks
that will be shoved on a queue and await worker action.&lt;/p&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tasks&lt;/span&gt;&lt;/code&gt; are essentially functions, that given relatively simple input, make
the desired income happen on either nameservers, or the Designate database.&lt;/p&gt;
&lt;section id="cache"&gt;
&lt;h4&gt;Cache&lt;/h4&gt;
&lt;p&gt;The cache performs a similar function to the current pool manager cache
now.&lt;/p&gt;
&lt;p&gt;It will store state for each different type of task that a worker can use
to decide if it needs to continue with a &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;task&lt;/span&gt;&lt;/code&gt; received from the queue, or
simply drop it and move on to the next task.&lt;/p&gt;
&lt;p&gt;This varies by task, some are relatively simple, knowing whether to perform
a zone update to a certain serial number is knowable by seeing the serial
number of a zone on each target in a pool. For DNSSEC zone signing, a key
would probably be placed to indicate that a certain worker was working on
resigning a zone, as it’s a more long-running process.&lt;/p&gt;
&lt;p&gt;In the absence of such a cache, each worker will act naive and try to complete
each task it receives.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="tasks"&gt;
&lt;h4&gt;Tasks&lt;/h4&gt;
&lt;p&gt;Each task will be idempotent, to the degree that it is possible.&lt;/p&gt;
&lt;p&gt;As mentioned in the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;Cache&lt;/span&gt;&lt;/code&gt; section, to a certain degree, tasks could be
able to know if they need to complete work based on information in the cache.&lt;/p&gt;
&lt;p&gt;But they should also make an effort to not duplicate work, for instance,
if it’s trying to delete a zone that’s already gone, it should interpret
the zone being gone as a sign that the delete is successful and move on.&lt;/p&gt;
&lt;p&gt;On the whole these tasks would simply be lifted from where they currently
exist in the code, and wouldn’t change all that much.&lt;/p&gt;
&lt;p&gt;A slight change might be that during the course of the task, we may recheck
that the work that is being undertaken still needs to be done.&lt;/p&gt;
&lt;p&gt;As an example:
An API customer creates many recordsets very quickly. The work being dispatched
to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; processes would go to a lot of different places, and one of
the first updates to actually reach a nameserver might contain all the changes
necessary to bring the zone up-to-date. The other tasks being worked should
check before they send their NOTIFY that the state is still behind, and check
again after they’ve sent their NOTIFY, but before they’ve began polling, so
that they can cut down on unnecessary work for themselves, and the nameservers.&lt;/p&gt;
&lt;p&gt;You could get even smarter about the markers that you drop in a cache for these
tasks. For example, on a zone update, you could drop a key in the cache of the
nature &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zoneupdate-foo.com.&lt;/span&gt;&lt;/code&gt;, and other if other zoneupdate tasks for the same
zone see that key, they could know to throw away their job and move on.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="designate-mdns-changes"&gt;
&lt;h4&gt;designate-mdns changes&lt;/h4&gt;
&lt;p&gt;The partioning of certain elements that Designate had previously disappears.
The worker service will send DNS queries, it will do cpu-bound tasks, but it
will be one place to scale. It should be possible to have an extremely robust
Designate architecture by simply scaling these workers.&lt;/p&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; will have it’s entire RPCAPI transferred to
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;. This will vastly simplify the amount of work it needs
to do while it sits in the critical path of providing zone transfers to
nameservers Designate manages.&lt;/p&gt;
&lt;p&gt;As a side-note, this would make this service much easier to optimize, or even
rewrite in a faster programming language.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="designate-producer"&gt;
&lt;h3&gt;Designate Producer&lt;/h3&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt; is the place where jobs that produce tasks that
are outside of the normal path of API operations and operate on
some kind of timer live.&lt;/p&gt;
&lt;p&gt;The &lt;strong&gt;key&lt;/strong&gt; difference to the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zone-manager&lt;/span&gt;&lt;/code&gt; service, is that this service
simply generates work to be done, rather than actually doing the work.
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt; simply decides what needs to be done, and sends RPC
messages on the queue to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; to actually perform the work.&lt;/p&gt;
&lt;p&gt;As we’ve grown Designate, we’ve seen the need
for this grow vastly, and even more so in the future.&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Deleted zone purging&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Refreshing Secondary Zones&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Emitting zone exists tasks and other billing events&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;DNSSEC signing of zones&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Alias record flattening&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;We could move the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;periodic_sync&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;periodic_recovery&lt;/span&gt;&lt;/code&gt; tasks from the
Pool Manager to this service.&lt;/p&gt;
&lt;p&gt;The &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;periodic_sync&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;periodic_recovery&lt;/span&gt;&lt;/code&gt; tasks in the Pool Manager have
been a constant struggle to maintain and get right. This is due to a lot of
factors.&lt;/p&gt;
&lt;p&gt;Making the generation of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tasks&lt;/span&gt;&lt;/code&gt; by periodic processes the job of only one
Designate component simplifies the architecture, and allows to solve the
problems it presents one time, one way, and generally do one thing well.&lt;/p&gt;
&lt;section id="timers"&gt;
&lt;h4&gt;Timers&lt;/h4&gt;
&lt;p&gt;This service would essentially be a group of timers that wake up on a cadence
and create work to be put on the queue for &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; processes to
pick up.&lt;/p&gt;
&lt;p&gt;The overhead is relatively low here, as we’re not actually doing the work, but
more just scheduling the work to be done. This way we can focus on the
unexpectedly difficult problem of dividing up the production of work that these
processes will put on the queue.&lt;/p&gt;
&lt;section id="dividing-work"&gt;
&lt;h5&gt;Dividing work&lt;/h5&gt;
&lt;p&gt;To explain more clearly, the biggest problem we have in this service is making
it fault-tolerant, but not duplicating work for &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; processes
to do. This was solved before by &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;tooz&lt;/span&gt;&lt;/code&gt; using the zone shards in the Designate
database in &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager&lt;/span&gt;&lt;/code&gt; and it seems to work well.&lt;/p&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; processes, as described above, will do a certain amount of
optimization so that they don’t duplicate work. But if we generate too much
cruft, those processes will be bogged down just by the task of seeing if they
need to do work. So we should work to minimize the amount of duplicate work we
produce.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="queue-priority"&gt;
&lt;h3&gt;Queue Priority&lt;/h3&gt;
&lt;p&gt;One potential complication of this implementation is that, as the number of
timers and tasks that are out of Designate’s critical path of implementation
grow, they may get in the way of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; processes doing the tasks
that are most important, namely CRUD of zones and records.&lt;/p&gt;
&lt;p&gt;We propose having queues/exchanges for each type of task, this would be an
optimal way to monitor the health of different types of tasks, and isolate the
sometimes long-running tasks that periodic timers will produce from the
relatively quicker, and more important CRUD operations. The algorithm for
choosing tasks from the various options could be customized by a particular
process if desired. But a good general default would be to handle CRUD
operations from &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-central&lt;/span&gt;&lt;/code&gt; first. Or use a weighted random
choice algorithm, with the critical-path CRUD operations having higher weights.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Stand up a &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; service&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Migrate CRUD zone operations to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;, reworking the cache
implementation.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Stand up &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt; service&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Migrate Pool Manager periodic tasks to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt;, with small
modifications to ensure they simply generate work for &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Move &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt;’ NOTIFYing and polling to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Fix up the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;update_status&lt;/span&gt;&lt;/code&gt; logic in &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-central&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Migrate all tasks from &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zone-manager&lt;/span&gt;&lt;/code&gt; to a split of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;
and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt;, where &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;producer&lt;/span&gt;&lt;/code&gt; creates the work on the queue
and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;worker&lt;/span&gt;&lt;/code&gt; executes it. Ensuring scalable logic for distributed work
production using cache or some other method in &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Deprecate &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;pool-manager&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;zone-manager&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Profit!!!&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="upgrade-implications"&gt;
&lt;h3&gt;Upgrade Implications&lt;/h3&gt;
&lt;p&gt;Upgrading to the next release with this change would introduce some operational
changes. Mostly around the services that need to be deployed. The deployment
need not be a cutover, deploying Newton Designate will work with or without the
worker. This is because of a variety of compatibility measures taken:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-central&lt;/span&gt;&lt;/code&gt; will have a configurable “zone api” that it can swap
between &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-pool-manager&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;. If the worker
process is enabled, central can send c/u/d zones events to the worker
instead of the pool manager.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;’s ability to send NOTIFYs and Poll DNS servers can
replace a portion of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt;’ responsibilities. For certain
DNS servers, it’s theorized that they won’t behave well if a NOTIFY comes
from a different server than it’s master that it zone transfers from.
For this reason, &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;’s ability to send NOTIFYs is a
configurable element. Since the worker calls into a backend plugin to update
zones, the NOTIFY via mdns logic in those backends can remain, and if the
operator so chooses, the NOTIFY task in the worker can no-op. This works both
ways. An operator can also choose to have the MiniDNS notify calls noop, and
allow them to be completed by the worker process.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;For those who choose to firewall all DNS traffic between Designate and DNS
servers, it will be safest to deploy &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; processes in
close proximity to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; processes. So that the DNS polling that
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt; does can be completed, where &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; used
to do it.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;As periodic-type processes are migrated to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt; and
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;, they can be marked as “worker tasks” in
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager&lt;/span&gt;&lt;/code&gt;, that can be turned off behind a configuration
flag.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The process for upgrading to the worker model code, after deploying Newton
could look something like this:&lt;/p&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;(To account for firewalling dns traffic) Start &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;
processes operating on the same IPs as &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; processes via
proximity or proxy. The default configuration will still allow NOTIFYs
and DNS polling to occur via &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt;, and all other operations
to work in &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-pool-manager&lt;/span&gt;&lt;/code&gt;. No traffic will reach the worker.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Toggle configuration values &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker::enabled&lt;/span&gt;&lt;/code&gt; and
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker::notify&lt;/span&gt;&lt;/code&gt; and restart &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-worker&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Restart &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-central&lt;/span&gt;&lt;/code&gt; and &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-mdns&lt;/span&gt;&lt;/code&gt; processes so that mdns
NOTIFY calls no-op, and central starts to use the worker instead of
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-pool-manager&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Toggle the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager::worker-tasks&lt;/span&gt;&lt;/code&gt; config flag and restart
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager&lt;/span&gt;&lt;/code&gt; so that it hands off periodic tasks to the
producer/worker.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Start the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-producer&lt;/span&gt;&lt;/code&gt; process so that the worker starts doing
recovery and other periodic tasks.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Stop the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-pool-manger&lt;/span&gt;&lt;/code&gt; processes, and if all processes are
migrated out of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;designate-zone-manager&lt;/span&gt;&lt;/code&gt;, that as well.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Newton&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="author-s"&gt;
&lt;h3&gt;Author(s)&lt;/h3&gt;
&lt;p&gt;Tim Simmons &lt;a class="reference external" href="https://launchpad.net/~timsim"&gt;https://launchpad.net/~timsim&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Paul Glass &lt;a class="reference external" href="https://launchpad.net/~pnglass"&gt;https://launchpad.net/~pnglass&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Eric Larson &lt;a class="reference external" href="https://launchpad.net/~eric-larson"&gt;https://launchpad.net/~eric-larson&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 03 Mar 2021 00:00:00 </pubDate></item><item><title>Filtering API</title><link>https://specs.openstack.org/openstack/designate-specs/specs/juno/filtering.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="filtering-api"&gt;

&lt;section id="discussion-needed"&gt;
&lt;h2&gt;Discussion Needed&lt;/h2&gt;
&lt;section id="update"&gt;
&lt;h3&gt;Update:&lt;/h3&gt;
&lt;p&gt;For now, wildcards will not be restricted, though limitations may have to be added
due to scaling concerns. Also, to address a bug with wildcard matching
(&lt;a class="reference external" href="https://bugs.launchpad.net/designate/+bug/1335902"&gt;https://bugs.launchpad.net/designate/+bug/1335902&lt;/a&gt;) and to conform to standards,
the wildcard character has been changed from ‘%’ to ‘*’.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="previous-discussion"&gt;
&lt;h3&gt;Previous Discussion:&lt;/h3&gt;
&lt;p&gt;&lt;a class="reference external" href="http://paste.openstack.org/show/85431/"&gt;http://paste.openstack.org/show/85431/&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/example"&gt;https://blueprints.launchpad.net/designate/+spec/example&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Filtering provides the ability to qualify the result set returned by a query to the designate api.
It will ultimately be available on all collections - zones, record sets, rdata of record sets, and pools.&lt;/p&gt;
&lt;p&gt;Filtering will be controlled using query parameters which match the name of the attribute being filtered.
It is &lt;em&gt;not&lt;/em&gt; required that all attributes are available as filter targets, but the majority will be.&lt;/p&gt;
&lt;p&gt;Filters are either an exact match or wildcard match, which is specified by the presence of the reserved
wildcard character (‘*’).&lt;/p&gt;
&lt;p&gt;If the filtering request is successful, the resources that pass the filter criteria are returned,
as well as links for retrieving more details.&lt;/p&gt;
&lt;p&gt;Pagination of results will take advantage of proposed Designate pagination
(&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/pagination"&gt;https://blueprints.launchpad.net/designate/+spec/pagination&lt;/a&gt;)&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;section id="filtering-vs-search-a-clarification"&gt;
&lt;h3&gt;Filtering vs. Search: A Clarification&lt;/h3&gt;
&lt;p&gt;NOTE: Filtering and searching are two completely different features and will be addressed separately.
Search involves the ability to compile a list of results from storage, possibly drawing from many
different places (for example, finding all of a tenant’s A records with a certain IP address). Filtering
only involves further restricting the standard queries that are offered by the API (for example, /zones,
/zones/{id}/recordsets, etc.).&lt;/p&gt;
&lt;p&gt;You can find the wiki for search &lt;a class="reference external" href="https://wiki.openstack.org/wiki/Designate/Blueprints/Search_API"&gt;here&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Basic filtering for:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Blacklists: pattern&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Recordsets: name, type, ttl, data&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;TLDs: name&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Zones: name&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Wildcard search using SQL pattern matching&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The examples below demonstrate the types of calls typically made with filtering.  These calls apply
to all of the aforementioned filtering parameters.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Verb&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Resource&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;GET&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;dl class="simple"&gt;
&lt;dt&gt;zones/{id}/recordsets/{id}/recordsets?&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;name=www.example.com&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/td&gt;
&lt;td&gt;&lt;p&gt;From the specified
recordset, return
any record with a
name that matches
the specified filter
(“name”) exactly.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;GET&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;dl class="simple"&gt;
&lt;dt&gt;zones/{id}/recordsets/{id}/recordsets?&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;name=www.test*&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/td&gt;
&lt;td&gt;&lt;p&gt;From the specified
recordset, return
any record with a
name that BEGINS
with the specified
“name” attribute.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;GET&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;dl class="simple"&gt;
&lt;dt&gt;zones/{id}/recordsets/{id}/recordsets?&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;name=*.com&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/td&gt;
&lt;td&gt;&lt;p&gt;From the specified
recordset, return
any record with a
name that ENDS
with the specified
“name” attribute.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;GET&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;dl class="simple"&gt;
&lt;dt&gt;zones/{id}/recordsets/{id}/recordsets?&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;name=www.*.com&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/td&gt;
&lt;td&gt;&lt;p&gt;From the specified
recordset, return
any record with a
name that contains
the specified name
data on both sides
of the wildcard.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="get-zones-zone-id-recordsets-name-example"&gt;
&lt;h4&gt;GET zones/{zone-id}/recordsets?name=example*&lt;/h4&gt;
&lt;p&gt;This call is for a privileged user filtering recordsets by name, for one tenant, using wildcard matching.&lt;/p&gt;
&lt;p&gt;Request:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;GET zones/{zone-id}/recordsets?name=example*
Host: dns.provider.com
Accept: application/json
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;Response:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"recordsets"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets/948a0233-abdf-434e-a003-c5d682daf0ea"&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[],&lt;/span&gt;
            &lt;span class="s2"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"948a0233-abdf-434e-a003-c5d682daf0ea"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a4e29ed3-d7a4-4e4d-945d-ce64678d3b94"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-08T20:28:27.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[],&lt;/span&gt;
            &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"NS"&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets/7da6119a-8b41-4f09-a2b7-a44ed2c9ebd0"&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="s2"&gt;"mail2.example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s2"&gt;"mail.example.org."&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"7da6119a-8b41-4f09-a2b7-a44ed2c9ebd0"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a4e29ed3-d7a4-4e4d-945d-ce64678d3b94"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-08T20:28:28.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="mi"&gt;10&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"MX"&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets?name=example%2A"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-zones-zone-id-recordsets-name-example-org"&gt;
&lt;h4&gt;GET zones/{zone-id}/recordsets?name=example.org.&lt;/h4&gt;
&lt;p&gt;This call is for customers filtering recordsets by name, using exact matching.&lt;/p&gt;
&lt;p&gt;Request:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;GET zones/{zone-id}/recordsets?name=www.example.org.
Host: dns.provider.com
Accept: application/json
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;Response:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"recordsets"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets/7da6119a-8b41-4f09-a2b7-a44ed2c9ebd0"&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="s2"&gt;"mail2.example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s2"&gt;"mail.example.org."&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"7da6119a-8b41-4f09-a2b7-a44ed2c9ebd0"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a4e29ed3-d7a4-4e4d-945d-ce64678d3b94"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-08T20:28:28.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="mi"&gt;10&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"MX"&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets?name=example%2A"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-zones-zone-id-recordsets-data-1-2-3"&gt;
&lt;h4&gt;GET zones/{zone-id}/recordsets?data=1.2.3.*&lt;/h4&gt;
&lt;p&gt;This call is for customers who wish to find all recordsets in a zone that contains
one or more records with the matching data value (with a wildcard applied).
The data parameter can be used in conjunction with other parameters.&lt;/p&gt;
&lt;p&gt;Request:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;GET zones/{zone-id}/recordsets?data=1.2.3.*
Host: dns.provider.com
Accept: application/json
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;Response:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"recordsets"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets/077ce2b4-1d52-4c3f-8c70-07dfddeed5cc"&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="s2"&gt;"1.2.3.4"&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"077ce2b4-1d52-4c3f-8c70-07dfddeed5cc"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"dns2.example.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a4e29ed3-d7a4-4e4d-945d-ce64678d3b94"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-08T20:28:26.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="n"&gt;null&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"A"&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets/758004fe-4f0f-4756-a8f3-ee01ca5db8a2"&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="s2"&gt;"1.2.3.10"&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"758004fe-4f0f-4756-a8f3-ee01ca5db8a2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"mail2.example.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a4e29ed3-d7a4-4e4d-945d-ce64678d3b94"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-08T20:28:20.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="n"&gt;null&lt;/span&gt;
            &lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"A"&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"http://192.168.33.8:9001/v2/zones/a4e29ed3-d7a4-4e4d-945d-ce64678d3b94/recordsets?data=1.2.3.*"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;Some restrictions on the usages of wildcard filtering may be applied in the future.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;p&gt;The API changes mentioned above have essentially been completed. Examples of potential
future changes include:
* Restrictions on wildcard search (currently wildcard searching is unrestricted)
* Adding more attributes that can be filtered&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 03 Jun 2020 00:00:00 </pubDate></item><item><title>Secondary Zones</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/secondary-zones.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="secondary-zones"&gt;
&lt;span id="id1"/&gt;
&lt;p&gt;Outline support for Secondary Zones concept in Designate.&lt;/p&gt;
&lt;section id="terminology"&gt;
&lt;h2&gt;Terminology&lt;/h2&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Term&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Meaning&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;axfr&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Full Zone Update (AXFR)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;zone&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Seconday Zone - Zone that transfers it’s
state / data from a given set of masters&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;We want to support Secondary Zones in order to lay the grounds for higher level
features like incoming (A|I)XFR, Federation and others (will be separate specs).&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;We introduce a new concept of a Secondary zone within Designate that has
external Masters. In term this means that Designate will be acting as a Slave.&lt;/p&gt;
&lt;p&gt;In MiniDNS we add support for inbound AXFR and NOTIFY.&lt;/p&gt;
&lt;p&gt;In terms of Pools a Secondary Zone would be placed equally as a Primary&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;API endpoints for recordsets should disallow any Create, Update, Delete action.&lt;/p&gt;
&lt;p&gt;&lt;em&gt;status&lt;/em&gt; fields will be the same as with Primary Zones.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="new-zone-parameters"&gt;
&lt;h3&gt;New Zone parameters&lt;/h3&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Parameter&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Required&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Default&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ENUM(PRIMARY, SECONDARY)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;false&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Primary or Secondary&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;masters&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;List&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;None&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Zone Masters&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;transferred_at&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Datetime&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;ul class="simple"&gt;
&lt;li/&gt;
&lt;/ul&gt;
&lt;/td&gt;
&lt;td&gt;&lt;p&gt;None&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Last successful transfer&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="create-secondary-zone"&gt;
&lt;h4&gt;Create Secondary Zone&lt;/h4&gt;
&lt;p&gt;When creating a new zone the &lt;em&gt;managed_resource_email&lt;/em&gt; is used as the initial &lt;em&gt;email&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;The fields &lt;em&gt;version&lt;/em&gt; will be &lt;em&gt;1&lt;/em&gt; since it’s not yet transferred and &lt;em&gt;transferred_at&lt;/em&gt; as &lt;em&gt;null&lt;/em&gt;.&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;POST&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt; &lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt;
&lt;span class="n"&gt;Host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mf"&gt;127.0.0.1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;9001&lt;/span&gt;
&lt;span class="n"&gt;Accept&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="s2"&gt;"zone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"This is an example zone."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"masters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"10.0.0.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"10.0.0.2:5354"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"SECONDARY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;201&lt;/span&gt; &lt;span class="n"&gt;Created&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="s2"&gt;"zone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"572ba08c-d929-4c70-8e42-03824bb24ca2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"4335d1f0-f793-11e2-b778-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"email"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"managed@foo.co"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"serial"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1404757531&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"This is an example zone."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"masters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"10.0.0.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"10.0.0.2:5354"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"SECONDARY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"transferred_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:25:31.275934"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-secondary-zone"&gt;
&lt;h4&gt;Get Secondary Zone&lt;/h4&gt;
&lt;p&gt;Retrieves a secondary zone with the specified ID.&lt;/p&gt;
&lt;p&gt;Example of GET on a untransferred zone:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;GET&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;a86dba58&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;0043&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="n"&gt;cc6&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;a1bb&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;69&lt;/span&gt;&lt;span class="n"&gt;d5e86f3ca3&lt;/span&gt; &lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt;
&lt;span class="n"&gt;Host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mf"&gt;127.0.0.1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;9001&lt;/span&gt;
&lt;span class="n"&gt;Accept&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;200&lt;/span&gt; &lt;span class="n"&gt;OK&lt;/span&gt;
&lt;span class="n"&gt;Vary&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Accept&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="s2"&gt;"zone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"572ba08c-d929-4c70-8e42-03824bb24ca2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"4335d1f0-f793-11e2-b778-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"email"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"managed@foo.co"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"serial"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1404757531&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"This is an example zone."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"masters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"10.0.0.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"10.0.0.2:5354"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"SECONDARY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"transferred_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:25:31.275934"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="list-secondary-zones"&gt;
&lt;h4&gt;List Secondary Zones&lt;/h4&gt;
&lt;p&gt;To filter on zone type do type=&amp;lt;PRIMARY|SECONDARY&amp;gt; as query parameters.&lt;/p&gt;
&lt;p&gt;Below there is examples of a Zone that’s not transferred yet and one that is.&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;GET /v2/zones?type=SECONDARY HTTP/1.1
Host: 127.0.0.1:9001
Accept: application/json
Content-Type: application/json
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;200&lt;/span&gt; &lt;span class="n"&gt;OK&lt;/span&gt;
&lt;span class="n"&gt;Vary&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Accept&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="s2"&gt;"zones"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[{&lt;/span&gt;
    &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"572ba08c-d929-4c70-8e42-03824bb24ca2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"4335d1f0-f793-11e2-b778-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"email"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"managed@foo.co"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"serial"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2014120100&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"This is an example zone."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"masters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"10.0.0.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"10.0.0.2:5354"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"SECONDARY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"transferred_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:25:31.275934"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:25:31.275934"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:25:31.275934"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"fdd7b0dc-52a3-491e-829f-41d18e1d3ada"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"572ba08c-d929-4c70-8e42-03824bb24ca2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"4335d1f0-f793-11e2-b778-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.net."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"email"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"managed@foo.co"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"serial"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1404756682&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"This is another example zone."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"masters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"10.0.0.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"10.0.0.2:5354"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"SECONDARY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"transferred_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:22:08.287743"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/fdd7b0dc-52a3-491e-829f-41d18e1d3ada"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}],&lt;/span&gt;
  &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones"&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="update-a-secondary-zone"&gt;
&lt;h4&gt;Update a Secondary Zone&lt;/h4&gt;
&lt;p&gt;Changes the specified attribute(s) for an existing zone.&lt;/p&gt;
&lt;p&gt;In the example below, we update one of the masters to 10.0.0.3.&lt;/p&gt;
&lt;p&gt;NOTE: In terms of a Secondary Zone only the following fields below are
editable.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Parameter&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;description&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Description of Zone&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;masters&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Master servers&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;PATCH&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;a86dba58&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;0043&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="n"&gt;cc6&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;a1bb&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;69&lt;/span&gt;&lt;span class="n"&gt;d5e86f3ca3&lt;/span&gt; &lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt;
&lt;span class="n"&gt;Host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mf"&gt;127.0.0.1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;9001&lt;/span&gt;
&lt;span class="n"&gt;Accept&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="s2"&gt;"zone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"masters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"10.0.0.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mf"&gt;10.0.0.3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;1053&lt;/span&gt;&lt;span class="s2"&gt;"]&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;200&lt;/span&gt; &lt;span class="n"&gt;OK&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="s2"&gt;"zone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"pool_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"572ba08c-d929-4c70-8e42-03824bb24ca2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"4335d1f0-f793-11e2-b778-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"serial"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"This is an example zone."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"masters"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"10.0.0.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"10.0.0.3:1053"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"SECONDARY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"transferred_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:25:31.275934"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-07-07T18:25:31.275934"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="delete-secondary-zone"&gt;
&lt;h4&gt;Delete Secondary Zone&lt;/h4&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;DELETE&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;a86dba58&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;0043&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="n"&gt;cc6&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;a1bb&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;69&lt;/span&gt;&lt;span class="n"&gt;d5e86f3ca3&lt;/span&gt; &lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt;
&lt;span class="n"&gt;Host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mf"&gt;127.0.0.1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="mi"&gt;9001&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;204&lt;/span&gt; &lt;span class="n"&gt;No&lt;/span&gt; &lt;span class="n"&gt;Content&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;Disallow changing of a zone from PRIMARY &amp;lt;&amp;gt; SECONDARY.&lt;/p&gt;
&lt;p&gt;Add a periodic task that loops over secondary zones looking at their &lt;cite&gt;transferred_at&lt;/cite&gt;
and does a call to MDNS to trigger a new AXFR to keep the zone updated.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;section id="modify-table-domains"&gt;
&lt;h4&gt;Modify Table - domains&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Action&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;EMUM(PRIMARY, SECONDARY)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Zone type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;transferred_at&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DATETIME&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes (Not transferred)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Last transfer at&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="new-table-domain-attributes"&gt;
&lt;h4&gt;New Table - domain_attributes&lt;/h4&gt;
&lt;p&gt;A new table to store any metadata / attributes that doesn’t need to be on the
on the domains table.&lt;/p&gt;
&lt;p&gt;An index across domain_id, key, value.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Action&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;UUID&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;no&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ID for this attribute&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;domain_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;FK to Domain UUID&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;no&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Domain ID this attribute belongs to&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;key&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ENUM(masters)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;no&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Zone type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;value&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;no&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Master servers for Zone&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="minidns-changes"&gt;
&lt;h3&gt;MiniDNS Changes&lt;/h3&gt;
&lt;section id="zone-creation"&gt;
&lt;h4&gt;Zone Creation&lt;/h4&gt;
&lt;p&gt;When a zone is created currently a notification is sent to mdns, we’ll plugin
here and do a AXFR if zone.type is SECONDARY.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="notify"&gt;
&lt;h4&gt;NOTIFY&lt;/h4&gt;
&lt;p&gt;We need to change __call__ to pass NOTIFY down to self._handle_notify().&lt;/p&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Receives a NOTIFY&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Query the SOURCE of the NOTIFY for SOA&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Compare response serial vs local if it doesn’t match then continue to next step.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Do a AXFR towards the server that sent the NOTIFY.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Call dnsutils.from_dnspython to get Domain a’la Designate version&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Call Central to method with the data from #5 to update the domain.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="new-requesthandler-handle-notify-context-request"&gt;
&lt;h4&gt;New - RequestHandler._handle_notify(context, request)&lt;/h4&gt;
&lt;p&gt;Handles a Notification and eventually hands off to do a AXFR.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;request&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The DNS request&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="new-service-zone-sync-context-zone-master-addr-none"&gt;
&lt;h4&gt;New - Service.zone_sync(context, zone, master_addr=None)&lt;/h4&gt;
&lt;p&gt;A method utilized by any method in MDNS that needs to do a AXFR.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;zone&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A objects.Domain object&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;master_addr&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Address to use for the AXFR&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="future-work"&gt;
&lt;h2&gt;Future work&lt;/h2&gt;
&lt;p&gt;The below is out of scope for this.&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;A task for /zones/&amp;lt;id&amp;gt;/tasks or so should be added in the future
to allow a “forced” AXFR via the API.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A task to switch from a SECONDARY &amp;gt; PRIMARY.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&amp;lt;&lt;a class="reference external" href="https://launchpad.net/~endre-karlson"&gt;https://launchpad.net/~endre-karlson&lt;/a&gt;&amp;gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Add new columns to storage&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Extend Zones API to allow CRUD for Secondary Zones&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Extend Central logic to check if it’s a Master / Secondary Zone.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference internal" href="zone-import-refactor.html#zone-import-refactor"&gt;&lt;span class="std std-ref"&gt;Zone Import Refactor&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 03 Jun 2020 00:00:00 </pubDate></item><item><title>Server Pools API</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/server-pools-api.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="server-pools-api"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/server-pools-api"&gt;https://blueprints.launchpad.net/designate/+spec/server-pools-api&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;This spec outlines the API changes needed for Server Pools. It is part of a
larger group of specs describing the design of Designate Server Pools. The
main blueprint is located
&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/server-pools"&gt;here&lt;/a&gt;.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Server Pools will need to be created, read, updated and deleted. An API needs
to exist in order to carry out these operations.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;This spec defines in detail the API changes needed for Server Pools.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;section id="api-details-create-list-patch-delete-pools"&gt;
&lt;h4&gt;API Details: Create/List/Patch/Delete Pools&lt;/h4&gt;
&lt;div class="admonition tip"&gt;
&lt;p class="admonition-title"&gt;Tip&lt;/p&gt;
&lt;p&gt;These should all be restricted to admins for general usage.&lt;/p&gt;
&lt;/div&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Verb&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Resource&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;GET&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;/pools&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Returns all pools&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;GET&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;/pools/{pool_id}&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Returns a specific pool with additional details&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;POST&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;/pools&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Creates a new pool&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;PATCH&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;/pools/{pool_id}&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Updates the pool with data in the request&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;DELETE&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;/pools/{pool_id}&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Deletes the pool&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="get-v2-pools"&gt;
&lt;h4&gt;GET /v2/pools&lt;/h4&gt;
&lt;p&gt;When no id is specified, all pools are returned. No body is provided in the
request.&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;200&lt;/span&gt; &lt;span class="n"&gt;OK&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;charset&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;UTF&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;
&lt;span class="n"&gt;Location&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;pools&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"pools"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"US Pool 1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"cf1fafc0-f2f0-11e3-ac10-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s2"&gt;"self"&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"/v2/pools/cf1fafc0-f2f0-11e3-ac10-0800200c9a66"&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-09-09T19:34:21.819615"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"US Pool 2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s2"&gt;"self"&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"/v2/pools/cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-09-09T19:34:21.819615"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"/v2/pools"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-v2-pools-pool-id"&gt;
&lt;h4&gt;GET /v2/pools/{pool_id}&lt;/h4&gt;
&lt;p&gt;When an id is provided in the url, the specific pool is returned with more
detail. No body is provided in the request.&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;200&lt;/span&gt; &lt;span class="n"&gt;OK&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;charset&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;UTF&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;
&lt;span class="n"&gt;Location&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;pools&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;cf1fafc0&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;f2f0&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mf"&gt;11e3&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;ac10&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;0800200&lt;/span&gt;&lt;span class="n"&gt;c9a66&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"pool"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"US Pool 1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"cf1fafc0-f2f0-11e3-ac10-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"attributes"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"geo-ip"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"anycast"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"scope"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s2"&gt;"pool_servers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="s2"&gt;"1.2.3.4:53"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"5.4.3.2:53"&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="s2"&gt;"nameservers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns1.example.com."&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns2.example.com."&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="s2"&gt;"project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&amp;lt;uuid&amp;gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"provisioner"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"unmanaged"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-09-04T19:34:20.819723"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"/v2/pools/cf1fafc0-f2f0-11e3-ac10-0800200c9a66"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="post-v2-pools"&gt;
&lt;h4&gt;POST /v2/pools/&lt;/h4&gt;
&lt;p&gt;When a new Pool is created, the user must supply the name and scope. Initially,
only “public” scope is supported. The other values shown here are
optional. If the name is the same as an existing Pool, the return
code will be 409 Conflict.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Request&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;charset&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;UTF&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;
&lt;span class="n"&gt;Location&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;pools&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"pool"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"US Pool 3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"attributes"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"scope"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;public&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s2"&gt;"pool_servers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="s2"&gt;"10.11.12.13:53"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"13.12.11.10:53"&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="s2"&gt;"nameservers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns1.example.com."&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns2.example.com."&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Response&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;201&lt;/span&gt; &lt;span class="n"&gt;Created&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;charset&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;UTF&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;
&lt;span class="n"&gt;Location&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;pools&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"pool"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"US Pool 3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"cf1fafc0-f2f0-11e3-ac10-0800200c81a5"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"attributes"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"scope"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="s2"&gt;"pool_servers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="s2"&gt;"10.11.12.13:53"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"13.12.11.10:53"&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="s2"&gt;"nameservers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns1.example.com."&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns2.example.com."&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-09-04T19:34:20.819723"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"/v2/pools/cf1fafc0-f2f0-11e3-ac10-0800200c81a5"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="patch-v2-pools-pool-id"&gt;
&lt;h4&gt;PATCH /v2/pools/{pool_id}&lt;/h4&gt;
&lt;p&gt;To modify a Pool, a PATCH request is submitted. If it is successful, a 200 is
returned.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Request&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;charset&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;UTF&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;
&lt;span class="n"&gt;Location&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;pools&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;cf1fafc0&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;f2f0&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mf"&gt;11e3&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;ac10&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;0800200&lt;/span&gt;&lt;span class="n"&gt;c81a5&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"pool"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"pool_servers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="s2"&gt;"4.5.6.7:53"&lt;/span&gt;
        &lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Response&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="mi"&gt;200&lt;/span&gt; &lt;span class="n"&gt;OK&lt;/span&gt;
&lt;span class="n"&gt;Content&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;application&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;json&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;charset&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;UTF&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;
&lt;span class="n"&gt;Location&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;v2&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;pools&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="n"&gt;cf1fafc0&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;f2f0&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mf"&gt;11e3&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;ac10&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;0800200&lt;/span&gt;&lt;span class="n"&gt;c81a5&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s2"&gt;"pool"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"US Pool 3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"cf1fafc0-f2f0-11e3-ac10-0800200c81a5"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"attributes"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s2"&gt;"scope"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s2"&gt;"pool_servers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="s2"&gt;"10.11.12.13:53"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"13.12.11.10:53"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s2"&gt;"4.5.6.7:53"&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="s2"&gt;"nameservers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns1.example.com."&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;"priority"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"hostname"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"ns2.example.com."&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="s2"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-09-04T19:34:20.819723"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="s2"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"2014-09-10T19:33:10.819555"&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="s2"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s2"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"/v2/pools/cf1fafc0-f2f0-11e3-ac10-0800200c81a5"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="delete-v2-pools-pool-id"&gt;
&lt;h4&gt;DELETE /v2/pools/{pool_id}&lt;/h4&gt;
&lt;p&gt;When deleting a Pool, the user must supply the id in the url. The request body
and return body are empty. A 204 is returned&lt;/p&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;p&gt;HTTP/1.1 204 No Content
Content-Type: application/json; charset=UTF-8
Location: /v2/pools/cf1fafc0-f2f0-11e3-ac10-0800200c81a5&lt;/p&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;The pool calls will have to be added to central to allow the CRUD of Server
Pools.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;The pool calls will have to be added to storage. The new tables are described
in a different spec.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~betsy-luzader"&gt;https://launchpad.net/~betsy-luzader&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Create pools controller and view&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add the calls to Central&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add the calls to Storage&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Write tests&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Server Pools Storage: &lt;a class="reference external" href="https://review.openstack.org/#/c/113447/"&gt;https://review.openstack.org/#/c/113447/&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Server Pools Service: &lt;a class="reference external" href="https://review.openstack.org/#/c/113462/"&gt;https://review.openstack.org/#/c/113462/&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Server Pools MiniDNS Support: &lt;a class="reference external" href="https://review.openstack.org/#/c/112688/"&gt;https://review.openstack.org/#/c/112688/&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 03 Jun 2020 00:00:00 </pubDate></item><item><title>Designate Split View</title><link>https://specs.openstack.org/openstack/designate-specs/specs/ussuri/split-view.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="designate-split-view"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/split-view"&gt;https://blueprints.launchpad.net/designate/+spec/split-view&lt;/a&gt;
&lt;a class="reference external" href="https://bugs.launchpad.net/designate/+bug/1875939"&gt;https://bugs.launchpad.net/designate/+bug/1875939&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Split view is an important feature most DNS servers have support for
based on the need to split internal, external view of the IPs and hostnames,
most of the companies have this feature on their existing DNS structers and
adding support for it Designate will make it easier for the user to integrate
Designate into the current user systems&lt;/p&gt;
&lt;p&gt;The below links provide insight on the split view feature and use cases:
* &lt;a class="reference external" href="http://techgenix.com/you_need_to_create_a_split_dns/"&gt;http://techgenix.com/you_need_to_create_a_split_dns/&lt;/a&gt;
* &lt;a class="reference external" href="https://en.wikipedia.org/wiki/Split-horizon_DNS"&gt;https://en.wikipedia.org/wiki/Split-horizon_DNS&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;The current implementation of Designate does not support the split view, users that
want to implement this must either patch Designate code or somehow do it in the backend of
Designate (bind, powerdns, ….)&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Introduce a new type of zone (split_view) in Designate. when a zone with that type is created
Designate will do the following:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Create the same zone twice in different views (internal, external), this will require
the pool.yaml to be configured with two pools seperated with attributes internal/external
Note: the user may use view parameter in bind or define two instances of powerdns
to acheive that&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Create two TSIG keys one for each zone and attach the TSIG to the right zone&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Provide AXFR based on TSIG key so if the TSIG sent is exteranl give the external view
the user should provide a regex for external/internal view that match the IPs that
should be included in each view, so if the IP match internal regex specified by
user and the AXFR request is signed with internal TSIG the IP will be included
in zone AXFR response&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Also notify requests should be signed with the right TSIG (internal, external)
the user should provide a regex for internal/external that match the IPs that should be
Included/Excluded from each view and based on that the TSIG key can be selected&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Backend should be configured as follows:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;All AXFR request should be signed with TSIG, so the AXFR can return the right view&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Most of Designate backend agents listed in the link below
&lt;a class="reference external" href="https://docs.openstack.org/designate/pike/contributor/backends/index.html"&gt;https://docs.openstack.org/designate/pike/contributor/backends/index.html&lt;/a&gt;
have support for TSIG AXFR/split_view (initial development could be for bind, powerdns)&lt;/p&gt;
&lt;p&gt;[bind]
&lt;a class="reference external" href="https://www.slashroot.in/how-to-configure-split-horizon-dns-in-bind"&gt;https://www.slashroot.in/how-to-configure-split-horizon-dns-in-bind&lt;/a&gt;
&lt;a class="reference external" href="https://bind9.readthedocs.io/en/latest/advanced.html#instructing-the-server-to-use-a-key"&gt;https://bind9.readthedocs.io/en/latest/advanced.html#instructing-the-server-to-use-a-key&lt;/a&gt;
[powerdns]
&lt;a class="reference external" href="https://www.frank.be/implementing-bind-views-with-powerdns/"&gt;https://www.frank.be/implementing-bind-views-with-powerdns/&lt;/a&gt;
&lt;a class="reference external" href="https://doc.powerdns.com/authoritative/tsig.html#provisioning-signed-notification-and-axfr-requests"&gt;https://doc.powerdns.com/authoritative/tsig.html#provisioning-signed-notification-and-axfr-requests&lt;/a&gt;
[djbdns]
djbdns does not support TSIG based on the link below
&lt;a class="reference external" href="https://en.wikipedia.org/wiki/Djbdns"&gt;https://en.wikipedia.org/wiki/Djbdns&lt;/a&gt;
&lt;a class="reference external" href="https://www.fefe.de/djbdns/#splithorizon"&gt;https://www.fefe.de/djbdns/#splithorizon&lt;/a&gt;
[gdnsd]
gdnsd not sure if it support split view/tsig AXFR
[infoblox]
&lt;a class="reference external" href="https://docs.infoblox.com/display/NAG8/Chapter+18+DNS+Views"&gt;https://docs.infoblox.com/display/NAG8/Chapter+18+DNS+Views&lt;/a&gt;
&lt;a class="reference external" href="https://docs.infoblox.com/display/NAG8/Enabling+Zone+Transfers"&gt;https://docs.infoblox.com/display/NAG8/Enabling+Zone+Transfers&lt;/a&gt;
[knote]
&lt;a class="reference external" href="https://www.knot-dns.cz/docs/2.6/html/configuration.html"&gt;https://www.knot-dns.cz/docs/2.6/html/configuration.html&lt;/a&gt;
&lt;a class="reference external" href="https://knot-resolver.readthedocs.io/en/v2.2.0/modules.html#views-and-acls"&gt;https://knot-resolver.readthedocs.io/en/v2.2.0/modules.html#views-and-acls&lt;/a&gt;
[MSDNS]
&lt;a class="reference external" href="https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-gssa/c0c6ffdd-a094-40b1-bbb9-bc4e5a58804f"&gt;https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-gssa/c0c6ffdd-a094-40b1-bbb9-bc4e5a58804f&lt;/a&gt;
&lt;a class="reference external" href="https://docs.microsoft.com/en-us/windows-server/networking/dns/deploy/split-brain-dns-deployment"&gt;https://docs.microsoft.com/en-us/windows-server/networking/dns/deploy/split-brain-dns-deployment&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;The Designate zones table should be updated to accept the new zone type split_view
type enum(‘PRIMARY’,’SECONDARY’) to type enum(‘PRIMARY’,’SECONDARY’,’SPLIT_VIEW’)&lt;/p&gt;
&lt;/section&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;p&gt;hamza alqtaishat&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 01 Jun 2020 00:00:00 </pubDate></item><item><title>Server Pools Manager</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/server-pools-service.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="server-pools-manager"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/server-pools-service"&gt;https://blueprints.launchpad.net/designate/+spec/server-pools-service&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;This specification outlines the Pool Manager, Central, backend driver,
and storage changes needed to support the new Pool Manager service.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Coordinating DNS operations across many different backends is difficult,
especially when there is a great number of DNS servers.  A Pool Manager
service is needed to manage the changes from the Designate database to
the many DNS servers.  A Pool Manager will also track the status of those
changes.  When this specification is implemented, a Pool Manager will
be used to manage a pool with multiple DNS servers, even if those DNS
servers are of different types.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="pool-manager-changes"&gt;
&lt;h3&gt;Pool Manager Changes&lt;/h3&gt;
&lt;p&gt;A new Designate service, called designate-pool-manager, will be created.
This is the Pool Manager.  The Pool Manager will get its configuration
from the configuration file when it is instantiated.&lt;/p&gt;
&lt;p&gt;The configuration section is called &lt;strong&gt;[service:pool_manager]&lt;/strong&gt;.  The options
for this section are:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Default&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Notes&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;pool_name&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘default’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The pool name of the pool managed by this instance of the Pool Manager&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;threshold_percentage&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;100&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The percentage of servers requiring a successful update for a domain change to be considered active&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;poll_timeout&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;30&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The time to wait for a NOTIFY response from a name server&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;poll_retry_interval&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;2&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The time between retrying to send a NOTIFY request and waiting for a NOTIFY response&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;poll_max_retries&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;3&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The maximum number of times minidns will retry sending a NOTIFY request and wait for a NOTIFY response&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;periodic_sync_interval&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;120&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The time between sychronizing the servers with Storage&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;The Pool Manager will contain a map of the servers to instantiated
backend drivers.  The backend driver will not be responsible for reading
the configuration information as the Pool Manager will read the
global backend driver and server specific backend driver sections
from the configuration file and pass the backend driver configuration
to the backend driver for instantiation.  This map will be created when
the Pool Manager is instantiated.  Please refer to the Backend Driver
Changes section in the Storage Pools - Storage specification for more
information concerning the global backend driver and server specific
backend driver sections.&lt;/p&gt;
&lt;p&gt;The methods in the base class for the Pool Manager service include:&lt;/p&gt;
&lt;section id="create-domain-context-domain"&gt;
&lt;h4&gt;create_domain(context, domain)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="return-value"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;No return value.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="design-considerations"&gt;
&lt;h5&gt;Design Considerations&lt;/h5&gt;
&lt;p&gt;Loop through each server in the pool and call the backend driver to create
the domain.  For each call to the backend driver, the status is stored in the
pool_manager_status table with an action of ‘CREATE’ and a second row is
created with an action of ‘UPDATE’.  Successful creations have a status of
‘SUCCESS’ and failed creations have a status of ‘ERROR’.  The ‘UPDATE’ action
row has no initial status.  Check to see if a consensus exists using the
pool_manager_status table.  Consensus exists if the number of servers for the
domain with a successful creation exceed the &lt;em&gt;threshold_percentage&lt;/em&gt;.  If
consensus exists, the Central &lt;strong&gt;update_status&lt;/strong&gt; method is called using the
serial number used when creating the domain and a status of ‘SUCCESS’.  If
consensus does not exist, the Central &lt;strong&gt;update_status&lt;/strong&gt; method is called
using the serial number used when creating the domain and a status of ‘ERROR’.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="cast-vs-call"&gt;
&lt;h5&gt;Cast vs. Call&lt;/h5&gt;
&lt;p&gt;This is an RPC cast.  Communication about the status of the domain
creation will be handled using the Central &lt;strong&gt;update_status&lt;/strong&gt; method.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="delete-domain-context-domain"&gt;
&lt;h4&gt;delete_domain(context, domain)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id1"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;No return value.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id2"&gt;
&lt;h5&gt;Design Considerations&lt;/h5&gt;
&lt;p&gt;Loop through each server in the pool and call the backend driver to delete
the domain.  For each call to the backend driver, the status is stored in the
pool_manager_status table with an action of ‘DELETE’.  Successful deletions
have a status of ‘SUCCESS’ and failed deletions have a status of ‘ERROR’.
Check to see if a consensus exists using the pool_manager_status table.
Consensus exists if the number of servers for the domain with a successful
deletion exceed the &lt;em&gt;threshold_percentage&lt;/em&gt;.  If consensus exists, the
Central &lt;strong&gt;update_status&lt;/strong&gt; method is called using the serial number used when
deleting the domain and a status of ‘SUCCESS’.  If consensus does not exist,
the Central &lt;strong&gt;update_status&lt;/strong&gt; method is called using the serial number
used when creating the domain and a status of ‘ERROR’.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id3"&gt;
&lt;h5&gt;Cast vs. Call&lt;/h5&gt;
&lt;p&gt;This is an RPC cast.  Communication about the status of the domain
deletion will be handled using the Central &lt;strong&gt;update_status&lt;/strong&gt; method.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="update-domain-context-domain"&gt;
&lt;h4&gt;update_domain(context, domain)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id4"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;No return value.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id5"&gt;
&lt;h5&gt;Design Considerations&lt;/h5&gt;
&lt;p&gt;Loop through each server in the pool and call the minidns
&lt;strong&gt;notify_zone_changed&lt;/strong&gt; method.  Loop through each server again and call
the minidns &lt;strong&gt;poll_for_serial_number&lt;/strong&gt; method.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id6"&gt;
&lt;h5&gt;Cast vs. Call&lt;/h5&gt;
&lt;p&gt;This is an RPC cast.  Communication about the status of the domain update
will be handled using the Central &lt;strong&gt;update_status&lt;/strong&gt; method which is
called by the Pool Manager &lt;strong&gt;update_status&lt;/strong&gt; method.  The minidns
&lt;strong&gt;poll_for_serial_number&lt;/strong&gt; method invokes the Pool Manager
&lt;strong&gt;update_status&lt;/strong&gt; method when it completes.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="update-status-context-domain-name-server-status-serial-number"&gt;
&lt;h4&gt;update_status(context, domain, name_server, status, serial_number)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;name_server&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The name server for which this serial number is applicable.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;status&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The status, ‘SUCCESS’ or ‘ERROR’.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;serial_number&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The serial number received from the name server for the domain.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id7"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;No return value.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id8"&gt;
&lt;h5&gt;Design Considerations&lt;/h5&gt;
&lt;p&gt;Reads the existing serial number from the pool_manager_status table for the
server and domain.  If the new serial number &amp;gt; the existing serial number,
update the row and check to see if a consensus exists using the
pool_manager_status table.  Consensus exists if the number of servers for
the domain with a serial number &amp;gt; the existing serial number exceed the
&lt;em&gt;threshold_percentage&lt;/em&gt;.  Servers are discounted from participating in the
consensus starting with the servers with the lowest serial numbers until the
minimum number of servers needed to achieve consensus based on the
&lt;em&gt;threshold_percentage&lt;/em&gt; is realized.  If the existing serial number &amp;lt; all the
serial numbers for the remaining servers, the Central &lt;strong&gt;update_status&lt;/strong&gt; method
is called using the lowest (consensus) serial number for those remaining
servers and a status of ‘SUCCESS’.&lt;/p&gt;
&lt;p&gt;If &amp;gt; 100 - &lt;em&gt;threshold_percentage&lt;/em&gt; servers for the domain have a status of
‘ERROR’, the Central &lt;strong&gt;update_status&lt;/strong&gt; method is called using the lowest
serial number greater than the consensus serial number (calculated above) and
a status of ‘ERROR’.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id9"&gt;
&lt;h5&gt;Cast vs. Call&lt;/h5&gt;
&lt;p&gt;This is an RPC cast.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="periodic-sync"&gt;
&lt;h4&gt;periodic_sync()&lt;/h4&gt;
&lt;section id="id10"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;No return value.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id11"&gt;
&lt;h5&gt;Design Considerations&lt;/h5&gt;
&lt;p&gt;This method is a thread that is created when Pool Manager is instantiated.
The intent of this thread is to read the pool_manager_status table and
perform failed create, delete, and updates operations.  Additionally, the
thread will call the minidns &lt;strong&gt;poll_for_serial_number&lt;/strong&gt; method for each
domain and server to ensure the server is synchronized with Storage.&lt;/p&gt;
&lt;p&gt;Every &lt;em&gt;period_sync_interval&lt;/em&gt;, this thread will perform the following
operations:&lt;/p&gt;
&lt;p&gt;Read the pool_manager_status table looking for ‘CREATE’ actions that
have a status of ‘ERROR’ grouping by domains and ordering by the row
create time.  Check to see if a consensus already exists for the domain
creation.  Loop through each servers with a failed creation, using the
backend driver to attempt creation.  If consensus does not already exist,
check for consensus and call the Central &lt;strong&gt;update_status&lt;/strong&gt; if consensus
is achieved.&lt;/p&gt;
&lt;p&gt;Read the pool_manager_status table looking for ‘DELETE’ actions that
have a status of ‘ERROR’ grouping by domains and ordering by the row
create time.  Check to see if a consensus already exists for the domain
deletion.  Loop through each servers with a failed deletion, using the
backend driver to attempt deletion.  If consensus does not already exist,
check for consensus and call the Central &lt;strong&gt;update_status&lt;/strong&gt; if consensus
is achieved.&lt;/p&gt;
&lt;p&gt;For each domain in the pool, read the domain’s serial number from Storage.
Loop through each server in the pool and read the pool_manager_status
table looking for ‘UPDATE’ actions for the domain that have a serial number
&amp;lt; the domain’s serial number and call the minidns &lt;strong&gt;notify_zone_changed&lt;/strong&gt;
method.&lt;/p&gt;
&lt;p&gt;Finally, for each domain in the pool, read the domain’s serial number
from Storage.  Loop through each server in the pool and call the minidns
&lt;strong&gt;poll_for_serial_number&lt;/strong&gt; method.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;The Central service will be updated to use the Pool Manager instead of the
backend driver.  Additionally, the default_pool_name option will be removed
from the &lt;strong&gt;[service:central]&lt;/strong&gt; section of the Designate configuration.&lt;/p&gt;
&lt;p&gt;All domains will be ‘PENDING’ status initially and calls to the Central
&lt;strong&gt;update_status&lt;/strong&gt; method by the Pool Manager will change the status.&lt;/p&gt;
&lt;p&gt;When creating, updating, or deleting records, records will have the serial
number field set to the new serial number of the domain.  The task will be
‘ADD’, ‘DELETE’, or ‘UPDATE’ corresponding to the operation.  The status
will be ‘PENDING’.&lt;/p&gt;
&lt;p&gt;Valid record states are:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;task&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;status&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;‘ADD’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘PENDING’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;‘ADD’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ERROR’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;‘DELETE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘PENDING’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;‘DELETE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ERROR’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;‘UPDATE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘PENDING’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;‘UPDATE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ERROR’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;‘NONE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ACTIVE’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;‘NONE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘DELETED’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Affected code in the Central service will be updated appropriately to align
with these states.&lt;/p&gt;
&lt;p&gt;The new method needed to update the status of domains and records is:&lt;/p&gt;
&lt;section id="update-status-context-domain-status-serial-number"&gt;
&lt;h4&gt;update_status(context, domain, status, serial_number)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;status&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The status, ‘SUCCESS’ or ‘ERROR’.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;serial_number&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The consensus serial number for the domain.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id12"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;No return value.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id13"&gt;
&lt;h5&gt;Design Considerations&lt;/h5&gt;
&lt;p&gt;If the status is ‘SUCCESS’:&lt;/p&gt;
&lt;p&gt;Check the status of the domain and if it has a status of ‘PENDING’ or ‘ERROR’,
set the status to ‘ACTIVE’.&lt;/p&gt;
&lt;p&gt;Check the status of records for the domain.  If they have a task of
‘ADD’ or ‘UPDATE’ and a status of ‘PENDING’ or ‘ERROR’, set the task
to ‘NONE’ and the status to ‘ACTIVE’ if the consensus serial number &amp;gt;= serial
number field.&lt;/p&gt;
&lt;p&gt;Check the status of records for the domain.  If they have a task of
‘DELETE’ and a status of ‘PENDING’ or ‘ERROR’, set the task to ‘NONE’ and
the status to ‘DELETED’ if the consensus serial number &amp;gt;= serial number field.&lt;/p&gt;
&lt;p&gt;If the status is ‘ERROR’:&lt;/p&gt;
&lt;p&gt;Check the status of the domain and if it has a status of ‘PENDING’, set the
status to ‘ERROR’.&lt;/p&gt;
&lt;p&gt;Check the status of records for the domain.  If they have a status of
‘PENDING’, set the status to ‘ERROR’ if the consensus serial number &amp;gt;=
serial number field.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="id14"&gt;
&lt;h5&gt;Cast vs. Call&lt;/h5&gt;
&lt;p&gt;This is an RPC call.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="backend-driver-changes"&gt;
&lt;h3&gt;Backend Driver Changes&lt;/h3&gt;
&lt;p&gt;The backend driver will now be instantiated with information provided by
the Pool Manager as explained in the Pool Manager Changes section.  This is
necessary because of server specific backend driver configurations.&lt;/p&gt;
&lt;p&gt;The backend driver will continue to support the same configuration options
they currently do, only the section names will change by adding a wildcard
qualifier for the server.  For example, the backend driver section for
PowerDNS will now be &lt;strong&gt;[backend:powerdns:*]&lt;/strong&gt;.  This syntax will denote the
global configuration for the backend driver.  This is done to allow for
server specific backend driver configurations.&lt;/p&gt;
&lt;p&gt;The new server specific backend driver section in the configuration will be
&lt;strong&gt;[backend:powerdns:&amp;lt;uuid&amp;gt;]&lt;/strong&gt; where uuid is a universally unique identifier.&lt;/p&gt;
&lt;p&gt;The options for this section are:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Default&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Notes&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;host&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;None&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The host name or IP address of the DNS server&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;port&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;53&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The port of the DNS server&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;tsig_key&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;None&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The TSIG key for the DNS server&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;In addition to the above options, the server specific backend driver section
will support the same options as the backend driver global section.  If
those options are not included in the server specific backend driver section,
the server configuration will default to using the global configuration
option.  These server specific backend driver sections will support
different backends in the same pool.&lt;/p&gt;
&lt;p&gt;The server object will be implemented.  The server object encapsulates the
server specific backend driver section in the configuration.&lt;/p&gt;
&lt;p&gt;The following methods will not be used in the backend driver:&lt;/p&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;create_tsigkey(tsigkey)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;update_tsigkey(tsigkey)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;delete_tsigkey(tsigkey)&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;p&gt;This is due to the only provisioner supported initially being the ‘unmanaged’
provisioner.  Those methods will be used for future provisioners.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;A new table for the Pool Manager status will be needed.  Additionally, the
domains and records tables will be modified to support pools.  Domains
and records will be ‘PENDING’ status initially.  A new status ‘ERROR’ will
be possible for domains and records.  Finally, a record can also be
‘DELETE_PENDING’ and ‘DELETE_ERROR’.&lt;/p&gt;
&lt;section id="new-table-pool-manager-status"&gt;
&lt;h4&gt;New Table - pool_manager_status&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;CHAR(32)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;PK&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;updated_at&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DATETIME&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;UTC time of last update&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;server_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR(32)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Server ID&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;domain_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;CHAR(32)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;FK to ID on domains table&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘SUCCESS’,’ERROR’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Status&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;serial_number&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;INT(11)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Serial number at time of status&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;action&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘CREATE’,’DELETE’,’UPDATE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Action resulting in status&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="modify-table-domains"&gt;
&lt;h4&gt;Modify Table - domains&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Default&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Action&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ACTIVE’,’PENDING’,’DELETED’,’ERROR’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘PENDING’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Record status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;update&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="modify-table-records"&gt;
&lt;h4&gt;Modify Table - records&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Default&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Action&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;serial_number&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;INT(11)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;td&gt;&lt;p&gt;Used for the record status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;task&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ADD’,’DELETE’,’UPDATE’,’NONE’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ADD’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Record operation task&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘ACTIVE’,’PENDING’,’DELETED’,’ERROR’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘PENDING’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Record status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;update&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~rjrjr"&gt;https://launchpad.net/~rjrjr&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;Additional assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~darshan104"&gt;https://launchpad.net/~darshan104&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Pool Manager changes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Central changes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Backend driver changes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Storage changes&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;This specification relies on the Server Pools - Storage specification.
This specification relies on the Server Pools - MiniDNS Support specification.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 07 Jan 2019 00:00:00 </pubDate></item><item><title>Centralize Validation Logic</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/validation-cleanup.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="centralize-validation-logic"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/validation-cleanup"&gt;https://blueprints.launchpad.net/designate/+spec/validation-cleanup&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Today, validations are duplicated between the V1 and V2 APIs, and validations
will be required in additional places going forward (Inbound AXFR, DynamicDNS
etc). Centralizing these validations into the Designate Objects provides a
single re-usable home for all entry points to use.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Centralizing this logic will require a number of phases to complete:&lt;/p&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Implement an Object Registry&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement Object Validation&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement an “Adaptor” layer, replacing the V2 APIs Views&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Migrate schemas from &lt;cite&gt;designate/resources/schemas&lt;/cite&gt; into the Objects&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Update the API layer (both V1 and V2) to use the new Validations and
Adaptors&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;section id="object-registry"&gt;
&lt;h3&gt;Object Registry&lt;/h3&gt;
&lt;p&gt;The object registry will allow for looking up a reference to any
DesignateObject’s class via the class name. This will allow an object’s schema
to reference other object easily.&lt;/p&gt;
&lt;div class="admonition note"&gt;
&lt;p class="admonition-title"&gt;Note&lt;/p&gt;
&lt;p&gt;The Object Registry will &lt;strong&gt;not&lt;/strong&gt; replace the standard and existing
method of retrieving an Object class by importing it. The Registry
provides an &lt;strong&gt;alternative&lt;/strong&gt; method of obtaining a class reference
using only the class name. This is useful for scenarios where we need
to reference an Object outside of python code. For example, in a
JSON-Schema, or in JSON messages passed from service to service with
oslo.messaging.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;To implement the registry, the &lt;cite&gt;DesignateObjectMetaclass&lt;/cite&gt; class will be updated
to track a reference to each of the Object classes as they are constructed.
These references will be stored in a dictionary attached to the
&lt;cite&gt;DesignateObject&lt;/cite&gt; base class.&lt;/p&gt;
&lt;div class="admonition note"&gt;
&lt;p class="admonition-title"&gt;Note&lt;/p&gt;
&lt;p&gt;The &lt;cite&gt;DesignateObjectMetaclass&lt;/cite&gt; code is executed while the object
classes are constructed, rather than when the object instances are
created. This ensures the code is only executed once upon startup of
the Designate services.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Registry lookups will be performed via a new
&lt;cite&gt;DesignateObject.obj_cls_from_name()&lt;/cite&gt; method, which will accept a single
string argument for the Object Name.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;object&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="nd"&gt;@classmethod&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;obj_cls_from_name&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;cls&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="k"&gt;pass&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;An example usage of the registry:&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;RecordSet&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;FIELDS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s1"&gt;'id'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt;
        &lt;span class="s1"&gt;'name'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="n"&gt;RecordSet&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;DesignateObject&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;obj_cls_from_name&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'RecordSet'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;my_recordset&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;RecordSet&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;id&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'12345'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'example.org.'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="object-validation"&gt;
&lt;h3&gt;Object Validation&lt;/h3&gt;
&lt;p&gt;Object Validation rules will continue to use JSON-Schema, implemented on a
per-field level:&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;ValidatableObject&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;FIELDS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s1"&gt;'id'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'required'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;True&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'string'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'format'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'uuid'&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s1"&gt;'ttl'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'integer'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'minimum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'maximum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;100&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s1"&gt;'recursive'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'$ref'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'obj://ValidatableObject/#'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s1"&gt;'nested'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'$ref'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'obj://AnotherObject/#'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;To construct the final and complete scheme, and instanciate the schema
validator, the &lt;cite&gt;DesignateObjectMetaclass&lt;/cite&gt; class will be updated
to call a &lt;cite&gt;make_class_validator(cls)&lt;/cite&gt; method, implemented similarily to
the &lt;cite&gt;make_class_properties(cls)&lt;/cite&gt; method.&lt;/p&gt;
&lt;p&gt;This &lt;cite&gt;make_class_validator&lt;/cite&gt; method will assemble the per-field schema fragments
into a full JSON Schema, with the necessary boilerplate being generated.
Additionally, this method will construct the python-jsonschema Validator
instance and attach it to the objects class as cls._obj_validator.&lt;/p&gt;
&lt;p&gt;Finally, three new methods will be added to the base &lt;cite&gt;DesignateObject&lt;/cite&gt; class:&lt;/p&gt;
&lt;ol class="arabic"&gt;
&lt;li&gt;&lt;p&gt;A &lt;cite&gt;obj_get_schema(cls)&lt;/cite&gt; method:&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;object&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="nd"&gt;@classmethod&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;obj_get_schema&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;cls&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="sd"&gt;"""Returns the JSON Schema for this Object."""&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A &lt;cite&gt;is_valid(self)&lt;/cite&gt; method:&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;object&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;is_valid&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="sd"&gt;"""Returns True if the Object is valid."""&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A &lt;cite&gt;validate(self)&lt;/cite&gt; method:&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;object&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;validate&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="sd"&gt;"""&lt;/span&gt;
&lt;span class="sd"&gt;        Raises an InvalidObject exception if the Object is invalid&lt;/span&gt;

&lt;span class="sd"&gt;        Attached to the `errors` attribute of exception will be a&lt;/span&gt;
&lt;span class="sd"&gt;        `ValidationErrorList` object containing the details of the&lt;/span&gt;
&lt;span class="sd"&gt;        failures.&lt;/span&gt;
&lt;span class="sd"&gt;        """&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;An example usage of the validation:&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;RecordSet&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;FIELDS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s1"&gt;'id'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'required'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;True&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'string'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'format'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'uuid'&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s1"&gt;'ttl'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'integer'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'minimum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'maximum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;100&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="n"&gt;my_recordset&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;RecordSet&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;id&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'12345'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ttl&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="c1"&gt;# Returns False, as the 12345 is NOT a UUID.&lt;/span&gt;
&lt;span class="n"&gt;my_recordset&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;is_valid&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

&lt;span class="k"&gt;try&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="c1"&gt;# Raises an InvalidObject exception, as the 12345 is NOT a UUID.&lt;/span&gt;
    &lt;span class="n"&gt;my_recordset&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;validate&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;span class="k"&gt;except&lt;/span&gt; &lt;span class="n"&gt;InvalidObject&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="n"&gt;LOG&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;warning&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'Invalid Object, Errors below:'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;error&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;errors&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;LOG&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;warning&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'Error at path &lt;/span&gt;&lt;span class="si"&gt;%s&lt;/span&gt;&lt;span class="s1"&gt;, Message: &lt;/span&gt;&lt;span class="si"&gt;%s&lt;/span&gt;&lt;span class="s1"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;absolute_path&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                    &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;message&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="object-adaptors"&gt;
&lt;h3&gt;Object Adaptors&lt;/h3&gt;
&lt;p&gt;Object Adaptors will replace the current V2 API Views, allowing for a
structured way to convert from Object to V1 or V2 API formats. This will
include renaming of fields in standard output, rendered JSON Schemas,
as well as in ValidationError messages, and will support hiding fields which
should not be visible in the matching API version.&lt;/p&gt;
&lt;div class="admonition note"&gt;
&lt;p class="admonition-title"&gt;Note&lt;/p&gt;
&lt;p&gt;Below is a WIP mockup - Expect changes!&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Example usage of the Object Adaptors:&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="c1"&gt;# Standard Object Definition&lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;Domain&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DesignateObject&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;FIELDS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s1"&gt;'id'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'required'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;True&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'string'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'format'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'uuid'&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s1"&gt;'name'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'string'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'pattern'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'domainname'&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s1"&gt;'ttl'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'integer'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'minimum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'maximum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;100&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="s1"&gt;'version'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="s1"&gt;'schema'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'integer'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'minimum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="s1"&gt;'maximum'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;100&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;


&lt;span class="c1"&gt;# Define the V2 API Adaptor for the Domain Object above&lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;DomainAdaptorV2&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DesignateObjectAdaptorV2&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;obj_cls&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;Domain&lt;/span&gt;
    &lt;span class="n"&gt;obj_list_cls&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;DomainList&lt;/span&gt;

    &lt;span class="c1"&gt;# Any fields NOT specificed will not be returned by the API.&lt;/span&gt;
    &lt;span class="n"&gt;FIELDS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s1"&gt;'id'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="c1"&gt;# No V2 Specific Customization Needed&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="s1"&gt;'ttl'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="c1"&gt;# Let's rename "ttl" to "default_ttl" in V2&lt;/span&gt;
            &lt;span class="s1"&gt;'name'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'default_ttl'&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;


&lt;span class="c1"&gt;# Use the Adaptor in the API&lt;/span&gt;
&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;ZonesController&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;rest&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RestController&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;_adaptor&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;DomainAdaptorV2&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

    &lt;span class="nd"&gt;@pecan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;expose&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;template&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'json:'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;content_type&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'application/json'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="nd"&gt;@utils&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;validate_uuid&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'zone_id'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;get_one&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;zone_id&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="sd"&gt;"""Get Zone"""&lt;/span&gt;

        &lt;span class="c1"&gt;# Real life would Fetch a zone from designate-central&lt;/span&gt;
        &lt;span class="n"&gt;domain&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;Domain&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;id&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'2b9e1b86-d4f1-42d2-88ff-b888f2dd068a'&lt;/span&gt;
                        &lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'example.com.'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                        &lt;span class="n"&gt;ttl&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;_adaptor&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;render&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;single&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="kc"&gt;True&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="nd"&gt;@pecan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;expose&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;template&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'json:'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;content_type&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'application/json'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;post_all&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="sd"&gt;"""Create Zone"""&lt;/span&gt;
        &lt;span class="n"&gt;request&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;pecan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;request&lt;/span&gt;
        &lt;span class="n"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;pecan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;response&lt;/span&gt;
        &lt;span class="n"&gt;context&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;request&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'context'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;

        &lt;span class="c1"&gt;# The Adaptor class will parse the incoming JSON into an&lt;/span&gt;
        &lt;span class="c1"&gt;# approperiate Object instance, trigger validation, and raise&lt;/span&gt;
        &lt;span class="c1"&gt;# an exception if there are any failures. The&lt;/span&gt;
        &lt;span class="c1"&gt;# `FaultWrapperMiddleware` will catch and render this exception.&lt;/span&gt;
        &lt;span class="n"&gt;domain&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;_adaptor&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;parse&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;request&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;body_dict&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;single&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="kc"&gt;True&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="c1"&gt;# Create the Domain&lt;/span&gt;
        &lt;span class="n"&gt;domain&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;central_api&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;create_domain&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="c1"&gt;# Prepare the response headers and status&lt;/span&gt;
        &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status_int&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;201&lt;/span&gt;
        &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;headers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'Location'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'&amp;lt;url for new zone&amp;gt;'&lt;/span&gt;

        &lt;span class="c1"&gt;# Send the response&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;_adaptor&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;render&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Any other changes to Designate, broken down by which sub system is being
changed&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;kiall&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;p&gt;Work items are as per the Proposed change section.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;No known dependencies&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Sat, 24 Nov 2018 00:00:00 </pubDate></item><item><title>Zone Exists Event</title><link>https://specs.openstack.org/openstack/designate-specs/specs/liberty/zone-exists-event.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="zone-exists-event"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/zone-exists-event"&gt;https://blueprints.launchpad.net/designate/+spec/zone-exists-event&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Designate emits several events for use by Ceilometer for Metering &amp;amp; Billing
purposes. Currently, these events are sent for zone/rrset/etc create, update
and delete actions. As these events are emitted over RabbitMQ, we cannot
guarantee delivery. In order to ensure accurate billing for customers, we need
to provide a mechanism for identifying “lost” events. This is particularity
important for Zone create/delete events, as per-Zone/per-Timeperiod is the
most common billing unit.&lt;/p&gt;
&lt;p&gt;The accepted standard solution to the loss of create/delete events is for each
service to emit a periodic “exists” event, this allows Ceilometer to, for
example, identify that N exists events in a row were not received, surmising
that a “delete” event was missed.&lt;/p&gt;
&lt;p&gt;In other services like Nova there is a clear “owner” for each core resource
(e.g. an instance is owned by the compute node it resides on), this allows
each nova-compute instance to periodically emit a &lt;cite&gt;compute.instance.exists&lt;/cite&gt;
event for a small number of instances. Designate has no such clear owner,
and many thousands of zones may belong to a single pool (the smallest
grouping we currently have available). This poses a problem, in that emitting
100’s of thousands of events, or more, each hour may be too demanding for the
active pool manager.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;We will introduce a new service &lt;cite&gt;designate-zone-manager&lt;/cite&gt; which will handle all
periodic tasks relating to the zones it is responsible for. Initially, this
will only be the periodic &lt;cite&gt;dns.domain.exists&lt;/cite&gt; event, but over time we will add
additional tasks, for example, polling of Secondary zones at their refresh
intervals.&lt;/p&gt;
&lt;p&gt;A concept of “zone shards” will be introduced, where every zone will be
allocated to a shard based on the first three characters of the zones UUID.
This will provide for 4,096 distinct shards to be distributed over the set of
available &lt;cite&gt;designate-zone-manager&lt;/cite&gt; processes, ensuring that no single
&lt;cite&gt;designate-zone-manager&lt;/cite&gt; is responsible for more zones than it can reasonably
handle. With 5 million zones, each shard should contain approx 1.2k zones.&lt;/p&gt;
&lt;p&gt;Finally, distribution of shards to available &lt;cite&gt;designate-zone-manager&lt;/cite&gt;
processes will be handled by the &lt;a class="reference external" href="https://github.com/openstack/tooz"&gt;OpenStack Tooz&lt;/a&gt; library. Tooz provides the building
blocks required to implement a “Partitioner”, using it’s Group Membership
APIs to divvy up the available shards between active workers, including
dynamically re-allocating based on membership changes.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;A new column will be added to the domains, recordsets and records tables, this
column will be populated by the storage driver with the integer representation
of the first 3 characters of the UUID, giving a whole number with a value
between 0 and 4095. We add the shard to the RecordSets/Records tables now,
as we know it will be used in a future blueprint (ALIAS records).&lt;/p&gt;
&lt;section id="domains-table-additions"&gt;
&lt;h4&gt;Domains Table Additions&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Row&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;shard&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;int(2)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="recordsets-records-table-additions"&gt;
&lt;h4&gt;RecordSets/Records Table Additions&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Row&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;domain_shard&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;int(2)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;A new service, &lt;cite&gt;designate-zone-manager&lt;/cite&gt; will be introduced. This service will
extend the Designate base &lt;cite&gt;Service&lt;/cite&gt; class, but will not include the typical
&lt;cite&gt;RPCService&lt;/cite&gt; mixin. For this initial use case, there is no requirement for
an RPC API.&lt;/p&gt;
&lt;p&gt;This service will use the existing oslo-incubator ThreadGroup.add_timer()
methods for scheduling tasks, and the tooz library for group membership.&lt;/p&gt;
&lt;p&gt;The timer interval will be exposed as a configuration value, defaulting to
3600 seconds. The interval will be independent of any other timers introduced
into this service in the future.&lt;/p&gt;
&lt;p&gt;Group membership will be implemented as a &lt;cite&gt;Service&lt;/cite&gt; mixin, similar to
&lt;cite&gt;RPCService&lt;/cite&gt;, allowing for it’s inclusion in other services such as
&lt;cite&gt;designate-pool-manager&lt;/cite&gt;.&lt;/p&gt;
&lt;p&gt;The &lt;cite&gt;dns.domain.exists&lt;/cite&gt; event format will be identical to the domain
create/update/delete event format, with the only difference being the event
name.&lt;/p&gt;
&lt;p&gt;Finally, the list of Zones each &lt;cite&gt;designate-zone-manager&lt;/cite&gt; is responsible for
will be gathered at the start of each timer interval, in batches of a
configurable size, based on the range of shard’s allocated.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Endre Karlson&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Liberty-2&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Implement “Partitioner” based on Tooz&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement &lt;cite&gt;GroupMembership&lt;/cite&gt; mixin (Name TBD)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Create new &lt;cite&gt;designate-zone-manager&lt;/cite&gt; service&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement periodic exists event&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Requires the OpenStack Tooz library be added to our requirements&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Requires infrastructure for the OpenStack Tooz library (memcache, redis,
or zookeeper)&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Sat, 24 Nov 2018 00:00:00 </pubDate></item><item><title>Alias Records</title><link>https://specs.openstack.org/openstack/designate-specs/specs/mitaka/alias-records.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="alias-records"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/alias-records"&gt;https://blueprints.launchpad.net/designate/+spec/alias-records&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;ALIAS records (aka ANAME’s, root CNAME’s, root domain redirect, zone
apex CNAME’s) are a relatively new “addition” to DNS. These pseudo
Resource Records (RR) are used to bypass restrictions placed within
the DNS protocol that forbid the presence of a CNAME RR next to any
other RR. This prevents some modern usage of DNS, for example, many
CDNs or other static-content hosting sites like GitHub Pages will
require users to CNAME e.g. “www.example.org.” towards their frontend
load balancers. A CNAME is used to ensure the provider can easily make
infrastructure changes without requiring every customer to implement
DNS changes in-sync with their deployment schedule.&lt;/p&gt;
&lt;p&gt;As this is not a true feature within the DNS protocol, support for
ALIAS RR’s must be implemented entirely within the end users
authoritative DNS infrastructure.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;DNS RFCs do not support a CNAME record set for the root domain:&lt;/p&gt;
&lt;div class="highlight-text notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;example.com IN CNAME example.github.com
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;As a result, this capability is not widely supported by DNS backends.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Designate will expose a new “ALIAS” record set type via API; the
record set will be flattened on a periodic basis into an “A” or “AAAA”
record set for propagation to DNS backends. This solution is
backend-independent and complies with RFCs implementations.&lt;/p&gt;
&lt;section id="acceptance-criteria"&gt;
&lt;h3&gt;Acceptance Criteria&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;An end user can create an “ALIAS” record set in the API and see that
record set through all other API requests (e.g. get record sets,
export zone, import zone)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;All “ALIAS” records will be flattened to “A/AAAA” record sets for
all backends.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;An IP change to example.github.com will result in an update the IP
address of the flattened “A” or “AAAA” record sets available on the
backend.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Operators can configure a custom caching name sever to use for
resolution and flattening of ALIAS record sets.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Operators can set the polling interval for the flattening process.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="admonition note"&gt;
&lt;p class="admonition-title"&gt;Note&lt;/p&gt;
&lt;p&gt;Not recommended for use with CDN implementations.&lt;/p&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;RRSets with the “visible” value (described below) set to “mdns” will
be filtered from view within the API.&lt;/p&gt;
&lt;p&gt;Additionally, ALIAS RRSets will not be visible in the V1 API. Instead,
a dynamically generated TXT record will be included to indicate the
existence of the ALIAS record that is only editable via the V2
API.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Example ALIAS record set creation request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;POST&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/2150b1bf-dee2-4221-9d85-11f7886fb15f/recordsets&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Host&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;127.0.0.1:9001&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"This is an example ALIAS record set."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ALIAS"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3600&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="s2"&gt;"example.github.com."&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;section id="flatten-task"&gt;
&lt;h4&gt;Flatten Task&lt;/h4&gt;
&lt;p&gt;The process of “flattening” the ALIAS record can be triggered by the
user. For example, if a user starts getting error messages the
resolution isn’t working, the user can make an API request to force an
update.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Example Manual Flatten Request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;POST&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/&amp;lt;zone_id&amp;gt;/recordsets/&amp;lt;recordset_id&amp;gt;/tasks/flatten&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Host&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;127.0.0.1:9001&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;The request body should be empty. Also, it is recommended the user
configure rate limits on this endpoint accordingly. This rate limiting
is outside the scope of this spec.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="exporting"&gt;
&lt;h4&gt;Exporting&lt;/h4&gt;
&lt;p&gt;When a zone is exported as a zone file, the export should contain two
lines, the ALIAS record, commented out, and the most recent A record.&lt;/p&gt;
&lt;p&gt;For example:&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;example&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;com&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt; &lt;span class="n"&gt;IN&lt;/span&gt; &lt;span class="n"&gt;ALIAS&lt;/span&gt; &lt;span class="n"&gt;example&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;org&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;
&lt;span class="n"&gt;example&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;com&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;  &lt;span class="n"&gt;IN&lt;/span&gt;  &lt;span class="n"&gt;A&lt;/span&gt;     &lt;span class="mf"&gt;192.0.2.1&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;This allows the user to have a valid zone file to import, while
providing visibility that the A record was generated from an ALIAS
record.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;Central’s create and update RecordSet methods will be updated to call
a new RPC method implemented on the Zone Manager service to trigger
immediate ALIAS flattening when ALIAS RRSets are created /
updated. If the resolution fails, the record will be placed in the
&lt;cite&gt;ERROR&lt;/cite&gt; status.&lt;/p&gt;
&lt;p&gt;Central’s delete RecordSet method will be updated to remove the
associated flattened &lt;cite&gt;A&lt;/cite&gt; and &lt;cite&gt;AAAA&lt;/cite&gt; RecordSets - the mechanism for
identifying these related RRSets is detailed in Zone Manager Changes.&lt;/p&gt;
&lt;p&gt;Additionally, ALIAS RRSets will be treated somewhat similarly to
CNAMEs. It will be invalid to place an ALIAS RRSet next to an A or
AAAA RecordSet. The recordset placement validation will be updated to
handle this case.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="minidns-changes"&gt;
&lt;h3&gt;MiniDNS Changes&lt;/h3&gt;
&lt;p&gt;MiniDNS will be updated to display RRSets with the “visible” field
(described below) set to ‘mdns’ or ‘all’, ensuring no attempt is made
to include non-RFC compliant RRSets within &lt;cite&gt;AXFRs&lt;/cite&gt;.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="zone-manager-changes"&gt;
&lt;h3&gt;Zone Manager Changes&lt;/h3&gt;
&lt;p&gt;First, for each zone it manages, &lt;cite&gt;designate-zone-manager&lt;/cite&gt; service will
find any ALIAS recordsets associated with the zone. The zone manager
will then issue a successful A/AAAA DNS query to get the IP
addresses associated with the ALIAS target. Designate’s database
will be updated to the “real” values, incrementing the SOA serial to
trigger an AXFR towards the public facing nameservers.&lt;/p&gt;
&lt;p&gt;If this query fails and the ALIAS target can’t be resolved, the
A/AAAA records will not be updated and the ALIAS RR will be put in
STALE status.&lt;/p&gt;
&lt;p&gt;The interval at which ALIAS records are flattened will be
configurable, defaulting to 1800 seconds (30 minutes).&lt;/p&gt;
&lt;p&gt;Finally, a new RPC method will be implemented to trigger immediate
ALIAS flattening for a specific Zone, allowing for newly created ALIAS
RR’s to be usable before the first periodic interval is hit. This RPC
method will also be utilized by the ALIAS RRset flattening task
endpoint.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;section id="recordsets-update-column-type"&gt;
&lt;h4&gt;Recordsets: update column “type”&lt;/h4&gt;
&lt;p&gt;Add “ALIAS” to “type”.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="recordsets-new-column"&gt;
&lt;h4&gt;Recordsets: New Column&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;tbody&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Field&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Null&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Key&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Default&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Extra&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;visible&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;enum(‘all’, ‘api’, ‘mdns’)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;NO&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;MUL&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘all’&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="sample-data"&gt;
&lt;h3&gt;Sample data&lt;/h3&gt;
&lt;p&gt;For the example scenario described above, corresponding database values are the
following (columns omitted for brevity):&lt;/p&gt;
&lt;section id="recordsets-table"&gt;
&lt;h4&gt;Recordsets Table&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;tbody&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;domain_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;name&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;tenant_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;visible&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;1230&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;768&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;example.github.com.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;391&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ALIAS&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘api’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;0100&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;768&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;example.org.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;391&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘mdns’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="records-table"&gt;
&lt;h4&gt;Records Table&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;tbody&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;recordset_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;data&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;managed&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;managed_resource_type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;managed_resource_id&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;3211&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;1230&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;example.org.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;0&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;NULL&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;NULL&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;3212&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;0100&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;192.168.1.10&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;1&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ALIAS&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;3211&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;Some DNS backends support flattening processes (e.g. PowerDNS). An
alternative implementation is to create a new record set type called
“ALIAS” that integrates with each respective backend’s implementation.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Assignee(s)&lt;/strong&gt;&lt;/p&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Eric Larson &amp;lt;&lt;a class="reference external" href="mailto:eric.larson%40rackspace.com"&gt;eric&lt;span&gt;.&lt;/span&gt;larson&lt;span&gt;@&lt;/span&gt;rackspace&lt;span&gt;.&lt;/span&gt;com&lt;/a&gt;&amp;gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;&lt;strong&gt;Milestones&lt;/strong&gt;&lt;/p&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Mitaka-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;&lt;strong&gt;Work Items&lt;/strong&gt;&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Implement support for hiding RRSets in the API and MiniDNS&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement the periodic ALIAS flattening within the &lt;cite&gt;designate-zone-manager&lt;/cite&gt;
service&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Update Central’s CUD RecordSet methods for ALIAS support&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 13 Nov 2018 00:00:00 </pubDate></item><item><title>Integrate yadifa dns backend to designate</title><link>https://specs.openstack.org/openstack/designate-specs/specs/ocata/yadifa-backend.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="integrate-yadifa-dns-backend-to-designate"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/yadifa-dns-backend"&gt;https://blueprints.launchpad.net/designate/+spec/yadifa-dns-backend&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;There are users or env that may want to use YADIFA as backend which is not supported by designate
as of now.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;YADIFA is a lightweight authoritative Name Server with DNSSEC capabilities.
It has a simple configuration syntax and can handle more queries per second while
maintaining one of the lowest memory footprints in the industry.
YADIFA also has one of the fastest zone file load times ever recorded on a name server.&lt;/p&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Functionality:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;. authoritative name server
. DNS UPDATE
. DNS NOTIFY
. AXFR
. IXFR
. full featured client (yadifa), which can be used to control the server
. key management, including a tool to generate dnssec keys
. multi-master support
. support for other network models
. detect and configure hyperthreading
. support for openssl 1.1.0 API&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;Use Cases:&lt;/dt&gt;&lt;dd&gt;&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Alternative for BIND and NSD for public TLD slave.
- Clean Implementation
- High query rate and portable.
- RFC compliant:
-  . Authoritative
-  . DNSSEC support
-  . AXFR/IXFR (master and slave)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Dynamic updates
- Dynamic updated(including continuous signing)
- Generic, extensible storage backend.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Zone management
- Dynamic zone provisioning.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Recursive Nameserver
- Recursion
- Validation&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Add driver ‘impl_yadifa’ to designate.backends using v2 api .
Authentication is done via the keystoneclient auth / session using the provided
credentials in the backend options.&lt;/p&gt;
&lt;p&gt;Add designate devstack plugin ‘backend-yadifa’ to configure yadifa as backend
while installing designate using devstack. Also add docs related to installation
and configuration of yadifa dns backend.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h3&gt;Implementation&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Sonu kumar &lt;a class="reference external" href="https://launchpad.net/~sonu-bhumca11"&gt;https://launchpad.net/~sonu-bhumca11&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;IRC Nick Name:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;sonuk&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;p&gt;Target Milestone for completion:&lt;/p&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;p&gt;. Create YADIFA backend
. Create YADIFA backend docs
. Create Devstack backend plugin for YADIFA
. Create experimental gate job&lt;/p&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Thu, 22 Dec 2016 00:00:00 </pubDate></item><item><title>Naming Conventions for Records</title><link>https://specs.openstack.org/openstack/designate-specs/specs/newton/naming-convention-for-records.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="naming-conventions-for-records"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/different-format-for-ipv4-and-ipv6"&gt;https://blueprints.launchpad.net/designate/+spec/different-format-for-ipv4-and-ipv6&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Naming Conventions for records
Right now we have a single format to define FQDN for records created
through designate sink.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;At present there is only one format we can define for both IPv4 and IPv6 ips.
If a user want to have different naming convention for records created through
Sink service, we do not have a way to do that since there is only one option
in designate.conf where we define the FQDN format.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;In designate.conf we should give an option under the Sink configuration where
we can define two different formats for IPv4 and IPv6. Similarly we need to make
appropriate changes in sink code under designate/notification_handler/ for
base.py, nova.py and neutron.py&lt;/p&gt;
&lt;p&gt;The  new format options in designate.conf would be “formatv4” and “formatv6”.&lt;/p&gt;
&lt;p&gt;To help users from older versions, we will still support “format” which will
work for IPv4 addresses. “format” or “formatv4” can be used interchangebaly
but if both of them are defined then “formatv4” will be accepted along with
a Warning message.&lt;/p&gt;
&lt;section id="sink-changes"&gt;
&lt;h3&gt;SINK Changes&lt;/h3&gt;
&lt;p&gt;Base.py, nova.py and neutron.py needs to be changed to get the format type from
designate.conf. The new formats that we need to get are formatv4 and formatv6 which will
now be implemented in designate.conf.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kumar Acharya&amp;lt;ma501v&amp;gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Mitaka-3&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;p&gt;Define the format for IPV4 and IPv6 FQDN and Implement it in designate.conf
Code changes required in designate&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;formatv4 and formatv6 should be implemented in designate.conf as new format types&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 30 May 2016 00:00:00 </pubDate></item><item><title>Get the Zone transfer accepts list</title><link>https://specs.openstack.org/openstack/designate-specs/specs/newton/accepted-zone-transfer.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="get-the-zone-transfer-accepts-list"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/zone-transfer-accept-list"&gt;https://blueprints.launchpad.net/designate/+spec/zone-transfer-accept-list&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Currently listing of all the accepted zone transfer is not supported by the designate API.&lt;/p&gt;
&lt;p&gt;This bp adds the support request that will enable users to view the list of all the accepted zone
transfers.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;A Zone Transfer is the term used to refer to the transferring of ownership of a zone from one tenant
say A over to another tenant B.&lt;/p&gt;
&lt;p&gt;The /zones/tasks/transfer_accepts API provides a way to list all the zone transfer accepts that will
enable users to view all the accepted zone ownership transfers.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;Expose the list of accepted zones transfer requests in the v2
API as “/zones/tasks/transfer_accepts”.&lt;/p&gt;
&lt;section id="get-v2-zones-tasks-transfer-accepts"&gt;
&lt;h4&gt;GET /v2/zones/tasks/transfer_accepts&lt;/h4&gt;
&lt;p&gt;This generates the list of accepted zone transfer requests&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Example Request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt;  &lt;span class="nn"&gt;/v2/zones/tasks/transfer_accepts&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Host&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;127.0.0.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Example Response:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;200&lt;/span&gt; &lt;span class="ne"&gt;OK&lt;/span&gt;
&lt;span class="na"&gt;Content-Length&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;649&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json; charset=UTF-8&lt;/span&gt;

&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;           &lt;/span&gt;&lt;span class="nt"&gt;"transfer_accepts"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;               &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"COMPLETE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"417fb114-df97-46e5-ba34-6f5cee925e49"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;                       &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/zones/tasks/transfer_accepts/bf92e7c8-8e21-40c7-8076-8285b035b1ad"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                       &lt;/span&gt;&lt;span class="nt"&gt;"zone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/zones/417fb114-df97-46e5-ba34-6f5cee925e49"&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2016-02-04T04:01:18.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2016-02-04T04:01:18.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"key"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"0469230b787b4154922c2a4a4b5fbcaa"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"bf92e7c8-8e21-40c7-8076-8285b035b1ad"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                  &lt;/span&gt;&lt;span class="nt"&gt;"zone_transfer_request_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"17bf5ba6-053f-4f1e-87c8-a2f8c3585d8f"&lt;/span&gt;
&lt;span class="w"&gt;               &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;           &lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="w"&gt;           &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;               &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/zones/tasks/transfer_accepts"&lt;/span&gt;
&lt;span class="w"&gt;           &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;           &lt;/span&gt;&lt;span class="nt"&gt;"metadata"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"total_count"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="w"&gt;           &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Cli Impact:&lt;/p&gt;
&lt;p&gt;A new cli will also  be added that will enable users to list the status of
all the accepted zone transfer i.e.&lt;/p&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;dl class="simple"&gt;
&lt;dt&gt;openstack zone transfer accept list [-h]&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;[-f {csv,json,table,value,yaml}]
[-c COLUMN]
[–max-width &amp;lt;integer&amp;gt;]
[–noindent]
[–quote {all,minimal,none,nonnumeric}]&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;List accepted zone transfers&lt;/p&gt;
&lt;dl&gt;
&lt;dt&gt;optional arguments:&lt;/dt&gt;&lt;dd&gt;&lt;dl class="option-list"&gt;
&lt;dt&gt;&lt;kbd&gt;&lt;span class="option"&gt;-h&lt;/span&gt;, &lt;span class="option"&gt;--help&lt;/span&gt;&lt;/kbd&gt;&lt;/dt&gt;
&lt;dd&gt;&lt;p&gt;show this help message and exit&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/dd&gt;
&lt;dt&gt;output formatters:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;output formatter options&lt;/p&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;-f {csv,json,table,value,yaml}, –format {csv,json,table,value,yaml}&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;the output format, defaults to table&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;dl class="option-list"&gt;
&lt;dt&gt;&lt;kbd&gt;&lt;span class="option"&gt;-c &lt;var&gt;COLUMN&lt;/var&gt;&lt;/span&gt;, &lt;span class="option"&gt;--column &lt;var&gt;COLUMN&lt;/var&gt;&lt;/span&gt;&lt;/kbd&gt;&lt;/dt&gt;
&lt;dd&gt;&lt;p&gt;specify the column(s) to include, can be repeated&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/dd&gt;
&lt;dt&gt;table formatter:&lt;/dt&gt;&lt;dd&gt;&lt;dl class="option-list"&gt;
&lt;dt&gt;&lt;kbd&gt;&lt;span class="option"&gt;--max-width &lt;var&gt;&amp;lt;integer&amp;gt;&lt;/var&gt;&lt;/span&gt;&lt;/kbd&gt;&lt;/dt&gt;
&lt;dd&gt;&lt;p&gt;Maximum display width, 0 to disable&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/dd&gt;
&lt;dt&gt;json formatter:&lt;/dt&gt;&lt;dd&gt;&lt;dl class="option-list"&gt;
&lt;dt&gt;&lt;kbd&gt;&lt;span class="option"&gt;--noindent&lt;/span&gt;&lt;/kbd&gt;&lt;/dt&gt;
&lt;dd&gt;&lt;p&gt;whether to disable indenting the JSON&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/dd&gt;
&lt;dt&gt;CSV Formatter:&lt;/dt&gt;&lt;dd&gt;&lt;dl class="simple"&gt;
&lt;dt&gt;–quote {all,minimal,none,nonnumeric}&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;when to include quotes, defaults to nonnumeric&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Sonu kumar &lt;a class="reference external" href="https://launchpad.net/~sonu-bhumca11"&gt;https://launchpad.net/~sonu-bhumca11&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;IRC Nick Name:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;sonuk&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Newton&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Add API changes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement CLI changes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add the documentation for the same&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Reference:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://bugs.launchpad.net/python-designateclient/+bug/1499539"&gt;https://bugs.launchpad.net/python-designateclient/+bug/1499539&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 24 May 2016 00:00:00 </pubDate></item><item><title>Expose recordsets endpoint</title><link>https://specs.openstack.org/openstack/designate-specs/specs/newton/expose-recordsets-api.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="expose-recordsets-endpoint"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/expose-recordsets-api"&gt;https://blueprints.launchpad.net/designate/+spec/expose-recordsets-api&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Currently the &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;/recordsets&lt;/span&gt;&lt;/code&gt; endpoint is a sub-resource of &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;/zones&lt;/span&gt;&lt;/code&gt;. But there is a need
to list all the records for a tenant in a single API call, so that doing filtering across
all the records under a tenant will be much easier.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Designate will have a new API endpoint &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;/v2/recordsets&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;A single recordset can be retrieved via a GET call to &lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;/v2/recordsets/{recordset_id}&lt;/span&gt;&lt;/code&gt;,
which reponds a 301 and redirects to the canonical location
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;/v2/zones/{zone_id}/recordsets/{recordset_id}&lt;/span&gt;&lt;/code&gt;. The “self” link in the response body
points to that location as well.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;All recordsets across all the zones owned by a tenant can be listed via a GET call to
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;/v2/recordsets&lt;/span&gt;&lt;/code&gt;, response will be paginated in this case if necessary.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Filtering on all recordsets under a tenant will be supported, for example
&lt;code class="docutils literal notranslate"&gt;&lt;span class="pre"&gt;/v2/recordsets?name=foo&lt;/span&gt;&lt;/code&gt;.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;API changes will be mainly about exposing the new API endpoint in controllers.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Example single recordset retrieval request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/recordsets/f7b10e9b-0cae-4a91-b162-562bc6096648&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Host&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;127.0.0.1:9001&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"This is an example recordset."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/2150b1bf-dee2-4221-9d85-11f7886fb15f/recordsets/f7b10e9b-0cae-4a91-b162-562bc6096648"&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="s2"&gt;"10.1.0.2"&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3600&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"f7b10e9b-0cae-4a91-b162-562bc6096648"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"www.example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2150b1bf-dee2-4221-9d85-11f7886fb15f"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"zone_name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-10-24T19:59:44.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"A"&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Example all recordset of a tenant retrieval request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/recordsets&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Host&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;127.0.0.1:9001&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"recordsets"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/2150b1bf-dee2-4221-9d85-11f7886fb15f/recordsets/65ee6b49-bb4c-4e52-9799-31330c94161f"&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="s2"&gt;"ns1.devstack.org."&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"action"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NONE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"65ee6b49-bb4c-4e52-9799-31330c94161f"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2150b1bf-dee2-4221-9d85-11f7886fb15f"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-10-24T19:59:11.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NS"&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/zones/2150b1bf-dee2-4221-9d85-11f7886fb15f/recordsets/14500cf9-bdff-48f6-b06b-5fc7491ffd9e"&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-10-24T19:59:46.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="s2"&gt;"ns1.devstack.org. jli.ex.com. 1458666091 3502 600 86400 3600"&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"action"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NONE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"14500cf9-bdff-48f6-b06b-5fc7491ffd9e"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2150b1bf-dee2-4221-9d85-11f7886fb15f"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"example.org."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-10-24T19:59:12.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"SOA"&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"jjli.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"12caacfd-f0fc-4bcb-aa24-c42769897822"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"SOA"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"jjli.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"action"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NONE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/zones/b8d7eaf1-e5c7-4b15-be6e-4b2809f47ec3/recordsets/12caacfd-f0fc-4bcb-aa24-c42769897822"&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2016-03-22T16:12:35.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2016-03-22T17:01:31.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="s2"&gt;"ns1.devstack.org. jli.ex.com. 1458666091 3502 600 86400 3600"&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"b8d7eaf1-e5c7-4b15-be6e-4b2809f47ec3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"jjli.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"f39c51d1-ec2c-48a8-b9f7-877d56b7b82a"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NS"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"jjli.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"action"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NONE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/zones/b8d7eaf1-e5c7-4b15-be6e-4b2809f47ec3/recordsets/f39c51d1-ec2c-48a8-b9f7-877d56b7b82a"&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2016-03-22T16:12:35.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;              &lt;/span&gt;&lt;span class="s2"&gt;"ns1.devstack.org."&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"b8d7eaf1-e5c7-4b15-be6e-4b2809f47ec3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="nt"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="w"&gt;       &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"metadata"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"total_count"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://127.0.0.1:9001/v2/recordsets"&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Example recordset filtering request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/recordsets?data=192.168*&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Host&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;127.0.0.1:9001&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"metadata"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"total_count"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/recordsets?data=192.168%2A"&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"recordsets"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ohoh.uyudbbgxdf.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"a48588c5-5093-4585-b0fc-3e399d169c01"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"A"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"zone_name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"uyudbbgxdf.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"action"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NONE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/zones/601a25f0-5c4d-4058-8d9c-e6a78f5ffbb8/recordsets/a48588c5-5093-4585-b0fc-3e399d169c01"&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2016-04-04T20:11:08.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="s2"&gt;"192.168.0.1"&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"601a25f0-5c4d-4058-8d9c-e6a78f5ffbb8"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"jli-1.uyudbbgxdf.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"f2c7a0f6-8ec7-4d14-b8ec-2a55a8129160"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"A"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"zone_name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"uyudbbgxdf.com."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"action"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"NONE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"ttl"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ACTIVE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:9001/v2/zones/601a25f0-5c4d-4058-8d9c-e6a78f5ffbb8/recordsets/f2c7a0f6-8ec7-4d14-b8ec-2a55a8129160"&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2016-04-04T22:21:03.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"updated_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"records"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="s2"&gt;"192.168.6.6"&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"601a25f0-5c4d-4058-8d9c-e6a78f5ffbb8"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;      &lt;/span&gt;&lt;span class="nt"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;Central changes will include changing functions for finding recordsets from storage
in central.service to support corresponding calls from api layer.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;Corresponding changes to support the API change.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;p&gt;newton-1&lt;/p&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Make code changes to api, central and storage&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add unit and functional tests.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Fri, 18 Mar 2016 00:00:00 </pubDate></item><item><title>Deleted domains purging</title><link>https://specs.openstack.org/openstack/designate-specs/specs/liberty/deleted-domains-purging.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="deleted-domains-purging"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/deleted-domains-purging"&gt;https://blueprints.launchpad.net/designate/+spec/deleted-domains-purging&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Implementation of a mechanism to routinely purge deleted domains from the
database.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Once deleted, domains are not removed immediately from the database, mostly for
billing reasons. They are flagged as deleted in the “deleted” database column
and the “deleted_at” column is populated with a timestamp.&lt;/p&gt;
&lt;p&gt;Currently, deleted domains are purged manually by running SQL queries against
the database.
The purging process impacts the database performance and requires manual
intervention.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;This change is to implement an automated purging mechanism for deleted domains.&lt;/p&gt;
&lt;p&gt;It also provides “purge_domain” and “purge_domains” calls to purge domains using an
arbitrary criterion.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;Central API bumps to version 5.3 with the addition of the “purge_domains” call.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="zone-manager-changes"&gt;
&lt;h3&gt;Zone Manager Changes&lt;/h3&gt;
&lt;p&gt;Implement purging as a periodic task in Zone Manager using a “domain_purge”
plugin. The task will select a group of domains and send a RPC call to Central.
Central will run a query against the database to purge any deleted domain if
needed and log the number of purged domains.&lt;/p&gt;
&lt;p&gt;Configuration parameters:&lt;/p&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Purging run frequency.&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Default: hourly. Users might want to run it frequently to minimize the cycle duration.&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;Per-cycle purging limit.&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Default: 100.&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;Time threshold.&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Default: 7 days.&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;Configuration example:&lt;/p&gt;
&lt;div class="highlight-cfg notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="c1"&gt;# Deleted domains purging&lt;/span&gt;
&lt;span class="c1"&gt;#------------------------&lt;/span&gt;
&lt;span class="k"&gt;[zone_manager:domain_purge]&lt;/span&gt;
&lt;span class="c1"&gt;# How frequently to purge deleted domains, in seconds&lt;/span&gt;
&lt;span class="c1"&gt;#run_interval = 3600  # 1h&lt;/span&gt;
&lt;span class="c1"&gt;# How many deleted domains to be purged on each run&lt;/span&gt;
&lt;span class="c1"&gt;#limit = 100&lt;/span&gt;
&lt;span class="c1"&gt;# How old deleted domains should be to be purged, in seconds (deleted_at column)&lt;/span&gt;
&lt;span class="c1"&gt;#time_threshold = 604800  # 7 days&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;Implement purge_domains() method.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;Implement purge_domain(), purge_domains() method.&lt;/p&gt;
&lt;p&gt;Update the _delete() method to allow forced hard delete.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Add a new task to setup.cfg and a new purge_domains policy item to policy.json&lt;/p&gt;
&lt;p&gt;Add some test utility functions.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;No change: keeping the current manual process in place.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Deleting+purging the domains immediately.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Purging the domains on a record creation/deletion event.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Purging deleted domains with a single SQL query.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="further-improvements"&gt;
&lt;h3&gt;Further improvements&lt;/h3&gt;
&lt;p&gt;Domains for purging are queried with a column comparison “deleted_at &amp;gt; $date”&lt;/p&gt;
&lt;p&gt;Query performance can be improved by indexing the “deleted_at” column as a
B-Tree (supported by InnoDB and MyISAM):
&lt;a class="reference external" href="https://dev.mysql.com/doc/refman/5.0/en/index-btree-hash.html"&gt;https://dev.mysql.com/doc/refman/5.0/en/index-btree-hash.html&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~federico-ceratto"&gt;https://launchpad.net/~federico-ceratto&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Liberty-3&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Implement purging&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Update documentation&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement benchmarks&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;TODO&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 17 Nov 2015 00:00:00 </pubDate></item><item><title>Bulk zone update throttling</title><link>https://specs.openstack.org/openstack/designate-specs/specs/mitaka/notify-throttling.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="bulk-zone-update-throttling"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/notify-throttling"&gt;https://blueprints.launchpad.net/designate/+spec/notify-throttling&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Implement a mechanism to throttle the delivery of NOTIFY transactions when
a large number of zones are updated at the same time.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;If a large number of zones are updated in a short time this will generate a
consequently large amount NOTIFY transaction to be sent to the nameservers
with no delay leading to a burst of incoming AXFR requests.
This might impact on bottlenecks in MiniDNS and the storage layer in terms of
CPU, I/O or network bandwidth.&lt;/p&gt;
&lt;p&gt;A typical trigger is the update of an NS record in a Pool containing many zones.&lt;/p&gt;
&lt;p&gt;The autonomous refreshing of zones performed by resolvers can also trigger a
similar burst of AXFR. This can happen on recently started resolvers, where the
refresh timers can share the same values across many zones.&lt;/p&gt;
&lt;p&gt;Related to bug &lt;a class="reference external" href="https://bugs.launchpad.net/designate/+bug/1498462"&gt;https://bugs.launchpad.net/designate/+bug/1498462&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Implement a mechanism for enqueuing and delayed delivery of notify transactions
at a configurable throttle speed.&lt;/p&gt;
&lt;p&gt;Also, implement staggering of zone refresh requests by randomizing the refresh
interval.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;Expose the count of zones flagged for delayed notify in the Admin
API as “/reports/counts/zones_pending_notify”.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;Implement support for a new database column “pending_notify” and set it to
True every time a Pool NS record is updated.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;Add an new boolean database column “pending_notify” on Zones.
Implement a migration script to add the column to existing databases,
defaulting to False. In future, the column might default to True.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Implement a Task in Zone Manager to periodically fetch a set of zones that need
to receive a Notify starting with the oldest in term of last update time.
The task frequency and the maximum set size can be configured to throttle the
amount of outgoing Notify.
Zone Manager will reset the “pending_notify” flag once done.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;p&gt;The throttling queue is implemented as a new database column containing a
boolean flag. See Central Changes and Storage Changes.&lt;/p&gt;
&lt;p&gt;Also, new zones will be created with an uniformly random refresh time between a minimum and a maximum value.&lt;/p&gt;
&lt;section id="design-considerations"&gt;
&lt;h3&gt;Design considerations&lt;/h3&gt;
&lt;p&gt;The throttling queue could be implemented outside of the database:
- No need to create an extra database column
- No increased database I/O&lt;/p&gt;
&lt;p&gt;We propose using the database for the following reasons:
- Zone Manager is the best candidate to handle the delayed Notify. Currently there are no ways for Central to send a list of Zones to Zone Manager other than through the database
- The queue can support delayed Notify for changes other than Pool NS record updates
- Ability to monitor the queue size and ETA to inform the user and for debugging
- A persistent queue can survive Zone Manager unhandled exceptions or restarts
- The increased database load is negligible compared to the existing traffic&lt;/p&gt;
&lt;/section&gt;
&lt;section id="risk-analysis"&gt;
&lt;h3&gt;Risk analysis&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Zone Manager fails to run the Notify delivery task. The nameservers will eventually refresh the zone anyways. Impact: slow update propagation. Mitigation: expose the notification queue length to the user through Admin API and by logging.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A big notification queue takes a considerable time to be handled. Impact: potentially prevents more urgent changes to be delivered quickly. Mitigation: encourage users to configure the throttling parameters; Provide sensible default values. Implementing a concept of notification priority seems unnecessary.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Federico Ceratto &lt;a class="reference external" href="https://launchpad.net/~federico-ceratto"&gt;https://launchpad.net/~federico-ceratto&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Liberty-3&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Implement refresh time staggering&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement Notify throttling&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add throttle parameters to configuration files&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Document throttling mechanism&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Write unit and functional tests&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Test throttling and staggering on devstack&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 17 Nov 2015 00:00:00 </pubDate></item><item><title>Designate to Designate driver</title><link>https://specs.openstack.org/openstack/designate-specs/specs/liberty/designate-driver.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="designate-to-designate-driver"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/d2d-driver"&gt;https://blueprints.launchpad.net/designate/+spec/d2d-driver&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Add a driver that uses a Designate service and SECONDARY zones like we do
with Dyn / Akamai.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;We want to be able to use a instance of a Designate service to act as the
target for our zones.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Create a driver that utilizes the SECONDARY zones feature of Designate.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Add driver ‘designate’ to designate.backends using v2 api and secondary zones.
Authentication is done via the keystoneclient auth / session using the
provided credentials in the backend options.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;endre-karlson &amp;lt;endre.karlson at hp dot com&amp;gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Liberty-3&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Create designate.backend.impl_designate with associated unit tests and
devstack support&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 17 Aug 2015 00:00:00 </pubDate></item><item><title>Hook Points API</title><link>https://specs.openstack.org/openstack/designate-specs/specs/liberty/hook-point-api.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="hook-points-api"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/hook-point-api"&gt;Hook Point API Blueprint&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Designate, by design, is required to interface with legacy DNS
applications. Organizations will typically have other systems that
must interface with DNS and vice versa. The hook points API provides a
generic way to add organization specific code that adds no overhead in
the default use case and does not allow changes to the underlying APIs
when code is hooked in to a method or function call.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Currently, in order to support organization specific functionality, it
is required to either:&lt;/p&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Maintain a fork of the Designate code base&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Monkey patch the code via a module&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Treat designate as a black box and use HTTP level tools to add org
specific code.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;p&gt;While maintaining a fork can be a reasonable solution, if there are
large changes, it can be very difficult to merge upstream
changes. Monkey patching forces the same level of knowledge regarding
the code base, yet it is tricky to get right as small code changes can
silently fail due to import changes. Lastly, treating Designate as a
black box will often require org specific code to reimplement aspects
of Designate due to limited level of granularity.&lt;/p&gt;
&lt;p&gt;The Hook Points API provides a practical supported means of injecting
code, while avoiding the pitfalls mentioned above.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;The Hook Points API provides a decorator to define a function or
method as a hook point.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nd"&gt;@hookpoints&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook_point&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'pool_manager_create_domain'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;create_domain&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="o"&gt;...&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;In the above case the hook point is a &lt;strong&gt;named&lt;/strong&gt; hook point called
&lt;cite&gt;pool_manager_create_domain&lt;/cite&gt;. When a name is not provided, the hook
point uses the path of the module and method.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nd"&gt;@hookpoints&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook_point&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;create_domain&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
     &lt;span class="o"&gt;...&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;The name is the combination of function’s module and name.&lt;/p&gt;
&lt;div class="highlight-default notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="s1"&gt;'&lt;/span&gt;&lt;span class="si"&gt;%s&lt;/span&gt;&lt;span class="s1"&gt;.&lt;/span&gt;&lt;span class="si"&gt;%s&lt;/span&gt;&lt;span class="s1"&gt;'&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;func&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="vm"&gt;__module__&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;func&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="vm"&gt;__name__&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;If no hook point is defined, the original function is returned
as-is.&lt;/p&gt;
&lt;p&gt;In order to define a hook point, a package must be installed
that provides a &lt;cite&gt;designate.hook_point&lt;/cite&gt; entry point.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;setuptools&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;setup&lt;/span&gt;


&lt;span class="n"&gt;setup&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'raxdns'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;entry_points&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="s1"&gt;'designate.hook_point'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="s1"&gt;'pool_manager_create_domain = raxdns.hooks.pool_manager:create_domain'&lt;/span&gt;
        &lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;When the package is installed, the hook point is then &lt;strong&gt;active&lt;/strong&gt;
meaning that it will be called when the target is called. It may be
disabled via the configuration if necessary.&lt;/p&gt;
&lt;section id="hook-point-implementation"&gt;
&lt;h3&gt;Hook Point Implementation&lt;/h3&gt;
&lt;p&gt;A hook point, as it will be applied as a decorator, is an object that
implements a &lt;cite&gt;__call__&lt;/cite&gt; method that accepts a single function as the
argument and returns an appropriate function as the result. It is up
to the implementor to ensure the hook point correctly implements the
API of the hook target.&lt;/p&gt;
&lt;p&gt;For convenience, there is &lt;cite&gt;BaseHook&lt;/cite&gt; that can be used to reuse common
patterns.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;BaseHook&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;object&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;

    &lt;span class="n"&gt;OPTS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
        &lt;span class="n"&gt;cfg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;BoolOpt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'disabled'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;default&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="kc"&gt;False&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;]&lt;/span&gt;

    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="fm"&gt;__init__&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;group&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;group&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;group&lt;/span&gt;

    &lt;span class="nd"&gt;@property&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;disabled&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;cfg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CONF&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;group&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'disabled'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kc"&gt;False&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;wrapper&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="n"&gt;kw&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook_target&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="n"&gt;kw&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="fm"&gt;__call__&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="c1"&gt;# Save our hook target as an attribute for our wrapper method&lt;/span&gt;
        &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook_target&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt;

        &lt;span class="nd"&gt;@functools&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;wraps&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook_target&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;wrapper&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="n"&gt;kw&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;disabled&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook_target&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="n"&gt;kw&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;**&lt;/span&gt;&lt;span class="n"&gt;kw&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;wrapper&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;The &lt;cite&gt;BaseHook&lt;/cite&gt; takes care of:&lt;/p&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;using &lt;cite&gt;functools.wrap&lt;/cite&gt; correctly&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;disabling the hook when configured to do so&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;setting the config group for later use of the config&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;simplifying the decorator implementation&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;p&gt;This base class is meant to make development of a hook simpler. A hook
author is free to implement the hook as a normal decorator as
well.&lt;/p&gt;
&lt;section id="configuration"&gt;
&lt;h4&gt;Configuration&lt;/h4&gt;
&lt;p&gt;It is important to note that any configuration must be accessed via
&lt;cite&gt;oslo.config&lt;/cite&gt;. The reason being is that the hooks are applied at
import time, where the confguration is typically loaded at run
time. Therefore, the hook may not have access to config data until the
hook target is actually called.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="hook-example"&gt;
&lt;h4&gt;Hook Example&lt;/h4&gt;
&lt;p&gt;Here is an example of a hook point that wraps the &lt;cite&gt;create_domain&lt;/cite&gt;
method in the Pool Manager service. It validates the domain doesn’t
exist in another application that can also manage domains via the same
backends.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kn"&gt;import&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;requests&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;oslo_log&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;logging&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;oslo_config&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;cfg&lt;/span&gt;

&lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;designate.pool_manager.service&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;ERROR_STATUS&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;designate.hookpoints&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;BaseHook&lt;/span&gt;


&lt;span class="n"&gt;LOG&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;logging&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;getLogger&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="vm"&gt;__name__&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;


&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;CheckDCXDomainHook&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;BaseHook&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;OPTS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;BaseHook&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;OPTS&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
        &lt;span class="n"&gt;cfg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Opt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'legacy_dns'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;required&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="kc"&gt;True&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
    &lt;span class="p"&gt;]&lt;/span&gt;

    &lt;span class="nd"&gt;@property&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;sess&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="nb"&gt;hasattr&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'_sess'&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
            &lt;span class="n"&gt;sess&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;requests&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Session&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
            &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;_sess&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;sess&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;_sess&lt;/span&gt;

    &lt;span class="nd"&gt;@property&lt;/span&gt;
    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;legacy_dns&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;cfg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CONF&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;group&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;legacy_dns&lt;/span&gt;

    &lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;hook&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;obj&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
        &lt;span class="n"&gt;resp&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sess&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;legacy_dns&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="s1"&gt;'/find_domains?name=&lt;/span&gt;&lt;span class="si"&gt;%s&lt;/span&gt;&lt;span class="s1"&gt;'&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="c1"&gt;# The domain is not found in the legacy system. Let Designate create it&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;resp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ok&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
            &lt;span class="c1"&gt;# We got a 404, so let Designate make the call&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;self&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hook_target&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;obj&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="c1"&gt;# The legacy system owns the domain. Notify central it was&lt;/span&gt;
        &lt;span class="c1"&gt;# an error.&lt;/span&gt;
        &lt;span class="c1"&gt;#&lt;/span&gt;
        &lt;span class="c1"&gt;# The `obj` is the Service object.&lt;/span&gt;
        &lt;span class="n"&gt;obj&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;central_api&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;update_status&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
            &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ERROR_STATUS&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;domain&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;serial&lt;/span&gt;
        &lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;It is the responsibility of the hook point author to be a good citizen
and properly handle any errors / return values in the original code, as
well as support any internal APIs.&lt;/p&gt;
&lt;p&gt;Again, the intent of the Hook Point API is to allow an organization a
means of injecting code, which implies a reasonably intimiate
knowledge with the code.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="hook-point-management-and-configuration"&gt;
&lt;h3&gt;Hook Point Management and Configuration&lt;/h3&gt;
&lt;p&gt;Hook points are installed by installing a package that includes
&lt;cite&gt;designate.hook_point&lt;/cite&gt; entry points. By default, these will be
&lt;strong&gt;enabled&lt;/strong&gt; and will be called when the specific hook point target is
called. These hooks &lt;strong&gt;MAY&lt;/strong&gt; be &lt;strong&gt;disabled&lt;/strong&gt; in the config at the hook
point level.&lt;/p&gt;
&lt;div class="highlight-cfg notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;[hook_point:pool_manager_create_domain]&lt;/span&gt;
&lt;span class="na"&gt;disabled&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s"&gt;True&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;If necessary, hook points can also receive configuration details.&lt;/p&gt;
&lt;div class="highlight-cfg notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="k"&gt;[hook_point:pool_manager_create_domain]&lt;/span&gt;
&lt;span class="na"&gt;legacy_dns_api&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s"&gt;https://my.dns.legacy.org.net:8975&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;The configuration will be available via the global
&lt;cite&gt;oslo.config.cfg.CONF&lt;/cite&gt; object.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Hook points can be added liberally or in an extremely limited, known
uses cases. Similarly, no hook points can be formally added and an
organization may apply them as necessary in an org specific patch.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;Other than the originally mentioned tactics for hooking into the
Designate code, more specific hook points could be created on a
per-use basis. For example, there could be very a specific API for
hooks that get called when a message is read from the queue. While
providing more specific hooks may allow for a use case specific API,
it would also require each API be designed, documented and tested. The
hook point API provides a single tested means of injecting code that
has limited effect on the API over time and allows a reasonable level
of support.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;eric-larson&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Liberty-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Add &lt;cite&gt;designate.hookpoints&lt;/cite&gt;, implementing the &lt;cite&gt;@hook_point&lt;/cite&gt;
decorator&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add documentation for writing hook points and enumrate what hook
points exist.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;&lt;/blockquote&gt;
&lt;p&gt;See &lt;a class="reference external" href="https://review.openstack.org/164748"&gt;this review&lt;/a&gt; for the
current implementation.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;stevedore&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 08 Apr 2015 00:00:00 </pubDate></item><item><title>Graded Backends</title><link>https://specs.openstack.org/openstack/designate-specs/specs/liberty/graded-backends.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="graded-backends"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/graded-backends"&gt;https://blueprints.launchpad.net/designate/+spec/graded-backends&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Currently we have quite a few backends, that are not tested, or actively maintained.
We should be informing users of what backends are most actively maintained and tested&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;A graduated level of grading for backends:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Grade&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Variations&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Integrated&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;None&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Tested on every commit by the OpenStack CI Infrastructure, and maintained by designate developers as a reference backend&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Master Compatible&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;In Tree / External&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Tested on every commit by 3rd party testing, and has a person or group dedicated to maintaining compatibility on a regular basis&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Release Compatible&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;In Tree / External&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Not necessarily tested on every commit, but has a maintainer committed to ensuring compatibility for each release&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Untested&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;In Tree / External&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;All other backends in the designate repository&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Failing&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;In Tree / External&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Backends that were previously “* Compatible”, but tests are now failing on a regular basis.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Known Broken&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;In Tree / External&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Backends that do not work, and have been broken with no sign of any fixes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;The current backends would be currently fall into the following pattern:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Backend&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Grade&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;PowerDNS + MySQL&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Integrated&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Bind&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Integrated&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Akamai&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Release Compatible - In Tree&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;DynECT&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Release Compatible - In Tree&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Agent&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Untested - In Tree&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;PowerDNS + pgSQL&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Untested - In Tree&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Microsoft DNS&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Untested - External&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;This will also include the creation of a support matrix like &lt;a class="reference external" href="http://docs.openstack.org/developer/nova/support-matrix.html"&gt;Nova&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;This info should be maintained along with the list of current driver maintainers
responsible for the “Non Integrated” backends. The upkeep of this list will fall on the PTL or his/her delegate&lt;/p&gt;
&lt;p&gt;Should a backend’s grade be in dispute, it falls
on the current project PTL to make the final decision
after listening to all sides concerns.&lt;/p&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;Continue on as is&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;grahamhayes&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Liberty-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;None&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 01 Apr 2015 00:00:00 </pubDate></item><item><title>Introduce Guru Meditation Reports into Designate</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/guru-meditation-reports.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="introduce-guru-meditation-reports-into-designate"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/guru-meditation-reports"&gt;https://blueprints.launchpad.net/designate/+spec/guru-meditation-reports&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Guru Meditation Reports enables Designate service to print a lot of detail
debug information about service running thread, configuration and greenlet
stack straces when receiving USR1 signal.&lt;/p&gt;
&lt;p&gt;Add Guru Meditation Reports into Designate will help us debugging problems
easier especially when dealing with bugs root in deadlocks between eventlet
greenthreads.&lt;/p&gt;
&lt;p&gt;Guru Meditation Reports is alreadly implemented in oslo-incubator and used in
Nova.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;Pick Guru Meditation Reports implementation from oslo-incubator and add the
USR1 signal handler.&lt;/p&gt;
&lt;p&gt;All Designate services will support Guru Meditation Reports, including:&lt;/p&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;designate-central&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;designate-api&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;designate-mdns&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;designate-agent&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;designate-pool-manager&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;designate-sink&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;designate-manage&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;Designate service processes will receive USR1 signal and print Guru Meditation
Reports.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;stanzgy&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-3&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;p&gt;Work items are listed in Proposed change section.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="documentation-impact"&gt;
&lt;h2&gt;Documentation Impact&lt;/h2&gt;
&lt;p&gt;Describe how to generate and view a Guru Meditation Reports.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="references"&gt;
&lt;h2&gt;References&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;GMR wiki: &lt;a class="reference external" href="https://wiki.openstack.org/wiki/GuruMeditationReport"&gt;https://wiki.openstack.org/wiki/GuruMeditationReport&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;GMR in Nova: &lt;a class="reference external" href="http://docs.openstack.org/developer/nova/devref/gmr.html"&gt;http://docs.openstack.org/developer/nova/devref/gmr.html&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Nova GMR User Manual: &lt;a class="reference external" href="http://docs.openstack.org/admin-guide-cloud/content/section_compute-GuruMed-reports.html"&gt;http://docs.openstack.org/admin-guide-cloud/content/section_compute-GuruMed-reports.html&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 09 Mar 2015 00:00:00 </pubDate></item><item><title>Zone Import Refactor</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/zone-import-refactor.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="zone-import-refactor"&gt;
&lt;span id="id1"/&gt;
&lt;p&gt;Migrate Zone import code from designate.api.v2.controllers.zones into a new
designate.dnsutils module and move functionality into Central.&lt;/p&gt;
&lt;section id="terminology"&gt;
&lt;h2&gt;Terminology&lt;/h2&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Term&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Meaning&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;zone&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DNS Zone (also refered to as a DNS domain)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Currently the Import functionality parses the Zone that is POST’ed in the API
and runs the creation of the Zone with its Records from the API side. There is
no transactional guarantee of a cleanup if the creation of anything fails.&lt;/p&gt;
&lt;p&gt;Also there’s a given value of having these methods outside of the API, it can
be used in any component outside of the API (for example AXFR support).&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;We introduce a new module called designate.dnsutils that contains functions
for parsing Zones / Records into dnspython object and dnspython objects to
DesignateObjects.&lt;/p&gt;
&lt;p&gt;Code for parsing a Zone file is already present in the
designate.api.v2.controller.ZoneController and can be easily extracted.&lt;/p&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;We need a new method that takes a Domain and a RecordSetList object, then
puts this into Designate accordingly.&lt;/p&gt;
&lt;p&gt;It should have the ability to either synchronize a existing zone or at a later
point in time a new zone with it’s records.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="new-module-dnsutils"&gt;
&lt;h3&gt;New module dnsutils&lt;/h3&gt;
&lt;section id="dnsutils-from-dnspython-zone-dnspython-zone"&gt;
&lt;h4&gt;dnsutils.from_dnspython_zone(dnspython_zone)&lt;/h4&gt;
&lt;p&gt;Takes a dnspython_zone and creates a Domain object also runs
records_to_recordset_list() on each record in the zone.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;dnspython_zone&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DNS Python zone&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="return-value"&gt;
&lt;h5&gt;Return value&lt;/h5&gt;
&lt;p&gt;Domain with a recordset relation attribute&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dnsutils-dnspyrecords-to-recordsetlist-dnspython-records"&gt;
&lt;h4&gt;dnsutils.dnspyrecords_to_recordsetlist(dnspython_records)&lt;/h4&gt;
&lt;p&gt;Convert a dnspython_zone.nodes structure to a RecordSetList, Recordsets,
RecordList and Records.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;dnspython_records&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DNS Python Record&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id2"&gt;
&lt;h5&gt;Return value&lt;/h5&gt;
&lt;p&gt;designate.objects.recordset.RecordSet with a record attribute of
designate.objects.record.RecordList from the given dnspython node / record.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dnsutils-dnspythonrecord-to-recordset-rname-rdataset"&gt;
&lt;h4&gt;dnsutils.dnspythonrecord_to_recordset(rname, rdataset)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;rname&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;dnspy node name / key&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;rdataset&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;dnspy rr dataset&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id3"&gt;
&lt;h5&gt;Return value&lt;/h5&gt;
&lt;p&gt;designate.objects.recordset.RecordSet with a record attribute of
designate.objects.record.RecordList from the given dnspython node / record.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&amp;lt;&lt;a class="reference external" href="https://launchpad.net/~endre-karlson"&gt;https://launchpad.net/~endre-karlson&lt;/a&gt;&amp;gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Extract code from Zones controller into new module “dnsutils” / new central
method.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Change parse_zonefile to call dnsutils.parse_zonefile() and call Central’s
new method with the results of this.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 29 Oct 2014 00:00:00 </pubDate></item><item><title>New Agent</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/new-agent.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="new-agent"&gt;

&lt;p&gt;This spec describes a proposed service for Designate, tentatively called the
“Agent,” not to be confused with the current component with the same name.&lt;/p&gt;
&lt;section id="terminology"&gt;
&lt;h2&gt;Terminology&lt;/h2&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Term&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Meaning&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;AXFR&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A DNS zone transfer&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;NOTIFY&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A DNS protocol to inform of a zone update&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;OPCODE&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Part of a DNS message that informs action
&lt;a class="reference external" href="http://bit.ly/1pfG8Zp"&gt;http://bit.ly/1pfG8Zp&lt;/a&gt;&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Backend&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Different code paths for various DNS servers&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;MiniDNS&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Designate component in charge of sending
NOTIFYs, and answering AXFRs.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;MiniDNS provides a very elegant solution for many DNS installations. Having a
Designate component as the DNS master enables Designate to have a great amount
of control over the DNS server, and makes certain processes much easier to
implement across backends.&lt;/p&gt;
&lt;p&gt;However, some deployments may not be able to use MiniDNS as a true DNS Master,
and would rather keep the current style of backends in some form with the added
benefits of MiniDNS. They might need a more specialized type of interaction
between Designate and the DNS server, making Designate more flexible.
Additionally, there are potential problems with having MiniDNS and it’s database
being a single point of failure for a DNS infrastructure.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;An agent deployed on the Master DNS server that interacts with MiniDNS solves
these problems. A plugable backend that enables users to use any backend with
MiniDNS, as well as the ability to isolate MiniDNS from being a master in
large deployments are much simpler with an Agent.&lt;/p&gt;
&lt;p&gt;The Agent would be a standalone service that acts as a sort of mirror to
MiniDNS. It would receive AXFR/IXFR, NOTIFYs, and other notifications and
perform changes to the DNS server through a plugin-style backend.&lt;/p&gt;
&lt;section id="pool-manager-changes"&gt;
&lt;h3&gt;Pool Manager Changes&lt;/h3&gt;
&lt;p&gt;A new backend for the Pool Manager would be created for the Agent.
It should send fire-and-forget DNS messages with classes and RRTYPE intended for
private use, shown here: &lt;a class="reference external" href="http://bit.ly/1soCZTffor"&gt;http://bit.ly/1soCZTffor&lt;/a&gt; on Creates/Deletes, and call
into MiniDNS as it would normally for updates.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="agent-changes"&gt;
&lt;h3&gt;Agent Changes&lt;/h3&gt;
&lt;p&gt;The agent service will need to be created (possibly supplanting the old “agent”)&lt;/p&gt;
&lt;p&gt;The structure will be very similar to MiniDNS. A service (TCP, rather than RPC)
will listen for TCP and UDP traffic. NOTIFYs and AXFRs will be handled, along
with regular DNS queries (via pass through to the real DNS server), and the
special DNS CLASSES and RRDTYPEs that are chosen to signify Creates and Deletes.
DNS traffic will result in calls into the configured backend. A special OPCODE,
14 will be used for all non-standard actions like Creating and Deleting zones.&lt;/p&gt;
&lt;section id="configuration"&gt;
&lt;h4&gt;Configuration&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Default&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Notes&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;backend_driver&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘None’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The name of the backend driver to use with the Agent&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;workers&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;None&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The number of worker processes to spawn&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;masters&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;[]&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;List of IP/Ports of Masters the Agent will query for AXFRs and SOA queries&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;allow-notify&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;[]&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;List of IP/Ports of Masters allowed to NOTIFY/AXFR with the Agent&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;host&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘0.0.0.0’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Bind host for the Agent&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;port&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;5354&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Port to bind to&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;tcp_backlog&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;100&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;TCP backlog for the Agent&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;There would also be sub-configuration sections for the different backends, using
the form [agent:backend_name]. These would be mostly ported from the current
backends.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="service"&gt;
&lt;h4&gt;Service&lt;/h4&gt;
&lt;p&gt;Initialization of the service, and basic handling of TCP/UDP traffic. Does some
validation on the traffic coming in, making sure it is valid before sending on
to the core application logic. This should be mostly taken from
designate/mdns/service.py
There could be some optimization, since the Agent will be talking only to mdns.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="middleware"&gt;
&lt;h4&gt;Middleware&lt;/h4&gt;
&lt;p&gt;A thin middleware that sits between the TCP message receiving, and the handler.
Allows for contexts or other metadata to be attached to a request before it goes
to a handler.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="handler"&gt;
&lt;h4&gt;Handler&lt;/h4&gt;
&lt;p&gt;The handler will take DNS requests in, and take the appropriate action. This
will be very similar to mdns/handler.py&lt;/p&gt;
&lt;section id="handle-update-request-op"&gt;
&lt;h5&gt;_handle_update(request, op)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;request&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Serialized request data from the DNS request&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;op&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Whether an update or create is happening&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Get the name from the request&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Make sure the requester is in the allowed list of notifiers&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Call the backend’s find_domain to see if the message is for a zone on the DNS
server. If not, throw the message away&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Query the requesting mdns (SOA), per the RFC (????)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Call out to the Agent’s AXFR module asynchronously which will perform the
AXFR, get the zone and call backend’s create or update domain, based on the
action.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="handle-delete-request"&gt;
&lt;h5&gt;_handle_delete(request)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;request&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Serialized request data from the DNS request&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Get the name from the request&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Make sure the requester is in the allowed list of notifiers&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Call out to the backend’s delete_domain&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="handle-record-query-request"&gt;
&lt;h5&gt;_handle_record_query(request)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;request&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Serialized request data from the DNS request&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Repackage the request, send it along to the local DNS server&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Return the results&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;This is a possible way for the Agent to answer DNS queries when MiniDNS is
polling for changes&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="axfr"&gt;
&lt;h4&gt;AXFR&lt;/h4&gt;
&lt;p&gt;The AXFR module will send the AXFR query to one of the masters specified in the
config for the zone name that was passed in. Based on the type of query that
called for the AXFR, a backend call will then be made with the information
gathered from the AXFR.&lt;/p&gt;
&lt;section id="do-axfr-zone-name-action"&gt;
&lt;h5&gt;_do_axfr(zone_name, action)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;zone_name&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The zone name to ask for the AXFR with&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;new_domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Boolean value to inform AXFR if the zone is a
new zone or not. Default is False&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;Pick a master from the config file&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Send the AXFR query&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Parse the response into a designate domain object&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Call the backend for the specified action (Create, Update)&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="admonition note"&gt;
&lt;p class="admonition-title"&gt;Note&lt;/p&gt;
&lt;p&gt;Eventually this module could be renamed “Transfer” and do IXFRs.&lt;/p&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="backend"&gt;
&lt;h4&gt;Backend&lt;/h4&gt;
&lt;p&gt;The Backend module will house a base plugin, and a variety of plugins with a
similar interface to the Pool Manager. The intent is to take the zone changes
gleaned from an AXFR (or IXFR) and apply them to the DNS server. The manner of
accomplishing this will vary widely for each DNS server, you might be editing a
flat file, or making database calls, or some other method. The following methods
would compose the base plugin.&lt;/p&gt;
&lt;section id="find-zone-zone-name"&gt;
&lt;h5&gt;find_zone(zone_name)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;zone_name&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The zone name to be searched for&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;When a NOTIFY comes in for a zone, the Agent must first check to make sure that
the zone is valid for the DNS server. Otherwise, it might do an AXFR and try to
update a zone that doesn’t exist on the server. It’s possible that this check
could be incorporated in to the update_zone function, but it seems more
efficient to do it here.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="create-zone-domain"&gt;
&lt;h5&gt;create_zone(domain)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A Designate domain object to create on the
backend server, including it’s recordsets&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Take the appropriate measure to create the zone on the DNS server. This object
will hold all the necessary information to serve the zone.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="update-zone-domain"&gt;
&lt;h5&gt;update_zone(domain)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A Designate domain object to update on the
backend server, including it’s recordsets&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Take the appropriate measure to update the zone on the DNS server. This has the
potential to be very similar to the create_zone logic if there is no way to
discern the differences between this object, and the zone on the server.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="delete-zone-zone-name"&gt;
&lt;h5&gt;delete_zone(zone_name)&lt;/h5&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;zone_name&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The zone name identified for deletion&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Take the appropriate measure to delete the zone on the DNS server, and ideally
all of it’s subresources.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;This should fit into the Designate pattern well. To the Pool Manager and
MiniDNS, the Agent is the same as any other DNS server. It’s possible that
something in MiniDNS could be supplemented to use with the Agent, but it
shouldn’t be needed.&lt;/p&gt;
&lt;p&gt;A lot of the code that MiniDNS uses for the actual DNS protocol stuff will
be reused in some form in the Agent. Development of the agent would be a good
time to port the commonalities into the dnsutils module of Designate.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="benefits"&gt;
&lt;h2&gt;Benefits&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Configurable backends that can do the work required for different DNS servers
(RNDC, Database addition) that don’t connect directly to the database&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A deployment with the benefits of MiniDNS, while keeping a traditional
Master/Slave DNS setup is possible&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Less DNS servers must be managed by Designate&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Less chatter between MiniDNS and the database because SOA refreshes and
other queries can be handled by a master&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;MiniDNS becomes less vital to a deployment, MiniDNS/Database issues are
isolated from the DNS infrastructure&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;An agent with direct control of the DNS servers adds the benefit of doing
things outside of pure DNS protocol with a DNS server, periodic syncs, etc are
made easier&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;tim-simmons-t&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Create the Agent service&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add support for receiving NOTIFYs&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add support for receiving AXFRs&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Decide and implement receiving messages with non-standard CLASS/RRDATA&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add a base class backend that is called for different operations&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Port some of the existing backends, or add some new ones&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 28 Oct 2014 00:00:00 </pubDate></item><item><title>Support for server pools in Minidns</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/server-pools-minidns-support.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="support-for-server-pools-in-minidns"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/server-pools-minidns-support"&gt;https://blueprints.launchpad.net/designate/+spec/server-pools-minidns-support&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;This spec outlines the apis that need to be added to MiniDNS for supporting
pool manager.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;notify_zone_changed:&lt;/strong&gt; The pool manager needs to notify pool servers when a
zone changes. It calls into mindns to notify the pool servers of the zone change.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;poll_for_serial_number:&lt;/strong&gt; When a zone is changed, the change is marked as
&lt;em&gt;PENDING&lt;/em&gt; in central.  It will be marked as &lt;em&gt;ACTIVE&lt;/em&gt; when a certain number of
pool servers have the change.  Server pools would use mindns to check the
pool servers for the presence of the change.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;There would be 2 calls added to minidns to support the features needed by pool manager.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="mindns-call-changes"&gt;
&lt;h2&gt;Mindns Call Changes&lt;/h2&gt;
&lt;section id="notify-zone-changed-context-domain-destination-timeout-retry-interval-max-retries"&gt;
&lt;h3&gt;notify_zone_changed(context, domain, destination, timeout, retry_interval, max_retries)&lt;/h3&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The user context.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;destination&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The recipient of the NOTIFY message. The format is
“ip:[port]”.  If there is no port, port 53 is used.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;timeout&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The time to wait for a NOTIFY response from &lt;em&gt;destination&lt;/em&gt;.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;retry_interval&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The time between retries.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;max_retries&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The maximum number of retries mindns would do for a NOTIFY
response. After this many retries, mindns drops the NOTIFY
message.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="design-considerations"&gt;
&lt;h4&gt;Design Considerations&lt;/h4&gt;
&lt;p&gt;Mindns uses &lt;em&gt;domain.name&lt;/em&gt; to construct a NOTIFY message and sends it to
&lt;em&gt;destination&lt;/em&gt;.  If a response is not received within &lt;em&gt;timeout&lt;/em&gt; interval, then
after a time interval of &lt;em&gt;retry_interval&lt;/em&gt;, the NOTIFY message is resent to &lt;em&gt;destination&lt;/em&gt;.
After trying for &lt;em&gt;max_retries&lt;/em&gt;, the call completes.  All times are in seconds.&lt;/p&gt;
&lt;section id="cast-vs-call"&gt;
&lt;h5&gt;Cast vs Call&lt;/h5&gt;
&lt;p&gt;This is an RPC cast rather than an RPC call.  The pool manager need not wait
for the NOTIFY response.  The reasoning here is that in the worst case after the
refresh interval, the zone on the &lt;em&gt;destination&lt;/em&gt; would be refreshed.  Also the
status would be correctly updated elsewhere so this need not be a call.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="single-call-vs-multiple-calls"&gt;
&lt;h5&gt;Single Call vs Multiple Calls&lt;/h5&gt;
&lt;p&gt;Pool Manager sends multiple requests to (potentially multiple instances of) minidns
with a single &lt;em&gt;destination&lt;/em&gt; in each call.  The reasoning is that the pool manager
has the global knowledge of the number of pool servers and NOTIFY messages that
need to be sent.  It is in a better position to decide the approach to parallelizing
the messages that need to be sent.  The minidns on the other hand is only concerned
with the dns protocol.  That said BIND sends a zone transfer request to the server
that sends the NOTIFY message.  So it makes sense to have a minidns server associated
with the same set of pool servers.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="parameter-sources-validations"&gt;
&lt;h5&gt;Parameter sources/validations&lt;/h5&gt;
&lt;p&gt;The &lt;em&gt;timeout&lt;/em&gt;, &lt;em&gt;retry_interval&lt;/em&gt; and &lt;em&gt;max_retries&lt;/em&gt; would possibly be specified in
the config file in the pool manager section for the initial version.  Irrespective
of where the pool manager gets its data, it passes these as parameters to minidns.
It makes sense for pool manager to track these parameters rather than minidns.&lt;/p&gt;
&lt;p&gt;Minidns does not do any validation of the &lt;em&gt;timeout&lt;/em&gt;, &lt;em&gt;retry_interval&lt;/em&gt; and &lt;em&gt;max_retries&lt;/em&gt;
parameters.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="poll-for-serial-number-context-domain-destination-timeout-retry-interval-max-retries"&gt;
&lt;h3&gt;poll_for_serial_number(context, domain, destination, timeout, retry_interval, max_retries)&lt;/h3&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The user context.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;destination&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The server to check for an updated serial number. The
format is “ip:[port]”.  If there is no port, port 53 is
used.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;timeout&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The time to wait for a SOA response from &lt;em&gt;destination&lt;/em&gt;.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;retry_interval&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The time between retries.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;max_retries&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The maximum number of retries mindns would do for an
expected serial number. After this many retries, mindns
returns an ERROR.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id1"&gt;
&lt;h4&gt;Design Considerations&lt;/h4&gt;
&lt;p&gt;Mindns uses &lt;em&gt;domain.name&lt;/em&gt; to construct a SOA request and sends it to &lt;em&gt;destination&lt;/em&gt;.
The serial number in the SOA response (hereafter referred to as &lt;em&gt;actual_serial&lt;/em&gt;)
is compared to &lt;em&gt;domain.serial&lt;/em&gt; (hereafter referred to as &lt;em&gt;expected_serial&lt;/em&gt;).&lt;/p&gt;
&lt;section id="id2"&gt;
&lt;h5&gt;Cast vs Call&lt;/h5&gt;
&lt;p&gt;This would be a cast.  Pool Manager would provide a function - &lt;em&gt;update_status&lt;/em&gt;
for minidns to inform of the result.  For more discussions on this see the
&lt;a class="reference external" href="http://eavesdrop.openstack.org/meetings/designate/2014/designate.2014-09-03-17.02.log.html"&gt;designate meeting log notes on 03-Sep-2014&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;section id="return-values"&gt;
&lt;span id="return-values-poll-for-serial"/&gt;&lt;h5&gt;Return Values&lt;/h5&gt;
&lt;p&gt;The return status from this function is sent to the pool manager using the pool
manager call back function - &lt;em&gt;update_status&lt;/em&gt;.  The values sent are summarized
below.  We actually could send just the serial number without a status too.&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Case&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Action&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;actual_serial&lt;/em&gt; = &lt;em&gt;expected_serial&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Send &lt;em&gt;SUCCESS&lt;/em&gt; and &lt;em&gt;actual_serial&lt;/em&gt;.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;actual_serial&lt;/em&gt; &amp;gt; &lt;em&gt;expected_serial&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Send &lt;em&gt;SUCCESS&lt;/em&gt; and &lt;em&gt;actual_serial&lt;/em&gt;.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;actual_serial&lt;/em&gt; &amp;lt; &lt;em&gt;expected_serial&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;poll again after a time interval of &lt;em&gt;retry_interval&lt;/em&gt; elapses.
Continue this until we get the &lt;em&gt;expected_serial&lt;/em&gt; or for
&lt;em&gt;max_retries&lt;/em&gt;. Send &lt;em&gt;ERROR&lt;/em&gt; and &lt;em&gt;actual_serial&lt;/em&gt; after
&lt;em&gt;max_retries&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;timeout for &lt;em&gt;max_retries&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Send &lt;em&gt;ERROR&lt;/em&gt; and &lt;em&gt;None&lt;/em&gt; for serial number.&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="pool-manager-dependencies"&gt;
&lt;h2&gt;Pool Manager Dependencies&lt;/h2&gt;
&lt;p&gt;Pool Manager would provide an api - &lt;em&gt;update_status&lt;/em&gt; for minidns to call in to
inform the status of the poll_for_serial_number call.  The &lt;a class="reference internal" href="#return-values-poll-for-serial"&gt;&lt;span class="std std-ref"&gt;Return Values&lt;/span&gt;&lt;/a&gt;
section of &lt;em&gt;poll_for_serial_number&lt;/em&gt; summarizes the values that would be sent with &lt;em&gt;update_status&lt;/em&gt;
As noted above, we need not send a separate status, sending the actual_serial (or None)
should be enough.&lt;/p&gt;
&lt;section id="update-status-context-domain-destination-status-actual-serial"&gt;
&lt;h3&gt;update_status(context, domain, destination, status, actual_serial)&lt;/h3&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The user context passed in the corresponding .
&lt;em&gt;poll_for_serial_number&lt;/em&gt; call&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;domain&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate domain object. &lt;em&gt;domain.serial&lt;/em&gt; has the
&lt;em&gt;expected_serial&lt;/em&gt; number. This object is the same as
the one sent in the corresponding
&lt;em&gt;poll_for_serial_number&lt;/em&gt; call&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;destination&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The &lt;em&gt;destination&lt;/em&gt; parameter from the corresponding
&lt;em&gt;poll_for_serial_number&lt;/em&gt; call&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;status&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The status would be one of &lt;em&gt;SUCCESS&lt;/em&gt;, &lt;em&gt;ERROR&lt;/em&gt;.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;actual_serial&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The actual serial number received from &lt;em&gt;destination&lt;/em&gt;
or &lt;em&gt;None&lt;/em&gt; in case of a timeout.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h2&gt;Storage Changes&lt;/h2&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&amp;lt;vinod-mang&amp;gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Api addition to mini-dns - notify_zone_changed&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Api addition to mini-dns - poll_for_serial_number&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Api to pool manager (minidns would call this api) - update_status&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;Pool Manager needs to add &lt;em&gt;update_status&lt;/em&gt; for minidns to inform the status of
&lt;em&gt;poll_for_serial_number&lt;/em&gt;.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 01 Oct 2014 00:00:00 </pubDate></item><item><title>Server Pools Storage</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/server-pools-storage.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="server-pools-storage"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/server-pools-storage"&gt;https://blueprints.launchpad.net/designate/+spec/server-pools-storage&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;This specification outlines the Central, Storage, and compatibility changes
needed to support server pools.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;For server pools, a new object is required to encapsulate pools.  When
this specification is implemented, the pool object will used by the backend
drivers for getting the name servers as a compatibility change.  Central
will continue to call the backend drivers.  Additional server pools
specifications will address using the entire pool object.  This is the
foundation for those other specifications.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;When the database is first initialized, a pool named ‘default’ will be
created.  This is the default pool.  The default pool will have no
also-notify hosts and no name servers.  New methods will be added to
Central to create, find, get, update, and delete pools and these methods
are described in the Central Changes section.  The database changes needed
to support pools are described in the Storage Changes section.  Finally,
name servers can be added to the default pool by using the V1 servers
endpoint described in the Compatibility Changes section.&lt;/p&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;The &lt;strong&gt;[service:central]&lt;/strong&gt; section of the Designate configuration will have a
new option:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Default&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Notes&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;default_pool_name&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘default’&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The pool name of the default pool&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;This value needs to be set to the pool name of the default pool which is
‘default’.&lt;/p&gt;
&lt;p&gt;The pool object will be implemented.&lt;/p&gt;
&lt;p&gt;The new methods implemented in the Central service for the
pool object are:&lt;/p&gt;
&lt;section id="create-pool-context-pool"&gt;
&lt;h4&gt;create_pool(context, pool)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;pool&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate pool object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="return-value"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;The created pool.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="find-pools-context-criterion-marker-limit-sort-key-sort-dir"&gt;
&lt;h4&gt;find_pools(context, criterion, marker, limit, sort_key, sort_dir)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;criterion&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The search criterion.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;marker&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Resource ID from which after the requested page will start after.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;limit&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Integer limit of objects of the page size after the marker.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;sort_key&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Key from which to sort after.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;sort_dir&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Direction to sort after using sort_key.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id1"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;The found pools.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="get-pool-context-pool-id"&gt;
&lt;h4&gt;get_pool(context, pool_id)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;pool_id&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The pool ID.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id2"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;The pool requested.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="update-pool-context-pool"&gt;
&lt;h4&gt;update_pool(context, pool)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;pool&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The designate pool object.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id3"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;The updated pool.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="delete-pool-context-pool-id"&gt;
&lt;h4&gt;delete_pool(context, pool_id)&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Parameter&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Description&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;&lt;strong&gt;Required&lt;/strong&gt;&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;context&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Security context information.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;&lt;em&gt;pool_id&lt;/em&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The pool ID.&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="id4"&gt;
&lt;h5&gt;Return Value&lt;/h5&gt;
&lt;p&gt;No return value.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;A new table for pools will be needed.  Another new table for the pool
attributes will be used to store the also-notify and name server values in
addition to supporting future enhancements to server pools.  The domains
table will be modified to support pools.&lt;/p&gt;
&lt;section id="new-table-pools"&gt;
&lt;h4&gt;New Table - pools&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;CHAR(32)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;PK&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;created_at&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DATETIME&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;UTC time of creation&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;updated_at&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DATETIME&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;UTC time of last update&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;version&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;INT(11)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Designate API version&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;name&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR(50)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Server pool name&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;description&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR(255)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Server pool description&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;project_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR(36)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Tenant ID that created the pool&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;provisioner&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ENUM&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Only ‘unmanaged’ provisioner is supported currently&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="new-table-pool-attributes"&gt;
&lt;h4&gt;New Table - pool_attributes&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;CHAR(32)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;PK&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;key&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR(255)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Pool attribute key (also-notify, name server, etc.)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;value&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR(255)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Pool attribute value&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;pool_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;CHAR(32)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;FK to ID on pools table&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="modify-table-domains"&gt;
&lt;h4&gt;Modify Table - domains&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Action&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;pool_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;CHAR(32)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;FK to ID on pools table&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;add&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="compatibility-changes"&gt;
&lt;h3&gt;Compatibility Changes&lt;/h3&gt;
&lt;p&gt;When adding a name server using the V1 servers endpoint, a pool_attributes
table entry will be created for the name server.  The columns and values used
will be:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Column&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Value&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;key&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;‘name_server’&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;value&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;&amp;lt;FQDN of name server&amp;gt;&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;pool_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;&amp;lt;default pool id&amp;gt;&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;When creating a domain using the V1 domains endpoint, the domains table entry
will include the pool ID of the default pool.&lt;/p&gt;
&lt;p&gt;The backend drivers will be modified to use the name servers defined for the
default pool in the pool_attributes table instead of the servers table.&lt;/p&gt;
&lt;p&gt;All Central methods for servers will be removed.&lt;/p&gt;
&lt;p&gt;The servers table will be removed and all Storage methods for servers will
be removed.&lt;/p&gt;
&lt;p&gt;The existing server object will be removed.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~rjrjr"&gt;https://launchpad.net/~rjrjr&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt&gt;Additional assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~darshan104"&gt;https://launchpad.net/~darshan104&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Central changes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Storage changes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Compatibility changes&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 11 Aug 2014 00:00:00 </pubDate></item><item><title>Zone and Record TotalCount</title><link>https://specs.openstack.org/openstack/designate-specs/specs/juno/zone-and-record-totalcount.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="zone-and-record-totalcount"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/zone-and-record-totalcount"&gt;https://blueprints.launchpad.net/designate/+spec/zone-and-record-totalcount&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;When a user makes a request for a list of zones or records, provide the
total count of zones or records that match the given query. The count will
ideally be provided when a user makes a request for something like /zones
or /records (to limit the need to make multiple queries).&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;section id="api-changes"&gt;
&lt;h3&gt;API Changes&lt;/h3&gt;
&lt;p&gt;This change would not add any new endpoints, but it would modify the data
presented by some existing endpoints.&lt;/p&gt;
&lt;p&gt;The following examples demonstrate the total_entries value for a generic
collection of “resources”. After implementation, this feature will be
supported by collections of zones and recordsets.&lt;/p&gt;
&lt;section id="get-v2-resources"&gt;
&lt;h4&gt;GET /v2/resources&lt;/h4&gt;
&lt;p&gt;&lt;strong&gt;Example Request:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/resources&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Example Response:&lt;/strong&gt;&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;200&lt;/span&gt; &lt;span class="ne"&gt;OK&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"resources"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"fdd7b0dc-52a3-491e-829f-41d18e1d3ada"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-06-23T18:39:32.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"...."&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"...."&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"a86dba58-0043-4cc6-a1bb-69d5e86f3ca3"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-07-08T20:28:19.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"...."&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"...."&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"460f7531-e381-4773-aff3-06a12fad096d"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-06-04t19:09:17.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"...."&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"...."&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"40ced622-fc70-498d-9f28-3d3021b19685"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"created_at"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2014-07-08T16:47:32.000000"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"...."&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"...."&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;}],&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://dns.provider.com/v2/resources?sort_key=id&amp;amp;sort_dir=desc"&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="nt"&gt;"meta"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"total_entries"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;
&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;A PagedListObjectMixin class will be added that will support the metadata
associated with list pagination. This class will be added as a superclass
of the ZonesList and RecordsList classes.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;p&gt;Any calls to find_domains will also internally call count_domains and add
this count to the DomainsList object that is returned.&lt;/p&gt;
&lt;p&gt;Any calls to find_records will also internally call count_records and add
this count to the RecordsList object that is returned.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="other-changes"&gt;
&lt;h3&gt;Other Changes&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;section id="alternatives"&gt;
&lt;h3&gt;Alternatives&lt;/h3&gt;
&lt;p&gt;None&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;p&gt;Primary assignee: jordan-cazamias&lt;/p&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Juno-2&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Agree on spec for API formatting&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Implement changes&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;p&gt;&lt;a class="reference external" href="https://review.openstack.org/#/c/105021/"&gt;https://review.openstack.org/#/c/105021/&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Thu, 10 Jul 2014 00:00:00 </pubDate></item><item><title>V2 API - Bindings</title><link>https://specs.openstack.org/openstack/designate-specs/specs/juno/v2-bindings.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="v2-api-bindings"&gt;

&lt;p&gt;BP: &lt;a class="reference external" href="https://blueprints.launchpad.net/python-designateclient/+spec/v2-api-bindings"&gt;https://blueprints.launchpad.net/python-designateclient/+spec/v2-api-bindings&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Provide bindings for the V2 API using the Session based approach used for V1.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Provide bindings for the V2 API. (This does not include the shell commands)&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;We will provide a designateclient.v2.client.Client object which would load the other Managers (not much unalike the Controllers or so in V1).&lt;/p&gt;
&lt;section id="manager-zone"&gt;
&lt;h3&gt;Manager - Zone&lt;/h3&gt;
&lt;section id="list"&gt;
&lt;h4&gt;List&lt;/h4&gt;
&lt;p&gt;List Zones.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;list&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get"&gt;
&lt;h4&gt;Get&lt;/h4&gt;
&lt;p&gt;Get a Zone.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="create"&gt;
&lt;h4&gt;Create&lt;/h4&gt;
&lt;p&gt;Create a Zone.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;create&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="update"&gt;
&lt;h4&gt;Update&lt;/h4&gt;
&lt;p&gt;Update a Zone.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="delete"&gt;
&lt;h4&gt;Delete&lt;/h4&gt;
&lt;p&gt;Delete a Zone.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;zones&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;delete&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="manager-recordsets"&gt;
&lt;h3&gt;Manager - RecordSets&lt;/h3&gt;
&lt;section id="id1"&gt;
&lt;h4&gt;List&lt;/h4&gt;
&lt;p&gt;List Recordsets in a Zone.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;recordsets&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;list&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id2"&gt;
&lt;h4&gt;Get&lt;/h4&gt;
&lt;p&gt;Get a RecordSet&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;recordsets&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;recordset&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id3"&gt;
&lt;h4&gt;Create&lt;/h4&gt;
&lt;p&gt;Create a RecordSet in a Zone.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;recordsets&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;create&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id4"&gt;
&lt;h4&gt;Update&lt;/h4&gt;
&lt;p&gt;Update a RecordSet.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;recoredsets&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;recordset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id5"&gt;
&lt;h4&gt;Delete&lt;/h4&gt;
&lt;p&gt;Delete a RecordSet.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;recoredsets&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;delete&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;zone&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;recordset&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="manager-tlds"&gt;
&lt;h3&gt;Manager - TLDs&lt;/h3&gt;
&lt;section id="id6"&gt;
&lt;h4&gt;List&lt;/h4&gt;
&lt;p&gt;List TLDs.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;tlds&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;list&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id7"&gt;
&lt;h4&gt;Get&lt;/h4&gt;
&lt;p&gt;Get a TLD&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;tlds&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tld&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id8"&gt;
&lt;h4&gt;Create&lt;/h4&gt;
&lt;p&gt;Create a TLDs.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;tlds&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;create&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id9"&gt;
&lt;h4&gt;Update&lt;/h4&gt;
&lt;p&gt;Update a TLD.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;tlds&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tld&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id10"&gt;
&lt;h4&gt;Delete&lt;/h4&gt;
&lt;p&gt;Delete a TLD.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;tlds&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;delete&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tld&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="manager-blacklists"&gt;
&lt;h3&gt;Manager - Blacklists&lt;/h3&gt;
&lt;section id="id11"&gt;
&lt;h4&gt;List&lt;/h4&gt;
&lt;p&gt;List Blacklists.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;blacklists&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;list&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id12"&gt;
&lt;h4&gt;Get&lt;/h4&gt;
&lt;p&gt;Get a Blacklist.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;blacklists&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;blacklist&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id13"&gt;
&lt;h4&gt;Create&lt;/h4&gt;
&lt;p&gt;Create a Blacklist.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;blacklists&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;create&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pattern&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id14"&gt;
&lt;h4&gt;Update&lt;/h4&gt;
&lt;p&gt;Update a Blacklist.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;blacklists&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;blacklist&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pattern&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id15"&gt;
&lt;h4&gt;Delete&lt;/h4&gt;
&lt;p&gt;Delete a Blacklist.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;blacklists&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;delete&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;blacklist&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="manager-floatingips"&gt;
&lt;h3&gt;Manager - FloatingIPs&lt;/h3&gt;
&lt;section id="id16"&gt;
&lt;h4&gt;List&lt;/h4&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;floatingips&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;list&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="id17"&gt;
&lt;h4&gt;Get&lt;/h4&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;floatingips&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;region&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;floatingip_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="set"&gt;
&lt;h4&gt;Set&lt;/h4&gt;
&lt;p&gt;Set a PTR record for a FloatingIP.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;floatingips&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;region&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;floatingip_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="unset"&gt;
&lt;h4&gt;Unset&lt;/h4&gt;
&lt;p&gt;Unset a PTR record for a FloatingIP.&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;floatingips&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;unset&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;region&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;floatingip_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;endre-karlson&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Juno-2&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;switch-to-keystone-session&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Sun, 06 Jul 2014 00:00:00 </pubDate></item><item><title>Use Keystone Client session / discovery code</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/switch-to-keystone-session.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="use-keystone-client-session-discovery-code"&gt;

&lt;p&gt;BP: &lt;a class="reference external" href="https://blueprints.launchpad.net/python-designateclient/+spec/switch-to-keystone-session"&gt;https://blueprints.launchpad.net/python-designateclient/+spec/switch-to-keystone-session&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Make the CLI use the Session pattern which should be better then the current
approach that’s based on a hook / taking the token from ksclient.auth_token
after ksclient.authenticate() is called.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;p&gt;V1 client code shouldn’t change except have added capabilities.&lt;/p&gt;
&lt;p&gt;We would end up having the following parameters for the designateclient.v1.Client object:&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Name&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;username&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Username (v2/v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;user_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;User’s ID (v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;user_domain_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;User’s Domain ID (v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;user_domain_name&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;User’s Domain Name (v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;password&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Password (v2/v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;tenant_name&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Tenant Name (v2)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;tenant_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Tenant ID (v2)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;project_name&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Project Name (v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;project_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Project ID (v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;project_domain_name&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Project Domain Name (v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;project_domain_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Project Domain ID (v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;auth_url&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Auth URL w/wo auth version in it
(It will be discovered by ks.discover if not present)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;token&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Existing authentication Token (v2/v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;endpoint_type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Endpoint type (v2/v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;service_type&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Service type (v2/v3)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;insecure&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Require valid SSL certs&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;cacert&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;CA Cert to use&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;cert&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;SSL Cert to use&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;endre-karlson&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-1&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;p&gt;N/A&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;python-keystoneclent v0.11.+&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Sun, 06 Jul 2014 00:00:00 </pubDate></item><item><title>Zone Ownership Transfer Between projects</title><link>https://specs.openstack.org/openstack/designate-specs/specs/juno/zone-migration-between-tenants.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="zone-ownership-transfer-between-projects"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/zone-migration-between-tenants"&gt;https://blueprints.launchpad.net/designate/+spec/zone-migration-between-tenants&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;For many projects, their organizational needs and structure can change. These
changes result in the need to move a zone from one project to another without
interruption to domain name resolution.&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Allow for a zone, and its associated recordsets and records to be moved from
one project to another.&lt;/p&gt;
&lt;p&gt;This will remove the original owning projects ability to modify the zone.&lt;/p&gt;
&lt;p&gt;This could also allow a project to create a sub domain, and transfer the
ownership to another project. (ie. the IT team of example.net allows developers
to manage records in dev-env.example.net)&lt;/p&gt;
&lt;p&gt;We allow both scoped (limited to a defined project), and unscoped (anyone with
the ID and access key can accept a request)&lt;/p&gt;
&lt;/section&gt;
&lt;section id="terminology"&gt;
&lt;h2&gt;Terminology&lt;/h2&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Term&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Meaning&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;zone&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DNS Zone (also refered to as a DNS domain)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;project&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;OpenStack keystone project (also refered to as tenant)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;transfer&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;method of transfering the ownership from one project to another (&lt;strong&gt;NOT&lt;/strong&gt; traditional DNS AFXR zone transfer)&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;section id="new-api-endpoint"&gt;
&lt;h3&gt;New API Endpoint&lt;/h3&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Parameter&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Description&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Required&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;zone_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ID of the DNS Zone to be tranfered&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;description&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Description of the transfer&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;target_project_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Restrict this share request to the specified project&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No - defaults to all projects&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;section id="post-v2-zones-zone-id-tasks-transfer-requests"&gt;
&lt;h4&gt;POST /v2/zones/&amp;lt;zone-id&amp;gt;/tasks/transfer-requests&lt;/h4&gt;
&lt;p&gt;This creates a transfer request for a zone owned by the requesting project.&lt;/p&gt;
&lt;p&gt;It returns an ID and an access key, which should be communicated out of band to
the reciepient (via email / IM etc). They will need both of these to accept the
transfer&lt;/p&gt;
&lt;div class="admonition important"&gt;
&lt;p class="admonition-title"&gt;Important&lt;/p&gt;
&lt;p&gt;There should only be one active transfer request per zone at any
one point in time&lt;/p&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;POST&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/c11ae7e0-f558-11e3-a3ac-0800200c9a66/tasks/transfer-requests&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"Transfer to Developers"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"target_project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"88cbc4c7-1dee-40be-804c-ecf86962198c"&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;201&lt;/span&gt; &lt;span class="ne"&gt;Created&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json; charset=UTF-8&lt;/span&gt;
&lt;span class="na"&gt;Location&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;/v2/zones/c11ae7e0-f558-11e3-a3ac-0800200c9a66/tasks/transfers/cddda8f0-f558-11e3-a3ac-0800200c9a66&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"key"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"tSzpOAoUYXhuKDyugHV4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"target_project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"88cbc4c7-1dee-40be-804c-ecf86962198c"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"Transfer dev-env.example.net to Developers"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"PENDING"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/tasks/transfer-requests/cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;This creates the tranfer request, which can be accepted by the recipent as
detailed below.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="get-v2-zones-zone-id-tasks-transfer-requests"&gt;
&lt;h4&gt;GET /v2/zones/&amp;lt;zone-id&amp;gt;/tasks/transfer-requests&lt;/h4&gt;
&lt;p&gt;This shows the outstanding transfer &lt;strong&gt;FROM&lt;/strong&gt; the requesting project for this
zone.&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/c11ae7e0-f558-11e3-a3ac-0800200c9a66/tasks/transfer-requests&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;200&lt;/span&gt; &lt;span class="ne"&gt;OK&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json; charset=UTF-8&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer_requests"&lt;/span&gt;&lt;span class="p"&gt;:[&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"c11ae7e0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"target_project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"88cbc4c7-1dee-40be-804c-ecf86962198c"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"Transfer to Developers"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"PENDING"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;                        &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/tasks/transfer-requests/cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-v2-zones-tasks-transfer-requests"&gt;
&lt;h4&gt;GET /v2/zones/tasks/transfer-requests&lt;/h4&gt;
&lt;p&gt;This shows the transfer requests for zones currently owned by the &lt;strong&gt;CALLING&lt;/strong&gt;
users project&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/tasks/transfer-requests&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;200&lt;/span&gt; &lt;span class="ne"&gt;OK&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json; charset=UTF-8&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer-requests"&lt;/span&gt;&lt;span class="p"&gt;:[&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"c11ae7e0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"target_project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"88cbc4c7-1dee-40be-804c-ecf86962198c"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"Transfer to Developers"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"PENDING"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/tasks/transfer-requests/cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"102e64fb-8fae-4c5e-9246-96a642822e03"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"05e94130-6356-4687-b5ac-36374f99bf2d"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"Transfer *.www.example.net to web team"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"PENDING"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/tasks/transfer-requests/102e64fb-8fae-4c5e-9246-96a642822e03"&lt;/span&gt;
&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="get-v2-zones-tasks-transfer-request-transfer-id"&gt;
&lt;h4&gt;GET /v2/zones/tasks/transfer-request/&amp;lt;transfer-id&amp;gt;&lt;/h4&gt;
&lt;p&gt;This shows the transfer details. If the ‘target_project_id’ was set, this will
be restricted to that project only.&lt;/p&gt;
&lt;p&gt;The “key” will only be shown to the project that the owns the zone being
transfered.&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/tasks/transfer-requests/cddda8f0-f558-11e3-a3ac-0800200c9a66&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;200&lt;/span&gt; &lt;span class="ne"&gt;OK&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json; charset=UTF-8&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"key"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"tSzpOAoUYXhuKDyugHV4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"target_project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"88cbc4c7-1dee-40be-804c-ecf86962198c"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"c11ae7e0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"Transfer dev-env.example.net to Developers"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"PENDING"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/tasks/transfer-requests/cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="post-v2-zones-tasks-transfer-accept"&gt;
&lt;h4&gt;POST /v2/zones/tasks/transfer-accept/&lt;/h4&gt;
&lt;p&gt;This is how a transfer gets accepted. The accepting project does a POST request
with the key to the tranfer URI. If successful, the API returns a loction
header to the user, with the API location of the zone.&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;POST&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/tasks/transfer-accept&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer_accept"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"key"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"tSzpOAoUYXhuKDyugHV4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;200&lt;/span&gt; &lt;span class="ne"&gt;OK&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json; charset=UTF-8&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer_accept"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"1c914bb0-f580-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"c11ae7e0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"COMPLETE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/tasks/transfer-accept/1c914bb0-f580-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"zone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/c11ae7e0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;A further GET on the transfer-request entity will show the following&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;GET&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/tasks/transfer-request/&amp;lt;transfer-id&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;span class="na"&gt;Accept&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;200&lt;/span&gt; &lt;span class="ne"&gt;OK&lt;/span&gt;
&lt;span class="na"&gt;Content-Type&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="l"&gt;application/json; charset=UTF-8&lt;/span&gt;

&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;"transfer_request"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"key"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"tSzpOAoUYXhuKDyugHV4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"target_project_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"88cbc4c7-1dee-40be-804c-ecf86962198c"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"zone_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"c11ae7e0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"description"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"Transfer dev-env.example.net to Developers"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"status"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="s2"&gt;"COMPLETE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;"links"&lt;/span&gt;&lt;span class="p"&gt;:{&lt;/span&gt;
&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nt"&gt;"self"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"/v2/zones/&amp;lt;zone-id&amp;gt;/tasks/transfer-requests/cddda8f0-f558-11e3-a3ac-0800200c9a66"&lt;/span&gt;
&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id="delete-v2-zones-zone-id-tasks-transfer-requests-request-id"&gt;
&lt;h4&gt;DELETE /v2/zones/&amp;lt;zone-id&amp;gt;/tasks/transfer-requests/&amp;lt;request-id&amp;gt;&lt;/h4&gt;
&lt;p&gt;This allows a user to cancel a tranfer request. This can only be performed
before the tranfer has happened, and &lt;strong&gt;DOES NOT&lt;/strong&gt; cause a tranfer to roll back.&lt;/p&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="nf"&gt;DELETE&lt;/span&gt; &lt;span class="nn"&gt;/v2/zones/tasks/transfer-requests/cddda8f0-f558-11e3-a3ac-0800200c9a66&lt;/span&gt; &lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="highlight-http notranslate"&gt;&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span/&gt;&lt;span class="kr"&gt;HTTP&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="m"&gt;1.1&lt;/span&gt; &lt;span class="m"&gt;204&lt;/span&gt; &lt;span class="ne"&gt;No Content&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="central-changes"&gt;
&lt;h3&gt;Central Changes&lt;/h3&gt;
&lt;p&gt;New Central methods to allow for the CRUD of Transfer Requests.
The Central methods should use currently in place update method for changing
the project ownership of the referenced zone&lt;/p&gt;
&lt;/section&gt;
&lt;section id="storage-changes"&gt;
&lt;h3&gt;Storage Changes&lt;/h3&gt;
&lt;section id="new-table-zonetransferrequesttasks"&gt;
&lt;h4&gt;New Table - ZoneTransferRequestTasks&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Row&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;zone_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;key&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;description&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;VARCHAR&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;project_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The project that created the ZoneTransferRequest&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;target_project_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ENUM(PENDING,COMPLETE,DELETED,ERROR)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;section id="new-table-zonetransferaccepttasks"&gt;
&lt;h4&gt;New Table - ZoneTransferAcceptTasks&lt;/h4&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Row&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Type&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Nullable?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Unique?&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;zone_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;project_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;The ID of the project that accepted the tranfer request&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;transfer_request_id&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;uuid&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Yes&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;status&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;ENUM(COMPLETE,ERROR)&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;No&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="implementation"&gt;
&lt;h2&gt;Implementation&lt;/h2&gt;
&lt;section id="assignee-s"&gt;
&lt;h3&gt;Assignee(s)&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Primary assignee:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~grahamhayes"&gt;https://launchpad.net/~grahamhayes&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Juno-2&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h2&gt;Work Items&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;Tasks Sub API&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;CRUD for the two tasks (Request &amp;amp; Accept)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Moving Zone to new tenant&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;None&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="references"&gt;
&lt;h2&gt;References&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="http://docs.openstack.org/user-guide/content/cli_manage_volumes.html#cli_transfer_volumes"&gt;Cinder Volume Transfer&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="http://lists.openstack.org/pipermail/openstack-dev/2014-May/036416.html"&gt;Glance Functional API Discussion&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 16 Jun 2014 00:00:00 </pubDate></item><item><title>Server Pools</title><link>https://specs.openstack.org/openstack/designate-specs/specs/kilo/server-pools.html</link><description>&lt;p&gt;This work is licensed under a Creative Commons Attribution 3.0 Unported License.
&lt;a class="reference external" href="http://creativecommons.org/licenses/by/3.0/legalcode"&gt;http://creativecommons.org/licenses/by/3.0/legalcode&lt;/a&gt;&lt;/p&gt;
&lt;section id="server-pools"&gt;

&lt;p&gt;&lt;a class="reference external" href="https://blueprints.launchpad.net/designate/+spec/server-pools"&gt;https://blueprints.launchpad.net/designate/+spec/server-pools&lt;/a&gt;&lt;/p&gt;
&lt;section id="problem-description"&gt;
&lt;h2&gt;Problem description&lt;/h2&gt;
&lt;p&gt;Server Pools are required for a few different scenarios:&lt;/p&gt;
&lt;section id="private-pools"&gt;
&lt;h3&gt;Private Pools&lt;/h3&gt;
&lt;p&gt;This allows users to have ‘private’ DNS servers. These servers would typically
allow non standard TLDs (.dev , .local etc), and may not have the same level of
blacklist restrictions. They would be aimed at people with Neutron Networking,
and VPC style set ups, where access to the DNS server would come from trusted
networks (E.G. in-cloud - owned instances, and onsite resources connect by VPN)&lt;/p&gt;
&lt;p&gt;This would allow customers to set DNS entries for internal servers, on domains
that would not be available on the public pools, and have them accessible by
internal users&lt;/p&gt;
&lt;/section&gt;
&lt;section id="distribution"&gt;
&lt;h3&gt;Distribution&lt;/h3&gt;
&lt;p&gt;Having multiple public pools with the same capabilities, would allow the
scheduler to distribute zones across multiple infrastructures.&lt;/p&gt;
&lt;p&gt;As part of the pools change we are also changing how the servers API works,
to allow for more fine grained control of servers, their capabilities and
backends&lt;/p&gt;
&lt;/section&gt;
&lt;section id="features-premium-systems"&gt;
&lt;h3&gt;Features / Premium Systems&lt;/h3&gt;
&lt;p&gt;By using scheduler hints, we can mark different pools as having different
capabilities - such as GeoIP / Round Robin DNS / Anycast.&lt;/p&gt;
&lt;p&gt;This allows operators to run different DNS infrastructures as required.
For example this allow users to have some zones on pools with GeoIP, and pay a
premium for this feature, while having the rest of their zones on a cheaper
‘standard’ tier.&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="proposed-change"&gt;
&lt;h2&gt;Proposed change&lt;/h2&gt;
&lt;section id="terminology"&gt;
&lt;h3&gt;Terminology&lt;/h3&gt;
&lt;p&gt;The terms for different parts of pool manager can be confusing, so the following list should be use when referring to components of Server Pools&lt;/p&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Term&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Meaning&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Also known as&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Server Pool&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;group of DNS servers&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;DNS Zone&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;DNS Zone (aka subzone.domain.com.) more commonly referred to as a domain&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Zone&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;See DNS Zone&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Presentation DNS Server&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Customer Facing DNS server (used by people to resolve zones owned by designate)&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;Name Server&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A FQDN (or IP, but usually a FQDN) that is used to populate the NS Records of a Designate Managed Zone. Each Pool will have a set of Name Servers, which users then delegate to from their registrar&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;nameserver, ns record&lt;/p&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;Backend&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A driver that allows Designate to control a particular type of DNS Server software (BIND, PowerDNS etc)&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;MiniDNS&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;A designate service that is used to send notifies to servers that need to be updated (with new information about Zones), and serves AFXR requests with the new information. There is usually a shared set of MiniDNS servers for all pools&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;FQDN&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;Fully Qualified Domain Name - a DNS entry that has both a hostname section (i.e. ns1. ) and a zone section (including the trailing ‘.’) (i.e. example.com. )&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;This will allow us to split domains between different groups of servers.
This will have a fairly massive impact across the whole system - and will
require changes to nearly every part of Designate.&lt;/p&gt;
&lt;p&gt;We will add 2 major pieces to Designate:&lt;/p&gt;
&lt;/section&gt;
&lt;section id="pool-manager"&gt;
&lt;h3&gt;Pool Manager&lt;/h3&gt;
&lt;p&gt;This is a service that will be responsible for notifying DNS servers that
changes have occured. This will take the backends implemented for MiniDNS, and
load them.&lt;/p&gt;
&lt;p&gt;It will take the place of the miniDNS notifier section, and will be responsible
for checking async operations.&lt;/p&gt;
&lt;/section&gt;
&lt;section id="scheduler"&gt;
&lt;h3&gt;Scheduler&lt;/h3&gt;
&lt;p&gt;This service will be resonsible for assigning zones to pools.&lt;/p&gt;
&lt;p&gt;The scheduler will assign a zone to a pool based on hints in the request, or if
there is no hints in the request, any pool that has capacity.&lt;/p&gt;
&lt;p&gt;Initially for pools there a single ‘default pool’ defined in the config, and overrides will be allowed via the ‘hints’ section of a zone create API request&lt;/p&gt;
&lt;/section&gt;
&lt;section id="flow-of-information-with-server-pools"&gt;
&lt;h3&gt;Flow of information with Server Pools&lt;/h3&gt;
&lt;p&gt;Single Frames available &lt;a class="footnote-reference brackets" href="#id4" id="id1" role="doc-noteref"&gt;&lt;span class="fn-bracket"&gt;[&lt;/span&gt;1&lt;span class="fn-bracket"&gt;]&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;a class="reference external" href="https://wiki.openstack.org/w/images/a/a7/Designate-MiniDNS-Pools.gif"&gt;Overview Image&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;a class="reference external" href="https://wiki.openstack.org/w/images/a/a7/Designate-MiniDNS-Pools.gif"&gt;https://wiki.openstack.org/w/images/a/a7/Designate-MiniDNS-Pools.gif&lt;/a&gt;
&lt;a class="footnote-reference brackets" href="#id5" id="id2" role="doc-noteref"&gt;&lt;span class="fn-bracket"&gt;[&lt;/span&gt;2&lt;span class="fn-bracket"&gt;]&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;We have discusses this in person twice now - once in the Icehouse mid-cycle,
and once in Atlanta at the design summit.&lt;/p&gt;
&lt;p&gt;&lt;a class="reference external" href="https://etherpad.openstack.org/p/juno-design-summit-designate-session-2"&gt;Etherpad&lt;/a&gt;&lt;/p&gt;
&lt;/section&gt;
&lt;section id="milestones"&gt;
&lt;h3&gt;Milestones&lt;/h3&gt;
&lt;dl class="simple"&gt;
&lt;dt&gt;Target Milestone for completion:&lt;/dt&gt;&lt;dd&gt;&lt;p&gt;Kilo-2 &lt;a class="footnote-reference brackets" href="#id6" id="id3" role="doc-noteref"&gt;&lt;span class="fn-bracket"&gt;[&lt;/span&gt;3&lt;span class="fn-bracket"&gt;]&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;/section&gt;
&lt;section id="work-items"&gt;
&lt;h3&gt;Work Items&lt;/h3&gt;
&lt;table class="docutils align-default"&gt;
&lt;thead&gt;
&lt;tr class="row-odd"&gt;&lt;th class="head"&gt;&lt;p&gt;Work Item&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Assignee&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Priority&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Milestone&lt;/p&gt;&lt;/th&gt;
&lt;th class="head"&gt;&lt;p&gt;Notes&lt;/p&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;server-pools-storage&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~rjrjr"&gt;https://launchpad.net/~rjrjr&lt;/a&gt; / &lt;a class="reference external" href="https://launchpad.net/~darshan104"&gt;https://launchpad.net/~darshan104&lt;/a&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;High&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;server-pool-manager&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~rjrjr"&gt;https://launchpad.net/~rjrjr&lt;/a&gt; / &lt;a class="reference external" href="https://launchpad.net/~darshan104"&gt;https://launchpad.net/~darshan104&lt;/a&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;High&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-even"&gt;&lt;td&gt;&lt;p&gt;server-pools-minidns-support&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~vinod-mang"&gt;https://launchpad.net/~vinod-mang&lt;/a&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;High&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;tr class="row-odd"&gt;&lt;td&gt;&lt;p&gt;server-pools-api&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;&lt;a class="reference external" href="https://launchpad.net/~betsy-luzader"&gt;https://launchpad.net/~betsy-luzader&lt;/a&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td&gt;&lt;p&gt;High&lt;/p&gt;&lt;/td&gt;
&lt;td/&gt;
&lt;td/&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id="dependencies"&gt;
&lt;h2&gt;Dependencies&lt;/h2&gt;
&lt;ul class="simple"&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://wiki.openstack.org/wiki/Designate/Blueprints/MiniDNS"&gt;MiniDNS&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id="footnotes"&gt;
&lt;h2&gt;Footnotes&lt;/h2&gt;
&lt;aside class="footnote-list brackets"&gt;
&lt;aside class="footnote brackets" id="id4" role="doc-footnote"&gt;
&lt;span class="label"&gt;&lt;span class="fn-bracket"&gt;[&lt;/span&gt;&lt;a role="doc-backlink" href="#id1"&gt;1&lt;/a&gt;&lt;span class="fn-bracket"&gt;]&lt;/span&gt;&lt;/span&gt;
&lt;p&gt;&lt;a class="reference external" href="https://imgur.com/a/CawLd"&gt;https://imgur.com/a/CawLd&lt;/a&gt;&lt;/p&gt;
&lt;/aside&gt;
&lt;aside class="footnote brackets" id="id5" role="doc-footnote"&gt;
&lt;span class="label"&gt;&lt;span class="fn-bracket"&gt;[&lt;/span&gt;&lt;a role="doc-backlink" href="#id2"&gt;2&lt;/a&gt;&lt;span class="fn-bracket"&gt;]&lt;/span&gt;&lt;/span&gt;
&lt;p&gt;&lt;a class="reference external" href="https://wiki.openstack.org/w/images/a/a7/Designate-MiniDNS-Pools.gif"&gt;https://wiki.openstack.org/w/images/a/a7/Designate-MiniDNS-Pools.gif&lt;/a&gt;&lt;/p&gt;
&lt;/aside&gt;
&lt;aside class="footnote brackets" id="id6" role="doc-footnote"&gt;
&lt;span class="label"&gt;&lt;span class="fn-bracket"&gt;[&lt;/span&gt;&lt;a role="doc-backlink" href="#id3"&gt;3&lt;/a&gt;&lt;span class="fn-bracket"&gt;]&lt;/span&gt;&lt;/span&gt;
&lt;p&gt;&lt;a class="reference external" href="https://wiki.openstack.org/wiki/Juno_Release_Schedule"&gt;https://wiki.openstack.org/wiki/Juno_Release_Schedule&lt;/a&gt;&lt;/p&gt;
&lt;/aside&gt;
&lt;/aside&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 16 Jun 2014 00:00:00 </pubDate></item></channel></rss>