繁体   English   中英

使用Openiddict的ASP.NET Core 1.0 OAuth服务器

[英]ASP.NET Core 1.0 OAuth Server using Openiddict

我想使用Openiddict OAuth来保护我的ASP.NET Core 1.0 Web应用程序中的api端点。 api端点将由电话应用程序调用,用户必须使用用户名和密码登录。

流程如下:

  • 用户可以通过Web应用程序注册和登录: https://www.domain.comhttps://www.domain.com
  • 用户安装手机应用程序,他们可以使用手机应用程序登录和注册。 登录,注册和数据访问是通过api端点完成的:示例: https://www.domain.com/api/service/getsomedatahttps://www.domain.com/api/service/getsomedata

如何配置Openiddict OAuth,以便使用OAuth保护API端点?

如何配置Openiddict OAuth,以便使用OAuth保护API端点?

您的方案听起来像是简单的“资源所有者密码凭据”授权的良好候选 ,它基本上是OAuth2等效的基本或表单身份验证。

这是我建议的:

创建一个新的AccountController / RegistrationController API控制器,负责创建新帐户:

由于此阶段不存在用户帐户,因此您无法在此处使用令牌身份验证(就像默认的AccountController.Register模板在注册用户之前不需要cookie身份验证一样)。

配置OpenIddict以启用令牌端点并允许资源所有者密码凭据授予:

services.AddOpenIddict<ApplicationDbContext>()
    // Disable the HTTPS requirement during development.
    .DisableHttpsRequirement()

    // Enable the token endpoint, required to use
    // the resource owner password credentials grant.
    .EnableTokenEndpoint("/connect/token")

    // Enable the password and the refresh token flows.
    .AllowPasswordFlow()
    .AllowRefreshTokenFlow();

使用OAuth2验证中间件来保护您的API:

要启用令牌身份验证,请参阅AspNet.Security.OAuth.Validation 1.0.0-alpha2-final包并在app.UseOAuthValidation()之前添加app.UseMvc() 要使身份验证成为必需,只需使用[Authorize]属性,就像使用Cookie身份验证一样。

不要犹豫,玩这个样本 它不会将移动应用程序用于客户端部分,但您应该很容易理解它是如何工作的。

有关更多信息,您还可以阅读此博客文章,由Mike Rousos撰写,用于Microsoft .NET Web开发和工具博客: ASP.NET核心中的承载令牌身份验证

好的,谢谢@Pinpoint指出我正确的方向。

但是这是我的Startup.cs配置:

   public class Startup
{
    public Startup(IHostingEnvironment env)
    {
        var builder = new ConfigurationBuilder()
            .SetBasePath(env.ContentRootPath)
            .AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
            .AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true);

        if (env.IsDevelopment())
        {
            // For more details on using the user secret store see http://go.microsoft.com/fwlink/?LinkID=532709
            builder.AddUserSecrets();
        }

        builder.AddEnvironmentVariables();
        Configuration = builder.Build();
    }

    public IConfigurationRoot Configuration { get; }

    // This method gets called by the runtime. Use this method to add services to the container.
    public void ConfigureServices(IServiceCollection services)
    {
        // Add framework services.
        services.AddDbContext<ApplicationDbContext>(options =>
            options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));

        services.AddIdentity<ApplicationUser, ApplicationRole>()
            .AddEntityFrameworkStores<ApplicationDbContext>()
            .AddDefaultTokenProviders();

        services.AddOpenIddict<ApplicationUser, ApplicationRole, ApplicationDbContext>()
          .DisableHttpsRequirement()
          .EnableTokenEndpoint("/connect/token")
          .AllowPasswordFlow()
          .AllowRefreshTokenFlow()
          .UseJsonWebTokens();

        services.AddMvc();

        // Add application services.
        services.AddTransient<IEmailSender, AuthMessageSender>();
        services.AddTransient<ISmsSender, AuthMessageSender>();
    }

    // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
    public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
    {


        loggerFactory.AddConsole(Configuration.GetSection("Logging"));
        loggerFactory.AddDebug();

        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
            app.UseDatabaseErrorPage();
            app.UseBrowserLink();
        }
        else
        {
            app.UseExceptionHandler("/Home/Error");
        }

        app.UseStaticFiles();      

        app.UseIdentity();

        app.UseOpenIddict();

        app.UseJwtBearerAuthentication(new JwtBearerOptions
        {
            AutomaticAuthenticate = true,
            AutomaticChallenge = true,
            RequireHttpsMetadata = false,
            Audience = "http://localhost:24624/",
            Authority = "http://localhost:24624/"
        });


        // Add external authentication middleware below. To configure them please see http://go.microsoft.com/fwlink/?LinkID=532715

        app.UseMvc(routes =>
        {
            routes.MapRoute(
                name: "default",
                template: "{controller=Home}/{action=Index}/{id?}");
        });
    }
}

ApplicationDbContext.cs:

  public class ApplicationDbContext : OpenIddictDbContext<ApplicationUser, ApplicationRole>
{
    public ApplicationDbContext(DbContextOptions options)
        : base(options)
    {
        Database.EnsureCreated();
    }

    protected override void OnModelCreating(ModelBuilder builder)
    {
        base.OnModelCreating(builder);
        // Customize the ASP.NET Identity model and override the defaults if needed.
        // For example, you can rename the ASP.NET Identity table names and more.
        // Add your customizations after calling base.OnModelCreating(builder);
    }
}

ApplicationRole.cs:

public class ApplicationRole : IdentityRole
{
}

ApplicationUser.cs:

  public class ApplicationUser : OpenIddictUser
{
}

ServiceController.cs:

 [Authorize(ActiveAuthenticationSchemes = OAuthValidationDefaults.AuthenticationScheme)]
[Route("api/service")]
public class ServiceController : Controller
{
    private readonly UserManager<ApplicationUser> _userManager;

    public ServiceController(UserManager<ApplicationUser> userManager)
    {
        _userManager = userManager;
    }

    [HttpGet]
    [Route("getdata")] 
    public async Task<IActionResult> GetData()
    {
        var user = await _userManager.GetUserAsync(User);
        if (user == null) return Ok("No user / not logged in");// if Authorize is not applied
        return Ok(user);
    }
}

这里的关键是ServiceController.cs: [Authorize(ActiveAuthenticationSchemes = OAuthValidationDefaults.AuthenticationScheme)]

@Pinpoint:我没有使用app.UseOAuthValidation(),因为它返回302并重定向到Account / Login。

所以现在它的工作原理如下:

  • 访问http://domain.com ,用户可以注册,登录,查看数据等。
  • 用户可以下载移动应用程序,注册,登录和获取数据

在api端实现用户注册登录非常简单直接。

问题是使用fiddler并向http://domain.com/api/service/getdata发出GET,返回302并重定向到Account / Login。 如果我删除了app.UseIdentity(),那么如果将返回401 Unauthorized但是用户将无法再使用用户界面http://domain.com登录。 [Authorize(ActiveAuthenticationSchemes = OAuthValidationDefaults.AuthenticationScheme)]到我的ServiceController解决了这个问题。

@Pinpoint app.UseOAuthValidation()的好处是什么?

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM