UNPKG

1.96 kBJavaScriptView Raw
1"use strict";
2
3const minimatch = require("minimatch");
4
5const dbs = {};
6const strictFormats = [
7 /^([0-9A-F]{2}[:-]){5}([0-9A-F]{2})$/i,
8 /^([0-9A-F]{2}[:-]){2}([0-9A-F]{2})$/i,
9 /^([0-9A-F]{4}[.]){2}([0-9A-F]{4})$/i,
10 /^[0-9A-F]{6}$/i,
11 /^[0-9A-F]{12}$/i
12];
13
14module.exports = (input, opts = {}) => {
15 if (typeof input !== "string") throw new Error("Input not a string");
16
17 const file = opts.file || "./oui.json";
18 if (!dbs[file]) dbs[file] = require(file);
19 const db = dbs[file];
20 input = input.toUpperCase();
21
22 if (opts.strict) {
23 const isStrict = strictFormats.some(regex => regex.test(input));
24 if (!isStrict) throw new Error("Input not in strict format");
25 input = input.replace(/[.:-]/g, "").substring(0, 6);
26 } else {
27 input = zeroPad(input).replace(/[^0-9a-fA-F]/g, "").substring(0, 6);
28 }
29
30 if (input.length < 6) return null;
31 return db[input] || null;
32};
33
34module.exports.search = (inputs, opts = {}) => {
35 if (typeof inputs !== "string" && !Array.isArray(inputs)) throw new Error("Input not a string or Array");
36 inputs = Array.isArray(inputs) ? inputs : [inputs];
37 const file = opts.file || "./oui.json";
38 if (!dbs[file]) dbs[file] = require(file);
39 const db = dbs[file];
40
41 const results = [];
42 for (const oui of Object.keys(db)) {
43 const organization = db[oui];
44 if (inputs.every(pattern => minimatch(organization, pattern, opts))) {
45 results.push({oui, organization});
46 }
47 }
48 return results;
49};
50
51module.exports.update = (opts) => {
52 return new Promise((resolve, reject) => {
53 opts = Object.assign({cli: false}, opts);
54 require("./update.js")(opts).then(newdb => {
55 dbs["./oui.json"] = newdb;
56 resolve();
57 }).catch(reject);
58 });
59};
60
61// Zero-pad colon notation as seen in BSD `arp`. eg. 1:2:3 should become 01:02:03
62function zeroPad(str) {
63 if (!/^[0-9A-F:]+$/.test(str)) return str;
64 return str.split(":").map(part => part.length === 1 ? `0${part}` : part).join(":");
65}