HQL syntax error - java

mysql 5.1
hibernate 4.3
spring 4
glassfish 4
I have written a application using spring and hibernate. It gives following error.
ERROR: 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 'FROM Account WHERE accountNo = '123'' at line 1
Warning: StandardWrapperValve[dispatcher]: Servlet.service() for servlet dispatcher threw exception
com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: 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 'FROM Account WHERE accountNo = '123'' at line 1
I think there is no issue with the hql statement.
method inside #Repository
public Account getAccountByNo(String accountNo) {
Account acc = null;
Query query = getSession().createSQLQuery(" FROM Account WHERE accountNo = :accno ");
query.setString("accno", accountNo);
List list = query.list();
if(!list.isEmpty()){
acc = (Account)list.get(0);
}
return acc;
}
#Entity
public class Account implements Serializable {
private static final long serialVersionUID = 1L;
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
#Column(name = "ACCOUNTNO", nullable = false)
private String accountNo;
#Column(name = "AMOUNT", nullable = false)
private Double amount;
#OneToOne
private AccHolder accHolder;
}

You do not create a HQL Query. Your create a SQL-Query:
Query query = getSession().createSQLQuery(" FROM Account WHERE accountNo = :accno ");
Change it to
Query query = getSession().createQuery(" FROM Account a WHERE a.accountNo = :accno ");

Related

spring boot jdbcTemplate.query throws table not found auto converting table name to upper case

i have a jdbcTemplate.query method with query bit complex with multiple left joins, so its difficult for me to implement interface based repository methods.
I am using a MySQL db from AWS RDS.
when the query is executing spring boot jpa automatically converting table name to upper case and it throws error as: table not found.
exception is:
with path [] threw exception [Request processing failed; nested exception is org.springframework.jdbc.BadSqlGrammarException: StatementCallback; bad SQL grammar [SELECT DISTINCT test_desc FROM test_name_table]; nested exception is org.h2.jdbc.JdbcSQLSyntaxErrorException: Table "TEST_NAME_TABLE" not found; SQL statement:
SELECT DISTINCT test_desc FROM test_name_table [42102-200]] with root cause
org.h2.jdbc.JdbcSQLSyntaxErrorException: Table "TEST_NAME_TABLE" not found; SQL statement:
SELECT DISTINCT test_desc FROM test_name_table [42102-200]
here are the solutions i have tried:
from application.properties:
spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
spring.jpa.database-platform=org.hibernate.dialect.MySQL8Dialect
spring.jpa.hibernate.naming_strategy = org.hibernate.cfg.DefaultNamingStrategy
database url:
spring.datasource.dataSourceProperties.serverName=test-instance.us-east-1.rds.amazonaws.com;DATABASE_TO_UPPER=FALSE;CASE_INSENSITIVE_IDENTIFIERS=TRUE;
as you see above sql query, i have even put the table name inside backtick. but no luck.
I tried to rename the table name in MySQL to TEST_NAME_TABLE, but still no luck.
any recommended fix for this?
its a good practice use #Table(name = "table_name") for a model and #Column(name = "column_name") annotation for every column in your Model.java
and use #Query("some query in SQL") for every query you use in ModelRepository.java
example:
#Entity
#Table
public class Employee implements Serializable {
#Id
#Column(name = "emp_id")
private Long id;
#Column(name = "name")
private String name;
#Column(name = "email")
private String email;
#Column(name = "jobTitle")
private String jobTitle;
#Column(name = "phone")
private String phone;
#Column(name = "imagUrl")
private String imageUrl;
#Column(name = "employeeCode")
private String employeeCode;
}
#Repository
public interface EmployeeRepository extends JpaRepository<Employee, Long> {
#Query("SELECT s FROM Employee s WHERE s.email = ?1")
Optional<Employee> findEmployeeByEmail(String email);
}

How to fix syntax error parsing JPQL with group by

I'm new using JPA and JPQL for a project, but I got SQL syntax error and I couldn't find the cause.
I'm using spring boot, MySQL.
I got a vote repository
public interface VoteRepository extends JpaRepository<Vote, Long> {
....
#Query(value = "SELECT NEW com.self.polls.model.ChoiceVoteCount(v.choice.id, count(v.id)) FROM Vote v WHERE v.poll.id = :pollId GROUP BY v.choice.id", nativeQuery = true)
List<ChoiceVoteCount> countByPollIdGroupByChoiceId(#Param("pollId") Long pollId);
....
}
ChoiceVoteCount
public class ChoiceVoteCount {
private Long choiceId;
private Long voteCount;
}
Vote
public class Vote {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
#ManyToOne(fetch = FetchType.LAZY, optional = false)
#JoinColumn(name = "poll_id", nullable = false)
private Poll poll;
#ManyToOne(fetch = FetchType.LAZY, optional = false)
#JoinColumn(name = "choice_id", nullable = false)
private Choice choice;
#ManyToOne(fetch = FetchType.LAZY, optional = false)
#JoinColumn(name = "user_id", nullable = false)
private User user;
}
But I got error when running this query
2019-03-27 16:01:34.783 ERROR 68064 --- [nio-5000-exec-4] o.h.engine.jdbc.spi.SqlExceptionHelper : 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 '.self.polls.model.ChoiceVoteCount(v.choice.id, count(v.id)) FROM Vote v WHERE v.' at line 1
2019-03-27 16:01:34.787 ERROR 68064 --- [nio-5000-exec-4] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.springframework.dao.InvalidDataAccessResourceUsageException: could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet] with root cause
java.sql.SQLSyntaxErrorException: 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 '.self.polls.model.ChoiceVoteCount(v.choice.id, count(v.id)) FROM Vote v WHERE v.' at line 1
You have to add a constructor in ChoiceVoteCount.
To play safe, the default constructor could also be added.
public ChoiceVoteCount() {
}
public ChoiceVoteCount(Long choiceId, Long voteCount) {
this.choiceId = choiceId;
this.voteCount = voteCount;
}

JPA how to query the database without creating a table

I am using JPA and Spring for my db tasks and I need to have a join query like below in the JPA Repo class
#Query("SELECT 1 as id, COUNT(bill) as bills, ba.resource, MAX(b.updatedAt) as latestdate FROM Bill b join b.billComp ba where ba.comp.comp = ?1 group by ba.resource")
public List<BillCalc> findByBills(Long comp);
My Entity class is as below
#Entity
public class BillCalc {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Integer id;
#Column(name = "latestdate", nullable = false)
private Date latestdate;
#Column(name = "bills", nullable = false)
private Long bills;
#Column(name = "resource", nullable = false)
private String resource;
I cannot create a table for this and can someone help me in getting the mapping to work? It gives me an error saying cannot cast from Object to BillCalc.
I tried #SubSelect but it does not take parameters
add a constructor to BillCalc.
BillCalc(Integer id, long bills, String resouce, Date latestdate) {...}
then use a Select new query:
SELECT new BillCalc(1, COUNT(bill), ba.resource, MAX(b.updatedAt))
FROM Bill b join b.billComp ba
WHERE ba.comp.comp = ?1 group by ba.resource")
#See Chapter 4.8.2 "Constructor Expressions in the SELECT Clause" in JSR-000220 Enterprise JavaBeans 3.0 Final Release (persistence)

hibernate can't detect named parameter

I am trying to execute a hibernate query. After I created the query, "query.getQueryString()"
prints like below:
select a
from com.mycompany.model.dwh.Instruction a
where a.custBillAcctId = :accountId
Then when I am trying to set parameter:
query.setParameter("accountId", new BigDecimal(accountId));
I get:
org.hibernate.QueryParameterException:
could not locate named parameter [accountId]
I print "query.getNamedParameters()", it seems empty. Hibernate somewhat can't detect :accountId. I tried different things, setting by parameter index, etc. All failed.
I did it millions of times in JEE-Hibernate, but I failed with Spring-Hibernate.
Environment: Eclipse-Jetty
hibernate: 4.1.9.Final
springframework: 3.2.1.RELEASE
#Entity
#Table(name = "TALIMAT")
public class Instruction implements Serializable {
private static final long serialVersionUID = 1L;
#Id
#Column(name = "TALIMAT_ID")
#GenericGenerator(name="kaugen" , strategy="increment")
#GeneratedValue(generator="kaugen")
private Long key;
#Id
#Column(name = "CUST_BILL_ACCT_ID")
private BigDecimal custBillAcctId;
....
#Column(name = "STATUS")
private String status;
#Temporal(TemporalType.DATE)
#Column(name = "INSERT_DATE")
private Date insertDate;
Here is my code:
try {
Session session = sessionFactory.getCurrentSession();
Query query = session.createQuery("select a from " +
Instruction.class.getName() + " a
where a.custBillAcctId = :accountId ");
System.out.println("getNamedParameters: ");
for(String g:query.getNamedParameters()){
System.out.println(g + "\n");
}
query.setParameter("accountId", new BigDecimal(accountId));
} catch (Exception e1) {
e1.printStackTrace();
}
Thanks
I just solved the problem. It was a silly side-effect problem. I have multiple databaseContext.xml files each containing a datasources definition for a different database which application use. Although they are in seperate files, datasource id's were coinciding, this resulted in ambiguous behaviour.
When I gave them unique names, problem disappeared

ORMlite + MySQL Foreign Key Binding

How do I create auto delete cascade using ORMLite? I am using ormlite-core and omlite-jdbc version 4.8. I tried
public class Account {
// for QueryBuilder to be able to find the fields
public static final String NAME_FIELD_NAME = "name";
public static final String PASSWORD_FIELD_NAME = "passwd";
#DatabaseField(generatedId = true)
private int id;
#DatabaseField(columnName = NAME_FIELD_NAME, canBeNull = false)
private String name;
#DatabaseField(columnName = PASSWORD_FIELD_NAME)
private String password;
}
and another class
#DatabaseTable(tableName = "orders")
public class Order {
public static final String ACCOUNT_ID_FIELD_NAME = "account_id";
#DatabaseField(generatedId = true)
private int id;
#DatabaseField(foreign = true, columnName = ACCOUNT_ID_FIELD_NAME,
canBeNull = false,index = true, foreignAutoRefresh = true,
columnDefinition = "integer references document(id) on delete cascade")
private Account account;
#DatabaseField
private int itemNumber;
#DatabaseField
private int quantity;
#DatabaseField
private float price;
}
But When I delete the parent key record, no exception is being thrown and also, if try to insert records in order table with foreign key values which are not defined in the Account table, no exception is being thrown and the records get created and inserted in database.
But When i delete the parent key record , no exception is being thrown and also , if try to insert records in order table with foreign key values which are not defined in the Account table, no exception is being thrown and the records get created and inserted in database .
Stupid answer but shouldn't the column definition be:
integer references account(id) on delete cascade
I assume that the Account table is named account and not document. Otherwise your SQL looks good.
I would take a look at the schema on the MySQL side to make sure that it matches what you are expecting. I'd also try some inserts from the MySQL command line to see if you can figure out what is going on outside of ORMLite.
Hope this helps.

Categories

Resources