You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

Heartbeat.java 5.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. /*
  2. * Copyright 2000-2014 Vaadin Ltd.
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License"); you may not
  5. * use this file except in compliance with the License. You may obtain a copy of
  6. * the License at
  7. *
  8. * http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
  12. * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
  13. * License for the specific language governing permissions and limitations under
  14. * the License.
  15. */
  16. package com.vaadin.client.communication;
  17. import java.util.logging.Logger;
  18. import com.google.gwt.http.client.Request;
  19. import com.google.gwt.http.client.RequestBuilder;
  20. import com.google.gwt.http.client.RequestCallback;
  21. import com.google.gwt.http.client.RequestException;
  22. import com.google.gwt.http.client.Response;
  23. import com.google.gwt.user.client.Timer;
  24. import com.vaadin.client.ApplicationConnection;
  25. import com.vaadin.client.ApplicationConnection.ApplicationStoppedEvent;
  26. import com.vaadin.shared.ApplicationConstants;
  27. import com.vaadin.shared.ui.ui.UIConstants;
  28. import com.vaadin.shared.util.SharedUtil;
  29. /**
  30. * Handles sending of heartbeats to the server and reacting to the response
  31. *
  32. * @since 7.2
  33. * @author Vaadin Ltd
  34. */
  35. public class Heartbeat {
  36. private Timer timer = new Timer() {
  37. @Override
  38. public void run() {
  39. send();
  40. }
  41. };
  42. private ApplicationConnection connection;
  43. private String uri;
  44. private int interval = -1;
  45. private static Logger getLogger() {
  46. return Logger.getLogger(Heartbeat.class.getName());
  47. }
  48. /**
  49. * Initializes the heartbeat for the given application connection
  50. *
  51. * @param connection
  52. * the connection
  53. */
  54. public void init(ApplicationConnection applicationConnection) {
  55. connection = applicationConnection;
  56. setInterval(connection.getConfiguration().getHeartbeatInterval());
  57. uri = SharedUtil.addGetParameters(connection
  58. .translateVaadinUri(ApplicationConstants.APP_PROTOCOL_PREFIX
  59. + ApplicationConstants.HEARTBEAT_PATH + '/'),
  60. UIConstants.UI_ID_PARAMETER + "="
  61. + connection.getConfiguration().getUIId());
  62. connection.addHandler(
  63. ApplicationConnection.ApplicationStoppedEvent.TYPE,
  64. new ApplicationConnection.ApplicationStoppedHandler() {
  65. @Override
  66. public void onApplicationStopped(
  67. ApplicationStoppedEvent event) {
  68. setInterval(-1);
  69. }
  70. });
  71. }
  72. /**
  73. * Sends a heartbeat to the server
  74. */
  75. public void send() {
  76. timer.cancel();
  77. final RequestBuilder rb = new RequestBuilder(RequestBuilder.POST, uri);
  78. final RequestCallback callback = new RequestCallback() {
  79. @Override
  80. public void onResponseReceived(Request request, Response response) {
  81. int status = response.getStatusCode();
  82. if (status == Response.SC_OK) {
  83. connection.getConnectionStateHandler().heartbeatOk();
  84. } else {
  85. // Handler should stop the application if heartbeat should
  86. // no longer be sent
  87. connection.getConnectionStateHandler()
  88. .heartbeatInvalidStatusCode(request, response);
  89. }
  90. schedule();
  91. }
  92. @Override
  93. public void onError(Request request, Throwable exception) {
  94. // Handler should stop the application if heartbeat should no
  95. // longer be sent
  96. connection.getConnectionStateHandler().heartbeatException(
  97. request, exception);
  98. schedule();
  99. }
  100. };
  101. rb.setCallback(callback);
  102. try {
  103. getLogger().fine("Sending heartbeat request...");
  104. rb.send();
  105. } catch (RequestException re) {
  106. callback.onError(null, re);
  107. }
  108. }
  109. /**
  110. * @return the interval at which heartbeat requests are sent
  111. */
  112. public int getInterval() {
  113. return interval;
  114. }
  115. /**
  116. * Updates the schedule of the heartbeat to match the set interval. A
  117. * negative interval disables the heartbeat.
  118. */
  119. public void schedule() {
  120. if (interval > 0) {
  121. getLogger()
  122. .fine("Scheduling heartbeat in " + interval + " seconds");
  123. timer.schedule(interval * 1000);
  124. } else {
  125. getLogger().fine("Disabling heartbeat");
  126. timer.cancel();
  127. }
  128. }
  129. /**
  130. * @return the application connection
  131. */
  132. @Deprecated
  133. protected ApplicationConnection getConnection() {
  134. return connection;
  135. }
  136. /**
  137. * Changes the heartbeatInterval in runtime and applies it.
  138. *
  139. * @param heartbeatInterval
  140. * new interval in seconds.
  141. */
  142. public void setInterval(int heartbeatInterval) {
  143. getLogger().info(
  144. "Setting hearbeat interval to " + heartbeatInterval + "sec.");
  145. interval = heartbeatInterval;
  146. schedule();
  147. }
  148. }