SQLSyntaxErrorException - java

I made one table Login using oracle. Firstly I have taken fields- id,username,password and connected database in java program for signup. I was trying to execute insert query before it was running fine than I altered table Login and dropped column id. Then again I tried to run insert query from java program but now I am getting below error. I am not getting what happened after alteration. I think changes should reflect everywhere but I am stuck with this exception.
java.sql.SQLSyntaxErrorException: ORA-04098: trigger 'SURABHI.BI_LOGIN' is invalid and failed re-validation
JAVA CODE:
public void insertLogin(String user,String pass) {
String query = "insert into Login(username,password)" + " values(?,?)";
try {
ps = con.prepareStatement(query);
ps.setString(1, user);
ps.setString(2, pass);
ps.execute();
System.out.println("inserted");
} catch(Exception e) {
e.printStackTrace();
}
}

It seems your table has a before insert trigger and it is invalid, probably because you dropped column id and it is used by the trigger.
Check your trigger and compile it successfully.

Related

Searching in sql, Transactions and DB File Locked

I am using JavaFX with SQLite DB for making a general store management. Previously I was using SQL server as an assignment but to implement it I needed an embedded database. For that purpose I chose SQLite. Here I faced many problems as it didn't have stored procedures now I got the following 3 problems in my whole management System:
Error in searching through query
Error in executing a transaction
Getting error message that database file is locked.
Now I am going to define each part separately.
1.Error in Searching through query
I was using stored procedure in SQL server for searching in a table using some text the inner query was:
Create PROC [dbo].[spGetProductListByQuery]
#query varchar(MAX)
AS
BEGIN
SELECT p.Product_id, p.Name, pt.Type, p.Pur_Price, p.Sale_Price, p.Stock,s.Name, s.Contact_No, s.Email
FROM ((Product AS p
INNER JOIN ProductType AS pt ON p.Type_Id=pt.Type_Id)
INNER JOIN Supplier AS s ON p.Supplier_Id=s.Supplier_Id)
WHERE p.Name LIKE #query+'%'
And in java i executed this stored procedure using following code:
pst=con.prepareStatement("EXEC spGetProductListByQuery #query=?");
pst.setString(1,query)
and it worked at that time but now as i am using SQLite studio for that purpose i am using following code:
sql="SELECT p.Product_id, p.Name, pt.Type, p.Pur_Price, p.Sale_Price, p.Stock,s.Name, s.PhoneNumber, s.Email\r\n" +
"FROM ((Product AS p\r\n" +
"INNER JOIN ProductType AS pt ON p.Type_Id=pt.Type_Id)\r\n" +
"INNER JOIN Supplier AS s ON p.Supplier_Id=s.Supplier_Id)\r\n" +
"WHERE p.Name LIKE ?+'%'";
System.out.println(searchText);
pst=con.prepareStatement(sql);
pst.setString(1, searchText);
rs=pst.executeQuery();
it works on SQLite studio but it returns nothing java, i can't understand where is the problem.
2.Error in executing a transaction
I have tried for so many time to execute even a single statement in transaction but it still returns error message as shown below:
BEGIN TRANSACTION;
INSERT INTO Staff (Name, Address, Contact_No,Salary,Accountant)
VALUES ('Danish', 'Gujrat','034803','22000,0)
END TRANSACTION
and i got following error message:
cannot start a transaction within a transaction Unable to fetch row.
3. Getting error message that database file is locked
As the 3rd problem is connected to 2nd problem if it resolves I can use multiple statements in one SQL Transaction and make it possible to work. But the strange thing is that when I tried to execute this function:
public static Boolean saleItem(int productId, double quantity) {
con=Connectivity.getConnectivity();
Connection con2 = null;
try {
if(productId!=0&&quantity!=0)
pst=con.prepareStatement("INSERT INTO SALE (Product_Id, Date, Quantity)\r\n" +
"VALUES (?, CURRENT_TIMESTAMP, ?)");
pst.setInt(1, productId);
pst.setDouble(2, quantity);
pst.executeUpdate();
if(!con.isClosed()) {
con.close();
}
pst=con.prepareStatement("UPDATE Product\r\n" +
"SET Stock=Stock-? WHERE Product_id=?");
pst.setInt(2, productId);
pst.setDouble(1, quantity);
pst.executeUpdate();
con.close();
} catch (SQLException e) {
//showErrorAlert(e.getMessage());
e.printStackTrace();
return false;
}catch(NullPointerException e) {
showErrorAlert(e.getMessage());
}
return true;
}
here we can see that two connections are being established at one time and it shows the error message
org.sqlite.SQLiteException: [SQLITE_BUSY] The database file is locked (database is locked)
But when I tried to execute the function having only one connection instances in which update query was executed:
public static void changeStock(double quantity, int id) {
con=Connectivity.getConnectivity();
if(quantity!=0) {
try {
pst=con.prepareStatement("UPDATE Product \r\n" +
"SET Stock=Stock+(?) \r\n" +
"WHERE Product_id=?");
pst.setDouble(1, quantity);
pst.setInt(2, id);
} catch (SQLException e) {
showErrorAlert(e.getMessage());
e.printStackTrace();
}
}
}
it still showed the error that is shown above.
My problems are a little long but hope so that you can help me.
Thanks

Batch Insert not Inserting

I have been trying to insert a "batch" of data into a SQLITE db in an Android application. I am getting no errors, but when trying to select from that Table later, no data is returned.
The application uses both SQL server and SQLITE since the device wont always be connected to the network it cannot access SQLServer all the time, so I am running a query to select from SQLServer and then I pass that resultset to the method that is meant to push the data to the SQLITE DB
The process flow I am following is as follows:
Delete everything currently in the sqliteDB
mDb = mDbHelper.getReadableDatabase();
mDb.execSQL("delete from TABLE_1");
Get data from SQLserver
Connection con = connectionClass.CONN();
connect = con;
try {
PreparedStatement statement = connect.prepareStatement("Exec SelectAll '" + Param1+ "'");
rs = statement.executeQuery();
liteAdapter.insertIntoDbLite(rs);
con.close();
} catch (SQLException ex) {
String error = ex.getMessage();
}
Pass resultset from step 2 to the method that should batch insert the data to sqlite
//Insert Records into Bale Table from SQL Server
public void insertIntoDbLite(ResultSet rs)
{
mDb = mDbHelper.getWritableDatabase();
mDb.beginTransaction();
try {
ContentValues values = new ContentValues();
try {
while (rs.next()) {
//put value(Column_Name, record)
values.put("COL1", rs.getString("Col1_Val"));
values.put("COL2", rs.getString("Col2_Val"));
values.put("COL3", rs.getString("Col3_Val"));
values.put("COL4", rs.getString("Col4_Val"));
values.put("COL5", rs.getString("Col5_Val"));
values.put("COL6", rs.getString("Col6_Val"));
values.put("COL7", rs.getString("Col7_Val"));
values.put("COL8", rs.getString("Col8_Val"));
values.put("COl9", rs.getString("Col9_Val"));
}
mDb.insert("TABLE_1", null, values);
}
catch (java.sql.SQLException e)
{
Log.e("Error in SQL",e.toString());
}
mDb.setTransactionSuccessful();
}
catch(Exception ex)
{
Log.e("Error in transaction",ex.toString());
}
finally
{
//End the transaction
mDb.endTransaction();
}
}
so it all seems to run fine, but when I later query the db and to a select, no values are returned from this table,
am I missing something or just doing it wrong?
Thanks
There appears to be nothing glaringly wrong with the given code. The likely scenario is that the update is in not performing the update due to a constraint (a rule such as, but not limited to NOT NULL, UNIQUE). Another, perhaps less likely scenario is that the while loop isn't being entered.
You could distinguish which by changing
mDb.insert("TABLE_1", null, values);
to
Log.d("INSERT","Return from insert is " + Long.toString(mDb.insert("TABLE_1", null, values)));
This will then either write output with :-
(a) no output to the log indicating that the while loop was not entered, so rs is empty.
(b) -1 being the sole value(s) returned, indicating that the update is not being done due to constraints.
(c) with all or some positive (> 0) value(s) returned, this would indicate, that the updates are being performed and that the issue is likely with the method used to checked the data later.
If (b) then changing mDb.insert to mDb.insertOrThrow should result in the first exception being caught which should indicate the issue.

Update statement working in SQLite Browser not in java with the exact same syntax

Okay I executed the same code thats in the update query in the SQLite db browser and it worked successfully
public void StatusUpdate(ActionEvent event) {
try {
String test = null;
test = txtEditStatus.getText();
System.out.println(test);
String query = "UPDATE member SET desc = ? WHERE username = ?";
PreparedStatement preparedStmt = connection.prepareStatement(query);
preparedStmt.setString (1, test);
preparedStmt.setString(2, "Custom Hue");
// execute the java preparedstatement
preparedStmt.executeUpdate();
connection.close();
} catch (Exception e) {
}
However when running eclipse with JFx, it prints what I type in the console but doesnt update in the db, anyone know why?
For the user asking about the connection:
Connection connection;
public ProfileController() {
connection = SQLConnection.Connector();
if (connection == null)
System.exit(1);
}
I would check that your connection is actually connected to the correct database.
are you sure you have the right connection string set up?
you should do an output on your exception handler, what if there is an exception?
are you sure the connection is open?
are you sure the user exists in the database and table you are trying to update?
try doing a read first, to see if you have an open connection. Print your exception, just in case, never leave it blank. That's just bad practice.
How about you try a
preparedStmt.executeUpdate();
connection.commit();
connection.close();
Just incase autocommit isn't enabled?

sqlite preparedstatement finalized

I have an error of
java.sql.SQLException: The prepared statement has been finalized
which happens when I call the same preparedStatement a second time. I am calling it in a method.
Here is the database Java class (the relevant piece)
//create the charge table. (ps is PreparedStatement)
try{
statement.executeUpdate("CREATE TABLE charge(username TEXT NOT NULL, date DATETIME DEFAULT CURRENT_TIMESTAMP, charge REAL, PRIMARY KEY(username, date));");
} catch (SQLException ex) {
System.out.println("charge table creation failed. exception" + ex);
}
Method that creates a charge:
public void createCharge(String username, double amount){
try {
System.out.println(username + amount);
ps = connection.prepareStatement("INSERT INTO charge VALUES(?, ?, ?);");
ps.setString(1, username);
ps.setDate(2, DateConvert.toSQLDate(Date.valueOf(LocalDate.MIN)));
ps.setDouble(3, amount);
ps.executeUpdate();
ps.clearParameters();
System.out.println("Complete");
} catch (SQLException ex) {
Logger.getLogger(MontsRentalDatabase.class.getName()).log(Level.SEVERE, null, ex);
}
}
This is in the class where the charge is created:
public void createCharge(String username, double amount){
try {
System.out.println(username + amount);
ps = connection.prepareStatement("INSERT INTO charge VALUES(?, ?, ?);");
ps.setString(1, username);
ps.setDate(2, DateConvert.toSQLDate(Date.valueOf(LocalDate.MIN)));
ps.setDouble(3, amount);
ps.executeUpdate(); //Line 170
ps.clearParameters();
System.out.println("Complete");
} catch (SQLException ex) {
Logger.getLogger(MontsRentalDatabase.class.getName()).log(Level.SEVERE, null, ex);
}
}
The class that converts a normal date to sqldate:
public class DateConvert {
public static java.sql.Date toSQLDate(java.util.Date date){
return new java.sql.Date(date.getTime());
}
public static java.util.Date toJavaDate(java.sql.Date date){
return new java.util.Date(date.getTime());
}
}
The error is in line 170 of create charge, which is when ps.executeUpdate runs. It runs successful the first time, fails on the second.
Log:
450100.0
Complete
450150.0
SEVERE: null
java.sql.SQLException: The prepared statement has been finalized
at org.sqlite.core.NativeDB.throwex(NativeDB.java:429)
at org.sqlite.core.NativeDB.reset(Native Method)
at org.sqlite.core.DB.executeUpdate(DB.java:878)
at org.sqlite.jdbc3.JDBC3PreparedStatement.executeUpdate(JDBC3PreparedStatement.java:99)
at server.RentalDatabase.createCharge(RentalDatabase.java:170)
Thanks for any help,
J
I believe that this is a bug in version 3.14.2.1 of the SQLite JDBC driver.
It seems to me that you're getting a unique constraint violation exception, but the SQLite JDBC driver is tripping over itself attempting to report this exception and some other exception is getting thrown instead.
I was able to reproduce your exception using sqlite-jdbc version 3.14.2.1 if I tried to insert the same data multiple times, e.g. by re-running your code. I downgraded the SQLite JDBC driver to 3.8.11.2 and I got the following exception after running your code:
java.sql.SQLException: [SQLITE_CONSTRAINT] Abort due to constraint violation (UNIQUE constraint failed: charge.username, charge.date)
at org.sqlite.core.DB.newSQLException(DB.java:890)
at org.sqlite.core.DB.newSQLException(DB.java:901)
at org.sqlite.core.DB.execute(DB.java:810)
at org.sqlite.core.DB.executeUpdate(DB.java:847)
at org.sqlite.jdbc3.JDBC3PreparedStatement.executeUpdate(JDBC3PreparedStatement.java:86)
at com.example.MontsRentalDatabase.createCharge(MontsRentalDatabase.java:40)
at com.example.Main.main(Main.java:17)
Of course, when re-running the program, the data I'm trying to insert is in the table already. So a unique constraint violation is to be expected.
I then added the line
statement.execute("DROP TABLE IF EXISTS charge");
to createChargeTable(), above the line that creates the table. The code then ran successfully multiple times using either version of the SQLite JDBC driver.
This bug has now been fixed in sqlite-jdbc version 3.15.1, so the fix is therefore to upgrade to this version or later.
After you create a prepared statement, you should close it and not use it again. I don't see it in your code, but you stated: "which happens when I call the same preparedStatement a second time".
Your 'ps' variable should be a local variable, declared in a try-with-resource block such as:
try (PreparedStatement ps = connection.prepareStatement("INSERT INTO charge VALUES(?, ?, ?);")) {
ps.setString(1, username);
ps.setDate(2, DateConvert.toSQLDate(Date.valueOf(LocalDate.MIN)));
ps.setDouble(3, amount);
ps.executeUpdate(); //Line 170
ps.clearParameters();
System.out.println("Complete");
}
That way it can't be used after its been closed.

Java sql update row in database

I have got adding a member to the database working.
I am trying to work out how to update a row in the table using the same system of passing in the values just not adding a new row, just altering the row using the passed in username.
Here is my method for inserting a new member:
public static void insertMember(String username,String firstName)
{
try
{
Class.forName("com.mysql.jdbc.Driver");
Connection connection = DriverManager.getConnection(url, username, password);
PreparedStatement st = connection.prepareStatement("INSERT INTO Members VALUES (?,?)");
st.setString(1, username);
st.setString(2, firstName);
st.executeUpdate();
}
catch (SQLException e)
{
System.out.println("SQL Exception: "+ e.toString());
}
catch (ClassNotFoundException cE)
{
System.out.println("Class Not Found Exception: "+ cE.toString());
}
}
You need to use an UPDATE command instead of INSERT command.
Take a look at SQL UPDATE statement.
You will need to provide some means by which you can identify the row which needs to be updated, but this is dependent upon the structure of your table
I have got adding a member to the database working. I am trying to work out how to update a row in the table using the same system of passing in the values just not adding a new row, just altering the row using the passed in username.
you need Update command
like
UPDATE Members set username='somename',firstname='firstname' where condition
Need to change SQL command instead of INSERT , uses UPDATE.
Below code will update username for matching firstname provided in where clause.
PreparedStatement st = connection.prepareStatement("UPDATE Members set username=? where firstName=?)");
st.setString(1, username);
st.setString(2, firstName);
int updateStatus=st.executeUpdate();

Categories

Resources