Authentication, take 2; take 3 forthcoming...
*cue sad trombone*
This commit is contained in:
parent
c0237e1433
commit
d3a80b9ceb
@ -8,6 +8,7 @@ open Microsoft.Extensions.Configuration
|
||||
open Microsoft.Extensions.DependencyInjection
|
||||
open Microsoft.Extensions.Logging
|
||||
open Microsoft.Extensions.Options
|
||||
open RethinkDB.DistributedCache
|
||||
open System
|
||||
open System.IO
|
||||
|
||||
@ -28,46 +29,45 @@ type Startup(env : IHostingEnvironment) =
|
||||
|
||||
// This method gets called by the runtime. Use this method to add services to the container.
|
||||
member this.ConfigureServices (services : IServiceCollection) =
|
||||
ignore <| services.AddOptions ()
|
||||
ignore <| services.Configure<AppConfig>(this.Configuration.GetSection("MyPrayerJournal"))
|
||||
ignore <| services.AddLocalization (fun options -> options.ResourcesPath <- "Resources")
|
||||
ignore <| services.AddMvc ()
|
||||
ignore <| services.AddDistributedMemoryCache ()
|
||||
services.AddOptions () |> ignore
|
||||
services.Configure<AppConfig> (this.Configuration.GetSection "MyPrayerJournal") |> ignore
|
||||
services.AddLocalization (fun opt -> opt.ResourcesPath <- "Resources") |> ignore
|
||||
services.AddMvc () |> ignore
|
||||
//ignore <| services.AddDistributedMemoryCache ()
|
||||
// RethinkDB connection
|
||||
async {
|
||||
let cfg = services.BuildServiceProvider().GetService<IOptions<AppConfig>>().Value
|
||||
let! conn = DataConfig.Connect cfg.DataConfig
|
||||
do! conn.EstablishEnvironment cfg
|
||||
ignore <| services.AddSingleton conn
|
||||
//ignore <| services.AddDistributedRethinkDBCache (fun options ->
|
||||
// options.Connection <- conn
|
||||
// options.Database <- match cfg.DataConfig.Database with null -> "" | db -> db
|
||||
// options.TableName <- "Session")
|
||||
ignore <| services.AddSession ()
|
||||
services.AddSingleton conn |> ignore
|
||||
services.AddDistributedRethinkDBCache (fun options ->
|
||||
options.Database <- match cfg.DataConfig.Database with null -> "" | db -> db
|
||||
options.TableName <- "Session") |> ignore
|
||||
services.AddSession () |> ignore
|
||||
} |> Async.RunSynchronously
|
||||
|
||||
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
|
||||
member this.Configure (app : IApplicationBuilder, env : IHostingEnvironment, loggerFactory : ILoggerFactory) =
|
||||
ignore <| loggerFactory.AddConsole(this.Configuration.GetSection "Logging")
|
||||
ignore <| loggerFactory.AddDebug ()
|
||||
loggerFactory.AddConsole(this.Configuration.GetSection "Logging") |> ignore
|
||||
loggerFactory.AddDebug () |> ignore
|
||||
|
||||
match env.IsDevelopment () with
|
||||
| true -> ignore <| app.UseDeveloperExceptionPage ()
|
||||
ignore <| app.UseBrowserLink ()
|
||||
| _ -> ignore <| app.UseExceptionHandler("/error")
|
||||
| true -> app.UseDeveloperExceptionPage () |> ignore
|
||||
app.UseBrowserLink () |> ignore
|
||||
| _ -> app.UseExceptionHandler "/error" |> ignore
|
||||
|
||||
ignore <| app.UseStaticFiles ()
|
||||
app.UseStaticFiles () |> ignore
|
||||
|
||||
ignore <| app.UseCookieAuthentication(
|
||||
CookieAuthenticationOptions(
|
||||
AuthenticationScheme = Keys.Authentication,
|
||||
LoginPath = PathString("/user/log-on"),
|
||||
AutomaticAuthenticate = true,
|
||||
AutomaticChallenge = true,
|
||||
ExpireTimeSpan = TimeSpan(2, 0, 0),
|
||||
SlidingExpiration = true))
|
||||
ignore <| app.UseMvc(fun routes ->
|
||||
ignore <| routes.MapRoute(name = "default", template = "{controller=Home}/{action=Index}/{id?}"))
|
||||
app.UseCookieAuthentication(
|
||||
CookieAuthenticationOptions(
|
||||
AuthenticationScheme = Keys.Authentication,
|
||||
LoginPath = PathString "/user/log-on",
|
||||
AutomaticAuthenticate = true,
|
||||
AutomaticChallenge = true,
|
||||
ExpireTimeSpan = TimeSpan (2, 0, 0),
|
||||
SlidingExpiration = true)) |> ignore
|
||||
app.UseMvc(fun routes ->
|
||||
routes.MapRoute(name = "default", template = "{controller=Home}/{action=Index}/{id?}") |> ignore) |> ignore
|
||||
|
||||
/// Default to Development environment
|
||||
let defaults = seq { yield WebHostDefaults.EnvironmentKey, "Development" }
|
||||
@ -81,12 +81,12 @@ let main argv =
|
||||
.AddEnvironmentVariables("ASPNETCORE_")
|
||||
.AddCommandLine(argv)
|
||||
.Build()
|
||||
|
||||
WebHostBuilder()
|
||||
.UseConfiguration(cfg)
|
||||
.UseKestrel()
|
||||
.UseContentRoot(Directory.GetCurrentDirectory())
|
||||
.UseStartup<Startup>()
|
||||
.Build()
|
||||
.Run()
|
||||
use host =
|
||||
WebHostBuilder()
|
||||
.UseConfiguration(cfg)
|
||||
.UseKestrel()
|
||||
.UseContentRoot(Directory.GetCurrentDirectory())
|
||||
.UseStartup<Startup>()
|
||||
.Build()
|
||||
host.Run()
|
||||
0
|
@ -2,20 +2,23 @@ namespace MyPrayerJournal.Controllers
|
||||
|
||||
open Microsoft.AspNetCore.Authorization
|
||||
open Microsoft.AspNetCore.Mvc
|
||||
open Microsoft.Extensions.Logging
|
||||
open MyPrayerJournal
|
||||
open RethinkDb.Driver.Net
|
||||
|
||||
/// Home controller
|
||||
[<Authorize>]
|
||||
[<Route("")>]
|
||||
type HomeController(data : IConnection) =
|
||||
type HomeController(data : IConnection, logger : ILogger<HomeController>) =
|
||||
inherit ApplicationController(data)
|
||||
|
||||
[<AllowAnonymous>]
|
||||
[<HttpGet("")>]
|
||||
member this.Index() =
|
||||
logger.LogDebug(Newtonsoft.Json.JsonConvert.SerializeObject this.HttpContext.User)
|
||||
async {
|
||||
match this.HttpContext.User with
|
||||
| :? AppUser as user -> return this.View "Dashboard" :> IActionResult
|
||||
| _ -> return upcast this.View ()
|
||||
} |> Async.StartAsTask
|
||||
}
|
||||
|> Async.StartAsTask
|
||||
|
@ -25,7 +25,7 @@ type UserController(data : IConnection, cfg : IOptions<AppConfig>) =
|
||||
async {
|
||||
let! user = data.LogOnUser form.Email (User.HashPassword form.Password cfg.Value.PasswordSaltBytes)
|
||||
match user with
|
||||
| Some usr -> do! this.HttpContext.Authentication.SignInAsync(Keys.Authentication, AppUser(user))
|
||||
| Some usr -> do! this.HttpContext.Authentication.SignInAsync (Keys.Authentication, AppUser user)
|
||||
// TODO: welcome message
|
||||
(* this.Session.[Keys.User] <- usr
|
||||
{ UserMessage.Empty with Level = Level.Info
|
||||
@ -37,13 +37,13 @@ type UserController(data : IConnection, cfg : IOptions<AppConfig>) =
|
||||
|> model.AddMessage
|
||||
return this.Redirect "/user/log-on" model *)
|
||||
return upcast this.RedirectToAction "ShowLogOn"
|
||||
//return this.View()
|
||||
} |> Async.StartAsTask
|
||||
}
|
||||
|> Async.StartAsTask
|
||||
|
||||
[<HttpGet("log-off")>]
|
||||
member this.LogOff () =
|
||||
async {
|
||||
do! this.HttpContext.Authentication.SignOutAsync(Keys.Authentication)
|
||||
do! this.HttpContext.Authentication.SignOutAsync Keys.Authentication
|
||||
// TODO: goodbye message
|
||||
return this.LocalRedirect "/"
|
||||
} |> Async.StartAsTask
|
@ -29,7 +29,7 @@ type IConnection with
|
||||
.Filter(ReqlFunction1(fun usr -> upcast usr.["PasswordHash"].Eq(passwordHash)))
|
||||
.RunResultAsync<User list>(this)
|
||||
return user |> List.tryHead
|
||||
}
|
||||
}
|
||||
|
||||
/// Set up the environment for MyPrayerJournal
|
||||
member this.EstablishEnvironment (cfg : AppConfig) =
|
||||
@ -50,7 +50,7 @@ type IConnection with
|
||||
| _ -> logStepStart " Database not found - creating..."
|
||||
do! r.DbCreate("MyPrayerJournal").RunResultAsync(this)
|
||||
logStepEnd ()
|
||||
}
|
||||
}
|
||||
/// Ensure all tables exit
|
||||
let checkTables () =
|
||||
async {
|
||||
@ -63,7 +63,7 @@ type IConnection with
|
||||
logStepStart <| sprintf " %s table not found - creating..." tbl
|
||||
do! db().TableCreate(tbl).RunResultAsync(this)
|
||||
logStepEnd()
|
||||
})
|
||||
})
|
||||
|> List.iter Async.RunSynchronously
|
||||
// Seed the user table if it is empty
|
||||
let! userCount = db().Table(DataTable.User).Count().RunResultAsync<int64>(this)
|
||||
@ -75,7 +75,8 @@ type IConnection with
|
||||
Email = "test@example.com"
|
||||
PasswordHash = User.HashPassword "password" cfg.PasswordSaltBytes
|
||||
Name = "Default User"
|
||||
TimeZone = "America/Chicago" }).RunResultAsync(this)
|
||||
TimeZone = "America/Chicago"
|
||||
}).RunResultAsync(this)
|
||||
logStepEnd ()
|
||||
| _ -> ()
|
||||
}
|
||||
@ -95,11 +96,11 @@ type IConnection with
|
||||
| _ -> logStepStart <| sprintf " %s.Email index not found - creating..." DataTable.User
|
||||
do! db().Table(DataTable.User).IndexCreate("Email").RunResultAsync(this)
|
||||
logStepEnd ()
|
||||
}
|
||||
}
|
||||
async {
|
||||
logStep "Database checks starting"
|
||||
do! checkDatabase ()
|
||||
do! checkTables ()
|
||||
do! checkIndexes ()
|
||||
logStep "Database checks complete"
|
||||
}
|
||||
}
|
||||
|
@ -75,6 +75,6 @@
|
||||
<script src="~/js/site.min.js" asp-append-version="true"></script>
|
||||
</environment>
|
||||
|
||||
@RenderSection("scripts", required: false)
|
||||
@RenderSection("Scripts", required: false)
|
||||
</body>
|
||||
</html>
|
||||
|
@ -28,4 +28,13 @@
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</form>
|
||||
|
||||
@section Scripts
|
||||
{
|
||||
<script type="text/javascript">
|
||||
/* <![CDATA[ */
|
||||
$(document).ready(function () { $("#Email").focus() })
|
||||
/* ]]> */
|
||||
</script>
|
||||
}
|
@ -37,6 +37,7 @@
|
||||
},
|
||||
"Newtonsoft.Json": "9.0.1",
|
||||
"NodaTime": "2.0.0-alpha20160729",
|
||||
"RethinkDB.DistributedCache": "0.9.0-alpha01",
|
||||
"RethinkDb.Driver": "2.3.15"
|
||||
},
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user