/** * Helios, OpenSource Monitoring * Brought to you by the Helios Development Group * * Copyright 2007, Helios Development Group and individual contributors * as indicated by the @author tags. See the copyright.txt file in the * distribution for a full listing of individual contributors. * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU Lesser General Public License as * published by the Free Software Foundation; either version 2.1 of * the License, or (at your option) any later version. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this software; if not, write to the Free * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA * 02110-1301 USA, or see the FSF site: http://www.fsf.org. * */ package org.helios.apmrouter.dataservice.json.proxy; import java.util.Map; import org.helios.apmrouter.dataservice.json.DataServiceUtils; import org.helios.apmrouter.dataservice.json.JSONRequestHandler; import org.helios.apmrouter.server.unification.pipeline.http.proxy.HttpRequestProxy; import org.jboss.netty.channel.Channel; import org.jboss.netty.channel.ChannelFuture; import org.jboss.netty.channel.Channels; import org.jboss.netty.channel.UpstreamMessageEvent; import org.jboss.netty.handler.codec.http.DefaultHttpRequest; import org.jboss.netty.handler.codec.http.HttpMethod; import org.jboss.netty.handler.codec.http.HttpRequest; import org.jboss.netty.handler.codec.http.HttpVersion; import org.jboss.netty.handler.codec.http.QueryStringEncoder; import org.json.JSONException; import org.json.JSONObject; import org.springframework.beans.factory.annotation.Autowired; /** * <p>Title: ProxyJSONRequestService</p> * <p>Description: A JSON data service that dispatches to the defined proxy.</p> * <p>Company: Helios Development Group LLC</p> * @author Whitehead (nwhitehead AT heliosdev DOT org) * <p><code>org.helios.apmrouter.dataservice.json.proxy.ProxyJSONRequestService</code></p> */ @JSONRequestHandler(name="http") public class ProxyJSONRequestService { /** The proxy request handler */ @Autowired(required=true) protected HttpRequestProxy requestProxy = null; /** * <p>Accepts a JSON encoded request for a proxy call to an HTTP endpoint. Parameters are:<ol> * <li><b>hostport</b>: An optional destination specification in the form of <b><code>[hostname]<:[port]></code></b>. If not specified, request will be routed within the current http context.</li> * <li><b>uri</b>: The mandatory URI of the http request to be proxied.</li> * <li><b>method</b>: The method http request to be proxied. Defaults to <b>GET</b></li> * <li><b>args</b>: An optional map of parameters to attach to the forwarded HTTP request</li> * <li><b>hdrs</b>: An optional map of headers to attach to the forwarded HTTP request</li> * <li><b>creds</b>: Simple HTTP auth credentials. <b>Not Implemented</b></li> * </ol></p> * @param request The JSON request * @param channel The channel through which the request came * @throws JSONException thrown on any JSON unmarshalling exception */ @JSONRequestHandler(name="req") public void proxyRequest(JSONObject request, Channel channel) throws JSONException { String uri = null; if(!request.has("uri")) { throw new JSONException("No uri supplied"); } uri = request.getString("uri"); String method = null; String hostPort = null; Map<String, Object> params = null; Map<String, Object> headers = null; if(request.has("method")) { method = request.getString("method").trim().toUpperCase(); } else { method = "GET"; } if(request.has("hostport")) hostPort = request.getString("hostport"); if(request.has("args")) params = DataServiceUtils.getMap(request, "args"); if(request.has("headers")) headers = DataServiceUtils.getMap(request, "headers"); QueryStringEncoder encoder = new QueryStringEncoder(uri); if(params!=null) { for(Map.Entry<String, Object> entry: params.entrySet()) { encoder.addParam(entry.getKey(), entry.getValue().toString()); } } HttpRequest proxyRequest = new DefaultHttpRequest(HttpVersion.HTTP_1_1, HttpMethod.valueOf(method), encoder.toString()); if(headers!=null) { for(Map.Entry<String, Object> entry: headers.entrySet()) { proxyRequest.addHeader(entry.getKey(), entry.getValue()); } } if(hostPort==null) { // Need to insert an interceptor in the pipeline so we can get our response back ChannelFuture cf = Channels.future(channel); channel.getPipeline().getContext(channel.getPipeline().getFirst()).sendUpstream(new UpstreamMessageEvent(channel, proxyRequest, channel.getRemoteAddress())); } else { } } }