<commit_before>package org.basex.query.func.file;

import static org.basex.query.QueryError.*;

import java.io.*;
import java.nio.file.*;

import org.basex.query.*;
import org.basex.query.value.item.*;

/**
 * Function implementation.
 *
 * @author BaseX Team 2005-15, BSD License
 * @author <NAME>
 */
public class FileCopy extends FileFn {
  @Override
  public Item item(final QueryContext qc) throws IOException, QueryException {
    return relocate(true, qc);
  }

  /**
   * Transfers a file path, given a source and a target.
   * @param copy copy flag (no move)
   * @param qc query context
   * @return result
   * @throws QueryException query exception
   * @throws IOException I/O exception
   */
  final synchronized Item relocate(final boolean copy, final QueryContext qc)
      throws QueryException, IOException {

    final Path source = toPath(0, qc);
    if(!Files.exists(source)) throw FILE_NOT_FOUND_X.get(info, source);
    final Path src = absolute(source);
    Path trg = absolute(toPath(1, qc));

    if(Files.isDirectory(trg)) {
      // target is a directory: attach file name
      trg = trg.resolve(src.getFileName());
      if(Files.isDirectory(trg)) throw FILE_IS_DIR_X.get(info, trg);
    } else if(!Files.exists(trg)) {
      // target does not exist: ensure that parent exists
      if(!Files.isDirectory(trg.getParent())) throw FILE_NO_DIR_X.get(info, trg);
    } else if(Files.isDirectory(src)) {
      // if target is file, source cannot be a directory
      throw FILE_IS_DIR_X.get(info, src);
    }

    // ignore operations on identical, canonical source and target path
    if(copy) {
      copy(src, trg);
    } else {
      Files.move(src, trg, StandardCopyOption.REPLACE_EXISTING);
    }
    return null;
  }

  /**
   * Recursively copies files.
   * @param src source path
   * @param trg target path
   * @throws IOException I/O exception
   */
  private synchronized void copy(final Path src, final Path trg) throws IOException {
    if(Files.isDirectory(src)) {
      Files.createDirectory(trg);
      try(DirectoryStream<Path> paths = Files.newDirectoryStream(src)) {
        for(final Path p : paths) copy(p, trg.resolve(p.getFileName()));
      }
    } else {
      Files.copy(src, trg, StandardCopyOption.REPLACE_EXISTING);
    }
  }
}<commit_msg>[FIX] XQuery, file:move: move to different file systems<commit_after>package org.basex.query.func.file;

import static org.basex.query.QueryError.*;

import java.io.*;
import java.nio.file.*;

import org.basex.query.*;
import org.basex.query.value.item.*;

/**
 * Function implementation.
 *
 * @author BaseX Team 2005-15, BSD License
 * @author <NAME>
 */
public class FileCopy extends FileFn {
  @Override
  public Item item(final QueryContext qc) throws IOException, QueryException {
    return relocate(true, qc);
  }

  /**
   * Transfers a file path, given a source and a target.
   * @param copy copy flag (no move)
   * @param qc query context
   * @return result
   * @throws QueryException query exception
   * @throws IOException I/O exception
   */
  final synchronized Item relocate(final boolean copy, final QueryContext qc)
      throws QueryException, IOException {

    final Path source = toPath(0, qc);
    if(!Files.exists(source)) throw FILE_NOT_FOUND_X.get(info, source);
    final Path src = absolute(source);
    Path trg = absolute(toPath(1, qc));

    if(Files.isDirectory(trg)) {
      // target is a directory: attach file name
      trg = trg.resolve(src.getFileName());
      if(Files.isDirectory(trg)) throw FILE_IS_DIR_X.get(info, trg);
    } else if(!Files.exists(trg)) {
      // target does not exist: ensure that parent exists
      if(!Files.isDirectory(trg.getParent())) throw FILE_NO_DIR_X.get(info, trg);
    } else if(Files.isDirectory(src)) {
      // if target is file, source cannot be a directory
      throw FILE_IS_DIR_X.get(info, src);
    }

    // ignore operations on identical, canonical source and target path
    relocate(src, trg, copy);
    return null;
  }

  /**
   * Recursively copies files.
   * @param src source path
   * @param trg target path
   * @param copy copy flag
   * @throws IOException I/O exception
   */
  private synchronized void relocate(final Path src, final Path trg, final boolean copy)
      throws IOException {

    if(Files.isDirectory(src)) {
      Files.createDirectory(trg);
      try(DirectoryStream<Path> paths = Files.newDirectoryStream(src)) {
        for(final Path p : paths) relocate(p, trg.resolve(p.getFileName()), copy);
      }
      if(!copy) Files.delete(src);
    } else if(copy) {
      Files.copy(src, trg, StandardCopyOption.REPLACE_EXISTING);
    } else {
      Files.move(src, trg, StandardCopyOption.REPLACE_EXISTING);
    }
  }
}
{'fraction_non_alphanumeric': 0.11631834494405742, 'fraction_numerical': 0.0033776651889381466, 'mean_word_length': 3.25696316262354, 'pattern_counts': {'":': 0, '<': 7, '<?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': '6614024', 'n_tokens_mistral': 1491, 'n_tokens_neox': 1467, 'n_words': 420}