[SalesForce] Rest API Salesforce with Certificate

I have a Rest API Service:

@HttpPost
    global static String actualizarAveriaIngenico(String numorden_stu, String numproceso_mant,
        String estado_averia, String nombre_tecnico, String tipo_intervencion, Date fecha_levantamiento_incidencia) {
        System.debug('**** actualizarAveriaIngenico INI');

        String responseJsonString = '';
        if(numproceso_mant != null && numproceso_mant != ''){
            List<Case> listCases = new List<Case>([Select Id, TXT_Estado_averia__c, TXT_ID_averia__c, TXT_Tipo_de_intervencion__c,
                                                    Status, PL_Motivo__c, PL_Escalado__c, CB_Parada_SLA__c,
                                                    DATE_Fecha_reactivacion_SLA__c, TXT_Nombre_completo_del_tecnico__c
                                                    From Case 
                                                    Where TXT_ID_averia__c =: numproceso_mant]);

            Case caso = listCases.get(0);
            if (caso != null){
                if(estado_averia.equals('Cerrada - OK') || estado_averia.equals('Cerrada - KO')){
                    caso.TXT_Estado_averia__c = estado_averia;
                    caso.Status = 'Cerrado';
                    if (caso.PL_Motivo__c == null){
                        caso.PL_Motivo__c = '';
                        //Falta por indicar un motivo. No es necesario si este ya esta relleno
                    }
                    caso.PL_Escalado__c = 'Nivel 1';
                    //Se deberia enviar un correo al cliente - A quien seria?
                } else if(estado_averia.equals('Cerrada - Incidencia')){
                    caso.TXT_Estado_averia__c = estado_averia;
                    caso.CB_Parada_SLA__c = true;
                    caso.DATE_Fecha_reactivacion_SLA__c = fecha_levantamiento_incidencia;
                    //Se debe evitar la llamada al WS Parada de SLA
                } else {
                    caso.TXT_Estado_averia__c = estado_averia;
                    caso.DATE_Fecha_reactivacion_SLA__c = fecha_levantamiento_incidencia;
                }

                caso.TXT_Nombre_completo_del_tecnico__c = nombre_tecnico;
                caso.TXT_Tipo_de_intervencion__c = tipo_intervencion;

                String codigo = '0';
                String descripcion = '';

                try{
                    update caso;
                }catch(DmlException e){
                    codigo = '-1';
                    descripcion = e.getMessage();
                }

                //Generamos el JSON de respuesta
                responseJsonString = processResponse(codigo, descripcion);
                System.debug('**** responseJsonString - Existe ID averia ' + responseJsonString);
            } else {
                //Generamos el JSON de respuesta
                responseJsonString = processResponse('-1', 'No existe ningun caso asociado a este ID de averia');
                System.debug('**** responseJsonString - No existe ID averia ' + responseJsonString);
            }

            System.debug('**** actualizarAveriaIngenico END');
        } else {
            System.debug('**** responseJsonString - numproceso_mant incorrecto ' + responseJsonString);
            responseJsonString = processResponse('-1', 'No se ha ofrecido un numproceso_mant correcto');
        }

        return responseJsonString;
    }

I also created a Connected App.

My doubt is about the authentication flow that i should use. The client does not want use username and password. They want a Certificate server to server.

I investigate that method of authentication and there are two options.

  • OAuth 2.0 Web Server Authentication Flow
  • OAuth 2.0 JWT Bearer Token Flow

What is the best option in my case?
And other question i have is, how i can check if the client do the request with the correct certificate? Do i need to do this in apex or the connected app do for me when i assign the certificate that i generate previously?

Thank you in advance.

Best Answer

The OAuth flow that uses a certification for authorization is JWT. You'd generate a certificate and populate it on the Connected App, then preauthorize Profiles or Permission Sets for the user account the remote system is going to use to authenticate.

Salesforce will validate that the remote system presents a valid JWT authorization that's signed via the certificate that you selected; your Apex class is not required to confirm that authentication step.

Here's the documentation on the JWT Flow.

The Web Server OAuth flow uses a secret value protected by the server but not a specific certificate for authorization.