From 3586917f4699cb1d3e83775a53ef26132c379846 Mon Sep 17 00:00:00 2001 From: Tyler McCraw Date: Mon, 22 Jan 2018 11:18:25 -0500 Subject: [PATCH] Enable additional body types for POST authorization --- .../pusher/client/util/ConnectionFactory.java | 35 ++++++++++ .../pusher/client/util/HttpAuthorizer.java | 69 +++++++++---------- .../util/UrlEncodedConnectionFactory.java | 58 ++++++++++++++++ 3 files changed, 126 insertions(+), 36 deletions(-) create mode 100644 src/main/java/com/pusher/client/util/ConnectionFactory.java create mode 100644 src/main/java/com/pusher/client/util/UrlEncodedConnectionFactory.java diff --git a/src/main/java/com/pusher/client/util/ConnectionFactory.java b/src/main/java/com/pusher/client/util/ConnectionFactory.java new file mode 100644 index 00000000..ef42a567 --- /dev/null +++ b/src/main/java/com/pusher/client/util/ConnectionFactory.java @@ -0,0 +1,35 @@ +package com.pusher.client.util; + +/** + * Abstract factory to be used for + * building HttpAuthorizer connections + */ +public abstract class ConnectionFactory { + private String channelName; + private String socketId; + + public ConnectionFactory() { + } + + public abstract String getBody(); + + public abstract String getCharset(); + + public abstract String getContentType(); + + public String getChannelName() { + return channelName; + } + + public void setChannelName(String channelName) { + this.channelName = channelName; + } + + public String getSocketId() { + return socketId; + } + + public void setSocketId(String socketId) { + this.socketId = socketId; + } +} diff --git a/src/main/java/com/pusher/client/util/HttpAuthorizer.java b/src/main/java/com/pusher/client/util/HttpAuthorizer.java index bfee012c..5558667b 100644 --- a/src/main/java/com/pusher/client/util/HttpAuthorizer.java +++ b/src/main/java/com/pusher/client/util/HttpAuthorizer.java @@ -1,5 +1,7 @@ package com.pusher.client.util; +import com.pusher.client.AuthorizationFailureException; +import com.pusher.client.Authorizer; import java.io.BufferedReader; import java.io.DataOutputStream; import java.io.IOException; @@ -8,15 +10,10 @@ import java.net.HttpURLConnection; import java.net.MalformedURLException; import java.net.URL; -import java.net.URLEncoder; import java.util.HashMap; import java.util.Map; - import javax.net.ssl.HttpsURLConnection; -import com.pusher.client.AuthorizationFailureException; -import com.pusher.client.Authorizer; - /** * Used to authenticate a {@link com.pusher.client.channel.PrivateChannel * private} or {@link com.pusher.client.channel.PresenceChannel presence} @@ -36,8 +33,7 @@ public class HttpAuthorizer implements Authorizer { private final URL endPoint; private Map mHeaders = new HashMap(); - private Map mQueryStringParameters = new HashMap(); - private final String ENCODING_CHARACTER_SET = "UTF-8"; + private ConnectionFactory mConnectionFactory = null; /** * Creates a new authorizer. @@ -48,12 +44,28 @@ public class HttpAuthorizer implements Authorizer { public HttpAuthorizer(final String endPoint) { try { this.endPoint = new URL(endPoint); + this.mConnectionFactory = new UrlEncodedConnectionFactory(); } catch (final MalformedURLException e) { throw new IllegalArgumentException("Could not parse authentication end point into a valid URL", e); } } + /** + * Creates a new authorizer. + * + * @param endPoint The endpoint to be called when authenticating. + * @param connectionFactory a custom connection factory to be used for building the connection + */ + public HttpAuthorizer(final String endPoint, final ConnectionFactory connectionFactory) { + try { + this.endPoint = new URL(endPoint); + this.mConnectionFactory = connectionFactory; + } catch (final MalformedURLException e) { + throw new IllegalArgumentException("Could not parse authentication end point into a valid URL", e); + } + } + /** * Set additional headers to be sent as part of the request. * @@ -71,31 +83,16 @@ public Boolean isSSL() { return endPoint.getProtocol().equals("https"); } - /** - * This methods is for passing extra parameters authentication that needs to - * be added to query string. - * - * @param queryStringParameters - * the query parameters - */ - public void setQueryStringParameters(final HashMap queryStringParameters) { - mQueryStringParameters = queryStringParameters; - } - @Override public String authorize(final String channelName, final String socketId) throws AuthorizationFailureException { - try { - final StringBuffer urlParameters = new StringBuffer(); - urlParameters.append("channel_name=").append(URLEncoder.encode(channelName, ENCODING_CHARACTER_SET)); - urlParameters.append("&socket_id=").append(URLEncoder.encode(socketId, ENCODING_CHARACTER_SET)); - - // Adding extra parameters supplied to be added to query string. - for (final String parameterName : mQueryStringParameters.keySet()) { - urlParameters.append("&").append(parameterName).append("="); - urlParameters.append(URLEncoder.encode(mQueryStringParameters.get(parameterName), - ENCODING_CHARACTER_SET)); - } + mConnectionFactory.setChannelName(channelName); + mConnectionFactory.setSocketId(socketId); + String body = mConnectionFactory.getBody(); + + final HashMap defaultHeaders = new HashMap(); + defaultHeaders.put("Content-Type", mConnectionFactory.getContentType()); + defaultHeaders.put("charset", mConnectionFactory.getCharset()); HttpURLConnection connection; if (isSSL()) { @@ -108,14 +105,14 @@ public String authorize(final String channelName, final String socketId) throws connection.setDoInput(true); connection.setInstanceFollowRedirects(false); connection.setRequestMethod("POST"); - connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded"); - connection.setRequestProperty("charset", "utf-8"); - connection.setRequestProperty("Content-Length", - "" + Integer.toString(urlParameters.toString().getBytes().length)); // Add in the user defined headers - for (final String headerName : mHeaders.keySet()) { - final String headerValue = mHeaders.get(headerName); + defaultHeaders.putAll(mHeaders); + // Add in the Content-Length, so it can't be overwritten by mHeaders + defaultHeaders.put("Content-Length","" + Integer.toString(body.getBytes().length)); + + for (final String headerName : defaultHeaders.keySet()) { + final String headerValue = defaultHeaders.get(headerName); connection.setRequestProperty(headerName, headerValue); } @@ -123,7 +120,7 @@ public String authorize(final String channelName, final String socketId) throws // Send request final DataOutputStream wr = new DataOutputStream(connection.getOutputStream()); - wr.writeBytes(urlParameters.toString()); + wr.writeBytes(body); wr.flush(); wr.close(); diff --git a/src/main/java/com/pusher/client/util/UrlEncodedConnectionFactory.java b/src/main/java/com/pusher/client/util/UrlEncodedConnectionFactory.java new file mode 100644 index 00000000..6aea9685 --- /dev/null +++ b/src/main/java/com/pusher/client/util/UrlEncodedConnectionFactory.java @@ -0,0 +1,58 @@ +package com.pusher.client.util; + +import java.io.UnsupportedEncodingException; +import java.net.URLEncoder; +import java.util.HashMap; +import java.util.Map; + +/** + * Form URL-Encoded Connection Factory + * + * Allows HttpAuthorizer to write URL parameters to the connection + */ +public class UrlEncodedConnectionFactory extends ConnectionFactory { + + private Map mQueryStringParameters = new HashMap(); + + /** + * Create a Form URL-encoded factory + */ + public UrlEncodedConnectionFactory() { + } + + /** + * Create a Form URL-encoded factory + * + * @param queryStringParameters extra parameters that need to be added to query string. + */ + public UrlEncodedConnectionFactory(final Map queryStringParameters) { + this.mQueryStringParameters = queryStringParameters; + } + + @Override + public String getCharset() { + return "UTF-8"; + } + + @Override + public String getContentType() { + return "application/x-www-form-urlencoded"; + } + + public String getBody() { + final StringBuffer urlParameters = new StringBuffer(); + try { + urlParameters.append("channel_name=").append(URLEncoder.encode(getChannelName(), getCharset())); + urlParameters.append("&socket_id=").append(URLEncoder.encode(getSocketId(), getCharset())); + + // Adding extra parameters supplied to be added to query string. + for (final String parameterName : mQueryStringParameters.keySet()) { + urlParameters.append("&").append(parameterName).append("="); + urlParameters.append(URLEncoder.encode(mQueryStringParameters.get(parameterName), getCharset())); + } + } catch (UnsupportedEncodingException e) { + e.printStackTrace(); + } + return urlParameters.toString(); + } +} \ No newline at end of file