view src/luan/modules/http/HttpServicer.java @ 1256:c147e2e877e3

allow subclassing of HttpServicer
author Franklin Schmidt <fschmidt@gmail.com>
date Wed, 19 Sep 2018 20:15:16 -0600
parents 354e661dee7f
children 382c444a6c77
line wrap: on
line source

package luan.modules.http;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import luan.webserver.Request;
import luan.webserver.Response;
import luan.webserver.Status;
import luan.LuanState;
import luan.LuanFunction;
import luan.LuanException;
import luan.LuanTable;
import luan.LuanCloner;
import luan.modules.PackageLuan;


public class HttpServicer {
	private static final Logger logger = LoggerFactory.getLogger(HttpServicer.class);

	public Response service(LuanState luan,Request request,String modName) {
		try {
			return serviceLuan(luan,request,modName);
		} catch(LuanException e) {
			return handleError(request,e);
		}
	}

	protected Response handleError(Request request,LuanException e) {
//e.printStackTrace();
		String err = e.getLuanStackTraceString();
		logger.error(err+"\n"+request.rawHead.trim()+"\n");
		String msg = "Internel Server Error\n\n" + err;
		return Response.errorResponse( Status.INTERNAL_SERVER_ERROR, msg );
	}

	protected Response serviceLuan(LuanState luan,Request request,String modName)
		throws LuanException
	{
		LuanFunction fn;
		synchronized(luan) {
			inSinchronized(luan,request);
			PackageLuan.enableLoad(luan,"luan:http/Http.luan",modName);
			PackageLuan.require(luan,"luan:http/Http.luan");
			Object mod = PackageLuan.load(luan,modName);
			if( mod.equals(Boolean.FALSE) )
				return null;
			if( !(mod instanceof LuanFunction) )
				throw new LuanException( "module '"+modName+"' must return a function" );
			LuanCloner cloner = new LuanCloner(LuanCloner.Type.INCREMENTAL);
			luan = (LuanState)cloner.clone(luan);
			fn = (LuanFunction)cloner.get(mod);
		}

		LuanTable module = (LuanTable)PackageLuan.require(luan,"luan:http/Http.luan");

		// request
		LuanFunction newRequestFn = (LuanFunction)module.rawGet("new_request");
		newRequestFn.call( luan, new Object[]{request} );

		// response
		LuanFunction newResponseFn = (LuanFunction)module.rawGet("new_response");
		newResponseFn.call(luan);

		fn.call(luan);

		LuanFunction finishFn = (LuanFunction)module.rawGet("finish");
		Response response = (Response)finishFn.call(luan);
		return response;
	}

	protected void inSinchronized(LuanState luan,Request request)
		throws LuanException
	{}

}