Как задать путь к файлу.QBW для ответа в Authenticate for Quickbooks Web Connector?

Хорошо, я использую отличные классы Кейта Палмерса для этого, расположенные здесь: https://github.com/consolibyte/quickbooks-php, и веб-коннектор работает нормально, но только когда у меня открыты Quickbooks и нажмите File-> Обновите веб-сервис на сервере, где работает веб-коннектор. Когда я выхожу с Сервера или даже закрываю приложение Quickbooks, Web Connector больше не работает. Я использую Quickbooks Enterprise и прочитал, что мне нужно отправить ответ от authenticate() метод, который я предполагаю, что сервер Web Connector (https) должен отправить, который является <AppURL> из.QWC файла. Единственная проблема в том, что я не до конца понимаю, как работает код Кейта, и даже не уверен, где выполняется метод authenticate(). И вполне возможно, что эта опция уже доступна в классе и / или функции / хуке, которых, похоже, так много в классах QB.

Прямо сейчас мой сервер имеет очень мало разметки и выглядит так:

<?php

/**
 * Example QuickBooks SOAP Server / Web Service
 * 
 * This is an example Web Service which adds customers to QuickBooks desktop 
 * editions via the QuickBooks Web Connector. 
 * 
 * MAKE SURE YOU READ OUR QUICK-START GUIDE:
 *  http://wiki.consolibyte.com/wiki/doku.php/quickbooks_integration_php_consolibyte_webconnector_quickstart
 *  http://wiki.consolibyte.com/wiki/doku.php/quickbooks
 * 
 * You should copy this file and use this file as a reference for when you are 
 * creating your own Web Service to add, modify, query, or delete data from 
 * desktop versions of QuickBooks software. 
 * 
 * The basic idea behind this method of integration with QuickBooks desktop 
 * editions is to host this web service on your server and have the QuickBooks 
 * Web Connector connect to it and pass messages to QuickBooks. So, every time 
 * that an action occurs on your website which you wish to communicate to 
 * QuickBooks, you'll queue up a request (shown below, using the 
 * QuickBooks_Queue class). 
 * 
 * You'll write request handlers which generate qbXML requests for each type of 
 * action you queue up. Those qbXML requests will be passed by the Web 
 * Connector to QuickBooks, which will then process the requests and send back 
 * the responses. Your response handler will then process the response (you'll 
 * probably want to at least store the returned ListID or TxnID of anything you 
 * create within QuickBooks) and this pattern will continue until there are no 
 * more requests in the queue for QuickBooks to process. 
 * 
 * @author Keith Palmer <keith@consolibyte.com>
 * 
 * @package QuickBooks
 * @subpackage Documentation
 */

// I always program in E_STRICT error mode... 
error_reporting(E_ALL | E_STRICT);
ini_set('display_errors', 1);

// We need to make sure the correct timezone is set, or some PHP installations will complain
if (function_exists('date_default_timezone_set'))
{
    // * MAKE SURE YOU SET THIS TO THE CORRECT TIMEZONE! *
    // List of valid timezones is here: http://us3.php.net/manual/en/timezones.php
    date_default_timezone_set('America/New_York');
}

// Require the framework
require_once(dirname(__FILE__) . '/../QuickBooks.php');

$user = 'quickbooks';
$pass = 'password';

// Map QuickBooks actions to handler functions
$map = array(
    QUICKBOOKS_ADD_CUSTOMER => array( '_quickbooks_customer_add_request', '_quickbooks_customer_add_response' ),
    QUICKBOOKS_QUERY_CUSTOMER => array('_quickbooks_query_customer_request', '_quickbooks_query_customer_response'),
    // ... more action handlers here ...
    );

// This is entirely optional, use it to trigger actions when an error is returned by QuickBooks
$errmap = array(
    // 3070 => '_quickbooks_error_stringtoolong',               // Whenever a string is too long to fit in a field, call this function: _quickbooks_error_stringtolong()
    // 'CustomerAdd' => '_quickbooks_error_customeradd',    // Whenever an error occurs while trying to perform an 'AddCustomer' action, call this function: _quickbooks_error_customeradd()
    'CustomerQuery' => '_quickbooks_error_customer_query',
    '*' => '_quickbooks_error_catchall',                // Using a key value of '*' will catch any errors which were not caught by another error handler
    // ... more error handlers here ...
    );

// An array of callback hooks
$hooks = array(
    // There are many hooks defined which allow you to run your own functions/methods when certain events happen within the framework
    // QuickBooks_WebConnector_Handlers::HOOK_LOGINSUCCESS => '_quickbooks_hook_loginsuccess',  // Run this function whenever a successful login occurs
    );

function _quickbooks_error_customer_query($requestID, $user, $action, $ID, $extra, &$err, $xml, $errnum, $errmsg)
{
    file_put_contents(dirname(__FILE__) . '/customer_query_error.txt', "Error Number " . $errnum . PHP_EOL . $errmsg . PHP_EOL, FILE_APPEND | LOCK_EX);
}

function _quickbooks_error_catchall($requestID, $user, $action, $ID, $extra, &$err, $xml, $errnum, $errmsg)
{
    mysql_query("
        UPDATE 
            my_customer_table 
        SET 
            quickbooks_errnum = '" . mysql_real_escape_string($errnum) . "', 
            quickbooks_errmsg = '" . mysql_real_escape_string($errmsg) . "'
        WHERE 
            id = " . (int) $ID);
}

// Logging level
$log_level = QUICKBOOKS_LOG_DEBUG;              
$soapserver = QUICKBOOKS_SOAPSERVER_BUILTIN;

$soap_options = array(      // See http://www.php.net/soap
    );

$handler_options = array(
    //'authenticate' => ' *** YOU DO NOT NEED TO PROVIDE THIS CONFIGURATION VARIABLE TO USE THE DEFAULT AUTHENTICATION METHOD FOR THE DRIVER YOU'RE USING (I.E.: MYSQL) *** '
    //'authenticate' => 'your_function_name_here', 
    //'authenticate' => array( 'YourClassName', 'YourStaticMethod' ),
    'deny_concurrent_logins' => false, 
    'deny_reallyfast_logins' => false, 
    );      // See the comments in the QuickBooks/Server/Handlers.php file

$driver_options = array(        // See the comments in the QuickBooks/Driver/<YOUR DRIVER HERE>.php file ( i.e. 'Mysql.php', etc. )
    //'max_log_history' => 1024,    // Limit the number of quickbooks_log entries to 1024
    //'max_queue_history' => 64,    // Limit the number of *successfully processed* quickbooks_queue entries to 64
    );

$callback_options = array(
    );

$dsn = 'mysql://{my_db_name}:{my_db_password}@localhost/{my_db}';

// Create a new server and tell it to handle the requests
// __construct($dsn_or_conn, $map, $errmap = array(), $hooks = array(), $log_level = QUICKBOOKS_LOG_NORMAL, $soap = QUICKBOOKS_SOAPSERVER_PHP, $wsdl = QUICKBOOKS_WSDL, $soap_options = array(), $handler_options = array(), $driver_options = array(), $callback_options = array()
$Server = new QuickBooks_WebConnector_Server($dsn, $map, $errmap, $hooks, $log_level, $soapserver, QUICKBOOKS_WSDL, $soap_options, $handler_options, $driver_options, $callback_options);
$response = $Server->handle(true, true);


function _quickbooks_customer_add_request($requestID, $user, $action, $ID, $extra, &$err, $last_action_time, $last_actionident_time, $version, $locale)
{
    // Grab the data from our MySQL database
    $arr = mysql_fetch_assoc(mysql_query("SELECT * FROM my_customer_table WHERE id = " . (int) $ID));

    $xml = '<?xml version="1.0" encoding="utf-8"?>
        <?qbxml version="2.0"?>
        <QBXML>
            <QBXMLMsgsRq onError="stopOnError">
                <CustomerAddRq requestID="' . $requestID . '">
                    <CustomerAdd>
                        <Name>' . $arr['name'] . '</Name>
                        <CompanyName>' . $arr['name'] . '</CompanyName>
                        <FirstName>' . $arr['fname'] . '</FirstName>
                        <LastName>' . $arr['lname'] . '</LastName>
                    </CustomerAdd>
                </CustomerAddRq>
            </QBXMLMsgsRq>
        </QBXML>';

    return $xml;
}


function _quickbooks_customer_add_response($requestID, $user, $action, $ID, $extra, &$err, $last_action_time, $last_actionident_time, $xml, $idents)
{   
    mysql_query("UPDATE my_customer_table SET quickbooks_listid = '" . mysql_escape_string($idents['ListID']) . "' WHERE id = " . (int) $ID);

}

// Get all Customers!
function _quickbooks_query_customer_request($requestID, $user, $action, $ID, $extra, &$err, $last_action_time, $last_actionident_time, $version, $locale) {
    $xml = '<?xml version="1.0" encoding="utf-8"?>
        <?qbxml version="11.0"?>
        <QBXML>
            <QBXMLMsgsRq onError="stopOnError">
                <CustomerQueryRq requestID="' . $requestID . '">
                    <MaxReturned>10000</MaxReturned>
                    <ActiveStatus>All</ActiveStatus>
                </CustomerQueryRq>
            </QBXMLMsgsRq>
        </QBXML>';

    return $xml;
}

function add_quotes($value)
{
    if (is_string($value))
        return sprintf("'%s'", mysql_escape_string($value));
    else
        return $value;
}

function _quickbooks_query_customer_response($requestID, $user, $action, $ID, $extra, &$err, $last_action_time, $last_actionident_time, $xml, $idents)
{
    $customers = json_decode(json_encode(simplexml_load_string($xml, "SimpleXMLElement", LIBXML_NOCDATA)), true);

    if (!empty($customers['QBXMLMsgsRs']) && !empty($customers['QBXMLMsgsRs']['CustomerQueryRs']) && !empty($customers['QBXMLMsgsRs']['CustomerQueryRs']['CustomerRet']))
    {
        foreach($customers['QBXMLMsgsRs']['CustomerQueryRs']['CustomerRet'] as $customer_data)
        {
            $customer_info = array();
            foreach($customer_data as $attribute => $info)
            {
                if ($attribute == 'BillAddressBlock') continue;

                if ($attribute == 'IsActive')
                    $info = $info == 'true' ? 1 : 0;

                if ($attribute == 'Sublevel')
                {
                    $info = (int) $info;
                    if (empty($info))
                        $info = 0;
                }

                if (is_array($info))
                {
                    foreach($info as $key => $value)
                    {
                        if (!is_array($value))
                            $customer_info[$attribute . '_' . $key] = stripslashes($value); // Magic Quotes being on, should check magic quotes before using stripslashes tho
                    }
                }
                else
                    $customer_info[$attribute] = stripslashes($info); // Magic Quotes being on, should check magic quotes before using stripslashes tho
            }

            if (!empty($customer_info))
            {
                $columns = implode(', ', array_keys($customer_info));
                $values = implode(', ', array_map('add_quotes', $customer_info));

                $sql = 'INSERT INTO quickbooks_customers (' . $columns . ') VALUES (' . $values . ')';

                // file_put_contents(dirname(__FILE__) . '/sql.txt', var_export($sql, true) . PHP_EOL, FILE_APPEND | LOCK_EX);
                // Insert this customer into the database now:
                mysql_query($sql);
            }
        }
    }
}


function _quickbooks_error_stringtoolong($requestID, $user, $action, $ID, $extra, &$err, $xml, $errnum, $errmsg)
{
    mail('your-email@your-domain.com', 
        'QuickBooks error occured!', 
        'QuickBooks thinks that ' . $action . ': ' . $ID . ' has a value which will not fit in a QuickBooks field...');
}
?>

Не уверен, где установить полный путь файла QBW здесь. Любая помощь будет принята с благодарностью. мой <QBType> установлен в QBFS если это поможет.

Я использую следующее, чтобы поставить в очередь действия:

$Queue = new QuickBooks_WebConnector_Queue($connection_string);
$Queue->enqueue(QUICKBOOKS_QUERY_CUSTOMER, $random_unique_id);

Но как указать путь к файлу.QBW? Должно ли оно быть в $soap_options или $handler_options, или оно существует отдельно от любых параметров, которые я могу отправить с помощью Сервиса? Если бы я мог просто увидеть пример того, как кто-то правильно связал файл QBW с помощью этого API, это было бы очень полезно. Я знаю путь к файлу.QBW на сервере, мне просто нужно отправить его обратно в ответ, и теперь я абсолютно уверен, как это сделать с помощью кода Кейта Палмерса, если это вообще возможно сделать легко в этом API...?

1 ответ

Решение

Не уверен, где установить полный путь файла QBW здесь.

Скопируйте / вставьте из нашей вики:

Вы можете указать платформе подключиться к QuickBooks, даже если QuickBooks не открыт, установив в поле "qb_company_file" в таблице SQL "quickbooks_user" полный путь к файлу компании. Это означает, что для финансовых выпусков QuickBooks (т. Е. Выпусков Pro, Premier, Enterprise) вы должны делать:

UPDATE quickbooks_user SET qb_company_file = 'C:\path\to\your\file.QBW' WHERE qb_username = 'your-web-connector-username'
Другие вопросы по тегам