/**
 * DataCollector - In-memory data storage with CSV/JSON export and localStorage backup.
 */
class DataCollector {
  constructor(taskName) {
    this.taskName = taskName;
    this.data = [];
    this.columns = [];
    this.storageKey = `gorilla_${taskName}_data`;
    this._restoreFromStorage();
  }

  /** Define the columns for the dataset */
  setColumns(columns) {
    this.columns = columns;
  }

  /** Add a trial/row of data */
  addRow(row) {
    // Add timestamp
    row._timestamp = new Date().toISOString();
    this.data.push(row);
    this._backupToStorage();
  }

  /** Get all collected data */
  getData() {
    return [...this.data];
  }

  /** Get count of collected rows */
  getCount() {
    return this.data.length;
  }

  /** Export as CSV string */
  toCSV() {
    if (this.data.length === 0) return '';

    const cols = this.columns.length > 0
      ? this.columns
      : Object.keys(this.data[0]);

    const header = cols.join(',');
    const rows = this.data.map(row =>
      cols.map(col => {
        const val = row[col] ?? '';
        const str = String(val);
        // Escape CSV values that contain commas, quotes, or newlines
        if (str.includes(',') || str.includes('"') || str.includes('\n')) {
          return `"${str.replace(/"/g, '""')}"`;
        }
        return str;
      }).join(',')
    );

    return [header, ...rows].join('\n');
  }

  /** Export as JSON string */
  toJSON() {
    return JSON.stringify(this.data, null, 2);
  }

  /** Download data as a CSV file */
  downloadCSV(filename) {
    filename = filename || `${this.taskName}_${this._dateStr()}.csv`;
    this._downloadFile(this.toCSV(), filename, 'text/csv');
  }

  /** Download data as a JSON file */
  downloadJSON(filename) {
    filename = filename || `${this.taskName}_${this._dateStr()}.json`;
    this._downloadFile(this.toJSON(), filename, 'application/json');
  }

  /** Clear all collected data */
  clear() {
    this.data = [];
    localStorage.removeItem(this.storageKey);
  }

  // Private helpers

  _backupToStorage() {
    try {
      localStorage.setItem(this.storageKey, JSON.stringify(this.data));
    } catch { /* storage full or unavailable */ }
  }

  _restoreFromStorage() {
    try {
      const stored = localStorage.getItem(this.storageKey);
      if (stored) {
        const parsed = JSON.parse(stored);
        if (Array.isArray(parsed) && parsed.length > 0) {
          console.log(`DataCollector: Restored ${parsed.length} rows from localStorage`);
          this.data = parsed;
        }
      }
    } catch { /* ignore */ }
  }

  _downloadFile(content, filename, mimeType) {
    const blob = new Blob([content], { type: mimeType });
    const url = URL.createObjectURL(blob);
    const a = document.createElement('a');
    a.href = url;
    a.download = filename;
    document.body.appendChild(a);
    a.click();
    document.body.removeChild(a);
    URL.revokeObjectURL(url);
  }

  _dateStr() {
    return new Date().toISOString().replace(/[:.]/g, '-').slice(0, 19);
  }
}
