This is my function:
query = "CREATE FUNCTION CheckSex(personID INT, G CHAR) " +
"RETURNS BIT " +
"BEGIN " +
"DECLARE Flag BIT; " +
"SET Flag = 1; " +
"If (G NOT IN (SELECT Sex FROM PERSONS WHERE ID = personID)) " +
"THEN SET Flag = 0; " +
"RETURN Flag; " +
"END";
pState = conn.prepareStatement(query);
pState.executeUpdate();
This is the error code:
check the manual that corresponds to your MySQL server version for the right syntax to use near '' at line 1
I have tried putting it into the mysql command line manually and I get an error after DECLARE Flag BIT;, also I have tried to change the delimiter which gave an error.
I have switched to an online compiler for now and this function works fine in MySql 2014 express written as follows
CREATE FUNCTION CheckSex(#personID AS INT, #G as CHAR)
RETURNS BIT
AS
BEGIN
DECLARE #Flag BIT = 1
If (#G NOT IN (SELECT Sex FROM PERSONS WHERE ID = #personID))
SET #Flag = 0
RETURN #FLAG
END;
Thank you for any feedback.
Related
I have a JDBI query that is as simple as it can be
#Override
#SqlQuery("SELECT COUNT(*) FROM " + TABLE_NAME + " WHERE (" + COLUMN_MODERATOR_CATEGORY_ID
+ " in (<categories>) OR " + COLUMN_EXPERT_CATEGORY_ID
+ " in (<categories>)) AND (" + COLUMN_STATUS + " <> 0)")
long getIdeasCountInCategories(#BindIn("categories") List<Long> categories);
The <> 0 fails with a syntax error at the end of input.... It works as soon as I change it to > 0 (which also serves the purpose).
Using Java 1.8.0 and Postgres 9.6. Please let me know if any more info is needed.
If you absolutely can't change the SQL query (e.g. switch operator to != or >) then you need to escape < with preceding \\.
I am trying to run PostgreSQL native query that contains ltree functions and operators.
Here's the definition:
#NamedNativeQuery(
name = "pathSegmentQuery",
query = "select ltree2text(okm_path) as okm_path, " +
" index(okm_path, text2ltree(:lastSegment)) + 2 <> nlevel(okm_path) as haschild, " +
" case " +
" when index(okm_path, text2ltree(:lastSegment)) + 1 <> nlevel(okm_path) " +
" then ltree2text(subpath(okm_path, index(okm_path, text2ltree(:lastSegment)) + 1, 1)) " +
" end as child " +
"from document " +
"where okm_path ~ :pathLike " +
"and " +
"index(okm_path, text2ltree(:path)) + 1 <> nlevel(okm_path) ",
resultSetMapping = "pathSegmentQueryRSMapping")
invoked like:
public List<PathSegment> getPathChildren(String path, String lastSegment) {
Query query = entityManager.createNamedQuery("pathSegmentQuery");
String pathLike = "'*." + path + ".*'";
query.setParameter("path", path);
query.setParameter("pathLike", pathLike);
query.setParameter("lastSegment", lastSegment);
return query.getResultList();
}
result is error ERROR: operator does not exist: ltree ~ character varying.
when I try to run the query directly against database it runs ok:
select ltree2text(okm_path) as okm_path,
index(okm_path, text2ltree('_root_')) + 2 <> nlevel(okm_path) as haschild,
case
when index(okm_path, text2ltree('_root_')) + 1 <> nlevel(okm_path)
then ltree2text(subpath(okm_path, index(okm_path, text2ltree('_root_')) + 1, 1))
end as child
from document
where
okm_path ~ '*._root_.*'
and
index(okm_path, text2ltree('_root_')) + 1 <> nlevel(okm_path)
from the error it's obvious that hibernate(?) dislikes the type on the right side of th ~ operator, but as you can see, I am using the string in the later query and works fine.
So what do I need to do with hibernate query to run the query successfully?
EDIT:
when I replace okm_path ~ :pathLike for "where okm_path ~ '*._root_.*' " I will be given:
org.postgresql.util.PSQLException: ERROR: syntax error at position 0 error
hibernate: 5.2.9.Final
postgresql: 9.2.23
it turned out that there is lquery() function that needs to be called when you do operations against lquery.
so my query translates to
...
where okm_path ~ lquery(:pathLike)
...
and this solves the problem
The error
operator does not exist: ltree ~ character varying
should be read as
operator does not exist: <left_data_type> <operator> <right_data_type> varying
Which means the operator is not defined for these data types. This happens when, for example, the left side of the operator is a integer and the right side a varchar, the error that time would be ERROR: operator does not exist: integer = character varying.
The problem here is when you set the value for right side,
query.setParameter("pathLike", pathLike)
pathLike is a string. So Postgres sees this as comparing a ltree to a string. When you execute the SQL directly the right hand side is taken as a ltree expression than a string.
I am not sure if this will work but can you try ltree can be directly cast to a varchar, but can you try this?:
query.setParameter("pathLike", pathLike, Hibernate.OBJECT)
See also Java type in JDBC to Postgres ltree
I'm learning swing in java. I've make a jtable that is populated by database's values (sql table --> user(id, name, age)). I want to make jtable that is if i change values from jtable is should also update database on click on button. but where i query is executed an error occurs. I want to know what is issue with this query ???
QUERY:
String sql = "UPDATE \'alarm bell marshal\' SET mr = \'" + mrs.get(row) +
"\' , shop = \'" +shops.get(row)+ "\' where id = \'" + ids.get(row) + "\'";
ERROR:
SEVERE: null
com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near ''alarm bell marshal' SET mr = '0' , shop = '0' where id = '1'' at line 1
try use something how that:
String sql = 'UPDATE `alarm bell marshal` SET `mr` = "' + mrs.get(row) + '" , `shop` = "' + shops.get(row) + '" WHERE `id` = "' + ids.get(row) + '"';
I'm trying to create a table using mySQL and Java. What I have is:
String sql = "CREATE TABLE IF NOT EXISTS " + Userinput.getTableName2() +
" (participant INT(255), " +
" 0 INT(255),"+
" name INT(3), " +
" occurances INT(255))";
stmt.executeUpdate(sql);
The Zero naming the second column is arbitrary, but I will need to have the column name be an integer.
The error I'm getting is:
You have an error in your SQL syntax; check the manual that
corresponds to your MySQL server version for the right syntax to use
near '0 INT(255), name INT(3), occurances INT(255))' at line 1
I would appreciate any and all help! Thanks!
According to this http://dev.mysql.com/doc/refman/5.0/en/identifiers.html
Identifiers may begin with a digit but unless quoted may not consist
solely of digits.
so you have to quote the 0
String sql = "CREATE TABLE IF NOT EXISTS " + Userinput.getTableName2() +
" (participant INT(255), " +
" `0` INT(255),"+ // using backticks
" name INT(3), " +
" occurances INT(255))";
stmt.executeUpdate(sql);
Although, it seems a dumb name for a column.
Please read mysql documentation:
http://dev.mysql.com/doc/refman/5.1/en/identifiers.html
Identifiers may begin with a digit but unless quoted may not consist
solely of digits.
Problem Synopsis:
When attempting to execute a SQL query in Java with a SQLite Database, the SQL statement fails to return from the execute() or executeQuery() method. In other words, the system "hangs" when executing this SQL statement.
Question:
What am I doing wrong to explain why the ResultSet never "returns?"
TroubleShooting
I tried to narrow the problem and the problem seems to be with the Java execute() or executeQuery(). A ResultSet never seems to return. For example, I tried executing exactly the same query directly in SQLite (that is, using a SQLite DB manager). The query (outside Java) executes in about 5ms and returns the valid result set.
NOTE: No exception is thrown. The system merely seems to "hang" and becomes unresponsive until a manual kill. (waiting more than 10 minutes.)
Code:
I heavily edited this code to make the problem simpler to see. (In production, this uses Prepared Statements. But, the error occurs in both methods--straight Statement and prepared Statement versions.)
Basically, the SELECT returns a single DB item so the user can review that item.
Statement st = conn.createStatement() ;
ResultSet rs = st.executeQuery("SELECT DISTINCT d1.id, d1.sourcefullfilepath, " +
"d1.sourcefilepath, d1.sourcefilename, d1.classificationid, d1.classid, " +
"d1.userid FROM MatterDataset, (SELECT MatterDataset.id, " +
"MatterDataset.sourcefullfilepath, MatterDataset.sourcefilepath, " +
"MatterDataset.sourcefilename, MatterDataset.matterid , " +
"DocumentClassification.classificationid, DocumentClassification.classid," +
" DocumentClassification.userid FROM MatterDataset " +
"LEFT JOIN DocumentClassification ON " +
"DocumentClassification.documentid = Matterdataset.id " +
"WHERE ( DocumentClassification.classid = 1 OR " +
"DocumentClassification.classid = 2 ) AND " +
"DocumentClassification.userid < 0 AND " +
"MatterDataset.matterid = \'100\' ) AS d1 " +
"LEFT JOIN PrivilegeLog ON " +
"d1.id = PrivilegeLog.documentparentid AND " +
"d1.matterid = PrivilegeLog.matterid " +
"WHERE PrivilegeLog.privilegelogitemid IS NULL " +
"AND MatterDataset.matterid = \'100\' " +
"ORDER BY d1.id LIMIT 1 ;") ;
Configuration:
Java 6,
JDBC Driver = Xerial sqlite-jdbc-3.7.2,
SQLite 3,
Windows
Update
Minor revision: as I continue to work with this, adding a MIN(d1.id) to the beginning of the SQL statement at least returns a ResultSet (rather than "hanging"). But, this is not really what I wanted as the MIN obviates the LIMIT function.
Statement st = conn.createStatement() ;
ResultSet rs = st.executeQuery("SELECT DISTINCT MIN(d1.id), d1.id,
d1.sourcefullfilepath, " +
"d1.sourcefilepath, d1.sourcefilename, d1.classificationid, d1.classid, " +
"d1.userid FROM MatterDataset, (SELECT MatterDataset.id, " +
"MatterDataset.sourcefullfilepath, MatterDataset.sourcefilepath, " +
"MatterDataset.sourcefilename, MatterDataset.matterid , " +
"DocumentClassification.classificationid, DocumentClassification.classid," +
" DocumentClassification.userid FROM MatterDataset " +
"LEFT JOIN DocumentClassification ON " +
"DocumentClassification.documentid = Matterdataset.id " +
"WHERE ( DocumentClassification.classid = 1 OR " +
"DocumentClassification.classid = 2 ) AND " +
"DocumentClassification.userid < 0 AND " +
"MatterDataset.matterid = \'100\' ) AS d1 " +
"LEFT JOIN PrivilegeLog ON " +
"d1.id = PrivilegeLog.documentparentid AND " +
"d1.matterid = PrivilegeLog.matterid " +
"WHERE PrivilegeLog.privilegelogitemid IS NULL " +
"AND MatterDataset.matterid = \'100\' " +
"ORDER BY d1.id LIMIT 1 ;") ;
What a messy SQL statement (sorry)! I don't know SQLite, but why not simplify to:
SELECT DISTINCT md.id, md.sourcefullfilepath, md.sourcefilepath, md.sourcefilename,
dc.classificationid, dc.classid, dc.userid
FROM MatterDataset md
LEFT JOIN DocumentClassification dc
ON dc.documentid = md.id
AND (dc.classid = 1 OR dc.classid = 2 )
AND dc.userid < 0
LEFT JOIN PrivilegeLog pl
ON md.id = pl.documentparentid
AND md.matterid = pl.matterid
WHERE pl.privilegelogitemid IS NULL
AND md.matterid = \'100\'
ORDER BY md.id LIMIT 1 ;
I was uncertain whether you wanted to LEFT JOIN or INNER JOIN to DocumentClassification (using LEFT JOIN and then put requirements on classid and userid in the WHERE statement is - in my opinion - contradictory). If DocumentClassification has to exist, then change to INNER JOIN and put the references to classid and userid into the WHERE clause, if DocumentClassification may or may not exist in your result set, then keep the query as I suggested above.
I went back and started over. The SQL syntax, while it worked outside Java, simply seemed too complex for the JDBC driver. This cleaned-up revision seems to work:
SELECT DISTINCT
MatterDataset.id, MatterDataset.sourcefullfilepath, MatterDataset.sourcefilepath,
MatterDataset.sourcefilename
FROM MatterDataset , DocumentClassification
ON DocumentClassification.documentid = MatterDataset.id
AND MatterDataset.matterid = DocumentClassification.matterid
LEFT JOIN PrivilegeLog ON MatterDataset.id = PrivilegeLog.documentparentid
AND MatterDataset.matterid = PrivilegeLog.matterid
WHERE PrivilegeLog.privilegelogitemid IS NULL
AND MatterDataset.matterid = '100'
AND (DocumentClassification.classid = 1 OR DocumentClassification.classid = 2)
AND DocumentClassification.userid = -99
ORDER BY MatterDataset.id LIMIT 1;
A nice lesson in: just because you can in SQL doesn't mean you should.
What this statement does is essentially locates items in the MatterDataset Table that are NOT in the PrivilegeLog table. The LEFT JOIN and IS NULL syntax locate the items that are "missing." That is, i want to find items that are in MatterDataset but not yet in PrivilegeLog and return those items.