Main.hs 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104
  1. {-# LANGUAGE DataKinds #-}
  2. {-# LANGUAGE FlexibleContexts #-}
  3. {-# LANGUAGE OverloadedStrings #-}
  4. {-# LANGUAGE QualifiedDo #-}
  5. {-# LANGUAGE QuasiQuotes #-}
  6. {-# LANGUAGE RecordWildCards #-}
  7. {-# LANGUAGE TemplateHaskell #-}
  8. module Main where
  9. import qualified Bazel.Runfiles as Runfiles
  10. import Control.Exception (handle, throwIO)
  11. import Control.Monad.IO.Class.Linear (MonadIO)
  12. import qualified Control.Functor.Linear as Linear
  13. import Data.Aeson
  14. import qualified Data.ByteString.Char8 as ByteString.Char8
  15. import Data.ByteString.Lazy (toStrict)
  16. import Data.String (fromString)
  17. import qualified Data.Text as Text
  18. import qualified Data.Text.IO as Text
  19. import DbHandler (createDbHandler)
  20. import qualified Foreign.JNI
  21. import Foreign.JNI.Safe (newGlobalRef_, withJVM, withLocalFrame_)
  22. import Language.Java.Inline.Safe
  23. import Language.Java.Safe (UnsafeUnrestrictedReference(..), reflect)
  24. import System.Environment (getArgs)
  25. import System.IO (stderr)
  26. import qualified System.IO.Linear as Linear
  27. import Wizzardo.Http.Handler (JHandler, createHandler)
  28. import qualified Prelude
  29. import Prelude (IO, (<>), map, ($))
  30. import Prelude.Linear (Ur(..))
  31. imports "com.wizzardo.http.*"
  32. imports "com.wizzardo.http.framework.*"
  33. imports "com.wizzardo.http.request.*"
  34. main :: IO ()
  35. main = do
  36. r <- Runfiles.create
  37. let jarPath = Runfiles.rlocation r "io_tweag_inline_java/wizzardo-http-benchmark/jar_deploy.jar"
  38. cpArg = "-Djava.class.path=" <> fromString jarPath
  39. args <- getArgs
  40. let -- We use the classpath provided at build time.
  41. otherJVMArgs =
  42. [ "-Xmx2G"
  43. , "-Xms2G"
  44. -- , "-server"
  45. , "-XX:+UseNUMA"
  46. , "-XX:+UseParallelGC"
  47. , "-XX:+AggressiveOpts"
  48. ]
  49. withJVM (cpArg : otherJVMArgs) $ showJVMExceptions $ withLocalFrame_ $ Linear.do
  50. jsonHandler <- createJsonHandler
  51. jPlainTextHandler <- createPlainTextHandler
  52. jDbHandler <- createDbHandler
  53. jargs <- reflect (map Text.pack args)
  54. [java| {
  55. WebApplication application = new WebApplication($jargs) {
  56. @Override
  57. protected void initHttpPartsCache() {
  58. ByteTree tree = httpStringsCache.getTree();
  59. for (Request.Method method : Request.Method.values()) {
  60. tree.append(method.name());
  61. }
  62. tree.append(HttpConnection.HTTP_1_1);
  63. }
  64. };
  65. application.onSetup(app -> {
  66. app.getUrlMapping()
  67. .append("/json", $jsonHandler)
  68. .append("/plaintext", $jPlainTextHandler)
  69. .append("/db", $jDbHandler);
  70. });
  71. application.start();
  72. } |]
  73. where
  74. showJVMExceptions = handle $ \e ->
  75. Foreign.JNI.showException e Prelude.>>= Text.hPutStrLn stderr Prelude.>> throwIO e
  76. createJsonHandler :: MonadIO m => m JHandler
  77. createJsonHandler = createHandler $ \_req resp -> Linear.withLinearIO $ Linear.do
  78. jmsg <- reflect (toStrict $ encode $ jsonObject resp)
  79. [java| { $resp
  80. .setBody($jmsg)
  81. .appendHeader(Header.KV_CONTENT_TYPE_APPLICATION_JSON);
  82. } |]
  83. Linear.return (Ur ())
  84. where
  85. -- Don't inline, so the serialization is not cached.
  86. {-# NOINLINE jsonObject #-}
  87. jsonObject _ = object ["message" .= Text.pack "Hello, World!"]
  88. createPlainTextHandler :: MonadIO m => m JHandler
  89. createPlainTextHandler = Linear.do
  90. jmsg <- reflect (ByteString.Char8.pack "Hello, World!")
  91. UnsafeUnrestrictedReference jGlobalMsg <- newGlobalRef_ jmsg
  92. createHandler $ \_req resp -> Linear.withLinearIO $ Linear.do
  93. let ujmsg = UnsafeUnrestrictedReference jGlobalMsg
  94. [java| { $resp
  95. .setBody($ujmsg)
  96. .appendHeader(Header.KV_CONTENT_TYPE_TEXT_PLAIN);
  97. } |]
  98. Linear.return (Ur ())