send/server/metadata.js

47 lines
1.2 KiB
JavaScript
Raw Normal View History

2020-07-27 18:18:52 +00:00
const crypto = require('crypto');
function makeToken(secret, counter) {
const hmac = crypto.createHmac('sha256', secret);
hmac.update(String(counter));
return hmac.digest('hex');
}
2018-02-06 22:31:18 +00:00
class Metadata {
2020-07-27 18:18:52 +00:00
constructor(obj, storage) {
this.id = obj.id;
2018-02-06 22:31:18 +00:00
this.dl = +obj.dl || 0;
2020-07-27 18:18:52 +00:00
this.dlToken = +obj.dlToken || 0;
2018-02-06 22:31:18 +00:00
this.dlimit = +obj.dlimit || 1;
2020-07-27 18:18:52 +00:00
this.pwd = !!+obj.pwd;
2018-02-06 22:31:18 +00:00
this.owner = obj.owner;
this.metadata = obj.metadata;
this.auth = obj.auth;
this.nonce = obj.nonce;
this.flagged = !!obj.flagged;
this.dead = !!obj.dead;
2020-07-27 18:18:52 +00:00
this.fxa = !!+obj.fxa;
this.storage = storage;
}
async getDownloadToken() {
if (this.dlToken >= this.dlimit) {
throw new Error('limit');
}
this.dlToken = await this.storage.incrementField(this.id, 'dlToken');
// another request could have also incremented
if (this.dlToken > this.dlimit) {
throw new Error('limit');
}
return makeToken(this.owner, this.dlToken);
}
async verifyDownloadToken(token) {
const validTokens = Array.from({ length: this.dlToken }, (_, i) =>
makeToken(this.owner, i + 1)
);
return validTokens.includes(token);
2018-02-06 22:31:18 +00:00
}
}
module.exports = Metadata;