package org.esmerilprogramming.overtown.http; import io.undertow.server.HttpServerExchange; import io.undertow.server.handlers.form.FormData; import io.undertow.server.handlers.form.FormData.FormValue; import io.undertow.server.handlers.form.FormDataParser; import io.undertow.server.handlers.form.FormEncodedDataDefinition; import java.io.IOException; import java.util.Deque; import java.util.HashMap; import java.util.Iterator; import java.util.Map; import java.util.Set; import io.undertow.util.AttachmentKey; import org.esmerilprogramming.overtown.http.converter.GenericConverter; import org.esmerilprogramming.overtown.http.converter.ParameterConverter; import org.esmerilprogramming.overtown.view.ViewAttributes; import org.jboss.logging.Logger; /** * @author efraimgentil (efraim.gentil@gmail.com) */ public class OvertownRequest { private static final Logger LOGGER = Logger.getLogger(OvertownRequest.class); private HttpServerExchange exchange; private OvertownSessionManager sessionManager; private Map<String, Deque<String>> queryParameters; private Map<String, GenericConverter<?>> parameterConverters; private FormData formData; private ViewAttributes viewAttributes; private Response response; public static final AttachmentKey<Exception> EXCEPTION_ATTACHMENT_KEY = AttachmentKey.create(Exception.class); public OvertownRequest() {} public OvertownRequest(HttpServerExchange exchange) { this.exchange = exchange; this.queryParameters = exchange.getQueryParameters(); this.parameterConverters = new HashMap<>(); this.viewAttributes = new ViewAttributes(); this.sessionManager = OvertownSessionManager.getInstance(); if (isPostRequest()) { FormDataParser create = new FormEncodedDataDefinition().create(exchange); try { formData = create != null ? create.parseBlocking() : null; } catch (IOException ioe) { LOGGER.error(ioe.getMessage()); } } if( exchange.getAttachment( EXCEPTION_ATTACHMENT_KEY ) != null){ Exception e = exchange.getAttachment( EXCEPTION_ATTACHMENT_KEY ); addAttribute(ErrorHandler.ERROR_500, e); exchange.removeAttachment( EXCEPTION_ATTACHMENT_KEY ); } } public OvertownSession getSession(){ return sessionManager.getSession( exchange ); } public OvertownSession createSession(){ return sessionManager.createNewSession(exchange); } public <T> void addAttribute(String name , T value ){ viewAttributes.add(name, value); } public Object getAttribute(String name){ return viewAttributes.getAsMap().get( name ); } public ViewAttributes getViewAttributes(){ return viewAttributes; } public Object getParameter(String name) { Object value = null; if (isPostRequest()) { value = getFromFormData(name); } if (value == null) { value = getFromParameters(name); } return value; } protected Object getFromFormData(String name) { if (formData != null) { Deque<FormValue> dequeVal = formData.get(name); if (dequeVal != null) { return dequeVal.getLast().getValue(); } } return null; } protected Object getFromParameters(String parameterName) { Deque<String> deque = queryParameters.get(parameterName); if (deque != null) { return deque.getLast(); } return null; } public boolean containsAttributeStartingWith(String parameterName) { boolean contains = false; Set<String> keySet = queryParameters.keySet(); String parameterPrefix = parameterName + "."; if (keySet.contains(parameterPrefix)) { contains = true; } if (isPostRequest() && contains == false && formData != null) { Iterator<String> iterator = formData.iterator(); while (iterator.hasNext()) { String next = iterator.next(); if (next.contains(parameterPrefix)) { contains = true; break; } } } return contains; } protected boolean isPostRequest() { return "POST".equalsIgnoreCase(exchange.getRequestMethod().toString()) || "PUT".equalsIgnoreCase(exchange.getRequestMethod().toString()) || "DELETE".equalsIgnoreCase(exchange.getRequestMethod().toString()); } public HttpServerExchange getExchange() { return exchange; } public void addConverter(String parameterName , GenericConverter<?> converter){ parameterConverters.put(parameterName, converter); } public void addConverters( Map<String, GenericConverter<?>> converterMaps ){ parameterConverters.putAll(converterMaps); } public void setConverters( Map<String, GenericConverter<?>> converterMaps ){ parameterConverters = converterMaps; } public boolean shouldConvertParameter(String parameterName) { return parameterConverters.containsKey(parameterName); } public ParameterConverter getTranslator(String parameterName) { return parameterConverters.get(parameterName); } protected void setQueryParameters(Map<String, Deque<String>> queryParameters) { this.queryParameters = queryParameters; } public void respondAsHttp() { if(response == null || !(response instanceof HttpResponse ) ){ response = new HttpResponse( exchange , viewAttributes ); } } public void respondAsJson() { if(response == null || !(response instanceof JsonResponse )){ response = new JsonResponse( exchange , viewAttributes ); } } public Response getResponse() { if(response == null){ respondAsHttp(); } return response; } public JsonResponse getJsonResponse(){ if(response == null || !(response instanceof JsonResponse )){ respondAsJson(); } return (JsonResponse) response; } public Object getHttpMethod() { return exchange.getRequestMethod().toString(); } }