The FaxReceiver property

class CallFaxReceiver

A class that provides an API for receiving a fax.

This class exposes a public property called Details of type FaxDetails (see below) which provides details on the fax job in progress.

The call channel object uses this class to provide fax reception functionality. The call channel object has a public property called FaxReceiver of this type. Please see the tutorial for examples on how to use this class.

class Cause

Once a receive job has ended and the receive state has returned to IDLE or ERROR, the cause will be one of these.

Receive termination causes:

ERROR

Receive has stopped due to an error.

NORMAL

Receive has stopped normally.

ABORTED

Receive has been aborted (probably because stop was called).

HANGUP

Receive ended due to a call hangup.

TIMEOUT

Receive stopped because a timer has expired.

NOTFAX

The transmitting end has not sent any fax signals, it is probably not a fax machine.

UNKNOWN_OPTION

An unknown fax option was supplied.

UNKNOWN_VALUE

A known fax option value was supplied with an incorrect value.

INCONSISTENT_OPTIONS

Inconsistent fax options were supplied.

STANDARDMISMATCH

A T.30 - T.38 negotiation mismatch has occurred and the call has been abandoned.

COMMSFAULT

A fax communication error has occurred. This could be due to the sending end not being a fax machine or due to bad line conditions. Check that the sending end is a compatible fax machine and then try again.

PAGEQUALITY

The Fax has been abandoned because there have been too many errors. Try again.

NONE

Receive is in progress or receive has not occurred.

When passing fax options to the send or start functions, the user will supply a dictionary of name - value pairs. These names, and their corresponding values can be found on the online fax documentation. If an invalid variable name or value is supplied, or if an invalid combination of variables is supplied, the action will fail and the cause will be one of UNKNOWN_OPTION, UNKNOWN_VALUE or INCONSISTENT_OPTIONS. It is a good idea to check for these causes as one of them would normally require a correction to the application. An example is given below.

This combination would make faxing impossible:

fax_options = {
    'v17':'NO',
    'MinDataRate':'14400'
}

if channel.FaxSender.start(fax_to_send=fax_to_send, fax_options=fax_options) is False:
    cause = channel.FaxSender.cause()
    if cause == channel.FaxSender.Cause.INCONSISTENT_OPTIONS:
        raise Error("This combination of options is not allowed: {0}".format(repr(channel.FaxSender.Details.failed_option)))

Sometimes a fax session will fail because the other end is not a fax machine (for example, an inbound fax call is placed by a human); In this case the cause will be NOTFAX, for example:

cause = channel.FaxReceiver.wait_until_finished()
if cause == channel.FaxReceiver.Cause.NOTFAX:
    raise Hangup("Hang up because caller is not a fax machine")

A fax session can also fail because the line quality is simply too bad for a fax to succeed. For these cases we have the causes COMMSFAULT and PAGEQUALITY. If a fax session fails and the cause is COMMSFAULT, it would be worthwhile checking the line before trying again. If the cause is PAGEQUALITY, it may be worth waiting ten minutes or so and before trying again.

class State

The receive state can be checked to determine whether a receive job is in progress. When a fax job ends and State has returned to IDLE or ERROR, the termination Cause can be checked to find the reason why.

receive states:

RECEIVING

Receiving is in progress.

IDLE

Receiving is not in progress.

ERROR

The most recent transmit job failed and none is currently in progress.

cause()

This function will return a cause.

When a particular job terminates, the reason why can be requested by calling this function.

If this function is called while a job is still running, the cause will be NONE.

receive(fax_to_receive, fax_options=None)

Receive a fax on the current connected call channel.

Required argument:
  • fax_to_receive

    the fax document object to which to receive the fax.

Optional arguments:
  • fax_options

    fax configuration options for this session.

fax_to_receive is an object that is used to configure the fax document for sending. A reference to the object is passed into this function. If you are not familiar with the fax document object, please read up on it before continuing.

fax_options is a dictionary of name - value pairs where the name is that of a fax option and the value is what that option should be set to. Fax options would normally be set on your inbound and outbound service pages. It is, however, possible to set options from within an application. For instance, to force a high resolution fax:

cause = channel.FaxSender.send(my_fax, fax_options={'HighRes':'YES'})

The list of option names, and their possible values, can be found on the online fax documentation page.

If the call state is IDLE, this function will raise a Hangup exception. If the call state is not IDLE but also not ANSWERED, this function will raise an Error exception.

If the receive state is already RECEIVING, this function will raise an Error exception.

This function will block until the fax receive session completes or a timeout expires.

Upon completion, this function will return a cause.

Usage example:

# receive a fax
my_fax = FaxToReceive()
my_fax.set_file_name('my_inbound_fax.tif')
cause = channel.FaxReceiver.receive(my_fax)
if cause == channel.FaxReceiver.Cause.NORMAL:
    print("the fax job ended normally")
elif cause == channel.FaxReceiver.Cause.NOTFAX:
    print("the caller was not a fax machine")
else:
    print("the fax job failed")
start(fax_to_receive, fax_options=None)

Start receiving a fax on the current connected call channel.

Required argument:
  • fax_to_receive

    the fax document object to which to receive the fax.

Optional arguments:
  • fax_options

    fax configuration options for this session.

fax_to_receive is an object that is used to configure the fax document for sending. A reference to the object is passed into this function. If you are not familiar with the fax document object, please read up on it before continuing.

fax_options is a dictionary of name - value pairs where the name is that of a fax option and the value is what that option should be set to. Fax options would normally be set on your inbound and outbound service pages. It is, however, possible to set options from within an application. For instance, to force a high resolution fax:

cause = channel.FaxReceiver.start(my_fax, fax_options={'HighRes':'YES'})

The list of option names, and their possible values, can be found on the online fax documentation page.

If the call state is IDLE, this function will raise a Hangup exception. If the call state is not IDLE but also not ANSWERED, this function will raise an Error exception.

If the receive state is already RECEIVING, this function will raise an Error exception.

This function will block until the fax receive session has started or a timeout expires.

Upon return, this function will return True for success, otherwise False.

Usage example:

# Start a fax receive session.
my_fax = FaxToReceive()
my_fax.set_file_name('my_inbound_fax.tif')
if channel.FaxReceiver.start(my_fax) == True:
    # While receiving, we can do something else and then
    # wait until receiving is complete.
    cause = channel.FaxReceiver.wait_until_finished()
    if cause == channel.FaxReceiver.Cause.NORMAL:
        print("the fax job ended normally")
    elif cause == channel.FaxReceiver.Cause.NOTFAX:
        print("the caller was not a fax machine")
    else:
        print("the fax job failed")
else:
    # The function returned False, this probably means that
    # the acknowledgement to indicate that fax receiving has begun
    # did not arrive in time, and the function has timed out.
    pass
state()

This function will return the current state.

When a particular job is busy, its status can be tracked by calling this function.

If this function is called when no job is in progress, the state will be IDLE.

stop()

Stop receiving a fax on the current connected call channel. This will abort the fax session.

If the call state is IDLE, this function will raise a Hangup exception. If the call state is not IDLE but also not ANSWERED, this function will raise a Error exception.

If the receive state is not RECEIVING, this function will simply return True.

This function will block until the fax receive session terminates or a timeout expires.

Upon return, this method will return True for success, otherwise False.

Usage example:

# Start a fax receive session.
if channel.FaxReceiver.start(filename="my_fax.tif") == True:
    # While receiving the fax, we can do something else, and then,
    # for whatever reason, stop it.
    channel.FaxReceiver.stop()
wait_for_negotiated_settings(seconds_timeout=None)

Wait for the fax endpoint negotiation to be completed.

Optional argument:
  • seconds_timeout

    The maximum time, in seconds, to wait.

This function will wait until the negotiated settings are available.

If the channel associated with this fax session goes to IDLE, this function will raise a Hangup exception,

If the fax session encounters an error, this function will raise an Error exception.

Once the negotiated settings are available, this function will return the settings dictionary. If the negotiated settings dictionary is empty, this means that fax negotiation has failed.

Usage example:

negotiated_settings = channel.FaxReceiver.wait_for_negotiated_settings()
if negotiated_settings == {}:
    # negotiation has failed, we should quit and hang up.
    cause = channel.FaxReceiver.cause()
    raise Hangup("fax receiver returned {0}".format(cause))

for setting, value in negotiated_settings.iteritems():
    print("{0:>15.15} : {1}".format(setting, value))
wait_for_next_page(seconds_timeout=None)

Wait for the next fax page to be completed.

Optional argument:
  • seconds_timeout

    The maximum time, in seconds, to wait.

This function will wait for the next page to be completed.

If the channel associated with this fax session is IDLE, this function will raise a Hangup exception.

If the fax session encounters an error, this function will raise an Error exception.

Once the next page has completed, this function will return the number of pages completed so far.

Usage example:

# We can wait for each page to be received, we do this until we've been told
# that no more pages will be received. For each page we print the page quality.
# This, and more, detail is available on the fax document object.
# It is important to note that the last_page flag does not indicate success, it simply
# means that no more pages will be processed.
while channel.FaxReceiver.Details.last_page is not True:
    pages = channel.FaxReceiver.wait_for_next_page()
    print("Received {0} pages so far".format(pages))
    print("Last received page quality: {0}".format(my_fax.PageDetails[-1].receive_quality))

# Now we need to wait until the fax session has finished. We need to do this even though
# the last page flag has been set. Remember to check the cause, the last_page indicator
# may have been set, but this does not mean that every page was received.
cause = channel.FaxReceiver.wait_until_finished()
if cause != channel.FaxReceiver.Cause.NORMAL:
    raise Error("Fax receiver failed with cause {0}".format(cause))
wait_until_finished(seconds_timeout=None)

Wait for the fax session to be completed.

Optional argument:
  • seconds_timeout

    the amount of time allocated to wait for the fax session to terminate. Default is to wait forever.

This function will block until the fax session completes or the timeout expires. Giving a value of None for seconds_timeout will enable an infinite wait. If the timeout does expire, a cause of TIMEOUT will be returned.

Upon return, this function will return a cause.

This function will not raise a HANGUP exception if the call state is already IDLE. It is possible for there to be a brief period during which the call can be IDLE whilst the fax session is still terminating.

Usage example:

# Start a fax receive session.
if channel.FaxReceiver.start(filename="my_fax.tif") == True:
    # While receiving the fax, we can do something else,
    # then wait until the fax session has completed.
    cause = channel.FaxReceiver.wait_until_finished()
    if cause == channel.FaxReceiver.Cause.NORMAL:
        print("the fax job ended normally")
    elif cause == channel.FaxReceiver.Cause.NOTFAX:
        print("the caller was not a fax machine")
    else:
        print("the fax job failed")

Fax Details

class FaxDetails(channel, logger)

Holds details of the fax session. The details are filled in as the fax progresses.

ID

The fax ID as returned by the cloud.

line

The connected line associated with this fax.

fax_standard

T.30 or T.38.

options

The fax options, this is a dictionary in the form { option:value, … }.

failed_option

The fax options that could not be set, this is a dictionary in the form { option:value, … }.

pages

The number of fax pages sent or received so far.

last_page

Will be True if no more pages are to be handled during this fax session. Note: this does not imply that the fax session was successful.

negotiated

The fax parameters that have been negotiated, this is a dictionary in the form { option:value, … }.

raw_cause

The fax error code returned when the cause is ERROR or NOTFAX.

Usage example:

# create the fax document object
my_fax = FaxToSend('my_fax.tiff')
# send the fax and check the termination cause
if channel.FaxSender.send(fax_to_send=my_fax) != channel.FaxSender.Cause.NORMAL:
    # the fax did not terminate normally, look at the raw_cause
    print("Fax failed with raw cause {0}".format(channel.FaxSender.Details.raw_cause))