javaspring-bootspring-securitybasic-authenticationdigest-authentication

Spring Security Basic Auth with digest over http for stateless APIs


Some clients/customers would use web app for offline large scale purposes with user management system. In this regards, they provide a real pain deploying the app with HTTPS support. Let a lone the UN-trust warning by browsers for self signed certificates which makes customers complain.

I've been trying to use Spring Security with Spring Boot to secure stateless APIs using Basic Authentication but I'd like to control the base64 header encryption/decryption avoiding sending the credentials in very easy to decrypt base64 string.

@Override
    protected void configure(HttpSecurity http) throws Exception {
      http.csrf()
          .disable()
          .cors()
          .and()
          .authorizeRequests()
          .antMatchers("/login")
          .permitAll()
          .and()
          .httpBasic();
    }

This method configuration extending WebSecurityConfigurerAdapter. I've tried to take a look at the source code of BasicAuthenticationFilter and found out it uses BasicAuthenticationConverter creating new object so I can't provide custom converter as bean to control the base64 decryption with more strong alternative (or an extra one).

Also this breaks Basic Auth standard anyway. Digest Auth stores password as text and this is not an option for me .

So,


Solution

  • Is there anyway to use Basic Auth with HTTP controlling the base64 decryption trying to reach a bit to what HTTPS offers ?

    Yes. Taking Basic Authentication as example to extend here. You'll need to create filter on your requests to do whatever you want with the base64 encoding in your header. You can encrypt your Authorizaion header which contains username:password value before encoding to base64.

    username:password >> encryption >> encode to base64

    Then in that filter, you do the decryption and recreate the base64 pure form

    request header Authorization encrypted >> decode from base64 >> decryption >> encode username:password to base64 >> continue filter chaine to BasicAuthenticationFilter

    You can add the filter before BasicAuthenticationFilter like

    http.addFilterBefore(tokenFilter(), BasicAuthenticationFilter.class);
    

    Note that this is customized workaround to extend basic authentication but it's not standard way of handling basic auth.

    Or using Digest Auth with encrypted stored passwords ?

    Digest Auth not that secured over HTTP but for better idea about how it works, you may take a look to this answer

    Concept of Digest authentication - does it really work?

    You will get more secure option using your first option than the second. But your best solution is to use HTTPs. Security is major concern and subject and you should spend some time trying to figure out what's best for your case.