I have spring boot application, that makes update in two database Postgres. I use Atomikos for distributed transaction management.
I see that my application makes query in both database each 10 seconds:
"SELECT gid FROM pg_prepared_xacts where database = current_database()"
I'm wonder why? Has atomikos some property for changing period? For example 1 minute. What will be if query returns some gids?
I had looked internet hard about this question, but didn't find the answer.
I have some assumption, and I want to know the right answer.
Why does Atomikos ping pg_prepared_xacts?
It calls "recovery scan" and aim is recovering after failing of application, or error in application. Because of it, in database will not be "orphaned" prepared transactions created by Atomikos.
Has atomikos some property for changing period?
Yes, it has: com.atomikos.icatch.recovery_delay. Other useful properties are here: JtaProperties
What will be if query returns some gids?
Atomikos checks if returned gids are in atomikos transaction log and have status "to commit". If it's so, he will commit prepare transactions, else he will rollback transactions. Note, that Atomikos will handle prepare transactions, that were created by him, and will not handle other prepare transactions.
Related
I was wondering if there is a specific way to override database connection timeout in the properties file in my Java web project? I am using Hibernate, Spring, and MySQL DB. I have tried several different property fields and reduced the timeout time to 1 millsecond, yet the connection is still completed with transactions still being processed properly.
These are the property fields I have used to no avail...
spring.jpa.properties.javax.persistence.query.timeout=1
spring.jdbc.template.query-timeout=1
hibernate.c3p0.timeout=1
Is hibernate overriding this timeout value or am I just setting it improperly?
Thanks in advance!
Assuming that you're using Spring Boot you can try:
spring.transaction.defaultTimeout=1
This property sets defaultTimeout for transactions to 1 second.
(Looking at the source code of TransactionDefinition it seems that it is not possible to use anything more precise than seconds.)
See also: TransactionProperties
javax.persistence.query.timeout
This is a hint for Query. It is supposed to work if you use it like this:
entityManager.createQuery("select e from SampleEntity e")
.setHint(QueryHints.SPEC_HINT_TIMEOUT, 1)
.getResultList();
See also QueryHints
spring.jdbc.template.query-timeout
Remember that according to the JdbcTemplate#setQueryTimeout javadoc:
Any timeout specified here will be overridden by the remaining transaction timeout when executing within a transaction that has a timeout specified at the transaction level.
hibernate.c3p0.timeout
I suspect that this property specifies timeout for getting from the connection pool, not for a query execution
that's a question which has confuse me a lot.
for example:
when I design the Dao layer,sometimes,I must do some insert operation,and than
I should do some query such as select the data's id by auto-generate in db.
my question was that:
when I use spring to help manage datasource,
when I do more than two sql operation one by one,
how many times the java client connect to the db?? only one ? or more?
code,such as fellows:
getSimpleJdbcTemplate().update(some params...);
getSimpleJdbcTemplate().query(some params...);
It depends on your Transactional settings.
Spring-transactions in local mode, work on a thread-local connection for all the db activities within single transaction.
If you have not configured transactions, then basically each DB call will retrieve connection from datasource using Datasource.getConnection()
In terms client connecting to DB, if you are using datasource with connection pooling capability, then connections are returned from the pool.
But if datasource is not backed by pool, then it will instantiate connection to DB server on demand ( on getConnection() ) call
In Glassfish, there is a JDBC Pool option called
Non Transactional Connections
So am I correct in thinking that "Non Transactional Connections" is the same as setting auto-commit=false ?
If that is correct, then why, when this option is disabled (i.e. non-transactional enabled) do I get an error saying
org.postgresql.util.PSQLException: Cannot commit when autoCommit is enabled.
This is when I have java code that looks like :
try {
preparedStatement = connection.prepareStatement(.....);
preparedStatement.executeQuery();
connection.commit();
}
Non Transactional Connections does not set the autoCommit property to false by default. That's not what non - transactional connections are for. From the Oracle glassfish documentation below,
The main advantage of using non-transactional connections is that the overhead incurred in enlisting and delisting connections in transaction contexts is avoided. However, use such connections carefully. For example, if a non-transactional connection is used to query the database while a transaction is in progress that modifies the database, the query retrieves the unmodified data in the database. This is because the in-progress transaction hasn’t committed. For another example, if a non-transactional connection modifies the database and a transaction that is running simultaneously rolls back, the changes made by the non-transactional connection are not rolled back.
You should
Connection con = ds.getConnection();
boolean initValue = con.getAutoCommit();
con.setAutoCommit(false);
//do your work here and commit or rollback
con.setAutoCommit(initValue );
I would like to set a timeout on a javax.persistence.TypedQuery.
I've found this easy method :
TypedQuery<Foo> query = ... ;
query.setHint("javax.persistence.query.timeout", 1000);
query.getReturnList();
But it seems that does not work, it's just ignored.
From the PRO JPA 2 book:
"Unfortunately, setting a query timeout is not portable behavior. It
may not be supported by all database platforms nor is it a requirement
to be supported by all persistence providers. Therefore, applications
that want to enable query timeouts must be prepared for three
scenarios.
The first is that the property is silently ignored and has no effect.
The second is that the property is enabled and any select, update, or
delete operation that runs longer than the specified timeout value is
aborted, and a QueryTimeoutException is thrown. This exception may be
handled and will not cause any active transaction to be marked for
rollback.
The third scenario is that the property is enabled, but in doing so
the database forces a transaction rollback when the timeout is
exceeded. In this case, a PersistenceException will be thrown and the
transaction marked for rollback. In general, if enabled the
application should be written to handle the QueryTimeoutException, but
should not fail if the timeout is exceeded and the exception is not
thrown."
Does anyone knows any other method to specify a timeout on a TypedQuery?
Or how can I make this "hint" working?
Thanks
EDIT: Oracle 11.2.0.4.0 and PostgreSql 9.2.9
with JPA 2.1 / Hibernate
I know its late to reply, but we faced similar problem Oracle 11g, JPA2.0 and this hint wasn't working.
Actually the problem was we were using it as #NamedQuery hint and were calling the function inside #transactional aspect. As #NamedQuery gets loaded and compiled at the time of context load this timeout was overridden by transaction timeout.
You can find more info at http://javadeveloperz0ne.blogspot.in/2015/07/why-jpa-hints-on-namedquery-wont-work.html.
Solution would be fetching named query again and then applying timeout.
Query query = entityManager.createNamedQuery("NamedQueryName");
query.setHint("org.hibernate.timeout", "5");
query.getSingleResult();
Hope it helps!
Yeah Hint ignored and its not work please review this question . you should set timeout for javax.persistence.query.timeout
Set timeout on EntityManager query
I am using JTA UserTransaction to perform some database and JMS related activity.
The problem goes as below.
1.Start UsertTransaction
2.Perform DB search operation
3.Perform DB updated operation
4.Perform JMS send and recieve operation----> Problematic work flow
5.Perform DB updated operation
6.Commit the transaction.
The 4th step is creating problem as the message sent would not be persisted in the queue until the transaction is committed and due to this JMS receive functionality is broken.
Step 4 cant be performed before stating the JTA transaction as there is lot of dependency on the other steps.
Is there any way I can handle this type of situation.IS there any way to bypass transaction for step4? Any help appreciated.
Thanks