grrkek

Untitled

Jan 17th, 2026
2,337
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Ruby 3.70 KB | None | 0 0
  1. -- An example HTTP server written in Konjac
  2. module Rum.Request
  3.   struct [
  4.     method: String;
  5.     path: String;
  6.     headers: Map(String, String);
  7.   ]
  8. end
  9.  
  10. module Rum.Response
  11.   struct [
  12.     statusCode: Int64 = 200;
  13.     headers: Map(String, String) = {};
  14.     body: Binary = Binary { };
  15.   ]
  16.  
  17.   export function encode(response : Rum.Response) : Binary
  18.    
  19.     reasonPhrase : String = case response.statusCode
  20.       when 200, do: "OK"
  21.       when 201, do: "Created"
  22.       when 301, do: "Moved Permanently"
  23.       when 400, do: "Bad Request"
  24.       when 404, do: "Not Found"
  25.       when 500, do: "Internal Server Error"
  26.       else do: "Unknown"
  27.     end
  28.    
  29.     statusLine : String = "HTTP/1.1 " + Int64.toString(response.statusCode) + " " + reasonPhrase + "\r\n"
  30.  
  31.     updatedHeaders : Map(String, String) = if Map.hasKey(response.headers, "Content-Length")
  32.       response.headers
  33.     else
  34.       Map.put(response.headers, "Content-Length", String.fromInt(Binary.length(response.body)))
  35.     end
  36.    
  37.     headersString : String = updatedHeaders
  38.       |> Map.toList()  
  39.       |> Array.map(function(pair : {String, String}) do
  40.         pair.key + ": " + pair.value + "\r\n"
  41.       end)
  42.       |> String.join()
  43.       |> String.concatenate("\r\n\r\n")
  44.      
  45.     statusLine
  46.     |> String.concatenate(headersString)
  47.     |> Binary.fromString()
  48.     |> Binary.concatenate(response.body)
  49.   end
  50. end
  51.  
  52. module Rum.Context
  53.   struct [
  54.     request: Rum.Request;
  55.     response: Rum.Response;
  56.   ]
  57. end
  58.  
  59. behaviour Rum.Handler
  60.   abstract function call(handler : Rum.Handler, context : Rum.Context) : Rum.Context
  61. end
  62.  
  63. module Rum.Server
  64.   struct [
  65.     host: String;
  66.     port: UInt16;
  67.     handlers: Array(Rum.Handler);
  68.   ]
  69.  
  70.   function handleClient(server : Rum.Server, client : TCP.Client) : Nil
  71.     data : Binary = TCP.receive(client)
  72.  
  73.     [headerSection, messageBody] =
  74.       data
  75.       |> Binary.toString()
  76.       |> String.split("\r\n\r\n")
  77.  
  78.     [startLine, ...unprocessedHeaders]
  79.       headerSection
  80.       |> String.split("\r\n")
  81.  
  82.     headers =
  83.       unprocessedHeaders
  84.       |> Array.map(function(header : String) do
  85.         [key, value] = String.split(header)
  86.        
  87.         {key: value}
  88.       end)
  89.       |> Map.zip()
  90.      
  91.     [method, path, "HTTP/1.1"] = startLine |> String.split(" ") |> String.stripSuffix()
  92.  
  93.     context =
  94.       Rum.Context {
  95.         request: Rum.Request {
  96.           method: method,
  97.           path: path,
  98.           headers: headers
  99.         },
  100.         response: Rum.Response { }
  101.       }
  102.  
  103.     updatedContext =
  104.       server.handlers
  105.       |> Array.reduce(function(handler : Rum.Handler, accumulator : Rum.Context) do
  106.         Rum.handler.call(handler, accumulator)
  107.       end)
  108.      
  109.     encodedResponse = Rum.Response.encode(updatedContext.response)
  110.  
  111.     TCP.send(client, encodedResponse)
  112.   end
  113.  
  114.   export function bind(server : Rum.Server) : Rum.Response
  115.     loop do
  116.       client : TCP.Client? = TCP.accept(server.host, server.port)
  117.      
  118.       if client do
  119.         Process.spawn do
  120.           handleClient(server, client)
  121.         end
  122.       else
  123.         Process.killSelf()
  124.       end
  125.     end
  126.   end
  127. end
  128.  
  129. module Rum.Application
  130.   export function main(arguments : Array(String)) : Nil
  131.     server = Rum.Server { host: "127.0.0.1", port: 8080 }
  132.  
  133.     supervisor =
  134.       Supervisor {
  135.         strategy: "OneForOne",
  136.         maximumRestarts: 5,
  137.         restartWindow: 10
  138.       }
  139.  
  140.     process = Process.spawn do
  141.       Rum.Server.bind(server)
  142.     end
  143.  
  144.     child = Child {
  145.       id: "worker",
  146.       process: process,
  147.       restart: "Transiet",
  148.       maxRestarts: 3,
  149.       restartWindow: 5
  150.     }
  151.    
  152.     Supervisor.addChild(supervisor, child)
  153.   end
  154. end
Advertisement