lex-dns 0.1.1
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/.github/workflows/ci.yml +16 -0
- data/.gitignore +12 -0
- data/.rspec +3 -0
- data/.rubocop.yml +56 -0
- data/CHANGELOG.md +11 -0
- data/Gemfile +13 -0
- data/README.md +75 -0
- data/lex-dns.gemspec +28 -0
- data/lib/legion/extensions/dns/client.rb +27 -0
- data/lib/legion/extensions/dns/helpers/client.rb +22 -0
- data/lib/legion/extensions/dns/runners/lookup.rb +52 -0
- data/lib/legion/extensions/dns/runners/reverse.rb +23 -0
- data/lib/legion/extensions/dns/version.rb +9 -0
- data/lib/legion/extensions/dns.rb +15 -0
- metadata +60 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA256:
|
|
3
|
+
metadata.gz: 68ae11252179b1e77a7a7dc7a8a3d8d093dbd1d34bcecf90318fc24df08ef2a9
|
|
4
|
+
data.tar.gz: 5f2635c914c1096ac7685765779a5bdc02748dee64180f552a78f960d5dfd43b
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: e0665b6d0061c1caad1ac67af0805f0d32483bba67d47d6964bd1665d3049e1b994a0d8009599a01ca5a7f78176add4cc38bbd787f32d74c60694f830fa20a4f
|
|
7
|
+
data.tar.gz: fee5b06e7677420ee1d221b56edc10ed4eedc9400860454067c5cdce016f6c4a6432fd8143655f17ca587e9478d68f7fba1087517ea9cf578aefafe4ae80d5a1
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
on:
|
|
3
|
+
push:
|
|
4
|
+
branches: [origin]
|
|
5
|
+
pull_request:
|
|
6
|
+
|
|
7
|
+
jobs:
|
|
8
|
+
ci:
|
|
9
|
+
uses: LegionIO/.github/.github/workflows/ci.yml@main
|
|
10
|
+
|
|
11
|
+
release:
|
|
12
|
+
needs: ci
|
|
13
|
+
if: github.event_name == 'push' && github.ref == 'refs/heads/origin'
|
|
14
|
+
uses: LegionIO/.github/.github/workflows/release.yml@main
|
|
15
|
+
secrets:
|
|
16
|
+
rubygems-api-key: ${{ secrets.RUBYGEMS_API_KEY }}
|
data/.gitignore
ADDED
data/.rspec
ADDED
data/.rubocop.yml
ADDED
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
AllCops:
|
|
2
|
+
TargetRubyVersion: 3.4
|
|
3
|
+
NewCops: enable
|
|
4
|
+
SuggestExtensions: false
|
|
5
|
+
|
|
6
|
+
Layout/LineLength:
|
|
7
|
+
Max: 160
|
|
8
|
+
|
|
9
|
+
Layout/SpaceAroundEqualsInParameterDefault:
|
|
10
|
+
EnforcedStyle: space
|
|
11
|
+
|
|
12
|
+
Layout/HashAlignment:
|
|
13
|
+
EnforcedHashRocketStyle: table
|
|
14
|
+
EnforcedColonStyle: table
|
|
15
|
+
|
|
16
|
+
Metrics/MethodLength:
|
|
17
|
+
Max: 50
|
|
18
|
+
|
|
19
|
+
Metrics/ClassLength:
|
|
20
|
+
Max: 1500
|
|
21
|
+
|
|
22
|
+
Metrics/ModuleLength:
|
|
23
|
+
Max: 1500
|
|
24
|
+
|
|
25
|
+
Metrics/BlockLength:
|
|
26
|
+
Max: 200
|
|
27
|
+
Exclude:
|
|
28
|
+
- 'spec/**/*'
|
|
29
|
+
|
|
30
|
+
Metrics/ParameterLists:
|
|
31
|
+
Max: 8
|
|
32
|
+
|
|
33
|
+
Naming/MethodParameterName:
|
|
34
|
+
MinNameLength: 2
|
|
35
|
+
|
|
36
|
+
Metrics/AbcSize:
|
|
37
|
+
Max: 60
|
|
38
|
+
|
|
39
|
+
Metrics/CyclomaticComplexity:
|
|
40
|
+
Max: 15
|
|
41
|
+
|
|
42
|
+
Metrics/PerceivedComplexity:
|
|
43
|
+
Max: 17
|
|
44
|
+
|
|
45
|
+
Style/Documentation:
|
|
46
|
+
Enabled: false
|
|
47
|
+
|
|
48
|
+
Style/SymbolArray:
|
|
49
|
+
Enabled: true
|
|
50
|
+
|
|
51
|
+
Style/FrozenStringLiteralComment:
|
|
52
|
+
Enabled: true
|
|
53
|
+
EnforcedStyle: always
|
|
54
|
+
|
|
55
|
+
Naming/FileName:
|
|
56
|
+
Enabled: false
|
data/CHANGELOG.md
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
## [0.1.0] - 2026-03-21
|
|
4
|
+
|
|
5
|
+
### Added
|
|
6
|
+
- Initial release
|
|
7
|
+
- `Helpers::Client.resolver` wrapping Ruby stdlib `Resolv::DNS`; accepts optional `nameserver:` (string or array)
|
|
8
|
+
- `Runners::Lookup`: `resolve_a`, `resolve_aaaa`, `resolve_cname`, `resolve_mx`, `resolve_txt`, `resolve_srv`
|
|
9
|
+
- `Runners::Reverse`: `reverse_lookup` (IP to hostname)
|
|
10
|
+
- Standalone `Client` class including all runners; takes `nameserver:` kwargs at construction
|
|
11
|
+
- No external runtime dependencies (uses Ruby stdlib `resolv`)
|
data/Gemfile
ADDED
data/README.md
ADDED
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
# lex-dns
|
|
2
|
+
|
|
3
|
+
LegionIO extension for DNS resolution via Ruby stdlib `Resolv::DNS`. No external runtime dependencies.
|
|
4
|
+
|
|
5
|
+
## Installation
|
|
6
|
+
|
|
7
|
+
Add to your Gemfile:
|
|
8
|
+
|
|
9
|
+
```ruby
|
|
10
|
+
gem 'lex-dns'
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
## Standalone Usage
|
|
14
|
+
|
|
15
|
+
```ruby
|
|
16
|
+
require 'legion/extensions/dns'
|
|
17
|
+
|
|
18
|
+
client = Legion::Extensions::Dns::Client.new
|
|
19
|
+
# or with custom nameservers:
|
|
20
|
+
client = Legion::Extensions::Dns::Client.new(nameserver: ['8.8.8.8', '8.8.4.4'])
|
|
21
|
+
|
|
22
|
+
client.resolve_a(hostname: 'example.com')
|
|
23
|
+
# => { result: ['93.184.216.34'] }
|
|
24
|
+
|
|
25
|
+
client.resolve_aaaa(hostname: 'example.com')
|
|
26
|
+
# => { result: ['2606:2800:220:1:248:1893:25c8:1946'] }
|
|
27
|
+
|
|
28
|
+
client.resolve_cname(hostname: 'www.example.com')
|
|
29
|
+
# => { result: 'example.com' }
|
|
30
|
+
|
|
31
|
+
client.resolve_mx(hostname: 'example.com')
|
|
32
|
+
# => { result: [{ priority: 10, exchange: 'mail.example.com' }] }
|
|
33
|
+
|
|
34
|
+
client.resolve_txt(hostname: 'example.com')
|
|
35
|
+
# => { result: ['v=spf1 ...'] }
|
|
36
|
+
|
|
37
|
+
client.resolve_srv(hostname: '_https._tcp.example.com')
|
|
38
|
+
# => { result: [{ priority: 10, weight: 20, port: 443, target: 'host.example.com' }] }
|
|
39
|
+
|
|
40
|
+
client.reverse_lookup(ip: '93.184.216.34')
|
|
41
|
+
# => { result: 'host.example.com' }
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
## Runners
|
|
45
|
+
|
|
46
|
+
### Lookup
|
|
47
|
+
|
|
48
|
+
| Method | Arguments | Returns |
|
|
49
|
+
|--------|-----------|---------|
|
|
50
|
+
| `resolve_a` | `hostname:` | `{ result: [String] }` — IPv4 addresses |
|
|
51
|
+
| `resolve_aaaa` | `hostname:` | `{ result: [String] }` — IPv6 addresses |
|
|
52
|
+
| `resolve_cname` | `hostname:` | `{ result: String \| nil }` — canonical name |
|
|
53
|
+
| `resolve_mx` | `hostname:` | `{ result: [{ priority:, exchange: }] }` |
|
|
54
|
+
| `resolve_txt` | `hostname:` | `{ result: [String] }` |
|
|
55
|
+
| `resolve_srv` | `hostname:` | `{ result: [{ priority:, weight:, port:, target: }] }` |
|
|
56
|
+
|
|
57
|
+
### Reverse
|
|
58
|
+
|
|
59
|
+
| Method | Arguments | Returns |
|
|
60
|
+
|--------|-----------|---------|
|
|
61
|
+
| `reverse_lookup` | `ip:` | `{ result: String \| nil }` — PTR hostname |
|
|
62
|
+
|
|
63
|
+
## Settings
|
|
64
|
+
|
|
65
|
+
```json
|
|
66
|
+
{
|
|
67
|
+
"lex-dns": {
|
|
68
|
+
"nameserver": ["8.8.8.8", "8.8.4.4"]
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
## License
|
|
74
|
+
|
|
75
|
+
MIT
|
data/lex-dns.gemspec
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative 'lib/legion/extensions/dns/version'
|
|
4
|
+
|
|
5
|
+
Gem::Specification.new do |spec|
|
|
6
|
+
spec.name = 'lex-dns'
|
|
7
|
+
spec.version = Legion::Extensions::Dns::VERSION
|
|
8
|
+
spec.authors = ['Esity']
|
|
9
|
+
spec.email = ['matthewdiverson@gmail.com']
|
|
10
|
+
|
|
11
|
+
spec.summary = 'LEX::dns'
|
|
12
|
+
spec.description = 'Connects LegionIO to DNS resolvers via Ruby stdlib Resolv::DNS'
|
|
13
|
+
spec.homepage = 'https://github.com/LegionIO/lex-dns'
|
|
14
|
+
spec.license = 'MIT'
|
|
15
|
+
spec.required_ruby_version = '>= 3.4'
|
|
16
|
+
|
|
17
|
+
spec.metadata['homepage_uri'] = spec.homepage
|
|
18
|
+
spec.metadata['source_code_uri'] = 'https://github.com/LegionIO/lex-dns'
|
|
19
|
+
spec.metadata['documentation_uri'] = 'https://github.com/LegionIO/lex-dns'
|
|
20
|
+
spec.metadata['changelog_uri'] = 'https://github.com/LegionIO/lex-dns'
|
|
21
|
+
spec.metadata['bug_tracker_uri'] = 'https://github.com/LegionIO/lex-dns/issues'
|
|
22
|
+
spec.metadata['rubygems_mfa_required'] = 'true'
|
|
23
|
+
|
|
24
|
+
spec.files = Dir.chdir(File.expand_path(__dir__)) do
|
|
25
|
+
`git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
|
26
|
+
end
|
|
27
|
+
spec.require_paths = ['lib']
|
|
28
|
+
end
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative 'helpers/client'
|
|
4
|
+
require_relative 'runners/lookup'
|
|
5
|
+
require_relative 'runners/reverse'
|
|
6
|
+
|
|
7
|
+
module Legion
|
|
8
|
+
module Extensions
|
|
9
|
+
module Dns
|
|
10
|
+
class Client
|
|
11
|
+
include Runners::Lookup
|
|
12
|
+
include Runners::Reverse
|
|
13
|
+
|
|
14
|
+
attr_reader :opts
|
|
15
|
+
|
|
16
|
+
def initialize(nameserver: nil, **extra)
|
|
17
|
+
@opts = extra
|
|
18
|
+
@opts[:nameserver] = nameserver if nameserver
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def resolver(**override)
|
|
22
|
+
Helpers::Client.resolver(**@opts, **override)
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'resolv'
|
|
4
|
+
|
|
5
|
+
module Legion
|
|
6
|
+
module Extensions
|
|
7
|
+
module Dns
|
|
8
|
+
module Helpers
|
|
9
|
+
module Client
|
|
10
|
+
def self.resolver(nameserver: nil, **_opts)
|
|
11
|
+
if nameserver
|
|
12
|
+
servers = Array(nameserver)
|
|
13
|
+
::Resolv::DNS.new(nameserver: servers)
|
|
14
|
+
else
|
|
15
|
+
::Resolv::DNS.new
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'legion/extensions/dns/helpers/client'
|
|
4
|
+
|
|
5
|
+
module Legion
|
|
6
|
+
module Extensions
|
|
7
|
+
module Dns
|
|
8
|
+
module Runners
|
|
9
|
+
module Lookup
|
|
10
|
+
def resolve_a(hostname:, **)
|
|
11
|
+
records = resolver(**).getresources(hostname, ::Resolv::DNS::Resource::IN::A)
|
|
12
|
+
{ result: records.map(&:address).map(&:to_s) }
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
def resolve_aaaa(hostname:, **)
|
|
16
|
+
records = resolver(**).getresources(hostname, ::Resolv::DNS::Resource::IN::AAAA)
|
|
17
|
+
{ result: records.map(&:address).map(&:to_s) }
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def resolve_cname(hostname:, **)
|
|
21
|
+
record = resolver(**).getresource(hostname, ::Resolv::DNS::Resource::IN::CNAME)
|
|
22
|
+
{ result: record.name.to_s }
|
|
23
|
+
rescue ::Resolv::ResolvError
|
|
24
|
+
{ result: nil }
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
def resolve_mx(hostname:, **)
|
|
28
|
+
records = resolver(**).getresources(hostname, ::Resolv::DNS::Resource::IN::MX)
|
|
29
|
+
{ result: records.map { |r| { priority: r.preference, exchange: r.exchange.to_s } } }
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def resolve_txt(hostname:, **)
|
|
33
|
+
records = resolver(**).getresources(hostname, ::Resolv::DNS::Resource::IN::TXT)
|
|
34
|
+
{ result: records.map { |r| r.strings.join } }
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def resolve_srv(hostname:, **)
|
|
38
|
+
records = resolver(**).getresources(hostname, ::Resolv::DNS::Resource::IN::SRV)
|
|
39
|
+
{
|
|
40
|
+
result: records.map do |r|
|
|
41
|
+
{ priority: r.priority, weight: r.weight, port: r.port, target: r.target.to_s }
|
|
42
|
+
end
|
|
43
|
+
}
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
extend Legion::Extensions::Dns::Helpers::Client
|
|
47
|
+
include Legion::Extensions::Helpers::Lex if defined?(Legion::Extensions::Helpers::Lex)
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
end
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'legion/extensions/dns/helpers/client'
|
|
4
|
+
|
|
5
|
+
module Legion
|
|
6
|
+
module Extensions
|
|
7
|
+
module Dns
|
|
8
|
+
module Runners
|
|
9
|
+
module Reverse
|
|
10
|
+
def reverse_lookup(ip:, **)
|
|
11
|
+
hostname = resolver(**).getname(ip).to_s
|
|
12
|
+
{ result: hostname }
|
|
13
|
+
rescue ::Resolv::ResolvError
|
|
14
|
+
{ result: nil }
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
extend Legion::Extensions::Dns::Helpers::Client
|
|
18
|
+
include Legion::Extensions::Helpers::Lex if defined?(Legion::Extensions::Helpers::Lex)
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'legion/extensions/dns/version'
|
|
4
|
+
require 'legion/extensions/dns/helpers/client'
|
|
5
|
+
require 'legion/extensions/dns/runners/lookup'
|
|
6
|
+
require 'legion/extensions/dns/runners/reverse'
|
|
7
|
+
require 'legion/extensions/dns/client'
|
|
8
|
+
|
|
9
|
+
module Legion
|
|
10
|
+
module Extensions
|
|
11
|
+
module Dns
|
|
12
|
+
extend Legion::Extensions::Core if Legion::Extensions.const_defined? :Core
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
end
|
metadata
ADDED
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
|
2
|
+
name: lex-dns
|
|
3
|
+
version: !ruby/object:Gem::Version
|
|
4
|
+
version: 0.1.1
|
|
5
|
+
platform: ruby
|
|
6
|
+
authors:
|
|
7
|
+
- Esity
|
|
8
|
+
bindir: bin
|
|
9
|
+
cert_chain: []
|
|
10
|
+
date: 1980-01-02 00:00:00.000000000 Z
|
|
11
|
+
dependencies: []
|
|
12
|
+
description: Connects LegionIO to DNS resolvers via Ruby stdlib Resolv::DNS
|
|
13
|
+
email:
|
|
14
|
+
- matthewdiverson@gmail.com
|
|
15
|
+
executables: []
|
|
16
|
+
extensions: []
|
|
17
|
+
extra_rdoc_files: []
|
|
18
|
+
files:
|
|
19
|
+
- ".github/workflows/ci.yml"
|
|
20
|
+
- ".gitignore"
|
|
21
|
+
- ".rspec"
|
|
22
|
+
- ".rubocop.yml"
|
|
23
|
+
- CHANGELOG.md
|
|
24
|
+
- Gemfile
|
|
25
|
+
- README.md
|
|
26
|
+
- lex-dns.gemspec
|
|
27
|
+
- lib/legion/extensions/dns.rb
|
|
28
|
+
- lib/legion/extensions/dns/client.rb
|
|
29
|
+
- lib/legion/extensions/dns/helpers/client.rb
|
|
30
|
+
- lib/legion/extensions/dns/runners/lookup.rb
|
|
31
|
+
- lib/legion/extensions/dns/runners/reverse.rb
|
|
32
|
+
- lib/legion/extensions/dns/version.rb
|
|
33
|
+
homepage: https://github.com/LegionIO/lex-dns
|
|
34
|
+
licenses:
|
|
35
|
+
- MIT
|
|
36
|
+
metadata:
|
|
37
|
+
homepage_uri: https://github.com/LegionIO/lex-dns
|
|
38
|
+
source_code_uri: https://github.com/LegionIO/lex-dns
|
|
39
|
+
documentation_uri: https://github.com/LegionIO/lex-dns
|
|
40
|
+
changelog_uri: https://github.com/LegionIO/lex-dns
|
|
41
|
+
bug_tracker_uri: https://github.com/LegionIO/lex-dns/issues
|
|
42
|
+
rubygems_mfa_required: 'true'
|
|
43
|
+
rdoc_options: []
|
|
44
|
+
require_paths:
|
|
45
|
+
- lib
|
|
46
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
|
47
|
+
requirements:
|
|
48
|
+
- - ">="
|
|
49
|
+
- !ruby/object:Gem::Version
|
|
50
|
+
version: '3.4'
|
|
51
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
52
|
+
requirements:
|
|
53
|
+
- - ">="
|
|
54
|
+
- !ruby/object:Gem::Version
|
|
55
|
+
version: '0'
|
|
56
|
+
requirements: []
|
|
57
|
+
rubygems_version: 3.6.9
|
|
58
|
+
specification_version: 4
|
|
59
|
+
summary: LEX::dns
|
|
60
|
+
test_files: []
|