use of org.osgl.mvc.result.Result in project actframework by actframework.
the class UrlEncodedParser method parse.
@Override
public Map<String, String[]> parse(ActionContext context) {
H.Request request = context.req();
// Encoding is either retrieved from contentType or it is the default encoding
final String encoding = request.characterEncoding();
InputStream is = request.inputStream();
try {
Map<String, String[]> params = new LinkedHashMap<String, String[]>();
ByteArrayOutputStream os = new ByteArrayOutputStream();
byte[] buffer = new byte[1024];
int bytesRead;
while ((bytesRead = is.read(buffer)) > 0) {
os.write(buffer, 0, bytesRead);
}
String data = new String(os.toByteArray(), encoding);
if (data.length() == 0) {
// data is empty - can skip the rest
return new HashMap<String, String[]>(0);
}
// check if data is in JSON format
if (data.startsWith("{") && data.endsWith("}") || data.startsWith("[") && data.endsWith("]")) {
return C.Map(ActionContext.REQ_BODY, new String[] { data });
}
// data is o the form:
// a=b&b=c%12...
// Let us lookup in two phases - we wait until everything is parsed before
// we decoded it - this makes it possible for use to look for the
// special _charset_ param which can hold the charset the form is encoded in.
//
// http://www.crazysquirrel.com/computing/general/form-encoding.jspx
// https://bugzilla.mozilla.org/show_bug.cgi?id=18643
//
// NB: _charset_ must always be used with accept-charset and it must have the same value
String[] keyValues = data.split("&");
int httpMaxParams = context.app().config().httpMaxParams();
// we should by default not lookup the params into HashMap if the count exceeds a maximum limit
if (httpMaxParams != 0 && keyValues.length > httpMaxParams) {
logger.warn("Number of request parameters %d is higher than maximum of %d, aborting. Can be configured using 'act.http.params.max'", keyValues.length, httpMaxParams);
// 413 Request Entity Too Large
throw new ErrorResult(H.Status.valueOf(413));
}
for (String keyValue : keyValues) {
// split this key-value on the first '='
int i = keyValue.indexOf('=');
String key = null;
String value = null;
if (i > 0) {
key = keyValue.substring(0, i);
value = keyValue.substring(i + 1);
} else {
key = keyValue;
}
if (key.length() > 0) {
MapUtil.mergeValueInMap(params, key, value);
}
}
// Second phase - look for _charset_ param and do the encoding
Charset charset = Charset.forName(encoding);
if (params.containsKey("_charset_")) {
// The form contains a _charset_ param - When this is used together
// with accept-charset, we can use _charset_ to extract the encoding.
// PS: When rendering the view/form, _charset_ and accept-charset must be given the
// same value - since only Firefox and sometimes IE actually sets it when Posting
String providedCharset = params.get("_charset_")[0];
// Must be sure the providedCharset is a valid encoding..
try {
"test".getBytes(providedCharset);
// it works..
charset = Charset.forName(providedCharset);
} catch (Exception e) {
logger.debug("Got invalid _charset_ in form: " + providedCharset);
// lets just use the default one..
}
}
// We're ready to decode the params
Map<String, String[]> decodedParams = new LinkedHashMap<String, String[]>(params.size());
for (Map.Entry<String, String[]> e : params.entrySet()) {
String key = e.getKey();
try {
key = Codec.decodeUrl(e.getKey(), charset);
} catch (Throwable z) {
// Nothing we can do about, ignore
}
for (String value : e.getValue()) {
try {
MapUtil.mergeValueInMap(decodedParams, key, (value == null ? null : Codec.decodeUrl(value, charset)));
} catch (Throwable z) {
// Nothing we can do about, lets fill in with the non decoded value
MapUtil.mergeValueInMap(decodedParams, key, value);
}
}
}
// add the complete body as a parameters
if (!forQueryString) {
decodedParams.put(ActionContext.REQ_BODY, new String[] { data });
}
return decodedParams;
} catch (Result s) {
// just pass it along
throw s;
} catch (Exception e) {
throw new UnexpectedException(e);
}
}
use of org.osgl.mvc.result.Result in project actframework by actframework.
the class RequestHandlerProxy method handle.
@Override
public void handle(ActionContext context) {
ensureAgentsReady();
context.handlerMethod(actionMethod);
if (null != webSocketConnectionHandler) {
webSocketConnectionHandler.handle(context);
return;
}
Result result = null;
try {
H.Method method = context.req().method();
boolean supportCache = this.supportCache && method == GET || (cacheSupport.supportPost && method == POST);
String cacheKey = null;
if (supportCache) {
cacheKey = cacheSupport.cacheKey(context);
ResponseCache cached = this.cache.get(cacheKey);
if (null != cached) {
cached.applyTo(context.prepareRespForWrite());
return;
}
context.enableCache();
}
saveActionPath(context);
context.startIntercepting();
result = handleBefore(context);
if (null == result) {
context.startHandling();
result = _handle(context);
}
if (context.resp().isClosed()) {
return;
}
context.startIntercepting();
Result afterResult = handleAfter(result, context);
if (null != afterResult) {
result = afterResult;
}
if (null == result) {
result = context.nullValueResult();
}
onResult(result, context);
if (supportCache) {
this.cache.put(cacheKey, context.resp(), cacheSupport.ttl);
}
} catch (Exception e) {
H.Request req = context.req();
logger.error(e, S.concat("Error handling request: [", req.method().name(), "] ", req.url()));
try {
result = handleException(e, context);
} catch (Exception e0) {
logger.error(e0, "Error invoking exception handler");
}
if (null == result) {
result = ActErrorResult.of(e);
}
try {
onResult(result, context);
} catch (Exception e2) {
logger.error(e2, "error rendering exception handle result");
onResult(ActErrorResult.of(e2), context);
}
} finally {
try {
handleFinally(context);
} catch (Exception e) {
logger.error(e, "Error invoking final handler");
} finally {
context.destroy();
}
}
}
use of org.osgl.mvc.result.Result in project actframework by actframework.
the class UnknownHttpMethodHandler method handle.
@Override
public void handle(ActionContext context) {
H.Method method = context.req().method();
Result result = configured(context.config()).handle(method);
try {
result = RequestHandlerProxy.GLOBAL_AFTER_INTERCEPTOR.apply(result, context);
} catch (Exception e) {
logger.error(e, "Error calling global after interceptor");
result = ActErrorResult.of(e);
}
result.apply(context.req(), context.prepareRespForWrite());
}
Aggregations