Permalink
Browse files

Merge pull request #19 from roam/master

UDP support
  • Loading branch information...
2 parents a809db0 + 534cc26 commit 46251e591d32b7c8075fc1a24cbf48deaceb65d7 @kencochrane kencochrane committed Jun 25, 2012
View
@@ -30,7 +30,7 @@ you'll find in the target directory of the project.
<dependency>
<groupId>net.kencochrane</groupId>
<artifactId>raven-java</artifactId>
- <version>0.5-SNAPSHOT</version>
+ <version>0.6-SNAPSHOT</version>
</dependency>
**Option 2**: add the plain jar and the jar files of all dependencies to your classpath
@@ -173,6 +173,8 @@ TODO
History
-------
+- 0.6
+ - Added support for sending messages through UDP
- 0.5
- Added async support
- Fixed issue with parsing of path and port in DSN
View
@@ -6,7 +6,7 @@
<groupId>net.kencochrane</groupId>
<artifactId>raven-java</artifactId>
- <version>0.5-SNAPSHOT</version>
+ <version>0.6-SNAPSHOT</version>
<packaging>jar</packaging>
<name>raven-java</name>
<description>Java Raven client and log4j appender.</description>
@@ -9,9 +9,7 @@
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
-import java.net.HttpURLConnection;
-import java.net.MalformedURLException;
-import java.net.URL;
+import java.net.*;
import static org.apache.commons.codec.binary.Base64.encodeBase64String;
@@ -23,7 +21,7 @@
public class RavenClient {
- private static final String RAVEN_JAVA_VERSION = "Raven-Java 0.4";
+ private static final String RAVEN_JAVA_VERSION = "Raven-Java 0.6";
private RavenConfig config;
private String sentryDSN;
private String lastID;
@@ -54,11 +52,16 @@ public RavenConfig getConfig() {
public void setConfig(RavenConfig config) {
this.config = config;
try {
- URL endpoint = new URL(config.getSentryURL());
- if (config.isNaiveSsl() && "https".equals(endpoint.getProtocol())) {
- messageSender = new NaiveHttpsMessageSender(config, endpoint);
+ String protocol = config.getProtocol();
+ if ("udp".equals(protocol)) {
+ messageSender = new UdpMessageSender(config, null);
} else {
- messageSender = new MessageSender(config, endpoint);
+ URL endpoint = new URL(config.getSentryURL());
+ if (config.isNaiveSsl() && "https".equals(protocol)) {
+ messageSender = new NaiveHttpsMessageSender(config, endpoint);
+ } else {
+ messageSender = new MessageSender(config, endpoint);
+ }
}
} catch (MalformedURLException e) {
throw new RuntimeException("Sentry URL is malformed", e);
@@ -311,6 +314,10 @@ public void send(String messageBody, long timestamp) throws IOException {
// get the auth header
String authHeader = buildAuthHeader(hmacSignature, timestamp, config.getPublicKey());
+ doSend(messageBody, authHeader);
+ }
+
+ protected void doSend(String messageBody, String authHeader) throws IOException {
HttpURLConnection connection = getConnection();
connection.setRequestMethod("POST");
connection.setDoOutput(true);
@@ -378,6 +385,29 @@ protected HttpURLConnection getConnection() throws IOException {
}
}
+ public static class UdpMessageSender extends MessageSender {
+
+ private final DatagramSocket socket;
+
+ public UdpMessageSender(RavenConfig config, URL endpoint) {
+ super(config, endpoint);
+ try {
+ socket = new DatagramSocket();
+ socket.connect(new InetSocketAddress(config.getHost(), config.getPort()));
+ } catch (SocketException e) {
+ throw new IllegalStateException(e);
+ }
+ }
+
+ @Override
+ protected void doSend(String messageBody, String authHeader) throws IOException {
+ byte[] message = (authHeader + "\n\n" + messageBody).getBytes("UTF-8");
+ DatagramPacket packet = new DatagramPacket(message, message.length);
+ socket.send(packet);
+ }
+
+ }
+
public static class AcceptAllHostnameVerifier implements HostnameVerifier {
@Override
public boolean verify(String hostname, SSLSession sslSession) {
@@ -29,20 +29,26 @@ public RavenConfig(String sentryDSN) {
*
* @param sentryDSN '{PROTOCOL}://{PUBLIC_KEY}:{SECRET_KEY}@{HOST}/{PATH}/{PROJECT_ID}'
* @param proxy proxy to use for the HTTP connections; blank or null when no proxy is to be used
- * @param naiveSsl use a hostname verifier for SSL connections that allows all connections
+ * @param naiveSsl use a hostname verifier for SSL connections that allows all connections
*/
public RavenConfig(String sentryDSN, String proxy, boolean naiveSsl) {
this.naiveSsl = naiveSsl;
try {
+ boolean udp = sentryDSN.startsWith("udp://");
+ if (udp) {
+ // So either we have to start registering protocol handlers which is a PITA to do decently in Java
+ // without causing problems for the actual application, or we hack our way around it.
+ sentryDSN = sentryDSN.replace("udp://", "http://");
+ }
URL url = new URL(sentryDSN);
this.host = url.getHost();
- this.protocol = url.getProtocol();
+ this.protocol = udp ? "udp" : url.getProtocol();
String urlPath = url.getPath();
int lastSlash = urlPath.lastIndexOf("/");
this.path = urlPath.substring(0, lastSlash);
// ProjectId is the integer after the last slash in the path
- this.projectId = urlPath.substring(lastSlash+1);
+ this.projectId = urlPath.substring(lastSlash + 1);
String userInfo = url.getUserInfo();
String[] userParts = userInfo.split(":");
@@ -59,7 +65,6 @@ public RavenConfig(String sentryDSN, String proxy, boolean naiveSsl) {
this.proxyPort = Integer.parseInt(proxyParts[2]);
}
-
} catch (MalformedURLException e) {
e.printStackTrace();
}
@@ -51,5 +51,11 @@ public void test_simple() {
} catch (RuntimeException e) {
logger.error("Error example with stacktrace", e);
}
+ // This really shouldn't be necessary
+ try {
+ Thread.sleep(5000);
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
}
}

0 comments on commit 46251e5

Please sign in to comment.