@nictool/dns-resource-record 1.1.7 → 1.2.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.
- package/CHANGELOG.md +26 -43
- package/README.md +48 -48
- package/index.js +83 -29
- package/lib/tinydns.js +68 -61
- package/package.json +1 -2
- package/rr/a.js +32 -23
- package/rr/aaaa.js +49 -35
- package/rr/caa.js +56 -44
- package/rr/cert.js +21 -19
- package/rr/cname.js +22 -23
- package/rr/dname.js +23 -23
- package/rr/dnskey.js +45 -43
- package/rr/ds.js +40 -40
- package/rr/hinfo.js +29 -28
- package/rr/https.js +62 -0
- package/rr/ipseckey.js +69 -50
- package/rr/key.js +23 -23
- package/rr/loc.js +71 -58
- package/rr/mx.js +41 -27
- package/rr/naptr.js +52 -53
- package/rr/ns.js +26 -23
- package/rr/nsec.js +24 -20
- package/rr/nsec3.js +59 -46
- package/rr/nsec3param.js +24 -26
- package/rr/nxt.js +65 -0
- package/rr/openpgpkey.js +18 -15
- package/rr/ptr.js +20 -21
- package/rr/rrsig.js +28 -23
- package/rr/sig.js +25 -20
- package/rr/smimea.js +36 -31
- package/rr/soa.js +56 -42
- package/rr/spf.js +21 -18
- package/rr/srv.js +45 -45
- package/rr/sshfp.js +30 -31
- package/rr/svcb.js +64 -0
- package/rr/tlsa.js +50 -45
- package/rr/tsig.js +56 -0
- package/rr/txt.js +42 -35
- package/rr/uri.js +33 -33
- package/rr/wks.js +45 -0
- package/rr.js +133 -87
- package/.codeclimate.yml +0 -25
- package/DEVELOP.md +0 -23
- package/test/a.js +0 -76
- package/test/aaaa.js +0 -79
- package/test/base.js +0 -138
- package/test/caa.js +0 -104
- package/test/cert.js +0 -48
- package/test/cname.js +0 -41
- package/test/dname.js +0 -53
- package/test/dnskey.js +0 -44
- package/test/ds.js +0 -44
- package/test/fake.js +0 -26
- package/test/hinfo.js +0 -75
- package/test/ipseckey.js +0 -115
- package/test/key.js +0 -37
- package/test/loc.js +0 -71
- package/test/mx.js +0 -75
- package/test/naptr.js +0 -40
- package/test/ns.js +0 -53
- package/test/nsec.js +0 -38
- package/test/nsec3.js +0 -40
- package/test/nsec3param.js +0 -26
- package/test/openpgpkey.js +0 -35
- package/test/ptr.js +0 -54
- package/test/rr.js +0 -196
- package/test/smimea.js +0 -45
- package/test/soa.js +0 -77
- package/test/spf.js +0 -48
- package/test/srv.js +0 -81
- package/test/sshfp.js +0 -62
- package/test/tinydns.js +0 -140
- package/test/tlsa.js +0 -54
- package/test/txt.js +0 -70
- package/test/uri.js +0 -61
package/rr/loc.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
|
|
2
1
|
import RR from '../rr.js'
|
|
3
2
|
import * as TINYDNS from '../lib/tinydns.js'
|
|
4
3
|
|
|
5
|
-
const REF = {
|
|
6
|
-
|
|
4
|
+
const REF = {
|
|
5
|
+
// RFC 1876
|
|
6
|
+
LATLON: 2 ** 31, // LAT equator, LON prime meridian
|
|
7
7
|
ALTITUDE: 100000 * 100, // reference spheroid used by GPS, in cm
|
|
8
8
|
}
|
|
9
9
|
|
|
@@ -14,13 +14,13 @@ const CONV = {
|
|
|
14
14
|
}
|
|
15
15
|
|
|
16
16
|
export default class LOC extends RR {
|
|
17
|
-
constructor
|
|
17
|
+
constructor(opts) {
|
|
18
18
|
super(opts)
|
|
19
19
|
}
|
|
20
20
|
|
|
21
21
|
/****** Resource record specific setters *******/
|
|
22
|
-
setAddress
|
|
23
|
-
if (!val)
|
|
22
|
+
setAddress(val) {
|
|
23
|
+
if (!val) this.throwHelp('LOC: address is required')
|
|
24
24
|
|
|
25
25
|
/*
|
|
26
26
|
... LOC ( d1 [m1 [s1]] {"N"|"S"} d2 [m2 [s2]]
|
|
@@ -32,53 +32,53 @@ export default class LOC extends RR {
|
|
|
32
32
|
this.set('address', val)
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
-
getDescription
|
|
35
|
+
getDescription() {
|
|
36
36
|
return 'Location'
|
|
37
37
|
}
|
|
38
38
|
|
|
39
|
-
getRdataFields
|
|
40
|
-
return [
|
|
39
|
+
getRdataFields(arg) {
|
|
40
|
+
return ['address']
|
|
41
41
|
}
|
|
42
42
|
|
|
43
|
-
getRFCs
|
|
44
|
-
return [
|
|
43
|
+
getRFCs() {
|
|
44
|
+
return [1876]
|
|
45
45
|
}
|
|
46
46
|
|
|
47
|
-
getTypeId
|
|
47
|
+
getTypeId() {
|
|
48
48
|
return 29
|
|
49
49
|
}
|
|
50
50
|
|
|
51
|
-
parseLoc
|
|
52
|
-
|
|
51
|
+
parseLoc(string) {
|
|
53
52
|
// d1 [m1 [s1]]
|
|
54
53
|
const dms = '(\\d+)\\s+(?:(\\d+)\\s+)?(?:([\\d.]+)\\s+)?'
|
|
55
54
|
|
|
56
55
|
// alt["m"] [siz["m"] [hp["m"] [vp["m"]]]]
|
|
57
|
-
const alt =
|
|
56
|
+
const alt =
|
|
57
|
+
'(-?[\\d.]+)m?(?:\\s+([\\d.]+)m?)?(?:\\s+([\\d.]+)m?)?(?:\\s+([\\d.]+)m?)?'
|
|
58
58
|
|
|
59
59
|
// put them all together
|
|
60
60
|
const locRe = new RegExp(`^${dms}(N|S)\\s+${dms}(E|W)\\s+${alt}`, 'i')
|
|
61
61
|
const r = string.match(locRe)
|
|
62
|
-
if (!r)
|
|
62
|
+
if (!r) this.throwHelp('LOC address: invalid format, see RFC 1876')
|
|
63
63
|
|
|
64
64
|
const loc = {
|
|
65
65
|
latitude: {
|
|
66
|
-
degrees
|
|
67
|
-
minutes
|
|
68
|
-
seconds
|
|
66
|
+
degrees: r[1],
|
|
67
|
+
minutes: r[2],
|
|
68
|
+
seconds: r[3],
|
|
69
69
|
hemisphere: r[4].toUpperCase(),
|
|
70
70
|
},
|
|
71
71
|
longitude: {
|
|
72
|
-
degrees
|
|
73
|
-
minutes
|
|
74
|
-
seconds
|
|
72
|
+
degrees: r[5],
|
|
73
|
+
minutes: r[6],
|
|
74
|
+
seconds: r[7],
|
|
75
75
|
hemisphere: r[8].toUpperCase(),
|
|
76
76
|
},
|
|
77
|
-
altitude
|
|
78
|
-
size
|
|
77
|
+
altitude: r[9] * 100, // m -> cm
|
|
78
|
+
size: r[10] * 100,
|
|
79
79
|
precision: {
|
|
80
80
|
horizontal: r[11] * 100,
|
|
81
|
-
vertical
|
|
81
|
+
vertical: r[12] * 100,
|
|
82
82
|
},
|
|
83
83
|
}
|
|
84
84
|
|
|
@@ -86,48 +86,61 @@ export default class LOC extends RR {
|
|
|
86
86
|
}
|
|
87
87
|
|
|
88
88
|
/****** IMPORTERS *******/
|
|
89
|
-
fromTinydns
|
|
89
|
+
fromTinydns(opts) {
|
|
90
90
|
// LOC via generic, :fqdn:n:rdata:ttl:timestamp:lo
|
|
91
|
-
const [
|
|
92
|
-
if (n != 29)
|
|
91
|
+
const [fqdn, n, rdata, ttl, ts, loc] = opts.tinyline.substring(1).split(':')
|
|
92
|
+
if (n != 29) this.throwHelp('LOC fromTinydns, invalid n')
|
|
93
93
|
|
|
94
94
|
// divide by 100 is to convert cm to meters
|
|
95
95
|
const l = {
|
|
96
|
-
version
|
|
97
|
-
size
|
|
96
|
+
version: TINYDNS.octalToUInt8(rdata.substring(0, 4)),
|
|
97
|
+
size: this.fromExponent(TINYDNS.octalToUInt8(rdata.substring(4, 8))),
|
|
98
98
|
precision: {
|
|
99
|
-
horizontal: this.fromExponent(
|
|
100
|
-
|
|
99
|
+
horizontal: this.fromExponent(
|
|
100
|
+
TINYDNS.octalToUInt8(rdata.substring(8, 12)),
|
|
101
|
+
),
|
|
102
|
+
vertical: this.fromExponent(
|
|
103
|
+
TINYDNS.octalToUInt8(rdata.substring(12, 16)),
|
|
104
|
+
),
|
|
101
105
|
},
|
|
102
|
-
latitude
|
|
103
|
-
|
|
104
|
-
|
|
106
|
+
latitude: this.arcSecToDMS(
|
|
107
|
+
TINYDNS.octalToUInt32(rdata.substring(16, 32)),
|
|
108
|
+
'lat',
|
|
109
|
+
),
|
|
110
|
+
longitude: this.arcSecToDMS(
|
|
111
|
+
TINYDNS.octalToUInt32(rdata.substring(32, 48)),
|
|
112
|
+
'lon',
|
|
113
|
+
),
|
|
114
|
+
altitude: TINYDNS.octalToUInt32(rdata.substring(48, 64)) - REF.ALTITUDE,
|
|
105
115
|
}
|
|
106
116
|
|
|
107
117
|
return new LOC({
|
|
108
|
-
type
|
|
109
|
-
owner
|
|
110
|
-
address
|
|
111
|
-
ttl
|
|
118
|
+
type: 'LOC',
|
|
119
|
+
owner: this.fullyQualify(fqdn),
|
|
120
|
+
address: this.toHuman(l),
|
|
121
|
+
ttl: parseInt(ttl, 10),
|
|
112
122
|
timestamp: ts,
|
|
113
|
-
location
|
|
123
|
+
location: loc !== '' && loc !== '\n' ? loc : '',
|
|
114
124
|
})
|
|
115
125
|
}
|
|
116
126
|
|
|
117
|
-
fromBind
|
|
118
|
-
const [
|
|
127
|
+
fromBind(opts) {
|
|
128
|
+
const [owner, ttl, c, type] = opts.bindline.split(/\s+/)
|
|
119
129
|
|
|
120
130
|
return new LOC({
|
|
121
131
|
owner,
|
|
122
|
-
ttl
|
|
123
|
-
class
|
|
124
|
-
type
|
|
132
|
+
ttl: parseInt(ttl, 10),
|
|
133
|
+
class: c,
|
|
134
|
+
type: type,
|
|
125
135
|
address: opts.bindline.split(/\s+/).slice(4).join(' ').trim(),
|
|
126
136
|
})
|
|
127
137
|
}
|
|
128
138
|
|
|
129
|
-
dmsToArcSec
|
|
130
|
-
let retval =
|
|
139
|
+
dmsToArcSec(obj) {
|
|
140
|
+
let retval =
|
|
141
|
+
obj.degrees * CONV.deg +
|
|
142
|
+
(obj.minutes || 0) * CONV.min +
|
|
143
|
+
(obj.seconds || 0) * CONV.sec
|
|
131
144
|
switch (obj.hemisphere.toUpperCase()) {
|
|
132
145
|
case 'W':
|
|
133
146
|
case 'S':
|
|
@@ -138,7 +151,7 @@ export default class LOC extends RR {
|
|
|
138
151
|
return retval
|
|
139
152
|
}
|
|
140
153
|
|
|
141
|
-
arcSecToDMS
|
|
154
|
+
arcSecToDMS(rawmsec, latlon) {
|
|
142
155
|
let msec = Math.abs(rawmsec - REF.LATLON)
|
|
143
156
|
// console.log(`rawmsec: ${rawmsec}, abs msec: ${msec}`)
|
|
144
157
|
|
|
@@ -160,19 +173,19 @@ export default class LOC extends RR {
|
|
|
160
173
|
hem = rawmsec >= REF.LATLON ? 'E' : 'W'
|
|
161
174
|
break
|
|
162
175
|
default:
|
|
163
|
-
|
|
176
|
+
this.throwHelp('unknown or missing hemisphere')
|
|
164
177
|
}
|
|
165
178
|
|
|
166
|
-
return `${deg} ${min} ${sec}${msec ? '.'+msec : ''} ${hem}`
|
|
179
|
+
return `${deg} ${min} ${sec}${msec ? '.' + msec : ''} ${hem}`
|
|
167
180
|
}
|
|
168
181
|
|
|
169
|
-
fromExponent
|
|
182
|
+
fromExponent(prec) {
|
|
170
183
|
const mantissa = ((prec >> 4) & 0x0f) % 10
|
|
171
184
|
const exponent = ((prec >> 0) & 0x0f) % 10
|
|
172
185
|
return mantissa * Math.pow(10, exponent)
|
|
173
186
|
}
|
|
174
187
|
|
|
175
|
-
toExponent
|
|
188
|
+
toExponent(val) {
|
|
176
189
|
/*
|
|
177
190
|
RFC 1876, ... expressed as a pair of four-bit unsigned
|
|
178
191
|
integers, each ranging from zero to nine, with the most
|
|
@@ -188,22 +201,22 @@ export default class LOC extends RR {
|
|
|
188
201
|
return (parseInt(val) << 4) | (exponent & 0x0f)
|
|
189
202
|
}
|
|
190
203
|
|
|
191
|
-
toHuman
|
|
192
|
-
let r = `${obj.latitude} ${obj.longitude} ${
|
|
193
|
-
if (obj.size)
|
|
204
|
+
toHuman(obj) {
|
|
205
|
+
let r = `${obj.latitude} ${obj.longitude} ${obj.altitude / 100}m`
|
|
206
|
+
if (obj.size) r += ` ${obj.size / 100}m`
|
|
194
207
|
if (obj.precision.horizontal) r += ` ${obj.precision.horizontal / 100}m`
|
|
195
|
-
if (obj.precision.vertical
|
|
208
|
+
if (obj.precision.vertical) r += ` ${obj.precision.vertical / 100}m`
|
|
196
209
|
return r
|
|
197
210
|
}
|
|
198
211
|
|
|
199
212
|
/****** EXPORTERS *******/
|
|
200
213
|
|
|
201
|
-
toTinydns
|
|
214
|
+
toTinydns() {
|
|
202
215
|
const loc = this.parseLoc(this.get('address'))
|
|
203
216
|
|
|
204
217
|
// LOC format declares in meters, tinydns uses cm (hence * 100)
|
|
205
218
|
let rdata = ''
|
|
206
|
-
rdata += TINYDNS.UInt8toOctal(0)
|
|
219
|
+
rdata += TINYDNS.UInt8toOctal(0) // version
|
|
207
220
|
rdata += TINYDNS.UInt8toOctal(this.toExponent(loc.size))
|
|
208
221
|
rdata += TINYDNS.UInt8toOctal(this.toExponent(loc.precision.horizontal))
|
|
209
222
|
rdata += TINYDNS.UInt8toOctal(this.toExponent(loc.precision.vertical))
|
package/rr/mx.js
CHANGED
|
@@ -1,25 +1,25 @@
|
|
|
1
|
-
|
|
2
|
-
import net from 'net'
|
|
1
|
+
import net from 'node:net'
|
|
3
2
|
|
|
4
3
|
import RR from '../rr.js'
|
|
5
4
|
|
|
6
5
|
export default class MX extends RR {
|
|
7
|
-
constructor
|
|
6
|
+
constructor(opts) {
|
|
8
7
|
super(opts)
|
|
9
8
|
}
|
|
10
9
|
|
|
11
10
|
/****** Resource record specific setters *******/
|
|
12
|
-
setPreference
|
|
11
|
+
setPreference(val) {
|
|
13
12
|
if (val === undefined) val = this?.default?.preference
|
|
13
|
+
if (val === undefined) this.throwHelp('MX: preference is required')
|
|
14
14
|
this.is16bitInt('MX', 'preference', val)
|
|
15
15
|
this.set('preference', val)
|
|
16
16
|
}
|
|
17
17
|
|
|
18
|
-
setExchange
|
|
19
|
-
if (!val)
|
|
18
|
+
setExchange(val) {
|
|
19
|
+
if (!val) this.throwHelp('MX: exchange is required')
|
|
20
20
|
|
|
21
21
|
if (net.isIPv4(val) || net.isIPv6(val))
|
|
22
|
-
|
|
22
|
+
this.throwHelp(`MX: exchange must be a FQDN`)
|
|
23
23
|
|
|
24
24
|
this.isFullyQualified('MX', 'exchange', val)
|
|
25
25
|
this.isValidHostname('MX', 'exchange', val)
|
|
@@ -28,47 +28,61 @@ export default class MX extends RR {
|
|
|
28
28
|
this.set('exchange', val.toLowerCase())
|
|
29
29
|
}
|
|
30
30
|
|
|
31
|
-
getDescription
|
|
31
|
+
getDescription() {
|
|
32
32
|
return 'Mail Exchanger'
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
-
getRdataFields
|
|
36
|
-
return [
|
|
35
|
+
getRdataFields(arg) {
|
|
36
|
+
return ['preference', 'exchange']
|
|
37
37
|
}
|
|
38
38
|
|
|
39
|
-
getRFCs
|
|
40
|
-
return [
|
|
39
|
+
getRFCs() {
|
|
40
|
+
return [1035, 2181, 7505]
|
|
41
41
|
}
|
|
42
42
|
|
|
43
|
-
getTypeId
|
|
43
|
+
getTypeId() {
|
|
44
44
|
return 15
|
|
45
45
|
}
|
|
46
46
|
|
|
47
|
+
getCanonical() {
|
|
48
|
+
return {
|
|
49
|
+
owner: 'example.com.',
|
|
50
|
+
ttl: 43200,
|
|
51
|
+
class: 'IN',
|
|
52
|
+
type: 'MX',
|
|
53
|
+
preference: 0,
|
|
54
|
+
exchange: 'mail.example.com.',
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
47
58
|
/****** IMPORTERS *******/
|
|
48
|
-
fromTinydns
|
|
59
|
+
fromTinydns(opts) {
|
|
49
60
|
// @fqdn:ip:x:dist:ttl:timestamp:lo
|
|
50
61
|
// eslint-disable-next-line no-unused-vars
|
|
51
|
-
const [
|
|
62
|
+
const [owner, ip, x, preference, ttl, ts, loc] = opts.tinyline
|
|
63
|
+
.substring(1)
|
|
64
|
+
.split(':')
|
|
52
65
|
|
|
53
66
|
return new MX({
|
|
54
|
-
type
|
|
55
|
-
owner
|
|
56
|
-
exchange
|
|
67
|
+
type: 'MX',
|
|
68
|
+
owner: this.fullyQualify(owner),
|
|
69
|
+
exchange: this.fullyQualify(/\./.test(x) ? x : `${x}.mx.${owner}`),
|
|
57
70
|
preference: parseInt(preference, 10) || 0,
|
|
58
|
-
ttl
|
|
59
|
-
timestamp
|
|
60
|
-
location
|
|
71
|
+
ttl: parseInt(ttl, 10),
|
|
72
|
+
timestamp: ts,
|
|
73
|
+
location: loc !== '' && loc !== '\n' ? loc : '',
|
|
61
74
|
})
|
|
62
75
|
}
|
|
63
76
|
|
|
64
|
-
fromBind
|
|
77
|
+
fromBind(opts) {
|
|
65
78
|
// test.example.com 3600 IN MX preference exchange
|
|
66
|
-
const [
|
|
79
|
+
const [owner, ttl, c, type, preference, exchange] =
|
|
80
|
+
opts.bindline.split(/\s+/)
|
|
67
81
|
|
|
68
82
|
return new MX({
|
|
69
83
|
owner,
|
|
70
|
-
ttl
|
|
71
|
-
class
|
|
84
|
+
ttl: parseInt(ttl, 10),
|
|
85
|
+
class: c,
|
|
72
86
|
type,
|
|
73
87
|
preference: parseInt(preference),
|
|
74
88
|
exchange,
|
|
@@ -76,11 +90,11 @@ export default class MX extends RR {
|
|
|
76
90
|
}
|
|
77
91
|
|
|
78
92
|
/****** EXPORTERS *******/
|
|
79
|
-
toBind
|
|
93
|
+
toBind(zone_opts) {
|
|
80
94
|
return `${this.getPrefix(zone_opts)}\t${this.get('preference')}\t${this.getFQDN('exchange', zone_opts)}\n`
|
|
81
95
|
}
|
|
82
96
|
|
|
83
|
-
toTinydns
|
|
97
|
+
toTinydns() {
|
|
84
98
|
return `@${this.getTinyFQDN('owner')}::${this.getTinyFQDN('exchange')}:${this.get('preference')}:${this.getTinydnsPostamble()}\n`
|
|
85
99
|
}
|
|
86
100
|
}
|
package/rr/naptr.js
CHANGED
|
@@ -1,136 +1,135 @@
|
|
|
1
|
-
|
|
2
1
|
import RR from '../rr.js'
|
|
3
2
|
import * as TINYDNS from '../lib/tinydns.js'
|
|
4
3
|
|
|
5
4
|
const rdataRe = /[\r\n\t:\\/]/
|
|
6
5
|
|
|
7
6
|
export default class NAPTR extends RR {
|
|
8
|
-
constructor
|
|
7
|
+
constructor(opts) {
|
|
9
8
|
super(opts)
|
|
10
9
|
}
|
|
11
10
|
|
|
12
|
-
getDescription
|
|
11
|
+
getDescription() {
|
|
13
12
|
return 'Naming Authority Pointer'
|
|
14
13
|
}
|
|
15
14
|
|
|
16
|
-
getQuotedFields
|
|
17
|
-
return [
|
|
15
|
+
getQuotedFields() {
|
|
16
|
+
return ['flags', 'service', 'regexp']
|
|
18
17
|
}
|
|
19
18
|
|
|
20
|
-
getRdataFields
|
|
21
|
-
return [
|
|
19
|
+
getRdataFields(arg) {
|
|
20
|
+
return ['order', 'preference', 'flags', 'service', 'regexp', 'replacement']
|
|
22
21
|
}
|
|
23
22
|
|
|
24
|
-
getRFCs
|
|
25
|
-
return [
|
|
23
|
+
getRFCs() {
|
|
24
|
+
return [2915, 3403]
|
|
26
25
|
}
|
|
27
26
|
|
|
28
|
-
getTypeId
|
|
27
|
+
getTypeId() {
|
|
29
28
|
return 35
|
|
30
29
|
}
|
|
31
30
|
|
|
32
31
|
/****** Resource record specific setters *******/
|
|
33
|
-
setOrder
|
|
32
|
+
setOrder(val) {
|
|
34
33
|
this.is16bitInt('NAPTR', 'order', val)
|
|
35
34
|
this.set('order', val)
|
|
36
35
|
}
|
|
37
36
|
|
|
38
|
-
setPreference
|
|
37
|
+
setPreference(val) {
|
|
39
38
|
this.is16bitInt('NAPTR', 'preference', val)
|
|
40
39
|
this.set('preference', val)
|
|
41
40
|
}
|
|
42
41
|
|
|
43
|
-
setFlags
|
|
44
|
-
if (![
|
|
45
|
-
|
|
42
|
+
setFlags(val) {
|
|
43
|
+
if (!['', 'S', 'A', 'U', 'P'].includes(val.toUpperCase()))
|
|
44
|
+
this.throwHelp(`NAPTR flags are invalid`)
|
|
46
45
|
|
|
47
46
|
this.set('flags', val.toUpperCase())
|
|
48
47
|
}
|
|
49
48
|
|
|
50
|
-
setService
|
|
49
|
+
setService(val) {
|
|
51
50
|
this.set('service', val)
|
|
52
51
|
}
|
|
53
52
|
|
|
54
|
-
setRegexp
|
|
53
|
+
setRegexp(val) {
|
|
55
54
|
this.set('regexp', val)
|
|
56
55
|
}
|
|
57
56
|
|
|
58
|
-
setReplacement
|
|
57
|
+
setReplacement(val) {
|
|
59
58
|
this.set('replacement', val)
|
|
60
59
|
}
|
|
61
60
|
|
|
62
61
|
/****** IMPORTERS *******/
|
|
63
|
-
fromTinydns
|
|
62
|
+
fromTinydns(opts) {
|
|
64
63
|
// NAPTR via generic, :fqdn:n:rdata:ttl:timestamp:lo
|
|
65
|
-
const [
|
|
66
|
-
if (n != 35)
|
|
64
|
+
const [fqdn, n, rdata, ttl, ts, loc] = opts.tinyline.substring(1).split(':')
|
|
65
|
+
if (n != 35) this.throwHelp('NAPTR fromTinydns, invalid n')
|
|
67
66
|
|
|
68
67
|
const binRdata = Buffer.from(TINYDNS.octalToChar(rdata), 'binary')
|
|
69
68
|
|
|
70
69
|
const rec = {
|
|
71
|
-
type
|
|
72
|
-
owner
|
|
73
|
-
ttl
|
|
74
|
-
timestamp
|
|
75
|
-
location
|
|
76
|
-
order
|
|
77
|
-
preference: binRdata.readUInt16BE(2,4),
|
|
70
|
+
type: 'NAPTR',
|
|
71
|
+
owner: this.fullyQualify(fqdn),
|
|
72
|
+
ttl: parseInt(ttl, 10),
|
|
73
|
+
timestamp: ts,
|
|
74
|
+
location: loc !== '' && loc !== '\n' ? loc : '',
|
|
75
|
+
order: binRdata.readUInt16BE(0, 2),
|
|
76
|
+
preference: binRdata.readUInt16BE(2, 4),
|
|
78
77
|
}
|
|
79
78
|
|
|
80
79
|
let idx = 4
|
|
81
|
-
const flagsLength = binRdata.readUInt8(idx)
|
|
82
|
-
|
|
80
|
+
const flagsLength = binRdata.readUInt8(idx)
|
|
81
|
+
idx++
|
|
82
|
+
rec.flags = binRdata.slice(idx, flagsLength).toString()
|
|
83
83
|
idx += flagsLength
|
|
84
84
|
|
|
85
|
-
const serviceLen
|
|
86
|
-
|
|
85
|
+
const serviceLen = binRdata.readUInt8(idx)
|
|
86
|
+
idx++
|
|
87
|
+
rec.service = binRdata.slice(idx, idx + serviceLen).toString()
|
|
87
88
|
idx += serviceLen
|
|
88
89
|
|
|
89
|
-
const regexpLen
|
|
90
|
-
|
|
90
|
+
const regexpLen = binRdata.readUInt8(idx)
|
|
91
|
+
idx++
|
|
92
|
+
rec.regexp = binRdata.slice(idx, idx + regexpLen).toString()
|
|
91
93
|
idx += regexpLen
|
|
92
94
|
|
|
93
|
-
const replaceLen
|
|
94
|
-
|
|
95
|
+
const replaceLen = binRdata.readUInt8(idx)
|
|
96
|
+
idx++
|
|
97
|
+
rec.replacement = binRdata.slice(idx, idx + replaceLen).toString()
|
|
95
98
|
|
|
96
99
|
return new NAPTR(rec)
|
|
97
100
|
}
|
|
98
101
|
|
|
99
|
-
fromBind
|
|
102
|
+
fromBind(opts) {
|
|
100
103
|
const str = opts.bindline
|
|
101
104
|
// test.example.com 3600 IN NAPTR order, preference, "flags", "service", "regexp", replacement
|
|
102
|
-
const [
|
|
103
|
-
const [
|
|
105
|
+
const [owner, ttl, c, type, order, preference] = str.split(/\s+/)
|
|
106
|
+
const [flags, service, regexp] = str.match(/(?:").*?(?:"\s)/g)
|
|
104
107
|
const replacement = str.trim().split(/\s+/).pop()
|
|
105
108
|
|
|
106
109
|
const bits = {
|
|
107
|
-
owner
|
|
108
|
-
ttl
|
|
109
|
-
class
|
|
110
|
-
type
|
|
111
|
-
order
|
|
112
|
-
preference
|
|
113
|
-
flags
|
|
114
|
-
service
|
|
115
|
-
regexp
|
|
110
|
+
owner: owner,
|
|
111
|
+
ttl: parseInt(ttl, 10),
|
|
112
|
+
class: c,
|
|
113
|
+
type: type,
|
|
114
|
+
order: parseInt(order, 10),
|
|
115
|
+
preference: parseInt(preference, 10),
|
|
116
|
+
flags: flags.trim().replace(/^['"]|['"]$/g, ''),
|
|
117
|
+
service: service.trim().replace(/^['"]|['"]$/g, ''),
|
|
118
|
+
regexp: regexp.trim().replace(/^['"]|['"]/g, ''),
|
|
116
119
|
replacement: replacement,
|
|
117
120
|
}
|
|
118
121
|
return new NAPTR(bits)
|
|
119
122
|
}
|
|
120
123
|
|
|
121
124
|
/****** EXPORTERS *******/
|
|
122
|
-
toTinydns
|
|
123
|
-
|
|
125
|
+
toTinydns() {
|
|
124
126
|
let rdata =
|
|
125
127
|
TINYDNS.UInt16toOctal(this.get('order')) +
|
|
126
128
|
TINYDNS.UInt16toOctal(this.get('preference')) +
|
|
127
|
-
|
|
128
129
|
TINYDNS.UInt8toOctal(this.get('flags').length) +
|
|
129
130
|
this.get('flags') +
|
|
130
|
-
|
|
131
131
|
TINYDNS.UInt8toOctal(this.get('service').length) +
|
|
132
132
|
TINYDNS.escapeOctal(rdataRe, this.get('service')) +
|
|
133
|
-
|
|
134
133
|
TINYDNS.UInt8toOctal(this.get('regexp').length) +
|
|
135
134
|
TINYDNS.escapeOctal(rdataRe, this.get('regexp'))
|
|
136
135
|
|
package/rr/ns.js
CHANGED
|
@@ -1,15 +1,14 @@
|
|
|
1
|
-
|
|
2
1
|
import RR from '../rr.js'
|
|
3
2
|
|
|
4
3
|
export default class NS extends RR {
|
|
5
|
-
constructor
|
|
4
|
+
constructor(opts) {
|
|
6
5
|
super(opts)
|
|
7
6
|
if (opts === null) return
|
|
8
7
|
}
|
|
9
8
|
|
|
10
9
|
/****** Resource record specific setters *******/
|
|
11
|
-
setDname
|
|
12
|
-
if (!val)
|
|
10
|
+
setDname(val) {
|
|
11
|
+
if (!val) this.throwHelp(`NS: dname is required`)
|
|
13
12
|
|
|
14
13
|
this.isFullyQualified('NS', 'dname', val)
|
|
15
14
|
this.isValidHostname('NS', 'dname', val)
|
|
@@ -18,57 +17,61 @@ export default class NS extends RR {
|
|
|
18
17
|
this.set('dname', val.toLowerCase())
|
|
19
18
|
}
|
|
20
19
|
|
|
21
|
-
getDescription
|
|
20
|
+
getDescription() {
|
|
22
21
|
return 'Name Server'
|
|
23
22
|
}
|
|
24
23
|
|
|
25
|
-
getRdataFields
|
|
26
|
-
return [
|
|
24
|
+
getRdataFields(arg) {
|
|
25
|
+
return ['dname']
|
|
27
26
|
}
|
|
28
27
|
|
|
29
|
-
getRFCs
|
|
30
|
-
return [
|
|
28
|
+
getRFCs() {
|
|
29
|
+
return [1035]
|
|
31
30
|
}
|
|
32
31
|
|
|
33
|
-
getTypeId
|
|
32
|
+
getTypeId() {
|
|
34
33
|
return 2
|
|
35
34
|
}
|
|
36
35
|
|
|
37
36
|
/****** IMPORTERS *******/
|
|
38
|
-
fromTinydns
|
|
37
|
+
fromTinydns(opts) {
|
|
39
38
|
// &fqdn:ip:x:ttl:timestamp:lo
|
|
40
39
|
// eslint-disable-next-line no-unused-vars
|
|
41
|
-
const [
|
|
40
|
+
const [fqdn, ip, dname, ttl, ts, loc] = opts.tinyline
|
|
41
|
+
.substring(1)
|
|
42
|
+
.split(':')
|
|
42
43
|
|
|
43
44
|
return new NS({
|
|
44
|
-
type
|
|
45
|
-
owner
|
|
46
|
-
dname
|
|
47
|
-
|
|
45
|
+
type: 'NS',
|
|
46
|
+
owner: this.fullyQualify(fqdn),
|
|
47
|
+
dname: this.fullyQualify(
|
|
48
|
+
/\./.test(dname) ? dname : `${dname}.ns.${fqdn}`,
|
|
49
|
+
),
|
|
50
|
+
ttl: parseInt(ttl, 10),
|
|
48
51
|
timestamp: ts,
|
|
49
|
-
location
|
|
52
|
+
location: loc !== '' && loc !== '\n' ? loc : '',
|
|
50
53
|
})
|
|
51
54
|
}
|
|
52
55
|
|
|
53
|
-
fromBind
|
|
56
|
+
fromBind(opts) {
|
|
54
57
|
// test.example.com 3600 IN NS dname
|
|
55
|
-
const [
|
|
58
|
+
const [owner, ttl, c, type, dname] = opts.bindline.split(/\s+/)
|
|
56
59
|
|
|
57
60
|
return new NS({
|
|
58
61
|
owner,
|
|
59
|
-
ttl
|
|
62
|
+
ttl: parseInt(ttl, 10),
|
|
60
63
|
class: c,
|
|
61
|
-
type
|
|
64
|
+
type: type,
|
|
62
65
|
dname: dname,
|
|
63
66
|
})
|
|
64
67
|
}
|
|
65
68
|
|
|
66
69
|
/****** EXPORTERS *******/
|
|
67
|
-
toBind
|
|
70
|
+
toBind(zone_opts) {
|
|
68
71
|
return `${this.getPrefix(zone_opts)}\t${this.getFQDN('dname', zone_opts)}\n`
|
|
69
72
|
}
|
|
70
73
|
|
|
71
|
-
toTinydns
|
|
74
|
+
toTinydns() {
|
|
72
75
|
return `&${this.getTinyFQDN('owner')}::${this.getTinyFQDN('dname')}:${this.getTinydnsPostamble()}\n`
|
|
73
76
|
}
|
|
74
77
|
}
|