First pass formatting with Prettier
* Added .prettierrc.json * Added .prettierignore * Formatted
This commit is contained in:
@@ -2,17 +2,17 @@
|
||||
'use strict';
|
||||
|
||||
// ENiGMA½
|
||||
const Address = require('./ftn_address.js');
|
||||
const Errors = require('./enig_error.js').Errors;
|
||||
const EnigAssert = require('./enigma_assert.js');
|
||||
const Address = require('./ftn_address.js');
|
||||
const Errors = require('./enig_error.js').Errors;
|
||||
const EnigAssert = require('./enigma_assert.js');
|
||||
|
||||
// deps
|
||||
const fs = require('graceful-fs');
|
||||
const CRC32 = require('./crc.js').CRC32;
|
||||
const _ = require('lodash');
|
||||
const async = require('async');
|
||||
const paths = require('path');
|
||||
const crypto = require('crypto');
|
||||
const fs = require('graceful-fs');
|
||||
const CRC32 = require('./crc.js').CRC32;
|
||||
const _ = require('lodash');
|
||||
const async = require('async');
|
||||
const paths = require('path');
|
||||
const crypto = require('crypto');
|
||||
|
||||
//
|
||||
// Class to read and hold information from a TIC file
|
||||
@@ -28,7 +28,11 @@ module.exports = class TicFileInfo {
|
||||
|
||||
static get requiredFields() {
|
||||
return [
|
||||
'Area', 'Origin', 'From', 'File', 'Crc',
|
||||
'Area',
|
||||
'Origin',
|
||||
'From',
|
||||
'File',
|
||||
'Crc',
|
||||
// :TODO: validate this:
|
||||
//'Path', 'Seenby' // these two are questionable; some systems don't send them?
|
||||
];
|
||||
@@ -40,13 +44,13 @@ module.exports = class TicFileInfo {
|
||||
|
||||
getAsString(key, joinWith) {
|
||||
const value = this.get(key);
|
||||
if(value) {
|
||||
if (value) {
|
||||
//
|
||||
// We call toString() on values to ensure numbers, addresses, etc. are converted
|
||||
//
|
||||
joinWith = joinWith || '';
|
||||
if(Array.isArray(value)) {
|
||||
return value.map(v => v.toString() ).join(joinWith);
|
||||
if (Array.isArray(value)) {
|
||||
return value.map(v => v.toString()).join(joinWith);
|
||||
}
|
||||
|
||||
return value.toString();
|
||||
@@ -58,12 +62,16 @@ module.exports = class TicFileInfo {
|
||||
}
|
||||
|
||||
get longFileName() {
|
||||
return this.getAsString('Lfile') || this.getAsString('Fullname') || this.getAsString('File');
|
||||
return (
|
||||
this.getAsString('Lfile') ||
|
||||
this.getAsString('Fullname') ||
|
||||
this.getAsString('File')
|
||||
);
|
||||
}
|
||||
|
||||
hasRequiredFields() {
|
||||
const req = TicFileInfo.requiredFields;
|
||||
return req.every( f => this.get(f) );
|
||||
return req.every(f => this.get(f));
|
||||
}
|
||||
|
||||
validate(config, cb) {
|
||||
@@ -77,63 +85,77 @@ module.exports = class TicFileInfo {
|
||||
async.waterfall(
|
||||
[
|
||||
function initial(callback) {
|
||||
if(!self.hasRequiredFields()) {
|
||||
return callback(Errors.Invalid('One or more required fields missing from TIC'));
|
||||
if (!self.hasRequiredFields()) {
|
||||
return callback(
|
||||
Errors.Invalid('One or more required fields missing from TIC')
|
||||
);
|
||||
}
|
||||
|
||||
const area = self.getAsString('Area').toUpperCase();
|
||||
|
||||
const localInfo = {
|
||||
areaTag : config.localAreaTags.find( areaTag => areaTag.toUpperCase() === area ),
|
||||
areaTag: config.localAreaTags.find(
|
||||
areaTag => areaTag.toUpperCase() === area
|
||||
),
|
||||
};
|
||||
|
||||
if(!localInfo.areaTag) {
|
||||
return callback(Errors.Invalid(`No local area for "Area" of ${area}`));
|
||||
if (!localInfo.areaTag) {
|
||||
return callback(
|
||||
Errors.Invalid(`No local area for "Area" of ${area}`)
|
||||
);
|
||||
}
|
||||
|
||||
const from = Address.fromString(self.getAsString('From'));
|
||||
if(!from.isValid()) {
|
||||
return callback(Errors.Invalid(`Invalid "From" address: ${self.getAsString('From')}`));
|
||||
if (!from.isValid()) {
|
||||
return callback(
|
||||
Errors.Invalid(
|
||||
`Invalid "From" address: ${self.getAsString('From')}`
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
// note that our config may have wildcards, such as "80:774/*"
|
||||
localInfo.node = Object.keys(config.nodes).find( nodeAddrWildcard => from.isPatternMatch(nodeAddrWildcard) );
|
||||
localInfo.node = Object.keys(config.nodes).find(nodeAddrWildcard =>
|
||||
from.isPatternMatch(nodeAddrWildcard)
|
||||
);
|
||||
|
||||
if(!localInfo.node) {
|
||||
if (!localInfo.node) {
|
||||
return callback(Errors.Invalid('TIC is not from a known node'));
|
||||
}
|
||||
|
||||
// if we require a password, "PW" must match
|
||||
const passActual = _.get(config.nodes, [ localInfo.node, 'tic', 'password' ] ) || config.defaultPassword;
|
||||
if(!passActual) {
|
||||
return callback(null, localInfo); // no pw validation
|
||||
const passActual =
|
||||
_.get(config.nodes, [localInfo.node, 'tic', 'password']) ||
|
||||
config.defaultPassword;
|
||||
if (!passActual) {
|
||||
return callback(null, localInfo); // no pw validation
|
||||
}
|
||||
|
||||
const passTic = self.getAsString('Pw');
|
||||
if(passTic !== passActual) {
|
||||
if (passTic !== passActual) {
|
||||
return callback(Errors.Invalid('Bad TIC password'));
|
||||
}
|
||||
|
||||
return callback(null, localInfo);
|
||||
},
|
||||
function checksumAndSize(localInfo, callback) {
|
||||
const crcTic = self.get('Crc');
|
||||
const stream = fs.createReadStream(self.filePath);
|
||||
const crc = new CRC32();
|
||||
let sizeActual = 0;
|
||||
const crcTic = self.get('Crc');
|
||||
const stream = fs.createReadStream(self.filePath);
|
||||
const crc = new CRC32();
|
||||
let sizeActual = 0;
|
||||
|
||||
let sha256Tic = self.getAsString('Sha256');
|
||||
let sha256Tic = self.getAsString('Sha256');
|
||||
let sha256;
|
||||
if(sha256Tic) {
|
||||
sha256Tic = sha256Tic.toLowerCase();
|
||||
sha256 = crypto.createHash('sha256');
|
||||
if (sha256Tic) {
|
||||
sha256Tic = sha256Tic.toLowerCase();
|
||||
sha256 = crypto.createHash('sha256');
|
||||
}
|
||||
|
||||
stream.on('data', data => {
|
||||
sizeActual += data.length;
|
||||
|
||||
// sha256 if possible, else crc32
|
||||
if(sha256) {
|
||||
if (sha256) {
|
||||
sha256.update(data);
|
||||
} else {
|
||||
crc.update(data);
|
||||
@@ -142,28 +164,40 @@ module.exports = class TicFileInfo {
|
||||
|
||||
stream.on('end', () => {
|
||||
// again, use sha256 if possible
|
||||
if(sha256) {
|
||||
if (sha256) {
|
||||
const sha256Actual = sha256.digest('hex');
|
||||
if(sha256Tic != sha256Actual) {
|
||||
return callback(Errors.Invalid(`TIC "Sha256" of ${sha256Tic} does not match actual SHA-256 of ${sha256Actual}`));
|
||||
if (sha256Tic != sha256Actual) {
|
||||
return callback(
|
||||
Errors.Invalid(
|
||||
`TIC "Sha256" of ${sha256Tic} does not match actual SHA-256 of ${sha256Actual}`
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
localInfo.sha256 = sha256Actual;
|
||||
} else {
|
||||
const crcActual = crc.finalize();
|
||||
if(crcActual !== crcTic) {
|
||||
return callback(Errors.Invalid(`TIC "Crc" of ${crcTic} does not match actual CRC-32 of ${crcActual}`));
|
||||
if (crcActual !== crcTic) {
|
||||
return callback(
|
||||
Errors.Invalid(
|
||||
`TIC "Crc" of ${crcTic} does not match actual CRC-32 of ${crcActual}`
|
||||
)
|
||||
);
|
||||
}
|
||||
localInfo.crc32 = crcActual;
|
||||
}
|
||||
|
||||
const sizeTic = self.get('Size');
|
||||
if(_.isUndefined(sizeTic)) {
|
||||
if (_.isUndefined(sizeTic)) {
|
||||
return callback(null, localInfo);
|
||||
}
|
||||
|
||||
if(sizeTic !== sizeActual) {
|
||||
return callback(Errors.Invalid(`TIC "Size" of ${sizeTic} does not match actual size of ${sizeActual}`));
|
||||
if (sizeTic !== sizeActual) {
|
||||
return callback(
|
||||
Errors.Invalid(
|
||||
`TIC "Size" of ${sizeTic} does not match actual size of ${sizeActual}`
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
return callback(null, localInfo);
|
||||
@@ -172,7 +206,7 @@ module.exports = class TicFileInfo {
|
||||
stream.on('error', err => {
|
||||
return callback(err);
|
||||
});
|
||||
}
|
||||
},
|
||||
],
|
||||
(err, localInfo) => {
|
||||
return cb(err, localInfo);
|
||||
@@ -199,7 +233,7 @@ module.exports = class TicFileInfo {
|
||||
//
|
||||
const to = this.get('To');
|
||||
|
||||
if(!to) {
|
||||
if (!to) {
|
||||
return allowNonExplicit;
|
||||
}
|
||||
|
||||
@@ -208,12 +242,12 @@ module.exports = class TicFileInfo {
|
||||
|
||||
static createFromFile(path, cb) {
|
||||
fs.readFile(path, 'utf8', (err, ticData) => {
|
||||
if(err) {
|
||||
if (err) {
|
||||
return cb(err);
|
||||
}
|
||||
|
||||
const ticFileInfo = new TicFileInfo();
|
||||
ticFileInfo.path = path;
|
||||
const ticFileInfo = new TicFileInfo();
|
||||
ticFileInfo.path = path;
|
||||
|
||||
//
|
||||
// Lines in a TIC file should be separated by CRLF (DOS)
|
||||
@@ -226,51 +260,51 @@ module.exports = class TicFileInfo {
|
||||
let entry;
|
||||
|
||||
lines.forEach(line => {
|
||||
keyEnd = line.search(/\s/);
|
||||
keyEnd = line.search(/\s/);
|
||||
|
||||
if(keyEnd < 0) {
|
||||
if (keyEnd < 0) {
|
||||
keyEnd = line.length;
|
||||
}
|
||||
|
||||
key = line.substr(0, keyEnd).toLowerCase();
|
||||
|
||||
if(0 === key.length) {
|
||||
if (0 === key.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
value = line.substr(keyEnd + 1);
|
||||
|
||||
// don't trim Ldesc; may mess with FILE_ID.DIZ type descriptions
|
||||
if('ldesc' !== key) {
|
||||
if ('ldesc' !== key) {
|
||||
value = value.trim();
|
||||
}
|
||||
|
||||
// convert well known keys to a more reasonable format
|
||||
switch(key) {
|
||||
case 'origin' :
|
||||
case 'from' :
|
||||
case 'seenby' :
|
||||
case 'to' :
|
||||
switch (key) {
|
||||
case 'origin':
|
||||
case 'from':
|
||||
case 'seenby':
|
||||
case 'to':
|
||||
value = Address.fromString(value);
|
||||
break;
|
||||
|
||||
case 'crc' :
|
||||
case 'crc':
|
||||
value = parseInt(value, 16);
|
||||
break;
|
||||
|
||||
case 'size' :
|
||||
case 'size':
|
||||
value = parseInt(value, 10);
|
||||
break;
|
||||
|
||||
default :
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
entry = ticFileInfo.entries.get(key);
|
||||
|
||||
if(entry) {
|
||||
if(!Array.isArray(entry)) {
|
||||
entry = [ entry ];
|
||||
if (entry) {
|
||||
if (!Array.isArray(entry)) {
|
||||
entry = [entry];
|
||||
ticFileInfo.entries.set(key, entry);
|
||||
}
|
||||
entry.push(value);
|
||||
|
||||
Reference in New Issue
Block a user