From 37742d3e76bf90be9e7f5d2d452cbfc2651e8e95 Mon Sep 17 00:00:00 2001 From: buraq Date: Tue, 27 Jul 2004 15:49:43 +0000 Subject: hello --- sources/scala/tools/servlet/ScalaServlet.scala | 29 +++++----- sources/scala/tools/servlet/engine/Main.scala | 41 +++++++++++--- sources/scala/tools/servlet/engine/Mapping.scala | 21 +------- .../scala/tools/servlet/engine/config/Config.scala | 10 ++++ .../servlet/engine/config/ConfigHandler.scala | 62 ++++++++++++++++++++++ .../tools/servlet/engine/config/ConfigReader.scala | 39 ++++++++++++++ sources/scala/tools/servlet/http/HTTP.scala | 2 +- .../scala/tools/servlet/http/HttpConnector.scala | 6 +-- sources/scala/tools/servlet/http/HttpHandler.scala | 13 +++-- .../scala/tools/servlet/http/HttpProcessor.scala | 1 - .../scala/tools/servlet/http/HttpServletPro.scala | 47 ++++++++-------- 11 files changed, 201 insertions(+), 70 deletions(-) create mode 100644 sources/scala/tools/servlet/engine/config/Config.scala create mode 100644 sources/scala/tools/servlet/engine/config/ConfigHandler.scala create mode 100644 sources/scala/tools/servlet/engine/config/ConfigReader.scala (limited to 'sources') diff --git a/sources/scala/tools/servlet/ScalaServlet.scala b/sources/scala/tools/servlet/ScalaServlet.scala index 627824f094..51e62fbde8 100644 --- a/sources/scala/tools/servlet/ScalaServlet.scala +++ b/sources/scala/tools/servlet/ScalaServlet.scala @@ -5,6 +5,20 @@ import scala.xml._; import scala.collection.mutable.HashMap ; import http.HttpOutputStream; +object ScalaServlet { + final def showError(out: HttpOutputStream, status:int, msg :String): Unit = + out.write( + + + SERVLET ERROR + + + Attention,erreur dans la servlet +
type de l erreur: { Status.getMessage(status) }
{ msg } + + .toString()); +} + /** subclasses can be registered with the servlet engine to handle requests */ abstract class ScalaServlet { @@ -19,23 +33,12 @@ abstract class ScalaServlet { } catch { case ServletException(status, msg) => - showError( status, msg ); + ScalaServlet.showError(out, status, msg ); case ex:Exception => - showError(Status.INTERNAL_ERROR, ex.getMessage()); + ScalaServlet.showError(out, Status.INTERNAL_ERROR, ex.getMessage()); } } - final def showError(status:int, msg :String): scala.xml.Node = { - - - SERVLET ERROR - - - Attention,erreur dans la servlet -
type de l erreur: { Status.getMessage(status) }
{ msg } - - - } } diff --git a/sources/scala/tools/servlet/engine/Main.scala b/sources/scala/tools/servlet/engine/Main.scala index d98fcdc432..ecde727fb8 100644 --- a/sources/scala/tools/servlet/engine/Main.scala +++ b/sources/scala/tools/servlet/engine/Main.scala @@ -13,13 +13,42 @@ import java.net.ServerSocket; */ object Main { - //@todo make this configurable with ports and handlers - private var hcon: Thread = new servlet.http.HttpConnector(8000); + final val sampleConfig = + + + + + ; + + def main(args: Array[String]): Unit = { - Console.println("starting http connector at 8000"); - hcon.start(); - while(true) { - Thread.sleep(50000) + if( args.length != 1 ) { + + Console.println("usage:"); + Console.println("scala scala.tools.servlet.engine.Main "); + Console.println(" where is the filename of a document like this one:"); + Console.println( new scala.xml.PrettyPrinter(80,5).format( sampleConfig )); + + } else { + val fileName = args(0); + Console.println("reading config file from \""+fileName+"\""); + val theConfig = new config.ConfigReader(fileName).element; + + import config._ ; + + for( val c <- theConfig ) c match { + case EngineConfig(list) => + for( val conn <- list ) conn match { + case HttpConnectorConfig(port,map) => + Console.println("starting http connector at "+port); + new http.HttpConnector(port, map).start(); //@todo + } + } + //Console.println("starting http connector at 8000"); + //hcon.start(); + while(true) { + Thread.sleep(50000) + } } } } diff --git a/sources/scala/tools/servlet/engine/Mapping.scala b/sources/scala/tools/servlet/engine/Mapping.scala index c709cab686..24000febb9 100644 --- a/sources/scala/tools/servlet/engine/Mapping.scala +++ b/sources/scala/tools/servlet/engine/Mapping.scala @@ -1,24 +1,7 @@ package scala.tools.servlet.engine; -import java.io._; +trait Mapping { -class Mapping(){ - - val map = new File(http.HTTP.SERVER_LOCATION,http.HTTP.translateFilename("map.prop")); - val myProp = new java.util.Properties(); - - try{ - myProp.load(new FileInputStream(map)); - } - - catch{ - case e:FileNotFoundException => System.out.println("FileNotFoundException "); - case e:IOException => System.out.println("IOException"); - case e: IllegalArgumentException => System.out.println(" IllegalArgumentException"); - } - - def switch(original:String):String={ - myProp.getProperty(original); - } + def switch(uri: String): String; } diff --git a/sources/scala/tools/servlet/engine/config/Config.scala b/sources/scala/tools/servlet/engine/config/Config.scala new file mode 100644 index 0000000000..50fdf38590 --- /dev/null +++ b/sources/scala/tools/servlet/engine/config/Config.scala @@ -0,0 +1,10 @@ +package scala.tools.servlet.engine.config ; + +abstract class Config; + +case class EngineConfig(xs:List[ConnectorConfig]) extends Config; + +abstract class ConnectorConfig extends Config; + +case class HttpConnectorConfig(port:Int, mapping: PartialFunction[String,String]) extends ConnectorConfig; + diff --git a/sources/scala/tools/servlet/engine/config/ConfigHandler.scala b/sources/scala/tools/servlet/engine/config/ConfigHandler.scala new file mode 100644 index 0000000000..537dbf6a0a --- /dev/null +++ b/sources/scala/tools/servlet/engine/config/ConfigHandler.scala @@ -0,0 +1,62 @@ +package scala.tools.servlet.engine.config ; + +import scala.collection.mutable; + +import scala.xml.{ Attribute, AttributeSeq, Elem }; +import scala.xml.parsing._; + +class ConfigHandler extends MarkupHandler[Config] { + + final val config_namespace = "http://scala.epfl.ch/scala.tools.servlet.engine/config"; + + def attributeCDataValue(pos: int, str:String) = CDataValue(str); + + def attributeIntValue(pos: int, value:Int) = IntValue(value); + + def attributeNamespaceDecl(pos: int, uri: String) = NamespaceDecl(uri); + + override def attribute(pos: int, key: String, value:String): AttribValue = + if( key == "port" ) + attributeIntValue(pos, Integer.parseInt(value)); + else + super.attribute(pos,key,value); + + var hmap = new mutable.HashMap[String,String]; + + /** be careful to copy everything from attrMap1, as it will change + * @param attrMap1 the attribute map. + */ + def element(pos: int, uri: String, label: String, attrMap1: mutable.Map[String,AttribValue], args: mutable.Buffer[Config]): Option[Config] = { + if( uri == config_namespace ) { + label match { + + case "engine" => + var list:List[ConnectorConfig] = Nil; + for( val c <- args ) c match { + case x:ConnectorConfig => + list = x::list; + case _ => + } + Some(EngineConfig( list )); + + case "connector" if attrMap1("protocol").asString == "http" => + val res = HttpConnectorConfig( attrMap1("port").asInt, hmap ); + hmap = new mutable.HashMap[String,String]; + Some(res) + + case "map" => + hmap.update(attrMap1("url").asString, attrMap1("to").asString); + None + } + } else None + + } + + def charData(pos: Int, txt: String ) = None; + def procInstr(pos: Int, target: String, txt: String) = None; + def comment(pos: Int, comment: String ) = None; + def entityRef(pos: Int, n: String) = None; + + def text(pos: Int, n: String) = None; + +} diff --git a/sources/scala/tools/servlet/engine/config/ConfigReader.scala b/sources/scala/tools/servlet/engine/config/ConfigReader.scala new file mode 100644 index 0000000000..abfc61d15c --- /dev/null +++ b/sources/scala/tools/servlet/engine/config/ConfigReader.scala @@ -0,0 +1,39 @@ +package scala.tools.servlet.engine.config ; + +import tools.util.SourceReader ; + +import scala.xml.parsing.MarkupParser; + +import scala.collection.mutable; + +case class ConfigReaderError(msg: String) extends Exception(msg); + +class ConfigReader(inp: String) extends MarkupParser[Config] { + + /** sets up reader for source files */ + val inputIt: Iterator[Char] = { + val charset = java.nio.charset.Charset.forName("ISO-8859-1"); // @todo + val decoder = charset.newDecoder(); + val reader = new SourceReader(decoder); + val file:Seq[Char] = reader.read( inp ); + file.elements + } + + override var ch = inputIt.next; + + def nextch = { + if( inputIt.hasNext ) + ch = inputIt.next; + } + + val handle = new ConfigHandler(); + + //val enableEmbeddedExpressions: Boolean; + + /** report a syntax error */ + def reportSyntaxError(str: String): Unit = throw ConfigReaderError(str); + + def init = nextch; + val preserveWS = false; + +} diff --git a/sources/scala/tools/servlet/http/HTTP.scala b/sources/scala/tools/servlet/http/HTTP.scala index 3e186ea136..8f74eadc83 100644 --- a/sources/scala/tools/servlet/http/HTTP.scala +++ b/sources/scala/tools/servlet/http/HTTP.scala @@ -7,7 +7,7 @@ import scala.collection.mutable.HashMap; /** constants */ object HTTP { val SERVER_INFO: String= "JNP-HTTPD/1.0"; - val SERVLET: String= "/servlet/"; + val SERVLET_PREFIX: String= "/servlet/"; val SERVER_LOCATION: File= new File(System.getProperty("user.dir")); val HTML_ROOT: File= new File(SERVER_LOCATION,"html"); val PORT:Int = 80 ; diff --git a/sources/scala/tools/servlet/http/HttpConnector.scala b/sources/scala/tools/servlet/http/HttpConnector.scala index 424d43e17d..685fce7915 100644 --- a/sources/scala/tools/servlet/http/HttpConnector.scala +++ b/sources/scala/tools/servlet/http/HttpConnector.scala @@ -1,12 +1,12 @@ package scala.tools.servlet.http; -import java.net.{ Socket, ServerSocket }; +import servlet.engine.config.HttpConnectorConfig; /** for every port, there is one connector that instantiates a handler * per client connection */ -class HttpConnector(port: Int) extends servlet.engine.Connector(port) { +class HttpConnector(port: Int, map: PartialFunction[String,String]) extends servlet.engine.Connector(port) { - def makeHandler(s: Socket) = new HttpHandler( s ); + def makeHandler(s: java.net.Socket) = new HttpHandler( s, map ); } diff --git a/sources/scala/tools/servlet/http/HttpHandler.scala b/sources/scala/tools/servlet/http/HttpHandler.scala index b8d78ab487..67c9582704 100644 --- a/sources/scala/tools/servlet/http/HttpHandler.scala +++ b/sources/scala/tools/servlet/http/HttpHandler.scala @@ -4,7 +4,7 @@ import java.io._; import java.net._; import scala.collection.mutable.HashMap; -class HttpHandler(client: Socket) extends Thread { +class HttpHandler(client: Socket, mapping: PartialFunction[String,String]) extends Thread { override def run(): Unit ={ @@ -34,7 +34,8 @@ class HttpHandler(client: Socket) extends Thread { /* La methode run: on a construit premierement un HttpInputStream dans le client Input Stream, ceci nous facilte lire et parser les requetes HTTP*/ - def getProcessor(httpIn: HttpInputStream): HttpProcessor={ + def getProcessor(httpIn: HttpInputStream): HttpProcessor = { + Console.println("HttpHandler.getProcessor"); var value = 0; var infoString = " " ; var info:HashMap[String, String] = null; @@ -50,9 +51,10 @@ class HttpHandler(client: Socket) extends Thread { info = HTTP.processing(infoString); } - if (httpIn.getPath().startsWith(HTTP.SERVLET)){ + if( mapping.isDefinedAt(httpIn.getPath())) { + //if (httpIn.getPath().startsWith(HTTP.SERVLET_PREFIX)){ value = 1; - srv = new HttpServletPro(httpIn, info); + srv = new HttpServletPro(httpIn, info, mapping(httpIn.getPath())+"$class"); } else{ value = 2; @@ -60,6 +62,7 @@ class HttpHandler(client: Socket) extends Thread { } } + catch { case e: HttpException => { error=e.toProcessor; @@ -73,6 +76,8 @@ class HttpHandler(client: Socket) extends Thread { error= exept.toProcessor;} } + Console.println("value = "+value); + if(value == 1) return srv ; else if(value == 2) diff --git a/sources/scala/tools/servlet/http/HttpProcessor.scala b/sources/scala/tools/servlet/http/HttpProcessor.scala index 41a79f3e23..5604fc0908 100644 --- a/sources/scala/tools/servlet/http/HttpProcessor.scala +++ b/sources/scala/tools/servlet/http/HttpProcessor.scala @@ -1,6 +1,5 @@ package scala.tools.servlet.http ; -import java.io._; /** le processing actuel de la requête du client est reporté aux classes qui implemetent le trait HttpProcessor, ce trait decrit la façon avec laquelle la classe Httpd peut appeler le processeur pour repondre à la requête du client. */ diff --git a/sources/scala/tools/servlet/http/HttpServletPro.scala b/sources/scala/tools/servlet/http/HttpServletPro.scala index 526b265644..f61569102f 100644 --- a/sources/scala/tools/servlet/http/HttpServletPro.scala +++ b/sources/scala/tools/servlet/http/HttpServletPro.scala @@ -5,15 +5,7 @@ import java.net._; import scala.collection.mutable.HashMap; -class HttpServletPro(in: HttpInputStream, info: HashMap[String,String]) with HttpProcessor{ - - var servletName="" ; - val servletInfo =""; - var servlet = new File (HTTP.SERVER_LOCATION,HTTP.translateFilename("src")); - val contentLength = 0; - //val repertoire = extract(); - - var servletClassName:String = extract(); +class HttpServletPro(in: HttpInputStream, info: HashMap[String,String], servletClassName: String) with HttpProcessor{ /* if(!servlet.exists()){ @@ -23,8 +15,10 @@ class HttpServletPro(in: HttpInputStream, info: HashMap[String,String]) with Htt */ // assumption: in.getPath() is a string a/b/c, looks up servlet by c + + /* final def extract():String ={ - val path = in.getPath();// retourne /servlet/repertoire/servletName + val path = in.getPath(); // retourne /servlet/repertoire/servletName Console.println("HttpServletPro:path = "+path); var repertoireExtract=""; var repertoireIdx = path.indexOf('/', 1); @@ -36,11 +30,15 @@ class HttpServletPro(in: HttpInputStream, info: HashMap[String,String]) with Htt var servletExtract = path.substring(servletIdx +1 ); Console.println("HttpServletPro:servletExtract = "+servletExtract); - var ma = new engine.Mapping(); + + //var ma = new engine.Mapping(); + //var servletRequested = ma.switch(servletExtract); - val res = ma.switch(servletExtract) + "$class"; - Console.println("mapping: servletRequested = "+res); - res + + //val res = ma.switch(servletExtract) + "$class"; + //Console.println("mapping: servletRequested = "+res); + //res + "foo$class"; //servletName = "/".concat(ma.switch(servletRequested)); //servlet = new File (HTTP.SERVER_LOCATION,HTTP.translateFilename("src")); //servlet = new File (servlet,HTTP.translateFilename(repertoireExtract)); @@ -48,15 +46,13 @@ class HttpServletPro(in: HttpInputStream, info: HashMap[String,String]) with Htt //return repertoireExtract ; } - - - + */ override def processRequest(out: HttpOutputStream): Unit ={ out.setHeader("Content-Type", "text/html"); val sc1:ScalaCookiee = new ScalaCookiee("Server", "test"); out.setCookie(sc1); - val x= out.sendHeaders (); + val x = out.sendHeaders (); try{ /* @@ -68,16 +64,21 @@ class HttpServletPro(in: HttpInputStream, info: HashMap[String,String]) with Htt Console.println("Getting class "+servletClassName); val servlet1 = Class.forName( servletClassName ); var servletInstance = servlet1.newInstance().asInstanceOf[ScalaServlet]; - servletInstance.doGet(out,info); + servletInstance.doGet(out, info); } catch{ - case e :ClassNotFoundException => System.out.println("error:attention le nom de la servlet est incorect"); - case e :InstantiationException => System.out.println("InstantiationException"); e.printStackTrace(); - case e : IllegalAccessException => System.out.println("IllegalAccessException"); - case e:Exception => + case e: Exception => + e.printStackTrace(); + ScalaServlet.showError(out, Status.INTERNAL_ERROR, e.toString()); + /* + case e: ClassNotFoundException => System.out.println("error:attention le nom de la servlet est incorect"); + case e: InstantiationException => System.out.println("InstantiationException"); e.printStackTrace(); + case e: IllegalAccessException => System.out.println("IllegalAccessException"); + case e: Exception => System.out.println("une erreur inconue dans al aclasse HttpServletPro"); e.printStackTrace(); + */ } } -- cgit v1.2.3