<commit_before>"use strict";

const whatwgEncoding = require("whatwg-encoding");
const parseContentType = require("content-type-parser");
const querystring = require("querystring");
const DOMException = require("../../web-idl/DOMException");
const EventTargetImpl = require("../events/EventTarget-impl").implementation;
const ProgressEvent = require("../generated/ProgressEvent");

const READY_STATES = Object.freeze({
  EMPTY: 0,
  LOADING: 1,
  DONE: 2
});

exports.implementation = class FileReaderImpl extends EventTargetImpl {
  constructor(args, privateData) {
    super([], privateData);

    this.error = null;
    this.readyState = READY_STATES.EMPTY;
    this.result = null;

    this.onloadstart = null;
    this.onprogress = null;
    this.onload = null;
    this.onabort = null;
    this.onerror = null;
    this.onloadend = null;

    this._ownerDocument = privateData.window.document;
  }

  readAsArrayBuffer(file) {
    this._readFile(file, "buffer");
  }
  readAsDataURL(file) {
    this._readFile(file, "dataURL");
  }
  readAsText(file, encoding) {
    this._readFile(file, "text", whatwgEncoding.labelToName(encoding) || "UTF-8");
  }

  abort() {
    if (this.readyState === READY_STATES.DONE || this.readyState === READY_STATES.EMPTY) {
      this.result = null;
      return;
    }

    if (this.readyState === READY_STATES.LOADING) {
      this.readyState = READY_STATES.DONE;
    }

    this._fireProgressEvent("abort");
    this._fireProgressEvent("loadend");
  }

  _fireProgressEvent(name, props) {
    const event = ProgressEvent.createImpl([name, Object.assign({ bubbles: false, cancelable: false }, props)], {});
    this.dispatchEvent(event);
  }

  _readFile(file, format, encoding) {
    if (this.readyState === READY_STATES.LOADING) {
      throw new DOMException(DOMException.INVALID_STATE_ERR);
    }

    this.readyState = READY_STATES.LOADING;
    this._fireProgressEvent("loadstart");

    process.nextTick(() => {
      let data = file._buffer;
      if (!data) {
        data = new Buffer("");
      }
      this._fireProgressEvent("progress", {
        lengthComputable: !isNaN(file.size),
        total: file.size,
        loaded: data.length
      });

      process.nextTick(() => {
        switch (format) {
          default:
          case "buffer": {
            this.result = (new Uint8Array(data)).buffer;
            break;
          }
          case "dataURL": {
            let dataUrl = "data:";
            const contentType = parseContentType(file.type);
            if (contentType && contentType.isText()) {
              const fallbackEncoding = whatwgEncoding.getBOMEncoding(data) ||
                whatwgEncoding.labelToName(contentType.get("charset")) || "UTF-8";
              const decoded = whatwgEncoding.decode(data, fallbackEncoding);

              contentType.set("charset", encoding);
              dataUrl += contentType.toString();
              dataUrl += ",";
              dataUrl += querystring.escape(decoded);
            } else {
              if (contentType) {
                dataUrl += contentType.toString();
              }
              dataUrl += ";base64,";
              dataUrl += data.toString("base64");<commit_msg>Make fileReader.abort() terminate ongoing reads properly<commit_after>"use strict";

const whatwgEncoding = require("whatwg-encoding");
const parseContentType = require("content-type-parser");
const querystring = require("querystring");
const DOMException = require("../../web-idl/DOMException");
const EventTargetImpl = require("../events/EventTarget-impl").implementation;
const ProgressEvent = require("../generated/ProgressEvent");

const READY_STATES = Object.freeze({
  EMPTY: 0,
  LOADING: 1,
  DONE: 2
});

exports.implementation = class FileReaderImpl extends EventTargetImpl {
  constructor(args, privateData) {
    super([], privateData);

    this.error = null;
    this.readyState = READY_STATES.EMPTY;
    this.result = null;

    this.onloadstart = null;
    this.onprogress = null;
    this.onload = null;
    this.onabort = null;
    this.onerror = null;
    this.onloadend = null;

    this._ownerDocument = privateData.window.document;
    this._terminated = false;
  }

  readAsArrayBuffer(file) {
    this._readFile(file, "buffer");
  }
  readAsDataURL(file) {
    this._readFile(file, "dataURL");
  }
  readAsText(file, encoding) {
    this._readFile(file, "text", whatwgEncoding.labelToName(encoding) || "UTF-8");
  }

  abort() {
    if (this.readyState === READY_STATES.EMPTY || this.readyState === READY_STATES.DONE) {
      this.result = null;
      return;
    }

    if (this.readyState === READY_STATES.LOADING) {
      this.readyState = READY_STATES.DONE;
      this.result = null;
    }

    this._terminated = true;
    this._fireProgressEvent("abort");
    this._fireProgressEvent("loadend");
  }

  _fireProgressEvent(name, props) {
    const event = ProgressEvent.createImpl([name, Object.assign({ bubbles: false, cancelable: false }, props)], {});
    this.dispatchEvent(event);
  }

  _readFile(file, format, encoding) {
    if (this.readyState === READY_STATES.LOADING) {
      throw new DOMException(DOMException.INVALID_STATE_ERR);
    }

    this.readyState = READY_STATES.LOADING;

    setImmediate(() => {
      if (this._terminated) {
        this._terminated = false;
        return;
      }

      this._fireProgressEvent("loadstart");

      let data = file._buffer;
      if (!data) {
        data = new Buffer("");
      }
      this._fireProgressEvent("progress", {
        lengthComputable: !isNaN(file.size),
        total: file.size,
        loaded: data.length
      });

      setImmediate(() => {
        if (this._terminated) {
          this._terminated = false;
          return;
        }

        switch (format) {
          default:
          case "buffer": {
            this.result = (new Uint8Array(data)).buffer;
            break;
          }
          case "dataURL": {
            let dataUrl = "data:";
            const contentType = parseContentType(file.type);
            if (contentType && contentType.isText()) {
              const fallbackEncoding = whatwgEncoding.getBOMEncoding(data) ||
                whatwgEncoding.labelToName(contentType.get("charset")) || "UTF-8";
              const decoded = whatwgEncoding.decode(data, fallbackEncoding);

              contentType.set("charset", encoding);
              dataUrl += contentType.toString();
              dataUrl += ",";
              dataUrl += querystring.escape(decoded);
            } else {
              if (contentType) {
                dataUrl += contentType.toString();
              }
              dataUrl += ";base64,";
              dataUrl += data.toString("base64");
{'fraction_non_alphanumeric': 0.13396702807069658, 'fraction_numerical': 0.0029704440813901676, 'mean_word_length': 2.58955223880597, 'pattern_counts': {'":': 4, '<': 3, '<?xml version=': 0, '>': 7, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6335486', 'n_tokens_mistral': 2030, 'n_tokens_neox': 1960, 'n_words': 364}