From 1e47e2d5bbdb1ee186dab0ea5da4fbf144092bd9 Mon Sep 17 00:00:00 2001 From: Michal Cichra Date: Thu, 23 Feb 2017 17:48:18 +0100 Subject: [PATCH] [dns] try empty search scope because in some configurations it is possible to have "naked" domain like in docker when linking containers so it is necessary to query for "redis." not for "redis" --- CHANGELOG.md | 1 + apicast/src/resty/resolver.lua | 32 +++++++++----------------------- docker-compose.yml | 6 ++++++ spec/resty/resolver_spec.lua | 12 ++++++------ 4 files changed, 22 insertions(+), 29 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index fc9e3608a..cf30b6a8c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/). - Use stale DNS cache when there is a query in progress for that record [PR #260](https://github.com/3scale/apicast/pull/260) - Bump s2i-openresty to 1.11.2.2-2 [PR #260](https://github.com/3scale/apicast/pull/260) - Echo API on port 8081 listens accepts any Host [PR #268](https://github.com/3scale/apicast/pull/268) +- Always use DNS search scopes [PR #271](https://github.com/3scale/apicast/pull/271) ### Added diff --git a/apicast/src/resty/resolver.lua b/apicast/src/resty/resolver.lua index f97b46219..d62c1ed39 100644 --- a/apicast/src/resty/resolver.lua +++ b/apicast/src/resty/resolver.lua @@ -31,7 +31,7 @@ local default_resolver_port = 53 local _M = { _VERSION = '0.1', _nameservers = {}, - search = {} + search = { '' } } local mt = { __index = _M } @@ -67,7 +67,7 @@ function _M.parse_nameservers(path) ngx.log(ngx.DEBUG, '/etc/resolv.conf:\n', resolv_conf) - local search = {} + local search = { '' } local nameservers = { search = search } local resolver = getenv('RESOLVER') local domains = match(resolv_conf, 'search%s+([^\n]+)') @@ -185,14 +185,6 @@ local function is_ip(address) end end -local function has_tld(qname) - return match(qname, '%.') -end - -local function have_addresses(answers) - return answers and next(answers.addresses or {}) and #answers > 0 and not answers.errcode -end - local function convert_answers(answers, port) local servers = {} @@ -216,18 +208,13 @@ local function lookup(dns, qname, search, options) ngx.log(ngx.DEBUG, 'host is ip address: ', qname) answers = { new_answer(qname) } else - answers, err = dns:query(qname, options) + for i=1, #search do + local query = qname .. '.' .. search[i] + ngx.log(ngx.DEBUG, 'resolver query: ', qname, ' search: ', search[i], ' query: ', query) + answers, err = dns:query(query, options) - if not has_tld(qname) and not have_addresses(answers) then - for i=1, #search do - - local query = qname .. '.' .. search[i] - ngx.log(ngx.DEBUG, 'resolver query: ', qname, ' search: ', search[i], ' query: ', query) - answers, err = dns:query(query, options) - - if answers and not answers.errcode and #answers > 0 then - break - end + if answers and not answers.errcode and #answers > 0 then + break end end end @@ -249,8 +236,7 @@ function _M.get_servers(self, qname, opts) end local cache = self.cache - local search = self.search or {} - + local search = self.search or _M.search -- TODO: pass proper options to dns resolver (like SRV query type) diff --git a/docker-compose.yml b/docker-compose.yml index 497f59e09..f99c8aa3a 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -21,12 +21,16 @@ services: environment: TEST_NGINX_BINARY: openresty TEST_NGINX_REDIS_HOST: redis + dns_search: + - example.com test: image: ${IMAGE_NAME} depends_on: - gateway entrypoint: "" dns: 127.0.0.1 + dns_search: + - example.com prove: image: ${IMAGE_NAME} user: root @@ -35,6 +39,8 @@ services: TEST_NGINX_APICAST_PATH: /opt/app TEST_NGINX_REDIS_HOST: redis command: prove + dns_search: + - example.com depends_on: - redis volumes: diff --git a/spec/resty/resolver_spec.lua b/spec/resty/resolver_spec.lua index 642c1f9af..5f8a85dbe 100644 --- a/spec/resty/resolver_spec.lua +++ b/spec/resty/resolver_spec.lua @@ -48,7 +48,7 @@ describe('resty.resolver', function() assert.falsy(err) assert.equal(1, #servers) - assert.spy(dns.query).was.called_with(dns, '3scale.net', { qtype = 'A' }) + assert.spy(dns.query).was.called_with(dns, '3scale.net.', { qtype = 'A' }) end) it('skips answers with no address', function() @@ -63,7 +63,7 @@ describe('resty.resolver', function() assert.falsy(err) assert.equal(1, #servers) - assert.spy(dns.query).was.called_with(dns, 'www.3scale.net', {}) + assert.spy(dns.query).was.called_with(dns, 'www.3scale.net.', {}) end) it('searches domains', function() @@ -77,13 +77,13 @@ describe('resty.resolver', function() end end) resolver.options = { qtype = 'A' } - resolver.search = { 'example.com', 'net' } + resolver.search = { '', 'example.com', 'net' } local servers, err = resolver:get_servers('3scale') assert.falsy(err) assert.equal(1, #servers) - assert.spy(dns.query).was.called_with(dns, '3scale', resolver.options) + assert.spy(dns.query).was.called_with(dns, '3scale.', resolver.options) assert.spy(dns.query).was.called_with(dns, '3scale.example.com', resolver.options) assert.spy(dns.query).was.called_with(dns, '3scale.net', resolver.options) end) @@ -139,8 +139,8 @@ describe('resty.resolver', function() it('returns search domains', function() local search = resty_resolver.parse_nameservers(tmpname).search - assert.equal(2, #search) - assert.same({ 'localdomain.example.com', 'local' }, search) + assert.equal(3, #search) + assert.same({ '', 'localdomain.example.com', 'local' }, search) end) end)