Methods for Getting Sent Fax Dispositions
There are three primary methods for obtaining sent fax dispositions in the eFax® Enterprise API. Users can:
- Pull sent notifications for completed transmissions using the GET /faxes/{fax_id}/metadata endpoint in the API.
- Pull real-time sent notifications for transmissions using the GET /faxes/{fax_id}/transmission-detail endpoint in the API.
- Pull sent notifications using the GET /faxes/sent endpoint in the API.
- Use the Webhook Notification Function to obtain fax disposition notices through an auto-posted URL notification.
Each of these methods uses the OAuth protocol for secure authentication and authorization. Refer to the Obtaining Authentication Credentials section of the Getting Started Guide.
The following sections describe each of these options.
Use the GET /faxes/{fax_id}/metadata Endpoint in the API
This method allows you to check for the fax status details on a SINGLE fax attempt using the fax_id received in response to a POST/faxes call. This endpoint is dedicated to final transmission state summary information only.
Use the GET /faxes/{fax_id}/transmission-detail Endpoint in the API
For an individual fax_id, this call displays detailed real-time status information related to all outbound delivery attempts, as well as a summary of the current status of this sent fax. Essentially, this method expands the available outbound fax transmission statuses to include:
- NEW – used for faxes that do not yet have an active connection
- IN PROGRESS – faxes currently being processed
- PENDING RETRY – includes faxes waiting for a retry
- COMPLETED – faxes successfully processed
- ERROR – faxes that encountered a transmission problem
- CANCELED – fax was canceled by sender
Using this endpoint, API users are able to troubleshoot active issues using all pertinent information that relates to a particular fax job.
Use the GET /faxes/sent Endpoint in the API
This method allows you to check for the status details of faxes sent within a given time frame (and other query parameters such originating or destination fax numbers or transmission status).
For users with hundreds of known faxes, you can provide pagination offsets in the query to limit the number of fax records returned. The default offsets are 1 to 100.
Use the Webhook Notification Function
This method allows eFax Enterprise API Admins to provide a secure destination URL, of their choosing, where sent fax notifications are auto-posted by the API. Admins can then configure their applications to pick up this information and route through their internal workflows as needed. The advantage of this approach is that it is more of a "set it and forget it" approach than the GET endpoints described above.
Attempts to the provided URL retry on any 5xx response code but do not retry on any other response – 2xx being successful and others denoting an error (e.g. authentication) that retrying would not resolve. Four retries are attempted in 5 minute intervals, up to 5 total attempts.
An example of a customized notification URL is:
https://101.202.303.404/OutboundFaxService/OutboundFaxService.svc/AcmeWidgets/SentNotifications
Note that HTTPS is required when setting up the destination URL.
We also support HMAC authentication for our webhooks using SHA256 hash encryption.
Ports
Our service allows customers to specify the URL for webhook delivery.
No port number needs be specified in setting up your webhooks; we use 443 by default. For example: https://api.example.com/webhook/path. If you have a need for an alternative port, we allow :8443. For example: https://api.example.com:8443/webhook/path.
Any webhook configuration that doesn't follow these guidelines will not be delivered.
JSON Payloads
Successful Example
The following is an example of the JSON payload delivered to the user’s notification endpoint for a sent fax that has been successfully transmitted. The status field shows COMPLETE with no errors.
POST HTTP/1.1 Host: {{webhook-url}} Content-Type: application/json Cache-Control: no-cache Postman-Token: 523b4bad-710d-efed-63d9-f32fe84d9db7
{ "app_id": "d580162d-d162-4353-bd55-c2044ab20711", "user_id": "ca4cd102-c3e7-4379-9a7e-38c61e1f7a55", "notification_id": "4f1f70d2-2862-4b12-9327-4f3f1ff45292", "fax_id": "a7cbe81b-f4c7-c97c-e053-690c950abca9", "direction": "OUTBOUND", "completed_timestamp": "2024-05-10T17:56:07Z", "duration": 45, "pages": 2, "destination_fax_number": "18664226438", "status": "COMPLETE", "billable_retries": 0, "client_data": { "billing_code": "mkm89", "client_code": "1111", "client_id": "ef9b6338-c267-11e9-9cb5-2a2ae2dbcce6", "client_matter": "someMatterCA1591865649", "client_name": "ClientName1591865649", "client_reference_id": "2222" } }
Failed Example
For this example, the status field shows ERROR and the error and error_reason fields are present.
{ "app_id": "d580162d-d162-4353-bd55-c2044ab20711", "user_id": "ca4cd102-c3e7-4379-9a7e-38c61e1f7a55", "notification_id": "e8b80e8a-4e3d-4bcf-bd62-e5462e7fa6df", "fax_id": "a7cc1059-2672-e8a1-e053-680c940ac083", "direction": "OUTBOUND", "completed_timestamp": "2024-05-10T17:56:07Z", "duration": 0, "pages": 0, "destination_fax_number": "11111111111", "status": "ERROR", "billable_retries": 0, "error": "E53", "error_reason": "Destination fax number not allowed", "client_data": { "billing_code": "mkm89", "client_code": "1111", "client_id": "ef9b6338-c267-11e9-9cb5-2a2ae2dbcce6", "client_matter": "someMatterCA1591865477", "client_name": "ClientName1591865477", "client_reference_id": "2222" } }
Client Response
The client should respond with a 200 OK if the delivery is a success. The client provided response body must use Content-Type:application/json
format; however, any response body is permissible as long as it is in JSON format. For example:
HTTP/1.1 200 Content-Type: application/json { "status": "SUCCESS" }
Testing Webhooks
We now support the ability to test a webhook via the POST /notifications/ping endpoint. For example:
POST https://api.securedocex.com/notifications/ping
{ "fax_direction": "OUTBOUND" #INBOUND }
Response:
[ { "app_id": "xxxx", "notify_id": "7b692d22-c7cf-11eb-9e0a-83dcedf47a3d", "notify_config_id": "xxxxx-182f-xxxx-ab9a-xxxxxxxxxxxx", "fax_direction": "OUTBOUND", "notify_type": "WEBHOOK", "event_type": "PING" } ]
The User will also get a webhook post request to the configured URL with payload:
{ "app_id": "xxxx", "notification_id": "7b692d22-c7cf-11eb-9e0a-83dcedf47a3d", "direction": "OUTBOUND", "event_type": "PING", "notification_config_id": "xxxxx-182f-xxxx-ab9a-xxxxxxxxxxxx" }
Fax Services API Spec — Test Notification Configuration
HMAC Webhook Header
HMAC (Hash-based message authentication code) is a message authentication methodology that uses a cryptographic key in conjunction with a hash function. HMAC may be used to simultaneously verify both the data integrity and the authenticity of a message.
We support HMAC authentication for our webhooks using SHA256 hash encryption. The eFax Enterprise API notification service and client each should be provided with a private key that is known only to the service and to the specific client. The private key should be provided by the client during configuration of the WebHook URL.
On each WebHook event request to the client endpoint the notification service will be generating a unique HMAC, or hash, by hashing the request data with the private key and sending it as part of the request in request headers. When the client receives the WebHook event they should be using the same hash function and private key to generate the hash code from the payload on their end and compare it with the received one.
To use HMAC authentication, the client must use the x-HMAC-Signature to validate webhooks. Validate the signature using HMAC best practices. Contact your account manager, sales engineer, or customer support to enroll in HMAC.
Java Code Sample:
import org.apache.commons.codec.binary.Hex; import java.security.MessageDigest; import javax.crypto.Mac; import javax.crypto.spec.SecretKeySpec; import java.nio.charset.StandardCharsets;
String hmacSecret = ...; // HMAC secret set in Notify Configuration String payload = ...; // WEBHOOK JSON body payload String payload = ...; // WEBHOOK JSON body payload String hmacSignature = header.getFirst("X-HMAC-Signature"); // HMAC signature
Mac mac = Mac.getInstance("HmacSHA256"); mac.init(new SecretKeySpec(hmacSecret.getBytes(), "HmacSHA256")); byte[] hmac = mac.doFinal(payload.getBytes(StandardCharsets.UTF_8)); bool isEqual = MessageDigest.isEqual(hmac, hmacSignature.getBytes(StandardCharsets.UTF_8)); // PREVENT timing attacks return isEqual
NodeJs Code Sample:
import { createHmac } from 'crypto';
const hmacSecret = ...; // HMAC secret set in Notify Configuration const payload = ...; // WEBHOOK JSON body payload const hmacSignature = req.headers.get("X-HMAC-Signature") // HMAC signature
const hmacHash = createHmac('SHA256', hmacSecret) .update(payload) .digest('hex'); return crypto.timingSafeEqual(Buffer.from(hmacHash, 'utf8'),Buffer.from(hmacSignature,'utf8')) // PREVENT timing attacks