Generating dynamic table using jsp - java

I am using jsp to display data from oracle database. the number of column in table may change each time for different users.
I am able to retrieve column label as below:
rsmd = result.getMetaData();
columns = rsmd.getColumnCount();
for (int i=1; i<=columns; i++) {
out.write("<th>" + rsmd.getColumnLabel(i) + "</th>");
The connection:
Class.forName("oracle.jdbc.driver.OracleDriver");
String url = "jdbc:oracle:thin:#localhost:8081:BI";
String username = "tech";
String password = "****";
Connection conn = DriverManager.getConnection(url, username, password);
Statement stmt = conn.createStatement();
String query = "SELECT * from item_table";
ResultSet rs = stmt.executeQuery(query);
while (rs.next()) {
}
But i am facing problem in retrieving column data as the column datatypes are different. Is there any way to retrieve data without mentioning the type of "cell"?
Any input will be appreciated.

You can use the getObject(int column) method to retrieve the data as an object. Then you have not to pay attention to the data type. Afterwards you can use the toString() Method on this objects to display the values in your table.
JavaDoc

Related

Check if a column already exists in the table

I need to verify if a column already exists in a table . My class extends CustomTaskChange so my method receives a Database object as an argument. Can I make the verification I want trough the ResultSetObject?
#Override
public void execute(Database database) throws CustomChangeException {
JdbcConnection connection = (JdbcConnection) database.getConnection();
DatabaseMetaData metadata;
metadata = connection.getMetaData();
String[] types = {"TABLE"};
ResultSet rs = metadata.getTables(null, null, "%", types);
Statement s = connection.createStatement();
while (rs.next()) {
String tableName = rs.getString(3);
if (tableName.endsWith(this.suffix)) {
String sql = sqlStatement.replaceAll("name", tableName);
s.execute(sql);
}
}
}
Basically what this piece of code is doing is going through all the tables in my database. If, a table name ends in a suffix, I will add the column to it. This way I can add a column to multiple tables at the same time.
But I want to add another verification to add the column to a table, and that is that there can't already be a column with that name in that table. Something like this(pseudocode)
if(tableName.endsWith(this.suffis) && columnName doesn't exist in that table){
String sql = sqlStatement.replaceAll("name", tableName);
s.execute(sql);
}
you can fetch columns from each of the tables then you can check column exist or not.
{
Statement st = con.createStatement();
ResultSet rs = st.executeQuery("SELECT * FROM TABLENAME LIMIT 1");
ResultSetMetaData md = rs.getMetaData();
int col = md.getColumnCount();
for (int i = 1; i <= col; i++){
String col_name = md.getColumnName(i);
if(col_name.equals("YourColumnName"){
/*Then the column already exist*/
}}
With the above code, you can check the metadata and then execute the SQL query to delete the same.

how to insert into database table with different data types using Java SQL

I have a Java SQL question relative to the insert method. If I have a database with multiple tables, I want to write a single insert method that can insert a row of data into any selected table for any type of relational database. If some tables contain different data types, for examples (integer, date, varchar, and etc.). My codes:
public void insertData(String tablename, String... values)
throws SQLException {
Connection con = null;
PreparedStatement prepStmt = null;
if (values.length == 0) {
throw new SQLException("Must supply values");
}
try{
con = getConnection();
String sql = "insert into "+tablename+" values(";
for (int i = 0; i < values.length; i++) {
sql += "?";
if (i != values.length-1) sql += ",";
}
sql += ")";
prepStmt = con.prepareStatement(sql);
for (int i = 0; i < values.length; i++) {
prepStmt.setString(i, values[i]);
}
prepStmt.executeUpdate();
}
finally {
closeStatement(prepStmt);
closeConnection(con);
}
}
For example, use case:
Table Teacher has int id, varchar(50) name, int age, text subject, int
classid;
Table Student has int id, varchar(50) name, date dateofbirth, text
address;
Table Class has int id, text subject;
If I use:
insertData(Teacher, new String[] {"10", "Cass", "32", "Math", "10222"});
Will that data insert into the table successfully? I heard the database is only using varchar. If that is the case, then I don't have to worry about the type. If the type is varchar, should I use prepStmt.setString()?
I need to support multiple different types of database, such like SQL Server, MySQL, Oracle and others. Will that one insertData() method work for all different databases?
The database meta data can tell you the details of the table.
What you can do is using DatabaseMetaData to get the column names, types and size, then you can choose PreparedStatement corresponding setXXX methods:
DatabaseMetaData metadata = connection.getMetaData();
ResultSet resultSet = metadata.getColumns(null, null, "mytable", null); // table name is mytable
while (resultSet.next()) {
String name = resultSet.getString("COLUMN_NAME");
String type = resultSet.getString("TYPE_NAME");
int size = resultSet.getInt("COLUMN_SIZE");
}
Another way is using ResultSetMetaDatabut you have to query from the table to get the ResultSet
ResultSet rs = stmt.executeQuery(query);
ResultSetMetaData rsmd = rs.getMetaData();
int columnCount = rsmd.getColumnCount() ; // returns the number of columns
for(int i = 1; i < columnCount + 1; i++){
rsmd.getColumnName(i); //get name
}
After you get the table's information(column name, type...), then you can choose proper query to update the table
Your scenario will work only in case when you are passing value for every column, if there is any nullable column in your table and you don't want to insert value on that it will not work and will throw sql exception as you have to specify the column name too in insert statement but when in your case you can pass Object array instead of String array and then call the appropriate setXXX according to the class type of parameter which your can fine from getClass method.

Unable to create/modify sqlite tables from Java application

I have a basic java application and a sqlite DB.
I can create table manually through sqLite browser. And I am able to access these tables from my JAVA application.
E.g. Reading from existing table: (I have omitted the try catch blocks in the sample below just to reduce the length of question)
PreparedStatement preparedStatement = null;
ResultSet resultSet = null;
String query = "select * from test1 where uname = ? and name = user1";
preparedStatement = connection.prepareStatement(query);
preparedStatement.setString(1, "test");
resultSet = preparedStatement.executeQuery();
if(resultSet.next())
return true;
else
return false;
I am able to perform this query successfully.
However, if I create / modify a table, changes does not show up in SQlite DB (I am viewing db in sqLite browser). If I copy paste the same query in SQlite browser, the query runs successfully and a row is added.
PreparedStatement preparedStatement = null;
ResultSet resultSet = null;
String query = "INSERT INTO COMPANY (ID,NAME,AGE) VALUES (3, 'tOM', 32);";
preparedStatement = connection.prepareStatement(query);
preparedStatement.executeUpdate();
Am I missing something?
EDIT: Both the above tables exist in my sqlite db. Both were created through sqlite browser
EDIT2: I was getting true from my example 1 above, that's why I felt that I am able to read from db. I update my code to print the data read and nothing gets printed which means I am not able to read the data as well:
resultSet = preparedStatement.executeQuery("SELECT * FROM test1");
and
private static void outputResultSet(ResultSet rs) throws Exception {
ResultSetMetaData rsMetaData = rs.getMetaData();
int numberOfColumns = rsMetaData.getColumnCount();
for (int i = 1; i < numberOfColumns + 1; i++) {
String columnName = rsMetaData.getColumnName(i);
System.out.print(columnName + " ");
}
System.out.println();
System.out.println("----------------------");
while (rs.next()) {
for (int i = 1; i < numberOfColumns + 1; i++) {
System.out.print(rs.getString(i) + " ");
}
System.out.println();
}
}
The connection string is:
Class.forName("org.sqlite.JDBC");
Connection conn = DriverManager.getConnection("jdbc:sqlite:C:\\Users\\akshay\\sqlite_test.sqlite");
conn.setAutoCommit(true);
return conn;

Need to fetch Metadata from sql query using java

I have a sql query fro which I need the column name and data type and it's table name and schema name:
Thsi is the method I am using for using and testing it for SQLSERVER:
public static void getMetadataForConn(Connection conn) throws SQLException
{
ResultSet rs = null;
try
{
Statement stmt = conn.createStatement();
rs = stmt.executeQuery("SELECT AB_DEMO_SRC.dbo.employee.dept_id dept_id, AB_DEMO_SRC.dbo.employee.email_add email_add, AB_DEMO_SRC.dbo.employee.emp_address emp_address, AB_DEMO_SRC.dbo.employee.emp_id emp_id, AB_DEMO_SRC.dbo.employee.emp_name emp_name FROM AB_DEMO_SRC.dbo.employee ");
ResultSetMetaData md = rs.getMetaData();
int columnCount = md.getColumnCount();
for (int i = 1; i <= columnCount; i++)
System.out.print(md.getColumnName(i) + "(" + md.getColumnType(i) + ") "+md.getSchemaName(i)+"."+md.getTableName(i));
System.out.println();
while (rs.next())
{
for (int i = 1; i <= columnCount; i++)
{
Object o = rs.getObject(i);
System.out.print(null == o ? "" : o.toString() + " ");
}
System.out.println();
}
}
finally
{
if (null != rs)
{
rs.close();
}
}
}
I get all the other metadata details like data type, precision and scale..Strangely, I am getting tablename and schema name as "" that is blank..IS there any other way to fetch the metadata of the columns present in a Query?
I think the problem is that the columns of a ResultSet are not related to any table, they are related just to the query. The query could be complex, it could have computed columns etc. That is why their table names are blank.
If you want to get the information about the columns of a specific table, you can use the metadata of the database:
DatabaseMetaData meta = conn.getMetaData();
ResultSet columns = meta.getColumns(null, "dbo", "employee", null);
You can fetch column name by calling 'getMetaData' method of ResultSet.
ResultSetMetaData metaData= resultSet.getMetaData();
String columnName = metaData.getColumnName(1);
All other column meta data can also be fetching using object of ResultSetMetaData

JAVA: get cell from table of mysql

I get a parameter is called 'id' in my function and want to print the cell of the name of this id row.
for example:
this is my table:
id name email
1 alon alon#gmail.com
I send to my function: func(1), so I want it to print 'alon'.
this is what I tried:
static final String url = "jdbc:mysql://localhost:3306/database_alon";
Class.forName("com.mysql.jdbc.Driver");
Connection con = DriverManager.getConnection(url, "root", "Admin");
String query_txt = "SELECT * FROM authors WHERE id = " + id;
Statement ps2 = con.createStatement();
ResultSet my_rs = ps2.executeQuery(query_txt);
System.out.println(my_rs.getString("name"));
con.close;
Everything is fine, but just one problem. You need to move your ResultSet cursor to the first row before fetching any values: -
Use: -
ResultSet my_rs = ps2.executeQuery(query_txt);
while (my_rs.next()) {
System.out.println(my_rs.getString("name"));
}
As a side note, consider using PreparedStatement to avoid getting attacked by SQL Injection.
Here's how you use it: -
PreparedStatement ps2 = con.prepareStatement("SELECT * FROM authors WHERE id = ?");
ps2.setInt(1, id);
ResultSet my_rs = ps2.executeQuery();
while (my_rs.next()) {
System.out.println(my_rs.getString("name"));
}
You need to use ResultSet.next() to navigate into the returned data:
if (my_rs.next()) {
System.out.println(my_rs.getString("name"));
}
Call my_rs.next(), which will move the ResultSet cursor onto the first row (which you are extracting data out of).
If this is a real application, use PreparedStatements instead of generic Statements. This is an extremely important matter of security if you plan on using user input in SQL queries.

Categories