function invoice(
        bytes32 id,
        address supplier,
        address purchaser,
        uint256 price,
        uint256 deposit,
        uint256 cancellationFee,
        uint64 cancelDeadline,
        uint64 disputeDeadline
    )
        external
        onlyWhitelisted
        invoices(id)
    {
        require(
            supplier != address(0x0),
            "Must provide a valid supplier address."
        );
        require(
            purchaser != address(0x0),
            "Must provide a valid purchaser address."
        );
        require(
            
            cancelDeadline > now.add(cancelPeriod),
            "Cancel deadline too soon."
        );
        require(
            disputeDeadline > uint256(cancelDeadline).add(disputePeriod),
            "Dispute deadline too soon."
        );
        require(
            price.add(deposit) >= cancellationFee,
            "Cancellation fee exceeds total."
        );
        details[id] = Details({
            active: true,
            supplier: supplier,
            cancelDeadline: cancelDeadline,
            purchaser: purchaser,
            disputeDeadline: disputeDeadline,
            price: price,
            deposit: deposit,
            cancellationFee: cancellationFee
        });
        uint256 expectedBalance = getTotal(id)
            .add(token.balanceOf(address(this)));
        require(
            token.transferFrom(purchaser, address(this), getTotal(id)),
            "Transfer failed during invoice."
        );
        require(
            token.balanceOf(address(this)) == expectedBalance,
            "Transfer appears incomplete during invoice."
        );
    }