"use strict";

const fs      = require('fs');
const path    = require('path');
const console = require('gifer-console');

function PluginAllowlist(opts){
    var cachePath = path.join(opts.profileRoot, 'allowlist.json');
    var rows      = null;

    try {
        var cached = JSON.parse(fs.readFileSync(cachePath, 'utf8'));

        rows = Array.isArray(cached.plugins) ? cached.plugins : null;
        if (rows) console.info('[plugins] allowlist cache loaded: revision=' + cached.revision + ' plugins=' + rows.length, console.logLevel.INFO);
    } catch (e) {
        rows = null;
    }

    function setList(payload){
        var normalized = {
            revision: payload.revision,
            plugins : (payload.plugins || []).map(function(row){
                return { id: row.id, name: row.name || row.id, checksum: row.checksum };
            })
        };
        var tmp = cachePath + '.tmp';

        fs.mkdirSync(path.dirname(cachePath), { recursive: true });
        fs.writeFileSync(tmp, JSON.stringify(normalized, null, 2), 'utf8');

        try {
            fs.renameSync(tmp, cachePath);
            rows = normalized.plugins;
            console.info('[plugins] allowlist updated: revision=' + normalized.revision + ' plugins=' + rows.length, console.logLevel.INFO);
        } catch (e) {
            try { fs.unlinkSync(tmp); } catch (ignore) {}
            console.error('[plugins] allowlist write failed: ' + e.message, console.logLevel.ERROR);
            throw e;
        }
    }

    function verify(id, checksum){
        if (!rows) return false;

        return rows.some(function(row){
            return row.id === id && row.checksum === checksum;
        });
    }

    this.setList  = setList;
    this.verify   = verify;
    this.hasCache = function(){ return rows !== null; };
}

module.exports = PluginAllowlist;
