vagrant-powerdns 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +12 -0
- data/.ruby-version +1 -0
- data/Gemfile +13 -0
- data/LICENSE.txt +22 -0
- data/README.md +37 -0
- data/Rakefile +3 -0
- data/bin/console +14 -0
- data/bin/setup +7 -0
- data/lib/vagrant-powerdns/action/add_record.rb +0 -0
- data/lib/vagrant-powerdns/action/del_record.rb +0 -0
- data/lib/vagrant-powerdns/action.rb +146 -0
- data/lib/vagrant-powerdns/config.rb +80 -0
- data/lib/vagrant-powerdns/errors.rb +17 -0
- data/lib/vagrant-powerdns/includes/Ip.class.rb +31 -0
- data/lib/vagrant-powerdns/includes/Zone.class.rb +41 -0
- data/lib/vagrant-powerdns/util/pdns_api.rb +177 -0
- data/lib/vagrant-powerdns/version.rb +5 -0
- data/lib/vagrant-powerdns.rb +45 -0
- data/locales/en.yml +15 -0
- data/vagrant-powerdns.gemspec +28 -0
- metadata +120 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 5b98ac2809c2093b13f504075eec9735f4481722
|
4
|
+
data.tar.gz: 3cda97d2e2071e4dc42c72f7a03c4cc431ec1d18
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 6fe362fb842a4b5502f5c53e049d968048f216e48f5d3dd85190c94bbe4799d57fef412b5b977ca25b4d85655bae4edb1246d6ab1d30c70cf12219637ba2b3d2
|
7
|
+
data.tar.gz: 71767572bba48605415ffd2febc5b56a09e5bf7fab432e8d186013337ca606d08295ffdc58b2f7ce583fcce0a177b48bc0bcf76c09d4dea5bdf00c9f1d310d9a
|
data/.gitignore
ADDED
data/.ruby-version
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
2.2.3
|
data/Gemfile
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
source "https://rubygems.org"
|
2
|
+
|
3
|
+
group :development do
|
4
|
+
gem "vagrant", git: "https://github.com/mitchellh/vagrant.git"
|
5
|
+
end
|
6
|
+
|
7
|
+
group :plugins do
|
8
|
+
# gem "vagrant-env"
|
9
|
+
# gem "pry-byebug"
|
10
|
+
# gem "httparty"
|
11
|
+
# gem "vagrant-xenserver", :path => "/Users/ayik/Repositories/xen/vagrant-xenserver"
|
12
|
+
gem "vagrant-powerdns", path: "."
|
13
|
+
end
|
data/LICENSE.txt
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
The MIT License (MIT)
|
2
|
+
|
3
|
+
Copyright (c) 2016 Sayid Munawar
|
4
|
+
Copyright (c) 2013 Matthias Kadenbach (https://github.com/mattes/vagrant-dnsmasq)
|
5
|
+
|
6
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
7
|
+
of this software and associated documentation files (the "Software"), to deal
|
8
|
+
in the Software without restriction, including without limitation the rights
|
9
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
10
|
+
copies of the Software, and to permit persons to whom the Software is
|
11
|
+
furnished to do so, subject to the following conditions:
|
12
|
+
|
13
|
+
The above copyright notice and this permission notice shall be included in
|
14
|
+
all copies or substantial portions of the Software.
|
15
|
+
|
16
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
17
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
18
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
19
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
20
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
21
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
22
|
+
THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,37 @@
|
|
1
|
+
# Vagrant PowerDNS
|
2
|
+
|
3
|
+
This Vagrant Plugins manage DNS `A` Record whenever you do `vagrant up` or `vagrant destroy`. Tested with old/compatible API of PowerDNS 4, so it should be configured with `last-3x-compat` tag
|
4
|
+
|
5
|
+
## Installation
|
6
|
+
|
7
|
+
$ vagrant plugin install vagrant-powerdns
|
8
|
+
|
9
|
+
## Usage
|
10
|
+
|
11
|
+
Vagrantfile Example
|
12
|
+
|
13
|
+
```ruby
|
14
|
+
VAGRANTFILE_API_VERSION = "2"
|
15
|
+
|
16
|
+
Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
|
17
|
+
config.vm.box = "centos7"
|
18
|
+
config.vm.hostname = "ayik"
|
19
|
+
|
20
|
+
# PowerDNS API Configuration
|
21
|
+
config.powerdns.api_url = "http://powerdns:8081"
|
22
|
+
config.powerdns.api_key = "rahasia"
|
23
|
+
config.powerdns.default_zone = "dev.example.com"
|
24
|
+
|
25
|
+
config.vm.network "public_network", ip: "192.168.2.2"
|
26
|
+
end
|
27
|
+
```
|
28
|
+
|
29
|
+
## Contributing
|
30
|
+
|
31
|
+
Bug reports and pull requests are welcome on GitHub at https://github.com/chenull/vagrant-powerdns.
|
32
|
+
|
33
|
+
|
34
|
+
## License
|
35
|
+
|
36
|
+
The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
|
37
|
+
|
data/Rakefile
ADDED
data/bin/console
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require "bundler/setup"
|
4
|
+
require "vagrant-powerdns"
|
5
|
+
|
6
|
+
# You can add fixtures and/or initialization code here to make experimenting
|
7
|
+
# with your gem easier. You can also use a different console, if you like.
|
8
|
+
|
9
|
+
# (If you use this, don't forget to add pry to your Gemfile!)
|
10
|
+
# require "pry"
|
11
|
+
# Pry.start
|
12
|
+
|
13
|
+
require "irb"
|
14
|
+
IRB.start
|
data/bin/setup
ADDED
File without changes
|
File without changes
|
@@ -0,0 +1,146 @@
|
|
1
|
+
module Vagrant
|
2
|
+
module Action
|
3
|
+
|
4
|
+
class Up
|
5
|
+
def initialize(app, env)
|
6
|
+
@app = app
|
7
|
+
@machine = env[:machine]
|
8
|
+
@host = env[:machine].config.vm.hostname.nil? ?
|
9
|
+
env[:machine].name.to_s : env[:machine].config.vm.hostname.to_s
|
10
|
+
@domain = @host + env[:machine].config.powerdns.default_zone.to_s
|
11
|
+
@zone = env[:machine].config.powerdns.default_zone.name
|
12
|
+
|
13
|
+
# Identify who i am
|
14
|
+
@myname = Etc.getpwuid[:gecos]
|
15
|
+
@myuser = Etc.getlogin.gsub(/\s+/, '')
|
16
|
+
@myhost = Socket.gethostname
|
17
|
+
end
|
18
|
+
|
19
|
+
def call(env)
|
20
|
+
if @machine.config.powerdns.enabled?
|
21
|
+
# assume default gateway address
|
22
|
+
@machine.communicate.sudo "ip route get to 8.8.8.8 | head -n 1" do |type,data|
|
23
|
+
stdout = data.chomp if type == :stdout
|
24
|
+
if !stdout.empty?
|
25
|
+
re = /src ([0-9\.]+)/
|
26
|
+
ip = stdout.match(re)[1]
|
27
|
+
|
28
|
+
p = PdnsRestApiClient.new(env[:machine].config.powerdns.api_url,
|
29
|
+
env[:machine].config.powerdns.api_key)
|
30
|
+
|
31
|
+
# Only update if IP changed
|
32
|
+
if p.zone(@zone)["records"].select { |v| v["type"] == "A" and
|
33
|
+
v["name"] == @domain and v["content"] == ip}.empty?
|
34
|
+
|
35
|
+
env[:ui].info "PowerDNS action..."
|
36
|
+
# Append new comment
|
37
|
+
new_comment = {
|
38
|
+
content: "#{@myname} (#{@myuser}) added this record from #{@myhost}",
|
39
|
+
account: @myname,
|
40
|
+
name: @domain,
|
41
|
+
type: "A"
|
42
|
+
}
|
43
|
+
comments = p.zone(@zone)["comments"].delete_if { |v| v["name"] != @domain }
|
44
|
+
comments << new_comment
|
45
|
+
|
46
|
+
ret = p.modify_domain(domain: @domain, ip: ip, zone_id: @zone,
|
47
|
+
comments: comments)
|
48
|
+
|
49
|
+
# Check return
|
50
|
+
error = nil
|
51
|
+
if ret.is_a?(String)
|
52
|
+
error = ret
|
53
|
+
else
|
54
|
+
if ret.is_a?(Hash)
|
55
|
+
error = ret.values[0] if ret.keys[0] == "error"
|
56
|
+
else
|
57
|
+
raise "Unknown esponse from PowerDNS API"
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
# Display ui
|
62
|
+
if error.nil?
|
63
|
+
env[:ui].detail "=> record #{@domain}(#{ip}) in zone #{@zone} added !"
|
64
|
+
else
|
65
|
+
env[:ui].detail "=> failed to add record #{@domain}(#{ip}) in zone #{@zone}. Error was: #{error}"
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
@app.call(env)
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
|
77
|
+
class Destroy
|
78
|
+
def initialize(app, env)
|
79
|
+
@app = app
|
80
|
+
@machine = env[:machine]
|
81
|
+
@host = env[:machine].config.vm.hostname.nil? ?
|
82
|
+
env[:machine].name.to_s : env[:machine].config.vm.hostname.to_s
|
83
|
+
@domain = @host + env[:machine].config.powerdns.default_zone.to_s
|
84
|
+
@zone = env[:machine].config.powerdns.default_zone.name
|
85
|
+
|
86
|
+
# Identify who i am
|
87
|
+
@myname = Etc.getpwuid[:gecos]
|
88
|
+
@myuser = Etc.getlogin.gsub(/\s+/, '')
|
89
|
+
@myhost = Socket.gethostname
|
90
|
+
end
|
91
|
+
|
92
|
+
def call(env)
|
93
|
+
if @machine.config.powerdns.enabled?
|
94
|
+
p = PdnsRestApiClient.new(env[:machine].config.powerdns.api_url,
|
95
|
+
env[:machine].config.powerdns.api_key)
|
96
|
+
|
97
|
+
# Get A record
|
98
|
+
record = p.zone(@zone)
|
99
|
+
|
100
|
+
# only disable if active
|
101
|
+
if not record["records"].find {|v| v["name"] == @domain}["disabled"]
|
102
|
+
env[:ui].info "PowerDNS action..."
|
103
|
+
|
104
|
+
# Prepare comment to be appended
|
105
|
+
new_comment = {
|
106
|
+
content: "#{@myname} (#{@myuser}) disabled this record from #{@myhost}",
|
107
|
+
account: @myname,
|
108
|
+
name: @domain,
|
109
|
+
type: "A"
|
110
|
+
}
|
111
|
+
comments = record["comments"].delete_if { |v| v["name"] != @domain }
|
112
|
+
comments << new_comment
|
113
|
+
|
114
|
+
# Get the old IP
|
115
|
+
ip = record["records"].find {|v| v["name"] == @domain}["content"]
|
116
|
+
|
117
|
+
ret = p.disable_domain(domain: @domain, ip: ip, zone_id: @zone,
|
118
|
+
comments: comments)
|
119
|
+
|
120
|
+
# Check return
|
121
|
+
error = nil
|
122
|
+
if ret.is_a?(String)
|
123
|
+
error = ret
|
124
|
+
else
|
125
|
+
if ret.is_a?(Hash)
|
126
|
+
error = ret.values[0] if ret.keys[0] == "error"
|
127
|
+
else
|
128
|
+
raise "Unknown esponse from PowerDNS API"
|
129
|
+
end
|
130
|
+
end
|
131
|
+
|
132
|
+
# Display ui
|
133
|
+
if error.nil?
|
134
|
+
env[:ui].detail "=> record #{@domain}(#{ip}) in zone #{@zone} disabled !"
|
135
|
+
else
|
136
|
+
env[:ui].detail "=> failed to disab;e record #{@domain} in zone #{@zone}. Error was: #{error}"
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
@app.call(env)
|
141
|
+
end
|
142
|
+
end
|
143
|
+
end
|
144
|
+
|
145
|
+
end
|
146
|
+
end
|
@@ -0,0 +1,80 @@
|
|
1
|
+
module Vagrant
|
2
|
+
module PowerDNS
|
3
|
+
class Config < Vagrant.plugin("2", :config)
|
4
|
+
|
5
|
+
attr_accessor :api_url
|
6
|
+
attr_accessor :api_key
|
7
|
+
attr_accessor :default_zone
|
8
|
+
attr_accessor :disable
|
9
|
+
|
10
|
+
def initialize
|
11
|
+
@api_url = UNSET_VALUE
|
12
|
+
@api_key = UNSET_VALUE
|
13
|
+
@default_zone = UNSET_VALUE
|
14
|
+
@disable = UNSET_VALUE
|
15
|
+
end
|
16
|
+
|
17
|
+
def finalize!
|
18
|
+
|
19
|
+
if @default_zone == UNSET_VALUE
|
20
|
+
@default_zone = nil
|
21
|
+
elsif !@default_zone.is_a?(Zone)
|
22
|
+
@default_zone = Zone.new @default_zone;
|
23
|
+
end
|
24
|
+
|
25
|
+
@disable = false if @disable == UNSET_VALUE
|
26
|
+
|
27
|
+
# default way to obtain ip address
|
28
|
+
if @ip == UNSET_VALUE
|
29
|
+
@ip = proc do |guest_machine|
|
30
|
+
ips = nil
|
31
|
+
puts "SUDO SUUUUUU............"
|
32
|
+
guest_machine.communicate.sudo("hostname -I") do |type, data|
|
33
|
+
ips = data.scan /[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}/
|
34
|
+
end
|
35
|
+
ips
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
end
|
40
|
+
|
41
|
+
def enabled?
|
42
|
+
not @disable and not @api_url.nil? and not @api_key.nil?
|
43
|
+
end
|
44
|
+
|
45
|
+
def validate(machine)
|
46
|
+
return unless enabled?
|
47
|
+
|
48
|
+
errors = []
|
49
|
+
|
50
|
+
# verify @disable
|
51
|
+
if @disable != true and @disable != false then errors << 'invalid disable setting' end
|
52
|
+
|
53
|
+
# verify zone
|
54
|
+
begin @default_zone = Zone.new @default_zone; rescue => e; errors << e.message end
|
55
|
+
|
56
|
+
# verify ip
|
57
|
+
if @ip.is_a? Array
|
58
|
+
@ip.map!{|ip| begin Ip.new(ip); rescue => e; errors << e.message end}
|
59
|
+
|
60
|
+
elsif @ip.is_a? String
|
61
|
+
begin @ip = Ip.new(@ip); rescue => e; errors << e.message end
|
62
|
+
@ip = [@ip]
|
63
|
+
|
64
|
+
elsif @ip.is_a? Proc
|
65
|
+
# okay, there is nothing to verify at the moment
|
66
|
+
else
|
67
|
+
@ip = nil
|
68
|
+
end
|
69
|
+
|
70
|
+
# verify API URL/key
|
71
|
+
#if @resolver
|
72
|
+
# errors << "file '#{@dnsmasqconf}' does not exist" unless File.exists? @dnsmasqconf
|
73
|
+
#end
|
74
|
+
|
75
|
+
return { 'PowerDNS configuration' => errors }
|
76
|
+
end
|
77
|
+
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
require "vagrant"
|
2
|
+
|
3
|
+
module Vagrant
|
4
|
+
module PowerDNS
|
5
|
+
module Errors
|
6
|
+
class PowerDNSError < Vagrant::Errors::VagrantError
|
7
|
+
error_namespace("vagrant_powerdns.errors")
|
8
|
+
end
|
9
|
+
|
10
|
+
class APIError < PowerDNSError
|
11
|
+
error_key(:api_error)
|
12
|
+
end
|
13
|
+
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
@@ -0,0 +1,31 @@
|
|
1
|
+
# Copyright (c) 2013 Matthias Kadenbach
|
2
|
+
# https://github.com/mattes/vagrant-dnsmasq
|
3
|
+
|
4
|
+
class Ip
|
5
|
+
|
6
|
+
MATCH_IP4 = /^(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]{1,2})(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]{1,2})){3}$/
|
7
|
+
|
8
|
+
def initialize(ipv4)
|
9
|
+
|
10
|
+
if ipv4.is_a? Ip
|
11
|
+
ipv4 = ipv4.v4
|
12
|
+
end
|
13
|
+
|
14
|
+
raise ArgumentError, "IPv4 '#{ipv4}' must match #{MATCH_IP4}" unless Ip::ipv4_valid?(ipv4)
|
15
|
+
|
16
|
+
@ipv4 = ipv4
|
17
|
+
end
|
18
|
+
|
19
|
+
def self.ipv4_valid?(ipv4)
|
20
|
+
if not ipv4.blank? and Ip::MATCH_IP4.match(ipv4) then true else false end
|
21
|
+
end
|
22
|
+
|
23
|
+
def v4
|
24
|
+
@ipv4
|
25
|
+
end
|
26
|
+
|
27
|
+
def to_s
|
28
|
+
v4
|
29
|
+
end
|
30
|
+
|
31
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
# Copyright (c) 2013 Matthias Kadenbach
|
2
|
+
# https://github.com/mattes/vagrant-dnsmasq
|
3
|
+
|
4
|
+
class Zone
|
5
|
+
|
6
|
+
MATCH = /^[a-z0-9]+([\-\.]{1}[a-z0-9]+)*$/
|
7
|
+
|
8
|
+
def initialize(name)
|
9
|
+
@name = nil
|
10
|
+
|
11
|
+
if name.is_a? Zone
|
12
|
+
name = name.dotted
|
13
|
+
end
|
14
|
+
|
15
|
+
raise ArgumentError, "no domain name given" if name.empty?
|
16
|
+
|
17
|
+
# parse domain name ...
|
18
|
+
name = name.to_s
|
19
|
+
name = name[1..-1] if name.start_with? '.'
|
20
|
+
name = name.downcase
|
21
|
+
raise ArgumentError, "Zone '#{name}' must match #{MATCH}" unless Zone::valid?(name)
|
22
|
+
@name = name # without leading .
|
23
|
+
end
|
24
|
+
|
25
|
+
def self.valid?(name)
|
26
|
+
if not name.empty? and Zone::MATCH.match(name.downcase) then true else false end
|
27
|
+
end
|
28
|
+
|
29
|
+
def dotted
|
30
|
+
'.' + @name
|
31
|
+
end
|
32
|
+
|
33
|
+
def name
|
34
|
+
@name
|
35
|
+
end
|
36
|
+
|
37
|
+
def to_s
|
38
|
+
dotted
|
39
|
+
end
|
40
|
+
|
41
|
+
end
|
@@ -0,0 +1,177 @@
|
|
1
|
+
# Copyright 2015 Arnoud Vermeer (https://github.com/funzoneq/powerdns-rest-api-client)
|
2
|
+
#
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
4
|
+
# you may not use this file except in compliance with the License.
|
5
|
+
# You may obtain a copy of the License at
|
6
|
+
#
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
8
|
+
#
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
12
|
+
# See the License for the specific language governing permissions and
|
13
|
+
# limitations under the License.
|
14
|
+
|
15
|
+
require 'httparty'
|
16
|
+
require 'json'
|
17
|
+
|
18
|
+
# A class to interact with the PowerDNS REST API
|
19
|
+
# https://doc.powerdns.com/md/httpapi/api_spec/
|
20
|
+
class PdnsRestApiClient
|
21
|
+
include HTTParty
|
22
|
+
attr_accessor :base_uri
|
23
|
+
|
24
|
+
def initialize(base_uri, api_key)
|
25
|
+
self.class.base_uri base_uri
|
26
|
+
|
27
|
+
self.class.headers 'X-API-Key' => api_key
|
28
|
+
|
29
|
+
@api_key = api_key
|
30
|
+
end
|
31
|
+
|
32
|
+
def servers
|
33
|
+
self.class.get('/servers')
|
34
|
+
end
|
35
|
+
|
36
|
+
def server(server_id)
|
37
|
+
self.class.get("/servers/#{server_id}")
|
38
|
+
end
|
39
|
+
|
40
|
+
def config(server_id)
|
41
|
+
self.class.get("/servers/#{server_id}/config")
|
42
|
+
end
|
43
|
+
|
44
|
+
def setting(server_id, config_setting_name)
|
45
|
+
self.class.get("/servers/#{server_id}/config/#{config_setting_name}")
|
46
|
+
end
|
47
|
+
|
48
|
+
def zones(server_id='localhost')
|
49
|
+
self.class.get("/servers/#{server_id}/zones")
|
50
|
+
end
|
51
|
+
|
52
|
+
def zone(zone_id, server_id='localhost')
|
53
|
+
self.class.get("/servers/#{server_id}/zones/#{zone_id}")
|
54
|
+
end
|
55
|
+
|
56
|
+
def modify_zone(zone, server_id='localhost')
|
57
|
+
self.class.post("/servers/#{server_id}/zones", body: zone.to_json)
|
58
|
+
end
|
59
|
+
|
60
|
+
def create_zone(domain, nsServers=[], kind='Native', masters=[], server_id='localhost')
|
61
|
+
zone = { name: domain, kind: kind, masters: masters, nameservers: nsServers }
|
62
|
+
|
63
|
+
modify_zone(zone, server_id)
|
64
|
+
end
|
65
|
+
|
66
|
+
def delete_zone(zone_id, server_id='localhost')
|
67
|
+
self.class.delete("/servers/#{server_id}/zones/#{zone_id}")
|
68
|
+
end
|
69
|
+
|
70
|
+
def notify(zone_id, server_id='localhost')
|
71
|
+
self.class.put("/servers/#{server_id}/zones/#{zone_id}/notify")
|
72
|
+
end
|
73
|
+
|
74
|
+
def axfr_retrieve(zone_id, server_id='localhost')
|
75
|
+
self.class.put("/servers/#{server_id}/zones/#{zone_id}/axfr-retrieve")
|
76
|
+
end
|
77
|
+
|
78
|
+
def zone_export(zone_id, server_id='localhost')
|
79
|
+
self.class.get("/servers/#{server_id}/zones/#{zone_id}/export")
|
80
|
+
end
|
81
|
+
|
82
|
+
def search_log(search_term, server_id='localhost')
|
83
|
+
self.class.get("/servers/#{server_id}/search-log", query: { q: search_term })
|
84
|
+
end
|
85
|
+
|
86
|
+
def stats(server_id='localhost')
|
87
|
+
self.class.get("/servers/#{server_id}/statistics")
|
88
|
+
end
|
89
|
+
|
90
|
+
def get_comments(domain, zone_id, server_id='localhost')
|
91
|
+
puts
|
92
|
+
end
|
93
|
+
|
94
|
+
def modify_domain(domain:, ip:, zone_id:, server_id:'localhost', comments: nil)
|
95
|
+
# {
|
96
|
+
# :rrsets => [
|
97
|
+
# [0] {
|
98
|
+
# :name => "gundul.dev.jcamp.net",
|
99
|
+
# :type => "A",
|
100
|
+
# :records => [
|
101
|
+
# [0] {
|
102
|
+
# :name => "gundul.dev.jcamp.net",
|
103
|
+
# :type => "A",
|
104
|
+
# :ttl => 3600,
|
105
|
+
# :disabled => false,
|
106
|
+
# :content => "192.168.10.11"
|
107
|
+
# }
|
108
|
+
# ],
|
109
|
+
# :comments => [
|
110
|
+
# [0] {
|
111
|
+
# :name => "gundul.dev.jcamp.net",
|
112
|
+
# :type => "A",
|
113
|
+
# :modified_at => 1461239952,
|
114
|
+
# :account => "ayik",
|
115
|
+
# :content => "NGopoE cuk..."
|
116
|
+
# }
|
117
|
+
# ],
|
118
|
+
# :changetype => "replace"
|
119
|
+
# }
|
120
|
+
# ]
|
121
|
+
# }
|
122
|
+
@body = {
|
123
|
+
rrsets: [
|
124
|
+
{
|
125
|
+
name: domain,
|
126
|
+
type: "A",
|
127
|
+
records: [
|
128
|
+
{
|
129
|
+
name: domain,
|
130
|
+
type: "A",
|
131
|
+
ttl: 300,
|
132
|
+
disabled: false,
|
133
|
+
content: ip
|
134
|
+
}
|
135
|
+
],
|
136
|
+
changetype: "replace"
|
137
|
+
}
|
138
|
+
]
|
139
|
+
}
|
140
|
+
if !comments.nil?
|
141
|
+
@body[:rrsets][0][:comments] = comments
|
142
|
+
end
|
143
|
+
self.class.patch("/servers/#{server_id}/zones/#{zone_id}", body: @body.to_json)
|
144
|
+
end
|
145
|
+
|
146
|
+
def disable_domain(domain:, zone_id:, ip:, server_id:'localhost', comments: nil)
|
147
|
+
@body = {
|
148
|
+
rrsets: [
|
149
|
+
{
|
150
|
+
name: domain,
|
151
|
+
type: "A",
|
152
|
+
records: [
|
153
|
+
{
|
154
|
+
name: domain,
|
155
|
+
type: "A",
|
156
|
+
ttl: 300,
|
157
|
+
content: ip,
|
158
|
+
disabled: true
|
159
|
+
}
|
160
|
+
],
|
161
|
+
changetype: "replace"
|
162
|
+
}
|
163
|
+
]
|
164
|
+
}
|
165
|
+
if !comments.nil?
|
166
|
+
@body[:rrsets][0][:comments] = comments
|
167
|
+
end
|
168
|
+
self.class.patch("/servers/#{server_id}/zones/#{zone_id}", body: @body.to_json)
|
169
|
+
end
|
170
|
+
# def trace(server_id='localhost')
|
171
|
+
# self.class.get("/servers/#{server_id}/trace")
|
172
|
+
# end
|
173
|
+
|
174
|
+
# def zone_check(zone_id, server_id='localhost')
|
175
|
+
# self.class.get("/servers/#{server_id}/zones/#{zone_id}/check")
|
176
|
+
# end
|
177
|
+
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
begin
|
2
|
+
require "vagrant"
|
3
|
+
rescue LoadError
|
4
|
+
raise "The Vagrant-PowerDNS plugin must be run within Vagrant."
|
5
|
+
end
|
6
|
+
|
7
|
+
|
8
|
+
module Vagrant
|
9
|
+
module PowerDNS
|
10
|
+
class Plugin < Vagrant.plugin("2")
|
11
|
+
name "vagrant-powerdns"
|
12
|
+
description "A PowerDNS Vagrant plugin that manages the zone record via vagrant up/destroy"
|
13
|
+
|
14
|
+
inc_path = Pathname.new(File.expand_path("../vagrant-powerdns/includes", __FILE__))
|
15
|
+
require inc_path.join("Zone.class.rb")
|
16
|
+
require inc_path.join("Ip.class.rb")
|
17
|
+
|
18
|
+
util_path = Pathname.new(File.expand_path("../vagrant-powerdns/util", __FILE__))
|
19
|
+
require util_path.join("pdns_api")
|
20
|
+
|
21
|
+
lib_path = Pathname.new(File.expand_path("../vagrant-powerdns", __FILE__))
|
22
|
+
require lib_path.join("action")
|
23
|
+
|
24
|
+
config "powerdns" do
|
25
|
+
require lib_path.join("config")
|
26
|
+
Config
|
27
|
+
end
|
28
|
+
|
29
|
+
action_hook(:powerdns, :machine_action_up) do |hook|
|
30
|
+
hook.append(Vagrant::Action::Up)
|
31
|
+
end
|
32
|
+
|
33
|
+
action_hook(:powerdns, :machine_action_destroy) do |hook|
|
34
|
+
hook.append(Vagrant::Action::Destroy)
|
35
|
+
end
|
36
|
+
|
37
|
+
autoload :Errors, lib_path.join("errors")
|
38
|
+
|
39
|
+
source_root ||= Pathname.new(File.expand_path("../../", __FILE__))
|
40
|
+
I18n.load_path << File.expand_path('locales/en.yml', source_root)
|
41
|
+
I18n.reload!
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
end
|
data/locales/en.yml
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
en:
|
2
|
+
vagrant_powerdns:
|
3
|
+
config:
|
4
|
+
api_url: |-
|
5
|
+
powerdns URL must be defined via "api_url"
|
6
|
+
api_key: |-
|
7
|
+
powerdns API Key must be defined via "api_key"
|
8
|
+
errors:
|
9
|
+
api_error: |-
|
10
|
+
API authentication error. Please check "api_url" and "api_key"
|
11
|
+
info:
|
12
|
+
post_record: |-
|
13
|
+
Creating record %{host} with address %{ip} into zone %{zone}
|
14
|
+
delete_record: |-
|
15
|
+
Deleting record %{host} from zone %{zone}
|
@@ -0,0 +1,28 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'vagrant-powerdns/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "vagrant-powerdns"
|
8
|
+
spec.version = Vagrant::PowerDNS::VERSION
|
9
|
+
spec.authors = ["Sayid Munawar"]
|
10
|
+
spec.email = ["sayid.munawar@gmail.com"]
|
11
|
+
|
12
|
+
spec.summary = "Vagrant plugin to manage powerdns zone record"
|
13
|
+
spec.description = "This plugin will push changes to PowerDNS API after vagrant up / halt"
|
14
|
+
spec.homepage = "https://github.com/chenull/vagrant-powerdns"
|
15
|
+
spec.license = "MIT"
|
16
|
+
|
17
|
+
spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
18
|
+
spec.bindir = "exe"
|
19
|
+
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
20
|
+
spec.require_paths = ["lib"]
|
21
|
+
|
22
|
+
spec.add_development_dependency "bundler", "~> 1.10"
|
23
|
+
spec.add_development_dependency "rake", "~> 10.0"
|
24
|
+
|
25
|
+
spec.add_runtime_dependency "httparty", "~> 0.13.7"
|
26
|
+
spec.add_runtime_dependency "json"
|
27
|
+
|
28
|
+
end
|
metadata
ADDED
@@ -0,0 +1,120 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: vagrant-powerdns
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Sayid Munawar
|
8
|
+
autorequire:
|
9
|
+
bindir: exe
|
10
|
+
cert_chain: []
|
11
|
+
date: 2016-04-21 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: bundler
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '1.10'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '1.10'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: rake
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '10.0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '10.0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: httparty
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - "~>"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: 0.13.7
|
48
|
+
type: :runtime
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - "~>"
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: 0.13.7
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: json
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :runtime
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - ">="
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
69
|
+
description: This plugin will push changes to PowerDNS API after vagrant up / halt
|
70
|
+
email:
|
71
|
+
- sayid.munawar@gmail.com
|
72
|
+
executables: []
|
73
|
+
extensions: []
|
74
|
+
extra_rdoc_files: []
|
75
|
+
files:
|
76
|
+
- ".gitignore"
|
77
|
+
- ".ruby-version"
|
78
|
+
- Gemfile
|
79
|
+
- LICENSE.txt
|
80
|
+
- README.md
|
81
|
+
- Rakefile
|
82
|
+
- bin/console
|
83
|
+
- bin/setup
|
84
|
+
- lib/vagrant-powerdns.rb
|
85
|
+
- lib/vagrant-powerdns/action.rb
|
86
|
+
- lib/vagrant-powerdns/action/add_record.rb
|
87
|
+
- lib/vagrant-powerdns/action/del_record.rb
|
88
|
+
- lib/vagrant-powerdns/config.rb
|
89
|
+
- lib/vagrant-powerdns/errors.rb
|
90
|
+
- lib/vagrant-powerdns/includes/Ip.class.rb
|
91
|
+
- lib/vagrant-powerdns/includes/Zone.class.rb
|
92
|
+
- lib/vagrant-powerdns/util/pdns_api.rb
|
93
|
+
- lib/vagrant-powerdns/version.rb
|
94
|
+
- locales/en.yml
|
95
|
+
- vagrant-powerdns.gemspec
|
96
|
+
homepage: https://github.com/chenull/vagrant-powerdns
|
97
|
+
licenses:
|
98
|
+
- MIT
|
99
|
+
metadata: {}
|
100
|
+
post_install_message:
|
101
|
+
rdoc_options: []
|
102
|
+
require_paths:
|
103
|
+
- lib
|
104
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
105
|
+
requirements:
|
106
|
+
- - ">="
|
107
|
+
- !ruby/object:Gem::Version
|
108
|
+
version: '0'
|
109
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
110
|
+
requirements:
|
111
|
+
- - ">="
|
112
|
+
- !ruby/object:Gem::Version
|
113
|
+
version: '0'
|
114
|
+
requirements: []
|
115
|
+
rubyforge_project:
|
116
|
+
rubygems_version: 2.4.5.1
|
117
|
+
signing_key:
|
118
|
+
specification_version: 4
|
119
|
+
summary: Vagrant plugin to manage powerdns zone record
|
120
|
+
test_files: []
|