Yo de Php muy poco, pero … leíste esto?
¿Capaz ahí salga como conectan?
Saludos a tod@s en el foro!
Amigo @Alvan1 te recomiendo que en lugar de utilizar la libreria php-saprfc, desarrolles un webservice en java utilizando SAP Java Connector 3.0 (JCo3) para la interface con R/3. Este conector JCo3 es provisto y recomendado por la mismisima SAP AG. Este esquema de conectividad que te planteo esta mas que probado, yo particularmente lo he implementado en n aplicativos que estan en productivo actualmente.
En su momento, hace 2 años aproximadamente, se trato de utilizar el conector php-saprfc-1.4.1 en un proyecto y fue desechado casi de inmediato por los problemas de configuracion e inestabilidad de conexión que presentaba, investigamos mas a fondo y nos dimos cuenta que la ultima actualizacion de la libreria habia sido en el año 2011, una libreria con 3 años sin actualizaciones es practicamente un proyecto que se dejo abandonado.
Ahora que @SidV coloco el link en git de la libreria es que me doy cuenta que al parecer retomaron el proyecto. Me voy a tomar como tarea probarla nuevamente a ver que tal.
Prueba la solución que te propuse, te garantizo que funciona bien. Ademas por tratarse de un webservice, vas a crear una solución mas abierta, basada en estandares y reutilizable desde cualquier plataforma.
Hasta te puedes ganar un punto extra por su implementación
Hola @Alvan1 yo realice la conexión de PHP con SAP, te comento lo que necesitas es lo siguiente:
Nota: toma encuenta si tu server es a 32 o 64
-
El archivo Librfc
-
php_saprfc_php5.6_ts.dll en tu caso por la version de tu PHP.
-
Abrir el archivo php.ini (que se encuentra en c:\xampp\php\php.ini)y agregar el dll dentro del archivo donde se encuentran las “extension= …” ejemplo:
extension=php_saprfc_php5.6_ts.dll -
Debes de crear una funcion RFC en sap, con tus tablas o estructuras correspondientes.
-
Crear una “Funcion en PHP” donde hagas la conexión a SAP (tomando en cuenta el envio de parametros a tu función y elementos entrantes a la misma).
-
El archivo que generes PHP se apoya de “otro” PHP el cual contiene librerias para la conexión.
En mi caso, lo implementé en una INTRANET usando XAMPP, cualquier duda o comentario hazlo saber o comunicate conmigo.
Saludos y suerte.
Este sería el código del archivo PHP donde llamarias a la funcion RFC de SAP …en mi caso:
<html>
<body>
<h1>CONEXIÓN SAP_PHP</h1>
<?PHP
// aqui en esta parte incluyes el archivo donde tendras las librerias que pondré más aabajo
require_once("saprfc.php");
// Create saprfc-instance
$sap = new saprfc(array(
"logindata"=>array(
"ASHOST"=>"10.10.10.10" // application server
,"SYSNR"=>"Numero de sistema" / system number
,"CLIENT"=>"Cliente" // client
,"USER"=>"USUARIO DE ACCESO A SAP" // user
,"PASSWD"=>"Password" // password
)
,"show_errors"=>false // let class printout errors
,"debug"=>false)) ; // detailed debugging information
// Call-Function
$result=$sap->callFunction("NOMBRE_DE_TU_FUNCION",
array( array("IMPORT","EL_NOMBRE_DEL_IMPORT_DE_TU_FUNCION","*"),
array("TABLE","TABLE_DE_TU_FUNCION",array())
));
// Si se realizo el llamado a la funcion correctamente
if ($sap->getStatus() == SAPRFC_OK)
{
// Entonces imprimes tus resultados....
?><table>
<tr>
<td>Nombre</td>
<td>Numero De Usuario</td>
</tr>
<?PHP
foreach ($result["USER_DISPLAY_TAB"] as $user)
{
echo "<tr>
<td>", $user["SAPNAM"],"</td><td>",$user["USRNO"],"</td> //Elementos o Campos de tu estructura o tabla
</tr>";
}
?></table><?PHP
}
else
{
// Si no se realizo la conexión a la funcion RFC
$sap->printStatus();
// Imprimes el mensaje de error
// $sap->getStatusText() or $sap->getStatusTextLong()
}
// Logoff/Cerrar SAP RFC
$sap->logoff();
?>
</body>
</html>
Y este seria tu archivo saprfc.php donde contendrías las librerias…y lo incluirás en el codigo anterior que te pase…
<?PHP
// For easy checking of BAPI-type values
if (!defined("SAPRFC_OK")) define("SAPRFC_OK",0);
if (!defined("SAPRFC_ERROR")) define("SAPRFC_ERROR",1);
if (!defined("SAPRFC_APPL_ERROR")) define ("SAPRFC_APPL_ERROR",2);
class saprfc {
var $logindata;
var $rfc_conn;
var $func_id;
var $show_status_flag;
var $check_bapi_errors;
var $status;
var $status_infos;
var $debug;
var $call_function_result;
function saprfc($config=array()) {
$this->rfc_conn=false;
$this->func_id=false;
$this->show_status_flag=isset($config["show_errors"]) ? $config["show_errors"] : true;
$this->check_bapi_errors=isset($config["check_bapi_errors"]) ? $config["check_bapi_errors"] : false;
$this->status="";
$this->status_infos="";
$this->debug=isset($config["debug"]) ? $config["debug"] : false;
$this->logindata=isset($config["logindata"])?$config["logindata"]:array();
$this->call_function_result=false; // Result of the last executed sapaccess-call_function()
}
function setLoginData($logindata) {
$this->logindata=$logindata;
}
// TODO: currently only login with logindata allowed
// that means you have to set logindata for the class on creation
// maybe we can use setcookie ("SAPRFC_LOGON", urlencode(serialize($this->logindata)),time()+7200);
function login() {
if (!$this->rfc_conn)
{
$this->rfc_conn=@saprfc_open($this->logindata);
if (!$this->rfc_conn) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::login()\nOpen RFC connection with saprfc_open() failed with error:\n".@saprfc_error());
}
}
return SAPRFC_OK;
}
// Close RFC_Connection
function logoff() {
if ($this->rfc_conn)
{
@saprfc_close($this->rfc_conn);
}
}
// set Status and optionally show Errors
function setStatus($status,$status_infos) {
$this->status=$status;
$this->status_infos=$status_infos;
if ($this->show_status_flag &&
$this->status!=SAPRFC_OK ) {
$this->printStatus();
}
return $this->status;
}
// Checks if last Call succeded
function getStatus() {
return $this->status;
}
// Returns actual Status/Error
function getStatusText() {
$statustext="";
switch ($this->status) {
case SAPRFC_OK:
$statustext=$this->status_infos;
break;
case SAPRFC_APPL_ERROR:
$statustext=$this->status_infos["TYPE"]." ".$this->status_infos["ID"]."-".$this->status_infos["NUMBER"].": ".$this->status_infos["MESSAGE"];
break;
case SAPRFC_ERROR:
$statustext=$this->status_infos;
break;
}
return $statustext;
}
// Returns actual Status/Error
function getStatusTextLong() {
$statustext="";
switch ($this->status) {
case SAPRFC_OK:
$statustext.="<br><font size=4 color=green><pre>";
$statustext.="No errors detected.";
$statustext.="</font><br><font size=3 color=green><pre>";
$statustext.="<br><b>".$this->getStatusText()."</b>";
$statustext.="</pre></font>";
break;
case SAPRFC_APPL_ERROR:
$statustext.="<br><font size=4 color=red><pre>";
$statustext.="Application-Errors found during BAPI-Calls:";
$statustext.="</font><br><font size=3 color=red><pre>";
$statustext.="<br><b>".$this->getStatusText()."</b>";
$statustext.="</pre></font>";
break;
case SAPRFC_ERROR:
$statustext.="<br><font size=4 color=red><pre>";
$statustext.="Errors found during saprfc-Calls:";
$statustext.="</font><br><font size=3 color=red><pre>";
$statustext.="<br><b>".$this->getStatusText()."</b>";
$statustext.="</pre></font>";
break;
}
return $statustext;
}
function printStatus() {
echo $this->getStatusTextLong();
}
// Call RFC-Function in SAP
function callFunction($func_name="",$parameters) {
/* typical call:
$result=$saprfc->call_function("RFC_SYSTEM_INFO",
array( array("EXPORT","SYSTEM","MBS")
array("IMPORT","CODEPAGE")
array("IMPORT","DBNAME")
array("TABLE","APPLLIST",array())
)
);
*/
// Initialize Variables
$result_data=array();
$this->call_function_result=false;
// Check SAPRFC-Installation
if (! extension_loaded ("saprfc")) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction()\n SAPRFC-Extension.dll not loaded.");
}
// Validate given data
if (empty($func_name)) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction():\n No Function-Name given");
}
// Move Parameters to local Arrays
$func_params_import=array();
$func_params_tables=array();
$func_params_export=array();
foreach ($parameters as $key => $param) {
$type=$param[0];
$name=$param[1];
$value=isset($param[2])?$param[2]:"";
switch ($type) {
case "IMPORT":
$func_params_import[$name]=$value;
break;
case "EXPORT":
$func_params_export[$name]="";
break;
case "TABLE":
$func_params_tables[$name]=$value;
if (!is_array($value)) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction()\n Wrong Parameter-Value for Table-Parameter ".$name.". We expected an Array.");
}
break;
default:
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction()\n Wrong Parameter-Type '".$type."'. Must be IMPORT, EXPORT or TABLE.");
}
}
// Do Login (only done in method login(), if necessary)
if ($this->login()==SAPRFC_ERROR) {
return $this->getStatus();
}
// Discover Function in SAP
$this->func_id=@saprfc_function_discover($this->rfc_conn,$func_name);
if (!$this->func_id) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction()\n Function module '".$func_name."' seems not to exist. function saprfc_function_discover() failed.");
}
// Set Import-Parameters
foreach ($func_params_import as $name => $value) {
$rc=@saprfc_import($this->func_id,$name,$value);
if (empty($rc)) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction('".$func_name."')\n Import-Parameter=".$name. " could not be set. (Does it exist?)");
}
}
// Set Table-Parameters (importing-values)
foreach ($func_params_tables as $name => $value) {
$rc=@saprfc_table_init($this->func_id,$name);
if (empty($rc)) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction('".$func_name."')\n Table-Parameter=".$name. " could not be set. (Does it exist?)");
}
foreach ($value as $key => $data) {
@saprfc_table_append($this->func_id,$name,$data);
}
}
// Execute Function
$result = @saprfc_call_and_receive ($this->func_id);
if ($result != SAPRFC_OK)
{
if ($result == SAPRFC_EXCEPTION ) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction('".$func_name."')\n saprfc_call_and_receive(): Exception raised: ".@saprfc_exception($this->func_id));
} else {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction('".$func_name."')\n saprfc_call_and_receive(): Call error: ".@saprfc_error($this->func_id));
}
}
// Get Exporting-Parameters
foreach ($func_params_export as $name =>$value) {
$rc=@saprfc_export($this->func_id,$name);
// if (empty($rc)) { // llaegner removed (Reason: when export returns the -good- value "0", then empty also evaluates to true (thanks Alexander Gouriev)
if (!isset($rc)) {
return $this->setStatus(SAPRFC_ERROR,"saprfc::callFunction('".$func_name."')\n Export-Parameter=".$name. " could not be set (Does it exist?)".@saprfc_error($this->func_id));
} else {
$result_data[$name]=$rc;
}
}
// Get Table-Parameters
foreach ($func_params_tables as $name => $content) {
// Ausgabe-Tabelle initialisieren
$result_data[$name]=array();
$rows=@saprfc_table_rows($this->func_id,$name);
for ($i=1; $i<=$rows; $i++)
{
$result_data[$name][$i]=@saprfc_table_read ($this->func_id,$name,$i);
}
}
// Save function-call result for later analysis
$this->call_function_result=$result_data;
// Echo Debug-Information, if flagged
if ($this->debug)
@saprfc_function_debug_info($this->func_id);
// Falls es ein BAPI-Aufruf ist, Fehler raussuchen
if ($this->check_bapi_errors) {
$bapi_return=@saprfc_export($this->func_id,"RETURN");
if (isset($bapi_return) &&
is_array($bapi_return) &&
isset($bapi_return["MESSAGE"]) &&
$bapi_return["NUMBER"] != 0) {
// FINISH FUNCTION-CALL
$this->setStatus(SAPRFC_APPL_ERROR,$bapi_return);
return $result_data;
}
}
// Close Function-Execution and free results removed because it sometimes stops completly executing PHP!!
//@saprfc_function_free($this->func_id);
// FINISH FUNCTION-CALL
$this->setStatus(SAPRFC_OK,"call function '".$func_name."' successfull.");
return $result_data;
}
}
?>
Si van a compartir muchas lineas de código, me parece mejor que usen https://gist.github.com/
Donde podrían hasta “folkear-se” entre ustedes y pegan aquí directamente la URL del GIST, y queda compartida en el tema
Volviendo al tema.
No les sirve esto?
Gracias…haré uso de ello¡¡¡ saludos
Una disculpa de antemano por haberme ausentado de este tópico fue por razones laborales, les comento aun sigo sin poder realizar dicha conexión pero el fin me dare la tarea de crear una maquina virtual para ahí montarle lo necesario en SO Linux con estas características kernel 2.6.25.18-0.2-pae i686.
Ya que al parecer todo esta mas orientada a hacerlo dentro de ese sistema. Agradecerles a todos por sus comentarios.
Gracias @marciano por lo que comentas, aquí el tema es que el sistema vive sea creo y ya está implementado en PHP y ahora lo que quieren hacer es darle ese plus con la interconexión a SAP, seria volver a reprogramar todo a JAVA EE y montar los JCO que como bien dices es lo mas idóneo y por WS pues que te digo así lo trabajamos en su momento en su momento en el INFONAVIT pero este cliente es nuevo y se aferró a hacer todo desde PHP y ahora si que al cliente lo que pida, pero de todos modos muchas gracias.
@iespino gracias por tus comentarios en la VM que cree me apegare a usar el XAMPP, nadamas tengo una duda en que S.O. montaste el XAMPP ?
E igualmente @Shadowdancer y @SidV como siempre respondiendo, sus guías me va a ayudar a terminar esta encrucijada que al final tiene que salir si o si
Muchas muchas gracias.
Saludos.
Y has investigado si SAP comparte Web-Services para consumirlos?. Yo no se mucho del tema pero aqui donde laboro lo poco que conozco es que SAP lo único que entrega son archivos de texto, supongo usando ABAP para alimentar otros sistemas…
El sistema operativo donde monte el XAMPP fue Windows Server 2008
No estimado con la librería nunca se pudo, lo que se hizo puros consumos de wsdl para la extracción de información. Pero pues solo así se pudo
Lo que pasa es que yo lo logré hacer en 2 servidores con windows server 2008, y estoy tratando de implementar en un windows server 2016 y es en el que me da ese error, no se si sea el lenguaje. Ya cambie el SAP Logon, y tampoco. Alguien del grupo @abapers sabe sobre el tema?
Buen día, tengo varios semanas tratando de instalar el php_saprfc_php5.6_ts en windows 2008 x64 y no se puede, alguien pudo con esto?, seguí todos los pasos y nada
te sale algún mensaje de error? tienes que buscar el dll correcto para tu versión de apache. que versión tienes?
Version de Apache/2.4.26 (Win32) OpenSSL/1.0.2l PHP/5.6.31
Puedes intentar con el php_saprfc_PHP5.6_x86_ts.dll para ver si te funciona, o que error te manda? crea un archivo php:
<?php
phpinfo();
?>
Para verificar que este activo el dll de saprfc.
@Alvan1 esto hice yo hace algunos meses, lo estoy usando full
Hoy por razones de compatibilidad con otros sistemas tuve que deupgradear a Xampp 5.6 e hice lo mismo y funcionó perfecto. Esto aplica a HANA, pero también se puede hacer parecido con SQL Server.
Saludos,
David
Buen día.
Reactivando nuevamente el tema de la conexión con PHP y SAP, Les comento que estoy tratando de conectar php7 con SAP, y me encontré una guía paso a paso la cual he seguido sin obtener éxito, continuo con mis pruebas, si alguien logra hacerlo funcionar favor de compartir.
Les comento que tengo SAP LOGO 720
1. XAMPP Versión 7.2.4-0
2. PHP Version 7.2.4
3. Apache/2.4.33 (Win32)
h_tps://gkralik.github.io/php7-sapnwrfc/installation.html
Bueno acá tu tema es:
- ¿Que tipo de BD usa SAP LOGO? De ser SQL no deberías tener problema más que la configuración de tu ODBC
Para esto:
h_tps://docs.microsoft.com/en-us/sql/connect/php/loading-the-php-sql-driver?view=sql-server-2017
h_tps://social.msdn.microsoft.com/Forums/es-ES/4ca96d4c-c706-4380-8929-7154b1889420/error-al-configurar-php-7-para-conexion-con-sql-server-2008?forum=sqlserveres
Después cheque el Manual que hice y veas tu configuración de php.ini es super importante que puedas configurar bien la extensión del odbc o del pdo_odbc
Estoy preparando un pequeño tutorial para lograr conexiones PHP con SQL Server…
Saludos,
David
PD: Yo no pude usar ese manual porque no tengo acceso al Centro de Software de SAP.
Otro buen Manual:
h_tp://www.ingdiaz.org/conectarse-microsoft-sql-server-desde-php-7-drivers-php-sql-server/