Skip to main content

I am trying to integrate DocuSign using ABAP, I am able to generate access token,

with the generated access I am trying to access below API:  'https://demo.docusign.net/restapi/v2.1/accounts/' lv_account_id '/envelopes'

the above API is called immediately after the generated access token, I am not sure why I am getting error message,

I have to complete the POC ASAP since we are planning for go-live by month end if everything goes good.

Kindly help.
 

Hello @imahmad4all, 

Thank you for reaching out here in the DocuSign Community.

I apologies for the inconvenience, I share how to solve this error.

 

Error message: The access token provided is expired, revoked or malformed.

Description

The access token in the request header is not valid for one of the following reasons:

  • It expired. Access token expiration periods for the supported authentication methods are:
    • Authorization Code Grant: eight hours
    • JWT Grant: one hour
    • Implicit Grant: eight hours
    When you make a request to obtain an access token, the expires_in field in the response contains the expiration period.
  • A user or admin has revoked consent for the app to make calls on behalf of a user. See Obtain and revoke consent for more information.
  • The access token does not have the correct format.

Recommendations

Regards,

 

Eric | Docusign


Hi Eric,

Thanks for your response, 

For envelope creation, what is the recommend approach..

I am using SAP ABAP for calling REST API for generating token and envelope creation:

 

Logic for generating token:

 DATA: lo_http_client   TYPE REF TO if_http_client,
          lv_response      TYPE string,
          lv_status_code   TYPE i,
          lv_reason_phrase TYPE string.

    CONSTANTS: lv_token_url     TYPE string VALUE 'https://account-d.docusign.com/oauth/token',
               lv_client_id     TYPE string VALUE '093fabd3-……….',
               lv_client_secret TYPE string VALUE '666ccb49-…...',
               lv_auth_code     TYPE string VALUE 'Basic MDkzZ…...YTJkNg==',
               lv_grant_type    TYPE string VALUE 'client_credentials', 
               lv_scope         TYPE string VALUE 'signature impersonation'.!--startfragment>


    DATA lv_object_id TYPE string.

    " Deserialize the JSON response to get the token
    TYPES:
      BEGIN OF t_entry,
        access_token TYPE string,
        token_type   TYPE string,
        expires_in   TYPE n LENGTH 8,
        scope        TYPE string,
        jti          TYPE string,
      END OF t_entry.

    TYPES:
      t_entry_map TYPE SORTED TABLE OF t_entry WITH UNIQUE KEY access_token.

    DATA: m_entries   TYPE t_entry,
          lr_instance TYPE REF TO /ui5/cl_json_parser.

    " Creating HTTP client by URL for token request
    CALL METHOD cl_http_client=>create_by_url
      EXPORTING
        url                = lv_token_url
      IMPORTING
        client             = lo_http_client
      EXCEPTIONS
        argument_not_found = 1
        plugin_not_active  = 2
        internal_error     = 3
        OTHERS             = 4.

    IF sy-subrc <> 0.
      " Error handling
      RETURN.
    ENDIF.

    " Set request method and headers
    lo_http_client->request->set_method( if_http_request=>co_request_method_post ).  " Use POST method for token request
    lo_http_client->request->set_header_field( name = 'Authorization' value = lv_auth_code ).
    lo_http_client->request->set_header_field( name = 'Content-Type' value = 'application/x-www-form-urlencoded' ).

    " Create request body (URL-encoded)
    DATA(lv_request_body) = |grant_type={ lv_grant_type }&scope={ lv_scope }&client_id={ lv_client_id }&client_secret={ lv_client_secret }|.

    lo_http_client->request->set_cdata( lv_request_body ).

    " Sending the request
    CALL METHOD lo_http_client->send
      EXCEPTIONS
        http_communication_failure = 1
        http_invalid_state         = 2
        http_processing_failed     = 3
        http_invalid_timeout       = 4
        OTHERS                     = 5.

    IF sy-subrc = 0.
      " Receiving the response
      CALL METHOD lo_http_client->receive
        EXCEPTIONS
          http_communication_failure = 1
          http_invalid_state         = 2
          http_processing_failed     = 3
          OTHERS                     = 5.
    ELSE.
      " Error handling
      RETURN.
    ENDIF.

    IF sy-subrc <> 0.
      " Error handling
      RETURN.
    ENDIF.

    " Fetch status code
    " Fetch the HTTP status code and reason phrase
    CALL METHOD lo_http_client->response->get_status
      IMPORTING
        code   = lv_status_code
        reason = lv_reason_phrase.

    " Fetch and log the full response content
    lv_response = lo_http_client->response->get_cdata( ).

    " Check if the status code indicates a successful request (200 range)
    IF lv_status_code >= 200 AND lv_status_code < 300.

      CREATE OBJECT lr_instance.

      /ui2/cl_json=>deserialize(
        EXPORTING
          json         = lv_response
          pretty_name  = /ui2/cl_json=>pretty_mode-camel_case
        CHANGING
          data         = m_entries
      ).

      ev_token = m_entries-access_token.
    ENDIF.

 

Logic for calling create envelope API using the above generated access token:

 DATA: lo_http_client     TYPE REF TO if_http_client,
          lv_boundary        TYPE string,
          lv_auth_header     TYPE string,
          lv_json_payload    TYPE string,
          lv_document        TYPE xstring,
          lv_pdf_encoded     TYPE string,
          lv_envelope_url    TYPE string,
          lv_response        TYPE string,
          lv_status_code     TYPE i,
          lv_reason_phrase   TYPE string,

          lv_recipient_email TYPE string VALUE '123@gmail.com',
          lv_recipient_name  TYPE string VALUE '123'.

    DATA: lv_data         TYPE STANDARD TABLE OF string WITH EMPTY KEY.

    CONSTANTS lv_account_id TYPE string VALUE 'becac86b-...'.

    CONCATENATE 'Bearer' iv_token INTO lv_auth_header SEPARATED BY space.
    CONCATENATE 'https://demo.docusign.net/restapi/v2.1/accounts/' lv_account_id '/envelopes' INTO lv_envelope_url.

    " Define boundary for multipart request
    lv_boundary = 'multipart-boundary'.

    " Define document details
    DATA(lv_document_details) = '{ "documentBase64": "<Base64_Encoded_PDF>", "name": "Example Document", "fileExtension": "pdf", "documentId": "1" }'.

    " Construct JSON payload with placeholders
    CONCATENATE '{"emailSubject": "Please sign this document", "documents":  '
                lv_document_details
                '], "recipients": {"signers":  '
                lv_recipient
                ']}, "status": "sent"}'
                INTO lv_json_payload.

    " Read PDF document as xstring (assume it's stored locally for this example)
    " You need to have the document read into lv_document as xstring
    SELECT SINGLE content
                  FROM ztable
                  INTO @DATA(lv_content)
                  WHERE guid = '0214840D5F501EEF'.

    IF sy-subrc <> 0.
      RETURN.
    ENDIF.

    lv_document = lv_content. "'<Your_PDF_Content_in_XSTRING>'.

    " Encode PDF document in Base64
    CALL FUNCTION 'SCMS_BASE64_ENCODE_STR'
      EXPORTING
        input  = lv_document
      IMPORTING
        output = lv_pdf_encoded.

    " Replace the placeholder with the actual Base64 encoded PDF content
    REPLACE '<Base64_Encoded_PDF>' WITH lv_pdf_encoded INTO lv_json_payload.

    " Create HTTP client by URL
    CALL METHOD cl_http_client=>create_by_url
      EXPORTING
        url                = lv_envelope_url
      IMPORTING
        client             = lo_http_client
      EXCEPTIONS
        argument_not_found = 1
        plugin_not_active  = 2
        internal_error     = 3
        OTHERS             = 4.

    IF sy-subrc <> 0.
      " Error handling
      RETURN.
    ENDIF.

    " Set request method and headers
    lo_http_client->request->set_method( if_http_request=>co_request_method_post ).
    lo_http_client->request->set_header_field( name = 'Authorization' value = lv_auth_header ).
    lo_http_client->request->set_header_field( name = 'Content-Type' value = 'application/json' ).
    lo_http_client->request->set_header_field( name = 'Accept' value = 'application/json' ).

    " Set the payload (JSON data)
    lo_http_client->request->set_cdata( lv_json_payload ).

    " Send the request
    CALL METHOD lo_http_client->send
      EXCEPTIONS
        http_communication_failure = 1
        http_invalid_state         = 2
        http_processing_failed     = 3
        http_invalid_timeout       = 4
        OTHERS                     = 5.

    IF sy-subrc = 0.
      " Receive the response
      CALL METHOD lo_http_client->receive
        EXCEPTIONS
          http_communication_failure = 1
          http_invalid_state         = 2
          http_processing_failed     = 3
          OTHERS                     = 5.
    ELSE.
      " Error handling
      RETURN.
    ENDIF.

    IF sy-subrc <> 0.
      " Error handling
      RETURN.
    ENDIF.

    " Fetch the HTTP status code and reason phrase
    lo_http_client->response->get_status(
      IMPORTING
        code    = lv_status_code
        reason  = lv_reason_phrase ).

    " Fetch the response content
    ev_response = lo_http_client->response->get_cdata( ).!--startfragment>

 

in the ev_response I am getting the said error.
 

 

 

I am not sure at which step I am doing wrong that I am getting auth error, please help me fix this error, I have shared the complete code.

Thank you.


Reply