Curso = Metodos Tecnicas y Modelos de Enseñanza.pdf
Find File Servlet DB
1. Servlet que lista los ficheros de manera recursiva que se encuentran en una
estructura de directorios y subdirectorios (a partir de un directorio raiz
dado) mostrando las apariciones del fichero que estamos buscando.
La idea de esta práctica es buscar un fichero proporcionando su nombre a
nuestro Servlet.
Para ello el Servlet deberá listar los ficheros de manera recursiva que se
encuentran en un directorio e insertarlos en nuestra base de datos. A
continuación mediante sentencias SQL deberá recuperar los ficheros que
coincidan con el fichero que estamos buscando.
Finalmente el Servlet mostrará por pantalla el/los fichero/os que coincidan
con el nombre proporcionado.
• Debes modificar si fuera necesario los datos de la conexión con la
base de datos.
• Debes modificar el nombre del fichero buscado.
• Debes modificar el directorio dentro del cual deseas buscar el citado
fichero.
Para nuestro ejemplo el directorio raíz será “C:repositorio” y la estructura
de directorios es la que se muestra. Vamos a buscar en esta estructura, de
forma recursiva, el fichero spam.txt
2. DBServlet2.java
package pkgServlets;
import java.io.File;
import java.io.IOException;
import java.io.PrintWriter;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* Servlet implementation class DBServlet2
*/
@WebServlet("/DBServlet2")
public class DBServlet2 extends HttpServlet {
private static final long serialVersionUID = 1L;
private static final String CONTENT_TYPE = "text/html; charset = windows-1252";
/**
* @see HttpServlet#HttpServlet()
*/ Comentario [J1]: Carga el
public DBServlet2() { HSQLDB JDBC driver.
super();
// TODO Auto-generated constructor stub Comentario [J2]: Conexión
} con base de dastos HSQLDB en
modo fichero. Para esta opción no
public void init(ServletConfig config) throws ServletException { es necesario arrancar un servi-
super.init(config); dor de HSQLDB. Nuestra propia
} aplicación indica el nombre del
fichero y establece la conexión.
/** Sobre el fichero sólo puede
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response) haber una aplicación trabajando
*/ con una única conexión.
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws "jdbc:hsqldb:file:path"
ServletException, IOException {
// TODO Auto-generated method stub Comentario [J3]: En el manejo
de rutas de ficheros, el carácter
// Exceptions may occur separador entre los niveles de los
try { directorios varía dependiendo del
Sistema Operativo. Para evitar
Class.forName("org.hsqldb.jdbcDriver" ); problemas a la hora de migrar de
Connection conn = un S.O. a otro (portabilidad), es
DriverManager.getConnection("jdbc:hsqldb:file:C:/J2EE_UNED/hsqldb/lib/mydb", "SA", ""); recomendable utilizar en Java
File.separator para representar
// Init the database and fill all file names in fillFileNames(conn, este separador en una variable del
"C:repositorio"); tipo java.lang.String, o bien
String dir_raiz = "C:" + File.separator + "repositorio" ; File.separatorChar si queremos
una variable del tipo char.
fillFileNames(conn, dir_raiz); Windows use "" (back slash) while
Linux use "/" (forward slash).
// Find and print the list of files that are like this
String s = listFiles(conn, "spam.txt"); Comentario [J4]: Establece el
tipo MIME y la codificación de
response.setContentType(CONTENT_TYPE); caracteres de la página.
Comentario [J5]: Obtenermos
PrintWriter out = response.getWriter(); un PrintWriter sobre el objeto
out.println("<html>"); HttpServletResponse y usamos
out.println("<head><title>Buscador de Archivos</title></head>"); "out" para enviar contenido al
out.println("<body>"); browser.
3. out.println("<p>El servidor ha recibido un GET... generando su
respuesta.</p>");
out.println(s);
out.println("</body></html>");
out.close();
conn.close();
} catch (Exception e) {
// Print out the error message
System.out.println(e);
e.printStackTrace();
}
}//fin doGet
// Re-create the database and fill the file names in
/**
* Method declaration
*
*
* @param conn
* @param root
*
* @throws SQLException
*/
static void fillFileNames(Connection conn, String root) throws SQLException {
// Create a statement object
Statement stat = conn.createStatement(); Comentario [J6]: Crea un
objeto Statement para enviar
// Try to drop the table sentencias SQL a la base de datos.
try {
stat.executeUpdate("DROP TABLE Files");
} catch (SQLException e) { // Ignore Exception, because the table may
// not yet exist
}
// For compatibility to other database, use varchar(255)
// In HSQL Database Engine, length is unlimited, like Java Strings
stat.execute("CREATE TABLE Files (Path varchar(255),Name varchar(255))");
// Close the Statement object, it is no longer used
stat.close();
// Use a PreparedStatement because Path and Name could contain '
PreparedStatement prep = conn.prepareCall("INSERT INTO Files (Path,Name) VALUES
(?,?)"); Comentario [J7]: Crea un
objeto PreparedStatement
// Start with the 'root' directory and recurse all subdirectories para enviar sentencias SQL
fillPath(root, "", prep); parametrizadas a la base de datos.
El objeto PreparedStatement no
// Close the PreparedStatement sólo contiene una sentencia SQL,
prep.close(); sino una sentencia SQL que ha
System.out.println("Finished"); sido precompilada. Esto significa
} que cuando se ejecuta la
PreparedStatement, el
controlador de base de datos puede
ejecutarla sin tener que compilarla
primero.
4. /**
* Method declaration
*
*
* @param path
* @param name
* @param prep
*
* @throws SQLException
*/
static void fillPath(String path, String name, PreparedStatement prep)
throws SQLException {
File f = new File(path);
if (f.isFile()) { Comentario [J8]: Tests
whether the file denoted by this
// Clear all Parameters of the PreparedStatement abstract pathname is a normal file.
prep.clearParameters();
// Fill the first parameter: Path
prep.setString(1, path);
// Fill the second parameter: Name
prep.setString(2, name);
// Its a file: add it to the table
prep.execute();
} else if (f.isDirectory()) { Comentario [J9]: Tests
whether the file denoted by this
abstract pathname is a directory.
if (!path.endsWith(File.separator)) {
path += File.separator;
}
String[] list = f.list(); Comentario [J10]: Returns an
array of strings naming the files
// Process all files recursivly and directories in the directory
for (int i = 0; (list != null) && (i < list.length); i++) { denoted by this abstract pathname.
fillPath(path + list[i], list[i], prep); Para nuestra estructura de
} directorios, la primera iteración del
} proceso recursivo el array de
} cadenas list contendrá:
list.length = 3
// Fill the file names, using the PreparedStatement list[0] = carpetaA
// Search in the database and list out files like this list[1] = carpetaB
list[2l = spam.txt
/**
* Method declaration
*
*
* @param conn
* @param name
*
* @throws SQLException
*/
static String listFiles(Connection conn, String name) throws SQLException {
String s = "";
s += "Archivos que coinciden con " + name + "<BR>";
// Convert to upper case, so the search is case-insensitive
name = name.toUpperCase();
// Create a statement object
Statement stat = conn.createStatement();
// Now execute the search query
// UCASE: This is a case insensitive search
// ESCAPE ':' is used so it can be easily searched for ''
ResultSet result = stat.executeQuery("SELECT Path FROM Files WHERE "
+ "UCASE(Path) LIKE '%" + name + "%' ESCAPE ':'");
5. // Moves to the next record until no more records
while (result.next()) {
// Print the first column of the result
// could use also getString("Path")
s += result.getString(1) + "<BR>";
}
// Close the ResultSet - not really necessary, but recommended
result.close();
return s;
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws
ServletException, IOException {
// TODO Auto-generated method stub
}//fin doPost
}//fin servlet
Resultado de la ejecución…
Y tras la ejecución en la base de datos quedan almacenados, hasta la próxima
ejecución del servlet, los siguientes registros en los campos PATH y NAME de
la tabla FILES.
6. java.sql
Interface Connection
public interface Connection
A connection (session) with a specific database. SQL statements are executed and
results are returned within the context of a connection.
Method
void close()
Releases this Connection object's database and JDBC
resources immediately instead of waiting for them to be
automatically released.
Statement createStatement()
Creates a Statement object for sending SQL statements
to the database.
PreparedStatement prepareStatement(String sql)
Creates a PreparedStatement object for sending
parameterized SQL statements to the database.
createStatement
public Statement createStatement()
throws SQLException
Creates a Statement object for sending SQL statements to the database. SQL
statements without parameters are normally executed using Statement objects.
If the same SQL statement is executed many times, it may be more efficient to
use a PreparedStatement object.
Result sets created using the returned Statement object will by default be type
TYPE_FORWARD_ONLY and have a concurrency level of CONCUR_READ_ONLY.
Returns:
a new default Statement object
Throws:
SQLException - if a database access error occurs
7. java.sql
Interface PreparedStatement
public interface PreparedStatement
extends Statement
An object that represents a precompiled SQL statement.
A SQL statement is precompiled and stored in a PreparedStatement object. This
object can then be used to efficiently execute this statement multiple times.
Note: The setter methods (setShort, setString, and so on) for setting IN parameter
values must specify types that are compatible with the defined SQL type of the input
parameter. For instance, if the IN parameter has SQL type INTEGER, then the method
setInt should be used.
If arbitrary parameter type conversions are required, the method setObject should be
used with a target SQL type.
In the following example of setting a parameter, con represents an active connection:
PreparedStatement pstmt = con.prepareStatement("UPDATE EMPLOYEES
SET SALARY = ? WHERE ID = ?");
pstmt.setBigDecimal(1, 153833.00)
pstmt.setInt(2, 110592)
8. java.io
Class File
java.lang.Object
java.io.File
All Implemented Interfaces:
Comparable, Serializable
public class File
extends Object
implements Serializable, Comparable
An abstract representation of file and directory pathnames.
Constructor Summary
File(String pathname)
Creates a new File instance by converting the given pathname string into an
abstract pathname.
Method
boolean isDirectory()
Tests whether the file denoted by this abstract pathname is a directory.
boolean isFile()
Tests whether the file denoted by this abstract pathname is a normal
file.
String[] list()
Returns an array of strings naming the files and directories in the
directory denoted by this abstract pathname.