Skip to content

Commit

Permalink
🐦[FSharp] Falco - Update benchmark for Falco to v2.0.0 (TechEmpower#5867
Browse files Browse the repository at this point in the history
)

* falco v1.2.3

* Server header, removed meta tag from head

* inline json message to meet spec

* [FSharp] - Falco upgraded to v2.0.0

* static mapper for datareader

* json closure for recomputation

* fortune feature reorg

Co-authored-by: pimbrouwers <pimnation@gmail.com>
  • Loading branch information
pimbrouwers and pimbrouwers authored Jul 14, 2020
1 parent 495f7c2 commit c1573cb
Show file tree
Hide file tree
Showing 6 changed files with 98 additions and 117 deletions.
2 changes: 1 addition & 1 deletion frameworks/FSharp/falco/src/App/App.fsproj
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
<ItemGroup>
<PackageReference Update="FSharp.Core" Version="4.7.*" />
<PackageReference Include="Donald" Version="3.0.*" />
<PackageReference Include="Falco" Version="1.2.*" />
<PackageReference Include="Falco" Version="2.0.*" />
<PackageReference Include="Npgsql" Version="4.1.3.1" />
</ItemGroup>

Expand Down
128 changes: 57 additions & 71 deletions frameworks/FSharp/falco/src/App/Fortune.fs
Original file line number Diff line number Diff line change
@@ -1,100 +1,86 @@
module App.Fortune

module Model =
open System.Threading.Tasks
open FSharp.Control.Tasks

type FortuneModel =
{
id : int
message : string
}

module FortuneModel =
open System.Data
open Donald

let extra =
open System.Data
open Donald
open Falco
open FSharp.Control.Tasks

type FortuneModel =
{
id : int
message : string
}

static member fromDataReader (rd : IDataReader) =
{
id = rd.GetInt32("id")
message = rd.GetString("message")
}

module Service =
open System.Threading.Tasks

module ListQuery =
type LoadFortunes = unit -> Task<FortuneModel list>

let extraFortune =
{
id = 0
message = "Additional fortune added at request time."
}

let fromDataReader (rd : IDataReader) =
{
id = rd.GetInt32("id")
message = rd.GetString("message")
}

module Index =
type Query =
unit -> Task<FortuneModel list>

type LoadFortunes =
unit -> Task<FortuneModel list>

let query
(loadFortunes : LoadFortunes) : Query =
let handle
(loadFortunes : LoadFortunes) =
fun () ->
task {
let! fortunes = loadFortunes ()
let fortunesWithExtra = FortuneModel.extra :: fortunes
let fortunesSorted =
fortunesWithExtra

return
extraFortune
:: fortunes
|> List.sortBy (fun f -> f.message)

return fortunesSorted
}

module Db =
open System.Data
open Donald
open Model

let selectAsync (connection : IDbConnection) =
module Db =
open System.Threading.Tasks

let selectAsync (connection : IDbConnection) : Task<FortuneModel list> =
queryAsync
"SELECT id, message FROM fortune"
[]
FortuneModel.fromDataReader
connection

module View =
open Falco.ViewEngine
open Model

open Falco.Markup

let index (fortunes : FortuneModel list) =
UI.layout "Fortunes" [
table [] [
yield tr [] [
th [] [ raw "id" ]
th [] [ raw "message" ]
Elem.table [] [
yield Elem.tr [] [
Elem.th [] [ Text.raw "id" ]
Elem.th [] [ Text.raw "message" ]
]
for fortune in fortunes ->
tr [] [
td [] [ raw (string fortune.id) ]
td [] [ enc fortune.message]
Elem.tr [] [
Elem.td [] [ Text.raw (string fortune.id) ]
Elem.td [] [ Text.enc fortune.message]
]
]
]

module Controller =
open Donald
open Falco
open FSharp.Control.Tasks
open Model

let handleIndex : HttpHandler =
fun next ctx ->
task {
let connFactory = ctx.GetService<DbConnectionFactory>()
use conn = createConn connFactory
let selectFortunes = fun () -> Db.selectAsync conn
let! fortunes = () |> Index.query selectFortunes

let handlerResult =
fortunes
|> View.index
|> htmlOut

return! handlerResult next ctx
}
let handleIndex : HttpHandler =
fun ctx ->
task {
let connFactory = ctx.GetService<DbConnectionFactory>()
use conn = createConn connFactory
let selectFortunes = fun () -> Db.selectAsync conn
let! fortunes = () |> Service.ListQuery.handle selectFortunes

return!
ctx
|> (fortunes
|> View.index
|> Response.ofHtml)
}
10 changes: 9 additions & 1 deletion frameworks/FSharp/falco/src/App/Program.fs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
module App.Program

open System.Data
open Falco
open Npgsql

[<Literal>]
Expand All @@ -11,5 +12,12 @@ let connectionFactory =

[<EntryPoint>]
let main args =
Server.startServer args connectionFactory
Host.startWebHost
args
(Server.buildServer connectionFactory)
[
get "/plaintext" Value.handlePlainText
get "/json" Value.handleJson
get "/fortunes" Fortune.handleIndex
]
0
48 changes: 18 additions & 30 deletions frameworks/FSharp/falco/src/App/Server.fs
Original file line number Diff line number Diff line change
@@ -1,22 +1,14 @@
module App.Server

open System.Threading.Tasks
open Donald
open Falco
open Microsoft.AspNetCore.Builder
open Microsoft.AspNetCore.Hosting
open Microsoft.AspNetCore.Server.Kestrel.Core
open Microsoft.Extensions.DependencyInjection
open Microsoft.Extensions.Logging
open Microsoft.Extensions.Hosting

let routes =
[
get "/plaintext" Value.Controller.handlePlainText
get "/json" Value.Controller.handleJson
get "/fortunes" Fortune.Controller.handleIndex
]

module Config =
let buildServer (connectionFactory : DbConnectionFactory) : Host.ConfigureWebHost =
let configureLogging (log : ILoggingBuilder) =
log.ClearProviders()
|> ignore
Expand All @@ -30,26 +22,22 @@ module Config =

let configure
(routes : HttpEndpoint list)
(app : IApplicationBuilder) =
(app : IApplicationBuilder) =
let handleNotFound : HttpHandler =
fun ctx ->
Response.withStatusCode 404 ctx |> ignore
Task.CompletedTask

app.UseRouting()
.UseHttpEndPoints(routes)
.UseNotFoundHandler(setStatusCode 404)
.UseHttpEndPoints(routes)
.UseNotFoundHandler(handleNotFound)
|> ignore

let builderServer
(connectionFactory : DbConnectionFactory)
(webHost : IWebHostBuilder) =
webHost
.UseKestrel()
.ConfigureLogging(Config.configureLogging)
.ConfigureServices(Config.configureServices connectionFactory)
.Configure(Config.configure routes)
|> ignore

let startServer
(args : string[])
(connectionFactory : DbConnectionFactory) =
Host.CreateDefaultBuilder(args)
.ConfigureWebHost(fun webHost -> builderServer connectionFactory webHost)
.Build()
.Run()
fun (routes : HttpEndpoint list)
(webHost : IWebHostBuilder) ->
webHost
.UseKestrel()
.ConfigureLogging(configureLogging)
.ConfigureServices(configureServices connectionFactory)
.Configure(configure routes)
|> ignore
10 changes: 5 additions & 5 deletions frameworks/FSharp/falco/src/App/UI.fs
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
module App.UI

open Falco.ViewEngine
open Falco.Markup

let layout pageTitle content =
html [] [
head [] [
title [] [ raw pageTitle ]
Elem.html [] [
Elem.head [] [
Elem.title [] [ Text.raw pageTitle ]
]
body [] content
Elem.body [] content
]
17 changes: 8 additions & 9 deletions frameworks/FSharp/falco/src/App/Value.fs
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,13 @@
open Falco

type JsonOutputModel = { message : string }

module Controller =
let defaultMsg = "Hello, World!"

let handleJson : HttpHandler =
fun next ctx ->
let json = { message = defaultMsg }
(jsonOut json) next ctx
let defaultMsg = "Hello, World!"

let handleJson : HttpHandler =
fun ctx ->
let output = { message = defaultMsg }
Response.ofJson output ctx

let handlePlainText : HttpHandler =
textOut defaultMsg
let handlePlainText : HttpHandler =
Response.ofPlainText defaultMsg

0 comments on commit c1573cb

Please sign in to comment.