ts_sqlx 0.1.3

Typescript SQLx compile-time checked queries without a DSL.
Documentation
use std::path::{Path, PathBuf, MAIN_SEPARATOR};

use once_cell::sync::Lazy;
use regex::Regex;
use walkdir::WalkDir;

pub fn pattern_to_regex(pattern: &str) -> Regex {
  let pattern = pattern.replace('!', "");
  let pattern = pattern.replace('.', "\\.");
  let pattern = pattern.replace('*', ".*");
  let pattern = format!("^{}$", pattern);
  Regex::new(&pattern).unwrap()
}

static NODE_MODULES: Lazy<String> =
  Lazy::new(|| format!("{}node_modules{}", MAIN_SEPARATOR, MAIN_SEPARATOR));

pub fn is_valid_path(
  entry_path: &str,
  extension: Option<&str>,
  ignore_regexes: &[(Regex, bool)],
  extensions: &[String],
) -> bool {
  if entry_path.contains(NODE_MODULES.as_str()) {
    return false;
  }
  let should_ignore = ignore_regexes.iter().any(|(re, not)| {
    if *not {
      !re.is_match(entry_path)
    } else {
      re.is_match(entry_path)
    }
  });
  if should_ignore {
    return false;
  }
  let valid_extension = if let Some(ext) = extension {
    extensions.contains(&ext.to_lowercase())
  } else {
    false
  };

  if valid_extension {
    return true;
  } else {
    return false;
  }
}

pub fn scan_folder(
  folder: &Path,
  extensions: &[String],
  ignore_regexes: &[(Regex, bool)],
) -> Vec<PathBuf> {
  let result: Vec<_> = WalkDir::new(Path::new(folder))
    .follow_links(true)
    .into_iter()
    .filter_map(|e| e.ok())
    .filter(|entry| {
      if let Some(entry_path) = entry.path().as_os_str().to_str() {
        is_valid_path(
          entry_path,
          entry.path().extension().and_then(|os| os.to_str()),
          &ignore_regexes,
          &extensions,
        )
      } else {
        false
      }
    })
    .map(|entry| entry.path().to_owned())
    .collect();

  result
}