tenebrous-dicebot/api/node_modules/dns-txt/index.js

95 lines
2.5 KiB
JavaScript

'use strict'
var bindexOf = require('buffer-indexof')
var equalSign = new Buffer('=')
module.exports = function (opts) {
var binary = opts ? opts.binary : false
var that = {}
that.encode = function (data, buf, offset) {
if (!data) data = {}
if (!offset) offset = 0
if (!buf) buf = new Buffer(that.encodingLength(data) + offset)
var oldOffset = offset
var keys = Object.keys(data)
if (keys.length === 0) {
buf[offset] = 0
offset++
}
keys.forEach(function (key) {
var val = data[key]
var oldOffset = offset
offset++
if (val === true) {
offset += buf.write(key, offset)
} else if (Buffer.isBuffer(val)) {
offset += buf.write(key + '=', offset)
var len = val.length
val.copy(buf, offset, 0, len)
offset += len
} else {
offset += buf.write(key + '=' + val, offset)
}
buf[oldOffset] = offset - oldOffset - 1
})
that.encode.bytes = offset - oldOffset
return buf
}
that.decode = function (buf, offset, len) {
if (!offset) offset = 0
if (!Number.isFinite(len)) len = buf.length
var data = {}
var oldOffset = offset
while (offset < len) {
var b = decodeBlock(buf, offset)
var i = bindexOf(b, equalSign)
offset += decodeBlock.bytes
if (b.length === 0) continue // ignore: most likely a single zero byte
if (i === -1) data[b.toString().toLowerCase()] = true
else if (i === 0) continue // ignore: invalid key-length
else {
var key = b.slice(0, i).toString().toLowerCase()
if (key in data) continue // ignore: overwriting not allowed
data[key] = binary ? b.slice(i + 1) : b.slice(i + 1).toString()
}
}
that.decode.bytes = offset - oldOffset
return data
}
that.encodingLength = function (data) {
if (!data) return 1 // 1 byte (single empty byte)
var keys = Object.keys(data)
if (keys.length === 0) return 1 // 1 byte (single empty byte)
return keys.reduce(function (total, key) {
var val = data[key]
total += Buffer.byteLength(key) + 1 // +1 byte to store field length
if (Buffer.isBuffer(val)) total += val.length + 1 // +1 byte to fit equal sign
else if (val !== true) total += Buffer.byteLength(String(val)) + 1 // +1 byte to fit equal sign
return total
}, 0)
}
return that
}
function decodeBlock (buf, offset) {
var len = buf[offset]
var to = offset + 1 + len
var b = buf.slice(offset + 1, to > buf.length ? buf.length : to)
decodeBlock.bytes = len + 1
return b
}