Tuesday, April 4, 2023

Authenticate users in python scripts using their Google account


Google offers user authentication through OpenID Connect. Although usually, this feature is used by web sites, it can also be used with desktop applications. In this repository you can find a Python3 script that authenticates users based on their Google account. 

What this script does is, it opens a web browser that redirects user to Google's authorization page and at the same time it begins a web server that "listens" for the access code. Upon receiving the access code it "exchanges" for an id token that includes user information.

Since the client secret of a desktop application can be easily protected, this script leverages Proof Key for Code Exchange by OAuth Public Clients, a technology defined in RFC 7636 and supported by Google. With PKCE, the script generates a random code verifier and transmits its SHA-256 hash when requesting the access code. Then, it transmits the actual code verifier when requesting the id token. 

Tuesday, March 28, 2023

A simple role-based access control system for .NET

In many cases, I need a simple solution for adding authentication and authorization in my .NET project, so as to easily develop the rest of the system. I need something simple, e.g., hardcode some user information in the configuration file. ASP.NET Identity is for most of the times an overkill. So I decided to create my own solution. You can find the source code of my solution in this GitHub repository

The most important part is in the appsettings.Development.json file where users, their passwords, and their roles are defined. For example:


  "AuthorizedUsers": {
    "administrator": {
      "Password": "admin!",
      "Roles": [ "Administrator" ]
    },
    "user1": {
      "Password": "user1!",
      "Roles": [ "User" ]
    }
  }

Then, in the Program.cs file the following code must be added:


builder.Services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme)
    .AddCookie(options =>
    {
        options.LoginPath = "/Account/Login";

    });

builder.Services.AddAuthorization(options =>
{
    options.FallbackPolicy = new AuthorizationPolicyBuilder()
        .RequireAuthenticatedUser()
        .Build();
});
...
app.UseAuthentication();
app.UseAuthorization();

User authentication is handled by the Account controller. By default all pages are accessed only by authenticated users. If you want to restrict a page to particular role a decorator can be added to the corresponding controller method, e.g.:


[Authorize(Roles = "Administrator")]
public IActionResult Admin()
{
   return View();
}

I hope you can find this code useful