Trabajando con WebService de Vtiger…

A pasado mucho tiempo desde que escribi por ultima vez, pero ahora voy a hacerlo aportando algo sobre como trabajar con el “vtwsclib1.4”  que es la libreria para WebService con Vtiger.

En primer lugar se necesitara descargar la libreria, para esto pueden entrar en el Forge de Vtiger en el apartado del proyecto , ahi encontraran los archivos, un zip con la libreria y un PDF con la documentacion y guia rapida.

Vamos a trabajar sobre un directorio que nombraremos “testvtwsclib”, entonces dentro de el descomprimimos el archivo zip que descargamos, quedandonos la siguiente estructura:

Se puede observar pues los directorios que estan contenidos en “vtwsclib“. ahora bien, vamos a crear un archivo nuevo llamado “index.php” y lo guardamos en el directorio “testvtwsclib”. Este ejemplo lo que hace es obtener la lista de modulos que actualmente estan instalados en Vtiger y muestra un SELECT con dicho listado, al momento de seleccionar un modulo de la lista se procede a mostrar la descripcion del mismo.

El contenido del archivo index.php es el siguiente:

// Incluir el archivo base de la libreria para PHP
include_once('vtwsclib/Vtiger/WSClient.php');

// Configurar el usuario con el que deseamos conectar con Vtiger
$user = 'admin';
$key  = 'O3BkR9oHR47x';

// Aqui va el URL de tu instalacion de Vtiger
$url = 'http://nombrehost.com/vtigercrm';

// Se genera se inicializa el Obejto WSClient pasandole como parametro el URL
$client = new Vtiger_WSClient($url);

// Lo siguiente es hacer el Login usando el Usuario y Key para acceso
$login = $client->doLogin($user, $key);

// $login debe ser TRUE si se ha logrado entrar correctamente, si ocurrio un error sera FALSE
if(!$login) {
echo 'Login Failed';
}
else {
    // En el caso de este script, se
    $modulename = (isset($_POST['mod']))?$_POST['mod']:$_GET['mod'];

    //** Imprimir el combo con la lista de modulos del CRM **//

    // Se obtienen todos los modulos que actualmente estan instalados en Vtiger
    $modules = $client->doListTypes();

    $html_string1 = '<form name="modules" method="get">'.
                   '<select name="mod">';

    foreach($modules as $modname => $moduleinfo) {
        $selected = '';
        if($modname == $modulename) $selected = 'selected=selected';
    
        $html_string1 .= '<option '.$selected.' value='.$modname.'>'.$modname.'</option>';
    }

    $html_string1 .= '</select>' .
                 '<input type="submit" name="checkMod" value="Consultar"/>' .
              '</form>';

    echo $html_string1;
    /**  Fin de crear la lista de modulos **/

    if($modulename!='')
    {
        $html = getModuleDescription($modulename);
        echo $html;
    }
}

/**
* Devuelve  la descripcion del Modulo, cuyo nombre se pase como parametro en $modulename
*/
function getModuleDescription($modulename)
{
    // globales, definidas fuera de la funcion
    global $client;
    global $user;

    $maxcols = 8;

    // Se ejecuta el metodo "doDescribe" que obtiene la configuracion del modulo, en este
    //   se incluyen permisos y campos del modulo.

    $describe = $client->doDescribe($modulename);

    $wasError= $client->lastError();
    if($wasError) {
        echo $wasError['code'] . ':' . $wasError['message'];
    }
    else{
        // Recuperar los permisos que el usuario actual tiene sobre el modulo seleccionado
        $cancreate     = ($describe['createable'])?'Si':'No';
        $canupdate     = ($describe['updateable'])?'Si':'No';
        $candelete     = ($describe['deleteable'])?'Si':'No';
        $canread     = ($describe['retrieveable'])?'Si':'No';
        $fields     = ($describe['fields']);

        $html_string = '<table width="200">'.
                         '<th colspan="2">Permisos para el usuario: <b>'.$user.'</b> en Modulo '.$modulename.'</th>' .
                          '<tr><td>Crear:</td><td>'.$cancreate.         '</td></tr>' .
                          '<tr><td>Actualizar:</td><td>'.$canupdate.    '</td></tr>' . 
                          '<tr><td>Eliminar:</td><td>'.$candelete.    '</td></tr>' .
                          '<tr><td>Leer:</td><td>'.$canread.    '</td></tr>' . 
                        '</table><br/>';

        // Aqui comienza el proceso para formar un "table" en HTML para mostrar la descripcion del modulo y sus campos
        //  incluyendo los campos personalizados

        $html_string .= '<table border="1"><th colspan='.$maxcols.'>Campos</th>';
        $col = 0;
        for($i=0; $i<count($fields); $i++)
        {
            $col ++;
            $tableseppref = '<td style="float: left; margin: 2px 5px 0pt;height:260px; width: 170px;">';
            $tablesepsuf = '</td>';
            if($col == 1) {
                $tableseppref = '<tr>'.$tableseppref;
            }
            elseif($col == $maxcols)
            {
                $tablesepsuf = $tablesepsuf.'</tr>';
                $col = 0;
            }
        
            $fieldlabel         = ($fields[$i]['label']) ? $fields[$i]['label'] : $fields[$i]['name'];
            $fieldname            = $fields[$i]['name'];
            $fieldismandatory     = ($fields[$i]['mandatory'])?'Si':'No';
            $fieldtype            = $fields[$i]['type']['name'];
            $dateformat            = ($fields[$i]['type']['name'] == 'date') ? '<br/>format: '.$fields[$i]['type']['format'] : '';
            $valuesLabel = '';
            
            // Hacemos una llamada a la función local "getRelList()" con la que nos regresa un string en formato HTML con los valores
            //  de los campos si estos fueran de tipo "picklist" o "reference"
            $fieldValues = getRelList($fieldtype, $fields[$i]);
        
            if($fieldValues != ''){
                $valuesLabel = 'Valores';
            }
        
            // Aqui solo formaremos un string de HTML para mostrar la descripcion del campo en una "table"
            $html_string .= $tableseppref.
                '<table style="float: left; width: 100%;"><th style="float: none; background-color: rgb(194, 194, 194);">'.$fieldlabel.'</th>'.
                '<tr><td>DB Name: '.$fieldname.'</td></tr>'.
                '<tr><td>Obligatorio: '. $fieldismandatory .'</td></tr>'.
                '<tr><td>Tipo: '.$fieldtype.' '.$dateformat.'</td></tr>'.
                '<tr><td>'.$valuesLabel.'</td></tr>'.
                '<tr><td>'.
                     '<div style="float: left;width: 100%;height: 100px; overflow: auto;">'.
                         $fieldValues.
                     '</div>'.
                '</td></tr>'.
                '</table>'.
                $tablesepsuf;
        }

        $html_string .= '</table>';
        return utf8_decode($html_string);
    }
}

/**
* Devuelve los valores de los campos de tipo "picklist" y "reference"
*/
function getRelList($fieldtype, $field, $tag = 'ul', $itemtag = 'li'){
    if(($fieldtype == 'picklist') || ($fieldtype == 'reference'))
    {
    $fieldValues = '<'.$tag.'>';
    if($fieldtype == 'picklist') $cellValues     = 'picklistValues';
    if($fieldtype == 'reference') $cellValues     = 'refersTo';

    for($f=0; $f < count($field['type'][$cellValues]); $f++)
    {
        $value = '';
        if($fieldtype == 'picklist')
        $value = $field['type'][$cellValues][$f]['label'].'<br/>('.$field['type'][$cellValues][$f]['value'].')';
        if($fieldtype == 'reference')
            $value = $field['type'][$cellValues][$f];

            $fieldValues .= '<'.$itemtag.'>'.$value.'</'.$itemtag.'>';
        }
        $fieldValues .= '</'.$tag.'>';

        return $fieldValues;
    }
    return '';
}

Hasta aqui queda definido el contenido del script, las funciones auxiliares “getModuleDescription()” y “getRelList()” se incluyeron en el mismo script por razones de comodidad para mostrar el funcionamiento, pero bien pueden estar definidas en otros script y hacer un “include()”.

En este ejemplo solo hacemos uso del webservice para obtener la lista de modulos con:

$client->doListTypes();

asi como para obtener la descripcion de cada uno de ellos con:

$describe = $client->doDescribe($modulename);

Y por ultimo saber si ocurrio algun error al realizar la ultima operacion:

$wasError= $client->lastError();

A continuacion se muestra una pantalla del resulatdo final:

*Nota: Cabe señalar que el usuario que se usa para obtener el acceso es el mismo con el que se inicia sesion en Vtiger y el Key se puede obtener revisando las preferencias del usuario, esto se puede ver en el modulo de “configuracion” y eligiendo la opcion de “Usuarios”, despues eligen el usuario que ustedes quieran para ver la Key (Clave de Acceso).

En proximas entradas vere la posibilidad de mostrar como agregar nuevos registros a un modulo y obtener la informacion de determinado registro existente.

Espero que sea de utilidad esta informacion y espero sus comentarios.

Saludos.

“Chava”

Anuncios

22 comentarios en “Trabajando con WebService de Vtiger…

  1. Muy buen post 🙂 una pregunta en todos lados ponen tutos de como agregar una cuenta o un contacto, particularmente nunca pude agregar otra cosa que no sea eso por webservice como por ejemplo un evento en el calendario por mas que vi la documentacion nunca me crea el evento, alguna idea de como se hace ?
    Saludos cordiales 🙂

    1. Hola Sergio, me da gusto que sirva lo que escribo aqui, aunque es sencillo y basico esto, pero que bueno que sirve para alguien mas.

      Que bueno que pudiste agregar el evento. De hecho algo asi lo hice tambien, agregar eventos y tareas, por algun lado tengo el codigo, puesto que fueron solo pruebas, no concrete ningun proyecto con eso.

      Recuerda, cualquier duda y en lo que pueda ayudar aqui me encuentras.

      Saludos

  2. un pequeño aporte sacado de vcommerce que es una integración de oscommerce con vtiger:

    // Create account in vtiger CRM
    require_once(DIR_WS_INCLUDES . ‘vtiger/vtwsclib/Vtiger/WSClient.php’);
    $vtiger_ws_client = new Vtiger_WSClient($vtiger_url);
    $login = $vtiger_ws_client->doLogin($vtiger_username, $vtiger_accesskey);
    if(!$login) {
    $lasterr = $vtiger_ws_client->lastError();
    die(‘Please contact an administrator, error:’.$lasterr[‘message’]);
    }
    $vt_module = ‘Accounts’;
    $vtiger_query = tep_db_query(“select countries_name from countries where countries_id = ‘” . (int)$country . “‘”);
    $vtiger_array = tep_db_fetch_array($vtiger_query);
    $country_name = $vtiger_array[“countries_name”];
    $user_data = array(
    ‘accountname’=> $firstname.’ ‘.$lastname,
    ‘cf_CF’ => $cf,
    ‘phone’=>$telephone,
    ‘email1’ => $email_address,
    ‘fax’ => $fax,
    ‘bill_street’ => $street_address,
    ‘bill_code’ => $postcode,
    ‘bill_city’ => $city,
    ‘bill_state’ => $state,
    ‘bill_country’ => $country_name,
    ‘accounttype’=>’Customer’,
    ‘rating’=>’Acquired’,
    //’inesistente’=>’bal’,
    );
    $record = $vtiger_ws_client->doCreate($vt_module,$user_data);
    $lasterr = $vtiger_ws_client->lastError();
    if ($lasterr) {
    die(‘Please contact an administrator, error:’.$lasterr[‘message’]);
    }
    // End of vtiger integration

    con ayuda de tu post probare crear prospectos o leads, gracias por tu aporte, espero puedas continuar con tus ejemplos de agregar nuevos registros a un modulo. saludos

    1. Hola Hugo, Buen día.

      Se me ocurre que puedes crear una función personalizada, después, creas un Workflow en donde ejecutes dicha función cada vez que afectes uno de tus registros, esto puede ser:
      Ejemplo:

      Pedidos de Venta — Cada que es guardado el registro | Cuando es creado
      Ejecutar la función personalizada.

      Dentro de la función colocas el código propio para registrar en tu aplicacion (INSERT de SQL, o lo que tu quieras)

      Creo que este tema es bueno para postear. Voy a postear como hacerlo. Pero mientras con este comentario te dejo el camino abierto para que te des una idea por donde buscar.

      Cualquier cosa no dudes en preguntar.

      Saludos!

      1. Hola chavamm, tu respuesta me enruta mucho por el camino que necesitaba, pero entonces seria crear un procedure en la base de datos del vtiger para que ejecute la funcion que crea el registro en mi sistema propio.

  3. Hola chavamm, tu respuesta me enruta mucho por el camino que necesitaba, pero entonces seria crear un procedure en la base de datos?

    1. Hola Hugo, no es necesario crear Procedure, en realidad, en mi opinion, es mas sencillo de lo que te imaginas.

      Pro ejemplo, creas un script con tu función, lo guardas por ejemplo en “include/MisFunciones”, con el nombre que tu decidas, ejemplo “myscript.php”. Despues de esto se tiene que registrar dicha función en el sistema de la siguiente manera:

      $emm = new VTEntityMethodManager($adb);

      // parametros
      // (Modulo, Nombre de funcion para vtiger, ruta del archivo, nombre de funcion en Script)

      $emm->addEntityMethod(‘SalesOrder’, ‘FunctionName’, ‘scriptPath’, ‘sFunctionName’);

      Estoy en estos momentos escribiendo un post relacionado con esto, si tienes pasciencia, en unos minutos podras leerlo.

      Saludos!

  4. Ya tengo una idea de como se hace, se crea un flujo de trabajo en vtiger y se crea la tarea y se le relaciona la funciona a ejecutar.

    Configuración > Flujo de Trabajo > Editar Flujo Trabajo
    Editar un flujo de trabajo existente o crear uno nuevo

    Resumen
    * Descripción
    Módulo Cuentas

    Cuando ejecutar el flujo de trabajo
    Solo al crear.
    Solo la primera vez que se cumple la condición.
    Cada vez que se guarda la entidad.
    Cada vez que se modifica la entidad.
    Sistema.

    1. Hola Hugo, asi es. En esa parte es en donde se registran los Workflows y las tareas a ejecutar con dicho Wrokflow, como bien dices, a la tarea le relacionas una funcion a ejecutar de la lista de Seleccion.

      Felicidades, vas por buen camino!
      Saludos!

  5. chavamm, echale un vistazo al proyecto que desarrolle y que apenas comienza, es para administar colegios, universidades, etc. Miralo haber si te interesa colaborar en este proyecto.

    usuario: prueba
    pass: 123
    url: http://demo.heoq-campus.net/

    esta entrad es temporal se desabilitara en una hora.

      1. Hola chavamm, verificando tue ejmplo cuando ingreso la funcion a registrar “CustomFunctionNew” y le pongo el scripst, por ejemplo “myscript.php” y le doy registrar, no me dice que ha registrado la funcion, que podra ser.

  6. Buena data, ya empece a jugar con esto principalmente con el modulo de quotes.

    El tema es que el josn devuelto no me relaciona de ninguna manera los productos que tiene relacionados una quote.

    Basicamente hago esto:

    $record = “13×21317”;
    $recordInfo = $client->doRetrieve($record);
    echo “

    ";
        print_r($recordInfo);
        echo "

    “;

    Me da la oportunidad, la cuenta, el contacto, currency, de todo.. pero nada relacionado a productos de esa quote.

    Sabes como puedo encaminarlo?

  7. Hola de esta manera también podría desde que se genera un tipo de incidencia (Se cumple una condición de tipo) generar un nuevo proyecto con las tareas definidas?? (Plantilla de proyecto)????

    1. Hola, buenas tardes.

      Si lo que quieres, es consumir un WebService que no tiene que ver con el WebService de Vtiger, entonces, debes investigar como Consumir un WebService desde PHP.

      Tal vez no entiendo bien cuál es tu situación. Pero si te sirve:

      http://php.net/manual/es/class.soapclient.php

      En este caso, es para consumir un WebService SOAP. Pero todo depende del tipo de WebService que deseas consumir.

      Saludos!

    1. Hola Antoniom55,

      Hay un error con el simbolo en esa linea.

      Si copiaste y pegaste el codigo a un archivo, entonces verifica que en esa linea 155 corrijas para que quede como sigue:

      for($f=0; $f < count($field['type'][$cellValues]); $f++)

      Saludos!

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión / Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión / Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión / Cambiar )

Google+ photo

Estás comentando usando tu cuenta de Google+. Cerrar sesión / Cambiar )

Conectando a %s