Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Securing Web Applications and APIs with ASP.NET Core 3

Securing Web Applications and APIs with ASP.NET Core 3

Dominick Baier

September 24, 2019
Tweet

More Decks by Dominick Baier

Other Decks in Programming

Transcript

  1. Securing Web Applications and
    APIs with ASP.NET Core 3.0
    Dominick Baier
    @leastprivilege
    https://github.com/leastprivilege/AspNetCoreSecuritySamples

    View full-size slide

  2. 2
    @leastprivilege / @brocklallen
    Me
    • Independent Consultant
    – Specializing on Application Security Architectures
    – Working with Software Development Teams (ISVs and in-house)
    • Co-Creator of IdentityServer & IdentityModel OSS Project
    – Certified OpenID Connect & OAuth 2.0 Implementation for .NET
    – https://identityserver.io
    • Co-Creator of PolicyServer
    – Modern Authorization Solution
    – https://policyserver.io
    email [email protected]
    blog http://leastprivilege.com
    twitter @leastprivilege
    slides https://speakerdeck.com/leastprivilege

    View full-size slide

  3. 3
    @leastprivilege / @brocklallen
    The dark ages…

    View full-size slide

  4. 4
    @leastprivilege / @brocklallen

    View full-size slide

  5. Modern Application Architecture
    Browser
    Native App
    Server App/Thing
    Web App
    Service Service
    Service
    Identity Provider
    Authorization Policy
    Provider

    View full-size slide

  6. Overview
    Hosting
    Data Protection
    Authentication
    Authorization
    ASP.NET Identity
    IdentityServer

    View full-size slide

  7. 7
    @leastprivilege / @brocklallen
    Hosting
    HTTPS
    HTTPS HTTP/HTTPS
    Using a
    reverse proxy
    Edge
    IIS/Kestrel
    HTTP.sys/Kestrel
    IIS, Nginx
    Apache, F5…

    View full-size slide

  8. 8
    @leastprivilege / @brocklallen
    Kestrel Security
    • HTTPS by default
    – static configuration or dynamic selection (SNI)
    – dotnet dev-certs tool for local development
    • Need to fine-tune transport parameters when doing edge hosting
    – Keep-Alive timeouts
    – Request Header limits
    – Request/Response buffer sizes
    – Request line size
    – Request header limits
    – Request header count limits
    – Request/Response body timeouts & data rates
    – Total client connections
    – Handshake timeouts
    – …

    View full-size slide

  9. 9
    @leastprivilege / @brocklallen
    Host
    ASP.NET Core Architecture
    .NET Core
    ASP.NET Core
    Middleware Middleware
    User Agent Endpoints
    DI

    View full-size slide

  10. 10
    @leastprivilege / @brocklallen
    Data Protection
    • Remember this?


    validationKey="07C1493415E4405F08...6EF8B1F" />

    For giggles: "https://www.google.com/#q=

    View full-size slide

  11. 11
    @leastprivilege / @brocklallen
    Data Protection in ASP.NET Core
    • Keys are stored outside of application directory
    – profile
    – registry
    – Azure web apps magic
    – Redis
    – manual
    • Automatic key management
    – 512 bit master key / AES-256 CBC / HMACSHA256
    – rotated every 90 days
    – automatic application isolation
    • Key protection
    – DPAPI, X509, Azure KeyVault

    View full-size slide

  12. 12
    @leastprivilege / @brocklallen

    View full-size slide

  13. 13
    @leastprivilege / @brocklallen
    Who uses Data Protection?
    • ASP.NET Core
    – protecting cookies
    – anti-forgery
    – protecting OpenID Connect/OAuth state
    – [TempData]
    • You
    – IDataProtectionProvider service
    – can be also used with non-ephemeral data
    • if key ring is properly stored / backed-up

    View full-size slide

  14. 14
    @leastprivilege / @brocklallen
    Authentication in ASP.NET Core
    • Authenticating users/clients
    – local
    – Google, Facebook, and other proprietary providers*
    – OpenID Connect, WS-Federation & SAML** for standards-based external
    authentication
    – JSON web token (JWT) for token-based API authentication
    • Session Management
    – cookies
    * 40+ more https://github.com/aspnet-contrib/AspNet.Security.OAuth.Providers ** https://github.com/Sustainsys/Saml2

    View full-size slide

  15. 15
    @leastprivilege / @brocklallen
    Setting up authentication
    public void ConfigureServices(IServiceCollection services)
    {
    services.AddAuthentication(defaultScheme: "cookies")
    .AddCookies(scheme: "cookies")
    .AddGoogle(scheme: "google")
    .AddOpenIdConnect(scheme: "idsrv");
    }
    public void Configure(IApplicationBuilder app)
    {
    app.UseAuthentication();
    }

    View full-size slide

  16. 16
    @leastprivilege / @brocklallen
    Interacting with the authentication system
    public interface IAuthenticationService
    {
    // authenticate the specified scheme.
    Task AuthenticateAsync(HttpContext context, string scheme);
    // session management
    Task SignInAsync(HttpContext context, string scheme, ClaimsPrincipal principal,
    AuthenticationProperties properties);
    Task SignOutAsync(HttpContext context, string scheme, AuthenticationProperties properties);
    // signal that authentication is required
    Task ChallengeAsync(HttpContext context, string scheme, AuthenticationProperties properties);
    // signal that access is denied
    Task ForbidAsync(HttpContext context, string scheme, AuthenticationProperties properties);
    }

    View full-size slide

  17. 17
    @leastprivilege / @brocklallen
    Session Management (1)
    public void ConfigureServices(IServiceCollection services)
    {
    services.AddAuthentication(defaultScheme: "Cookies")
    .AddCookie("Cookies", options =>
    {
    options.LoginPath = "/account/login";
    options.AccessDeniedPath = "/account/denied";
    options.Cookie.Name = "myapp";
    options.Cookie.Expiration = TimeSpan.FromHours(8);
    options.SlidingExpiration = false;
    options.Cookie.SameSite = SameSiteMode.Lax;
    });
    }

    View full-size slide

  18. 18
    @leastprivilege / @brocklallen
    Session Management (2)
    • Cookie contains
    – claims
    – metadata
    var claims = new List
    {
    new Claim("sub", "123"),
    new Claim("name", "Bob")
    };
    var ci = new ClaimsIdentity(claims, "password", "name", "role");
    var props = new AuthenticationProperties
    {
    Items =
    {
    { "token", "abc" }
    }
    };
    await HttpContext.SignInAsync(new ClaimsPrincipal(ci), props);
    await HttpContext.SignOutAsync();

    View full-size slide

  19. 19
    @leastprivilege / @brocklallen
    Advanced Features
    • The cookie handler has an eventing model
    – additional validation on incoming cookie
    – redirect/sign-in/sign-out interception
    – sign-out cleanup
    • Session storage mechanism can be replaced
    – e.g. server-side (Redis, Cosmos DB..)
    – keeps cookies small
    – allows for server-side revocation
    https://leastprivilege.com/2019/01/14/automatic-oauth-2-0-token-management-in-asp-net-core/

    View full-size slide

  20. 20
    @leastprivilege / @brocklallen
    External Authentication
    • Special type of authentication handler – RemoteAuthenticationHandler
    – ChallengeAsync sends authentication/token request
    – SignOutAsync sends sign-out request
    – provides callback endpoints to process protocol responses
    Challenge(scheme)
    Handler's
    ChallengeAsync
    method gets
    invoked
    Redirect to external
    provider
    External provider
    Authentication
    middleware asks
    handlers who wants
    to process request
    callback Handlers does the
    protocol post-
    processing
    Call sign-in handler
    (sets cookie
    containing external
    identity)
    Redirect to final URL

    View full-size slide

  21. 21
    @leastprivilege / @brocklallen
    Example: Sign-in & Token Request w/ OpenID Connect
    services.AddAuthentication(options =>
    {
    options.DefaultScheme = "cookies";
    options.DefaultChallengeScheme = "oidc";
    })
    .AddCookie("cookies")
    .AddOpenIdConnect("oidc", options =>
    {
    options.Authority = "https://demo.identityserver.io";
    options.ClientId = "server.hybrid";
    options.ClientSecret = "secret";
    options.ResponseType = "code id_token";
    options.Scope.Clear();
    options.Scope.Add("openid");
    options.Scope.Add("api");
    });

    View full-size slide

  22. 22
    @leastprivilege / @brocklallen
    API Authentication
    • Built-in support for JWT bearer tokens
    – see https://github.com/IdentityModel/IdentityModel.AspNetCore.OAuth2Introspection
    for RFC 7662 support
    public void ConfigureServices(IServiceCollection services)
    {
    services.AddAuthentication("jwt")
    .AddJwtBearer("jwt", options =>
    {
    options.Authority = "https://demo.identityserver.com";
    options.Audience = "api"
    });
    }

    View full-size slide

  23. 23
    @leastprivilege / @brocklallen
    Authorization
    • Policy-based authorization
    – based on properties of the caller/user
    • Resource-based authorization
    – takes the resource that is being manipulated into account as well
    • Authorization is a service in DI
    – automatically invoked by authorization middleware for endpoints
    – testable
    – extensible
    https://github.com/blowdart/AspNetAuthorizationWorkshop

    View full-size slide

  24. 24
    @leastprivilege / @brocklallen
    Authorization policies & endpoints
    services.AddAuthorization(options =>
    {
    options.AddPolicy("ManageCustomers", policy =>
    {
    policy.RequireAuthenticatedUser();
    policy.RequireClaim("department", "sales");
    policy.RequireClaim("status", "senior");
    });
    });
    app.UseEndpoints(endpoints =>
    {
    endpoints.MapGet("/", context =>. context.Response.WriteAsync("Hello Manager"))
    .RequireAuthorization("ManageCustomers");
    });

    View full-size slide

  25. 25
    @leastprivilege / @brocklallen
    [Authorize]
    • MVC Integration
    [Authorize]
    public class HomeController : Controller
    {
    [AllowAnonymous]
    public IActionResult Index()
    {
    return View();
    }
    [Authorize("ManageCustomers")]
    public IActionResult Manage()
    {
    return View();
    }
    }

    View full-size slide

  26. 26
    @leastprivilege / @brocklallen
    Programmatically using policies
    public class CustomerController : Controller
    {
    private readonly IAuthorizationService _authz;
    public CustomerController(IAuthorizationService authz)
    {
    _authz = authz;
    }
    public async Task Manage()
    {
    var result = await _authz.AuthorizeAsync(User, "ManageCustomers");
    if (result.Succeeded) return View();
    return Forbid();
    }
    }

    View full-size slide

  27. 27
    @leastprivilege / @brocklallen
    Custom Authorization Handler
    public class JobLevelRequirementHandler : AuthorizationHandler
    {
    private readonly IOrganizationService _service;
    public JobLevelRequirementHandler(IOrganizationService service)
    {
    _service = service;
    }
    protected override void Handle(
    AuthorizationContext context, JobLevelRequirement requirement)
    {
    var currentLevel = _service.GetJobLevel(context.User);
    if (currentLevel == requirement.Level)
    {
    context.Succeed(requirement);
    }
    }
    }

    View full-size slide

  28. 28
    @leastprivilege / @brocklallen
    Authentication & Authorization State Machine
    Browser sends
    request
    Authentication
    middleware checks
    DefaultAuthenticate
    scheme
    Default
    authenticate
    handler calls
    AuthenticateAsync
    Cookie
    found?
    Populate
    HttpContext.User
    Authz
    Policy?
    Execute
    endpoint
    Get current user or
    call handler based
    on specified scheme
    AuthZ middleware
    calls Challenge and
    redirects to
    LoginPath
    Is user
    authenticated?
    Account controller
    authenticates user
    and redirects back
    Is user
    authorized?
    AuthZ middleware
    calls Forbid and
    redirects to
    AccessDeniedPath
    yes
    no
    yes
    no
    no
    yes
    no
    yes
    Resolve
    endpoint

    View full-size slide

  29. 29
    @leastprivilege / @brocklallen
    Resource-based Authorization
    Subject Object
    Operation
    - client ID
    - subject ID
    - scopes
    - more claims
    + DI
    - read
    - write
    - send via email
    - ...
    - ID
    - owner
    - more properties
    + DI

    View full-size slide

  30. 30
    @leastprivilege / @brocklallen
    Example: Document resource
    public class DocumentAuthorizationHandler :
    AuthorizationHandler
    {
    public override Task HandleRequirementAsync(
    AuthorizationHandlerContext context,
    OperationAuthorizationRequirement operation,
    Document resource)
    {
    // authz logic
    }
    }

    View full-size slide

  31. 31
    @leastprivilege / @brocklallen
    Invoking the authorization handler
    public class DocumentController : Controller
    {
    private readonly IAuthorizationService _authz;
    public DocumentController(IAuthorizationService authz)
    {
    _authz = authz;
    }
    public async Task Update(Document doc)
    {
    if ((await _authz.AuthorizeAsync(User, doc, Operations.Update)).Failure)
    {
    return Forbid();
    }
    // do stuff
    }
    }

    View full-size slide

  32. 32
    @leastprivilege / @brocklallen
    ASP.NET Identity
    • Library for managing identity data for users
    – manages credentials (e.g. passwords, complexity)
    – lockout for brute force prevention
    – mapping external authentication
    • Stores this data in database
    – can be used to maintain additional user attributes/claims
    • Provides primitives for email confirmation, password reset, and MFA
    workflows
    • Abstraction on cookie authentication handler
    – sign-in/sign-out

    View full-size slide

  33. 33
    @leastprivilege / @brocklallen
    The missing link
    • ASP.NET Identity templates are geared towards local authentication
    • IdentityServer adds OpenID Connect & OAuth 2.0 server capabilities
    • ASP.NET Core 3.0 ships with an IdentityServer integration library
    – "zero config" IdentityServer using ASP.NET Identity & local APIs
    – Integrated in Angular and React templates
    • Will be expanded to more advanced scenarios in .NET 5
    – separating IdentityServer from APIs
    – dynamic client registration

    View full-size slide

  34. 34
    @leastprivilege / @brocklallen
    References
    • Samples
    – https://github.com/leastprivilege/AspNetCoreSecuritySamples
    • ASP.NET Core Security docs
    – https://docs.microsoft.com/en-us/aspnet/core/security
    • SPA templates docs
    – https://docs.microsoft.com/en-us/aspnet/core/security/authentication/identity-
    api-authorization
    • IdentityServer4 docs
    – https://identityserver4.readthedocs.io

    View full-size slide

  35. 35
    @leastprivilege / @brocklallen
    Thanks!
    …and (because I always forget) - we have stickers!

    View full-size slide