Tengo una página web que muestra una lista de mis archivos locales, y tengo una barra de búsqueda que recorre la lista de archivos y resalta la primera coincidencia.

Sin embargo, ¿cómo puedo mostrar los archivos solo cuando un usuario busca un nombre de archivo? Entonces, en lugar de mostrar todos los archivos, solo me gustaría que se devuelvan los archivos que coinciden con los criterios de búsqueda.

PHP, JavaScript, jQuery es totalmente una opción aquí si alguien puede ayudar en esa área.

Testexec.php:

<?php
$path = '/var/www/html/'; //get list of files
$files = scandir($path);

//display the links

foreach($files as $file) {
     if($file != '.' && $file != '..') {
        echo '<div><a href="readfile.php?file='.urlencode($file).'"> '.$file.'</a></div>';
     }
}

?>

Readfile.php:

<?php
 // PHP script to allow the file to be downloaded
$filename = $_GET['file'];

if (file_exists($filename)) {
  header('Content-Description: File Transfer');
  header('Content-Type: application/octet-stream');
  header('Content-Disposition: attachment; 
filename="'.basename($filename).'"');
  header('Expires: 0');
  header('Cache-Control: must-revalidate');
  header('Pragma: public');
  header('Content-Length: ' . filesize($file));
  readfile($filename);
  exit;
 }
 ?>
    //JavaScript for searchbar

     function FindNext() {
     var str = document.getElementById ("livesearch").value;
            if (str == "") {
                alert ("Please enter some text to search!");
                return;
            }
     var supported = false;
            var found = false;
            if (window.find) {        // Firefox, Google Chrome, Safari
                supported = true;
                    // if some content is selected, the start position of the search 
                    // will be the end position of the selection
                found = window.find (str);
            } else {
                if (document.selection && document.selection.createRange) { // Internet Explorer, Opera before version 10.5
                    var textRange = document.selection.createRange ();
                    if (textRange.findText) {   // Internet Explorer
                        supported = true;
                            // if some content is selected, the start position of the search 
                            // will be the position after the start position of the selection
                        if (textRange.text.length > 0) {
                            textRange.collapse (true);
                            textRange.move ("character", 1);
                        }

                        found = textRange.findText (str);
                        if (found) {
                            textRange.select ();
                        }
                    }
                }
            }

            if (supported) {
                if (!found) {
                    alert ("The following text was not found:\n" + str);
                }
            }
            else {
                alert ("Your browser does not support this example!");
            }
        }
    
1
Kai 23 feb. 2018 a las 13:57

3 respuestas

La mejor respuesta

Esto es realmente fácil. solo necesita usar el evento keyup y alguna corrección de código

Index.php

<input type="text" id="searchbar" placeholder="search file"> <span id="loading" style="display:none;">loading</span>
<div id="result"></div>
<script src="../../vendor/jquery/jquery-3.2.1.min.js"></script>
<script>
    $(function(){
        $('#searchbar').keyup(function(){//event after user release keyboard
            var val = $(this).val();
            if(val.length >= 2){//min 2 words to start find
                $.ajax({
                    url: 'search.php',
                    type: 'POST',
                    dataType: 'json', //we use json
                    data: {keyword: val},
                    beforeSend: function(){
                        $('#loading').show();
                    },
                    success: function(d){
                        if(d.ok==1){
                            $('#result').html(d.list);
                        }else{
                            alert(d.msg);
                        }
                        $('#loading').hide();
                    },
                    error: function(d){
                        alert('error');
                        $('#loading').hide();
                    }
                });
            }
        })
    });
</script>

Search.php

<?php
$path = 'C:/xampp/htdocs/';
$keyword = isset($_POST['keyword']) ? $_POST['keyword'] : '';
$scan = scandir($path);
$result = array('ok'=>0); //prepare output cz we will use json instead text/html
if($scan !== false){
    $result['ok']=1;
    $list = array();
    foreach($scan as $file){
        if(is_file($path.$file)){ //only file
            if(preg_match('/'.$keyword.'/', $file)) //is file containts keyword?
            $list[] = '<div><a href="readfile.php?file='.$file.'">'.$file.'</a></div>';
        }
    }
    $result['list'] = count($list) == 0 ? 'no file match': $list;
}else
    $result['msg'] = "failed open dir";

echo json_encode($result);

Readfile.php

<?php
 // PHP script to allow the file to be downloaded
$filename = $_GET['file'];
$path = 'C:/xampp/htdocs/';
$fullPath = $path.$filename; //you need this
if (file_exists($fullPath)) {
  header('Content-Description: File Transfer');
  header('Content-Type: application/octet-stream');
  header('Content-Disposition: attachment; filename="'.basename($filename).'"');
  header('Expires: 0');
  header('Cache-Control: must-revalidate');
  header('Pragma: public');
  header('Content-Length: ' . filesize($fullPath));
  readfile($fullPath);
  exit;
 }
 ?>
0
plonknimbuzz 24 feb. 2018 a las 13:57

Hay muchas formas de hacer eso.

Sugeriría que:

  1. Haga que su PHP responda un JSON con los archivos que coinciden con un criterio dado. Entonces le preguntará al PHP, pasando los datos POST o la cadena QUERY el "texto" que se está buscando. Le dará solo los archivos que coincidan.

  2. En su archivo html (también podría ser otro PHP), llamará a ajax (puede usar jQuery) a la página de arriba cada vez que el usuario cambie el texto de búsqueda. Es bueno "acelerar" (ver biblioteca lodash / subrayado) (esperar un tiempo esperando más pulsaciones de teclas).

  3. Después de recibir el JSON con los archivos que coinciden, cree dinámicamente su tabla (u otra forma que desee).

Search.php:

<?php
header('Content-Type: application/json');

$path = '/var/www/html/'; //get list of files
$files = scandir($path);
$search = $_GET['search'];

$links = array();

foreach ($files as $file) {
    if($file != '.' && $file != '..' && strpos(strtolower($file), strtolower($search)) !== false) {
        array_push($links, array(
            "name" => $file,
            "url" => "readfile.php?file=" . urlencode($file)
        ));
    }
}

echo json_encode($data);
?>

Index.php / index.html

<html>
<head>
    <script src="http://code.jquery.com/jquery-2.2.4.min.js">
    <script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.5/lodash.min.js">
</head>
<body>

    <input id="searchbox" type="text" placeholder="search for files" />

    <div id="results">
    </div>

    <script>
        $(function () {
          var searchbox = $("#searchbox");
          var results = $("#results");
          var doSearch = _.throttle(function () {
              var searchtext = searchbox.val();
              $.ajax({
                  type: 'get',
                  url: 'search.php',
                  dataType: "json",
                  data: {
                      search: searchtext
                  }
              }).done(function (response) {
                  results.html(response.reduce(function (html, item) {
                      return html + '<div><a href="' + item.url + '">' + item.name + '</a></div>';
                  }, ''));
              });
          }, 200);
          searchbox.on('keydown', doSearch);
        });
    </script>
</body>
</html>
0
Rafael Paulino 23 feb. 2018 a las 11:19

Esta es la idea más simple.

Interfaz

Index.html

$('input').keydown(function(e) {
  var str = $(this).val();
  alert(str);
  $.get("/search.php?query=" + str, function(data) {
    $('.result').html(data);
  });
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<h3>File search and download</h3>
<input name="filename" placeholder="file name" class="kw"/>
<div class="result">
</div>

Backend

Search.php

<?php
// You need code search file
// after search $files
$str = '';
foreach($files as file) {
    $str .= '<a href="readfile.php?file=...">'.$file.'</a> <br>'
}
return $str;
?>

Readfile.php

    <?php
     // PHP script to allow the file to be downloaded
    $filename = $_GET['file'];

    if (file_exists($filename)) {
      header('Content-Description: File Transfer');
      header('Content-Type: application/octet-stream');
      header('Content-Disposition: attachment; 
    filename="'.basename($filename).'"');
      header('Expires: 0');
      header('Cache-Control: must-revalidate');
      header('Pragma: public');
      header('Content-Length: ' . filesize($file));
      readfile($filename);
      exit;
     }
     ?>
1
Leng Keng 23 feb. 2018 a las 11:27