// eslint-disable-next-line you-dont-need-lodash-underscore/get
import get from 'lodash/get';
/**
 * Utility function that makes iterating over async calls step by step
 * @param {array} array - target array
 * @param {func} callback - an async action to perform
 */
const asyncForEach = async (array, callback) => {
  for (let index = 0; index < array.length; index++) {
    await callback(array[index], index, array);
  }
};

/**
 * This method checks folder depth against provided limit
 * @param {number} maxLevel - max depth
 * @param {string} fullPath - a path to validate
 */
const isDepthAllowed = (maxLevel, fullPath) => {
  let checkResult = true;
  if (maxLevel) {
    checkResult = fullPath.slice(1).split('/').length <= maxLevel;
  }
  return checkResult;
};

/**
 * This method converts callback pattern of readEntries to Promise pattern
 * 'readEntries' entries by batches
 */
const readEntriesAsync = directoryReader => new Promise(resolve => {
  let allEntries = [];
  function readEntries() {
    directoryReader.readEntries(entries => {
      if (entries && entries.length) {
        allEntries = allEntries.concat(entries);
        readEntries();
        return;
      }
      resolve(allEntries);
    }, () => resolve());
  }
  readEntries();
});

/**
 * Converts callback pattern to Promise pattern
 */
const getEntryFileAsync = itemEntry => new Promise(resolve =>
// eslint-disable-next-line no-promise-executor-return
itemEntry.file(resolve, () => resolve()));

/**
 * Check for feature support
 */
const isItemsFileStructureSupported = items => {
  const browserSupports = !!window.DataTransfer && !!window.DataTransferItemList && !!window.DataTransferItem;
  const itemsAllow = get(items, '[0].webkitGetAsEntry');
  // Cypress does not support webkitGetAsEntry, so fileUploader becomes impossible to test
  return browserSupports && itemsAllow && !window.Cypress;
};

/**
 * Default file structure adaptor
 */

const defaultFileStructureAdapter = () => {
  const adaptedFileStructure = [];
  const addFile = ({
    file,
    path
  }) => {
    adaptedFileStructure.push({
      file,
      name: file.name,
      path: path.replace(/^\//g, ''),
      timestamp: new Date().getTime()
    });
  };
  const resetFileStructure = () => {
    adaptedFileStructure.length = 0;
  };
  return {
    adaptedFileStructure,
    addFile,
    resetFileStructure
  };
};
export { asyncForEach, defaultFileStructureAdapter, isDepthAllowed, readEntriesAsync, getEntryFileAsync, isItemsFileStructureSupported };