Skocz do zawartości
gregoriii

webservice - modyfikacja z XMLRPC na NuSoap

Polecane posty

Potrzebuję pomocy przy modyfikacji webservice z XMLRPC(użytego w forum) na Nusoapa.

W tej chwili testowo przygotowałem działające funkcje oparte na NuSoap (spakowany załącznik - wszystkie pliki, które wrzucam do wybranego katalogu "moje_forum\interface\nusoap\"), podgląd przez www funkcji http://localhost/mojeforum/interface/nusoap/index.php, widok WSDL http://localhost/mojeforum/interface/nusoap/index.php?wsdl . Plik index.php jest serwerem.

Aby sprawdzić poprawność działa nie pisałem klienta tylko używam programu soapUI (można pobrać wersje darmową z strony http://www.soapui.org/).

Po zainstalowaniu programu tworzymy nowy projekt i dajemy linka do naszego serwera, pliku (http://localhost/mojeforum/interface/nusoap/index.php?wsdl) z rozszerzeniem WSDL, testuje lokalnie. Po załadowaniu projektu widzimy wszystkie funkcje, odpalamy np "hello" -> "Request 1" - w miejscu "?" wpisujemy jakiegoś dowolnego "stringa(np.: dziala)" , następnie odpalamy strzałkę zieloną i mamy wynik jakim jest "Hello dziala".

Potrzebuję pomocy przy modyfikacji funkcji zawartych/napisanych standardowo w pliku \interface\board\modules\ipb\api.php, plik wrzuciłem do katalogu/załącznika u mnie lokalizacja \interface\nusoap\apis\server_api.php.

Będę chciał aby mieć funkcję:

- sprawdzania czy dany użytkownik istnieje,

- rejestracja nowego użytkownika(pomijając rejestrację która jest standardowa na forum)

- aktualizacja danych podstawowych,

- usuwanie użytkownika,

- itp.

Cel : celem jest aby była jedna "rejestracja" z jednego dowolnego miejsca do kilku serwisów jednocześnie.

Nie wrzucam kodu plików - są w załączniku(poniżej tylko server nusoap).

PS. W jednej z funkcji użyłem połączenia z bazą mysql, testowe - sprawdzenie poprawności działania, chciałbym aby wszystkie połączenia z bazą, metody, funkcje które są możliwe były zgodne z formą jaką jest pisane forum.

Koda servera nusoap poniżej, potrzebuje tutaj wrzucić odpowiednio zmodyfikowane funkcje (i odpowiednie rejestracje ich $server->register(....) )


<?php

require_once("lib/nusoap.php");


class gsSopaTest {

	function Test1() {

		$server = new nusoap_server();

		$server->soap_defencoding = 'UTF-8';

		$server->xml_encoding = 'UTF-8';

		$namespace = "http://www.my-service.pl/wsdl";

		$server->configureWSDL("gsForumWsdl", $namespace);

		$server->wsdl->schemaTargetNamespace = $namespace;

		$server->debug_flag = false;


		/*** function hello ***/

		$server->register(

                // method name:

                'hello', 	

                // parameter list:

                array('name'=>'xsd:string'), 

                // return value(s):

                array('return'=>'xsd:string'),

                // namespace:

                $namespace,

                // soapaction: (use default)

                false,

                // style: rpc or document

                'rpc',

                // use: encoded or literal

                'encoded',

                // description: documentation for the method

                'Simple Hello World Method');



		/*** function HelloComplexWorld ***/

		//Register our method using the complex type

		$server->register(

						// method name:

						'HelloComplexWorld', 	

						// parameter list:

						array('name'=>'tns:MyComplexType'), 

						// return value(s):

						array('return'=>'tns:MyComplexType'),

						// namespace:

						$namespace,

						// soapaction: (use default)

						false,

						// style: rpc or document

						'rpc',

						// use: encoded or literal

						'encoded',

						// description: documentation for the method

						'Complex Hello World Method');


		//Create a complex type

		$server->wsdl->addComplexType('MyComplexType','complexType','struct','all','',

				array( 'ID' => array('name' => 'ID','type' => 'xsd:int'),

					   'YourName' => array('name' => 'YourName','type' => 'xsd:string')));				



		/*** function sum ***/			

		$server->register('sum',

			array('a' => 'xsd:int', 'b' => 'xsd:int'),

			array('c' => 'xsd:int'),

			$namespace);	


		/*** function getMembersFromEmail ***/	

		// add complex type

		$server->wsdl->addComplexType(

			'MembersData',

			'complexType',

			'struct',

			'all',

			'',

			array(

				'member_group_id' => array('name'=>'member_group_id', 'type'=>'xsd:string'), 

				'name' => array('name'=>'name', 'type'=>'xsd:string'))

		);


		// register method

		$server->register('getMembersFromEmail', 

			array('email' => 'xsd:string'), 

			array('return'=>'tns:MembersData'), 

			$namespace

		);



		$server->register('taxcalc', 

			array ('amount' => 'xsd:int'), 

			array ('return' => 'xsd:int'), 

			$namespace);


		$server->register('CalculateOntarioTax',

			array('amount' => 'xsd:int'),

			array('return' => 'xsd:int'),

			$namespace);	




		/****************************************************************/				

		/*** function hello ***/

		function hello($name)

		{

			return "Hello " . $name;

		}


		/*** function HelloComplexWorld ***/

		//Our complex method

		function HelloComplexWorld($mycomplextype)

		{

			return $mycomplextype;	

		}	


		/*** function sum ***/

		function sum($a, $B) {

			return ($a + $B);

		}


		/*** function getMembersFromEmail ***/

		// method code (get DB result)

		function getMembersFromEmail ($a_stInput) {

			if (is_string($a_stInput)) {   

				$l_oDBlink   = @mysql_connect('localhost', 'root', 'vertrigo');

				$l_oDBresult = @mysql_db_query(

					'forum01', 

					'SELECT member_group_id, name FROM members WHERE email = LCASE("' . mysql_escape_string((string)$a_stInput) . '") LIMIT 1');


				// simple error checking

				if (!$l_oDBresult) {

					return new soap_fault('Server', '', 'Internal server error.');

				}


				// no data avaible for x email

				if (!mysql_num_rows($l_oDBresult)) {

					return new soap_fault('Server', '', 'Service contains data only for a few email.');

				}

				mysql_close($l_oDBlink);


				// return data

				return mysql_fetch_array($l_oDBresult, MYSQL_ASSOC);    

			} 

			// we accept only a string

			else {

			  return new soap_fault('Client', '', 'Service requires a string parameter.');

			}

		}




		function taxcalc($amount) { 

			$calc=$amount * .08; 

			//return new soapval('return','string',$calc); 

			return $calc;

		} 



		function CalculateOntarioTax($amount){

		   $taxcalc=$amount*.15;

		   //return new soapval('return','int',$taxcalc);

		   return $taxcalc;

		}



		/***********************************************/

		/***********************************************/

		$server->decode_utf8  = false;

		// Get our posted data if the service is being consumed

		// otherwise leave this data blank. 

		//$HTTP_RAW_POST_DATA = isset($HTTP_RAW_POST_DATA) ? $HTTP_RAW_POST_DATA : '';

		$HTTP_RAW_POST_DATA = isset($GLOBALS['HTTP_RAW_POST_DATA']) ? $GLOBALS['HTTP_RAW_POST_DATA'] : '';

		// pass our posted data (or nothing) to the soap service  

		$server->service($HTTP_RAW_POST_DATA);

		exit();




	}






}

?>

nusoap.zip

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

Skoro chcesz rejestrację, to nie lepiej użyć IP.Converge ? w bardzo prosty sposób tutaj będziesz mógł połączyć wszystkie skrypty z forum

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

Skoro chcesz rejestrację, to nie lepiej użyć IP.Converge ? w bardzo prosty sposób tutaj będziesz mógł połączyć wszystkie skrypty z forum

Nie chcę używać IP.Converge, zależy mi implementacji webservice z użyciem NuSoap.

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

Ok, to w takim razie w czym dokładnie oczekujesz pomocy :) bo chyba nie w tym, że ktoś napisze za Ciebie całą integrację?

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

Ok, to w takim razie w czym dokładnie oczekujesz pomocy :) bo chyba nie w tym, że ktoś napisze za Ciebie całą integrację?

Oczywiście że nie cała.

Chodzi mi o to aby uruchomić jakąś jedną funkcjonalność (np: sprawdzenie czy użytkownik istnieje (checkMemberExists) lub utworzenie nowego użytkownika (create_user_account)), implementując odpowiednio kod w pliku gsSoapTest.php ( rejestrując metodę np: $server->register(name: 'checkMemberExists', ... ); i tworząc funkcję do niej function checkMemberExists (...) { ... }). Nie jest to mało, a dla Mnie to było by bardzo dużo, poznaje całe forum i uczę się powoli programowania.

W pliku gsSoapTest.php zrobiłem działającą funkcję function getMembersFromEmail ($a_stInput) {...} , używając połączenia takiego jakiego nie chciałbym, tylko używając z IPB i tu u mnie jest problem aby odpowiednio zaimplementować dostęp do bazy (połączenie (głównie używam bazy mssql, a testowo lokalnie mysql), wyciągnięcie danych, obróbka ich).

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

Ok, nie znam nusoap jeszcze do tego jest w php4 :/ ale coś postaram się pomóc.

W gsSoapTest.php musisz zarejestrować nową usługę:


$server->register(
// method name:
'checkMemberExists',
// parameter list:
array('name'=>'xsd:string'),
// return value(s):
array('return'=>'xsd:string'),
// namespace:
$namespace,
// soapaction: (use default)
false,
// style: rpc or document
'rpc',
// use: encoded or literal
'encoded',
// description: documentation for the method
'Simple Hello World Method');[/code] Zamień:
[code]class gsSopaTest {
na:

class gsSopaTest {

var $registry;

function gsSopaTest($registry)
{
$this->registry = $registry;
}[/code] następnie utwórz metodę:
[code]

function checkMemberExists($email)
{
$email_check = $this->registry->DB()->buildAndFetch( array( 'select' => 'member_id', 'from' => 'members', 'where' => "email='".$email."'" ) );

return $email_check['member_id'] ? 'Użytkownik istnieje' : 'Brak użytkownika';
}
następnie w index.php zamień:

$so = new gsSopaTest();
[/code] na:
[code]
$so = new gsSopaTest($registry);

Przypuszczam, że da się to jeszcze inaczej zrobić, ale dobrze by było, jakbyś użył jakiejś biblioteki w php5 też :)

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

wprowadzając zmiany mam błąd:

Fatal error: Using $this when not in object context in D:\Program Files (x86)\...\gsSoapTest.php on line 125

odnosi się do linii:

$email_check = $this->registry->DB()->buildAndFetch( array( 'select' => 'member_id', 'from' => 'members', 'where' => "email='".$email."'" ) );

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

a spróbuj zamienić:

function gsSopaTest($registry)
{
$this->registry = $registry;
}[/code] na:
[code]
function __construct($registry)
{
$this->registry = $registry;
}

Jeśli będzie to samo to trzeba posprawdzać z tym przekazywaniem $registry czy coś się nie zwaliło :/

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

po zmianie jest ten sam błąd :(

Jeśli chcesz to zainstaluj SoapUI, będziesz mógł zobaczyć jak to działa(client).

Edytowano przez gregoriii

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

no to musisz sobie zdebugować, gdzie ginie informacja. Chyba, że do konstruktora nie przekazujesz obiektu ipsRegistry :)

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

no to musisz sobie zdebugować, gdzie ginie informacja. Chyba, że do konstruktora nie przekazujesz obiektu ipsRegistry :)

problem jest z tym że mając taką strukturę wywala się, bo w funkcji mam funkcje, cały plik poniżej (gsSoapTest.php)

class gsSopaTest { 

  //...

  //mam 

  function Test1() { 

  // ...

    //a w niej funkcje konkretnie odpowiadające za dane działanie 

    function checkMemberExists($email) {

    ...

    }

    function checkExists($test) {

    ...

    }

  }

}
testowo dla sprawdzenia czy działa jakaś funkcja sprawdziłem wywołanie w pliku index
$so = new gsSopaTest($registry);

$so->UpdateMember();
wywołanie z:

<?php


class gsSopaTest {


	var $registry;

	function __construct( ipsRegistry $registry )

	{


		$this->registry = $registry;

		$this->DB       = $this->registry->DB();

	}


	function UpdateMember()

	{

		$this->DB->update( 'members',	array( 'allow_admin_mails' => 0 ), "member_id=1" );


	}


}

?>

działa update poprawnie. Jak musiałbym poprawić w poniższym kodzie (plik gsSoapTest.php) wywołując go w index.php
require_once ('gsSoapTest.php');

$so = new gsSopaTest($registry);

$so->Test1();
gsSoapTest.php

<?php

require_once("lib/nusoap.php");


class gsSopaTest {


    var $registry;

    function __construct( ipsRegistry $registry )

		{	

			$this->registry = $registry;

			$this->DB       = $this->registry->DB();

			$this->settings =& $this->registry->fetchSettings();

			$this->request  =& $this->registry->fetchRequest();

		}



	function Test1() {

		$server = new nusoap_server();

		$server->soap_defencoding = 'UTF-8';

		$server->xml_encoding = 'UTF-8';

		$namespace = "http://www.my-service.pl/wsdl";

		$server->configureWSDL("gsForumWsdl", $namespace);

		$server->wsdl->schemaTargetNamespace = $namespace;

		$server->debug_flag = false;




		$server->register(

                // method name:

                'checkMemberExists',    

                // parameter list:

                array('name'=>'xsd:string'), 

                // return value(s):

                array('return'=>'xsd:string'),

                // namespace:

                $namespace,

                // soapaction: (use default)

                false,

                // style: rpc or document

                'rpc',

                // use: encoded or literal

                'encoded',

                // description: documentation for the method

                'Simple Hello World Method');



		/*** function HelloComplexWorld ***/

		//Register our method using the complex type

		$server->register(

						// method name:

						'HelloComplexWorld', 	

						// parameter list:

						array('name'=>'tns:MyComplexType'), 

						// return value(s):

						array('return'=>'tns:MyComplexType'),

						// namespace:

						$namespace,

						// soapaction: (use default)

						false,

						// style: rpc or document

						'rpc',

						// use: encoded or literal

						'encoded',

						// description: documentation for the method

						'Complex Hello World Method');


		//Create a complex type

		$server->wsdl->addComplexType('MyComplexType','complexType','struct','all','',

				array( 'ID' => array('name' => 'ID','type' => 'xsd:int'),

					   'YourName' => array('name' => 'YourName','type' => 'xsd:string')));				








		/****************************************************************/

        function checkMemberExists($email)

		{	

			//$this->DB->update( 'members',	array( 'allow_admin_mails' => 0 ), "member_id=1" );

			//$this->DB->update( 'members',	array( 'allow_admin_mails' => 1 ), "member_id='".$email."'" );

			$email_check = $this->registry->DB()->buildAndFetch( array( 'select' => 'member_id', 'from' => 'members', 'where' => "email='".$email."'" ) );

			return $email_check['member_id'] ? 'Użytkownik istnieje' : 'Brak użytkownika';

		}


		function HelloComplexWorld($mycomplextype)

		{

			return $mycomplextype;	

		}	







		/***********************************************/

		/***********************************************/

		$server->decode_utf8  = false;

		// Get our posted data if the service is being consumed

		// otherwise leave this data blank. 

		//$HTTP_RAW_POST_DATA = isset($HTTP_RAW_POST_DATA) ? $HTTP_RAW_POST_DATA : '';

		$HTTP_RAW_POST_DATA = isset($GLOBALS['HTTP_RAW_POST_DATA']) ? $GLOBALS['HTTP_RAW_POST_DATA'] : '';

		// pass our posted data (or nothing) to the soap service  

		$server->service($HTTP_RAW_POST_DATA);

		exit();




	}




}

?>

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

a spróbuj wywalić te funkcje z body tej metody i dać je poza nią, może to coś zmieni

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

a spróbuj wywalić te funkcje z body tej metody i dać je poza nią, może to coś zmieni

funkcje (function checkMemberExists($email), function HelloComplexWorld($mycomplextype)) muszą się znajdować w function Test1() {...} lub poza class gsSopaTest {...} bo nie działa poprawnie serwer Nusopa (mam błąd "method 'HelloComplexWorld'('HelloComplexWorld') not defined in service('' '')" )

Pytanie, dlaczego mając poniższy kod, wywołując function checkMemberExists() nie zwraca mi wartości przez return tylko jak dałem echo to widzę wynik


<?php


class gsSopaTest {


	var $registry;

	function __construct( ipsRegistry $registry )

	{	

		$this->registry = $registry;

		$this->DB       = $this->registry->DB();

	}



	function checkMemberExists()

	{

		$email_check = $this->registry->DB()->buildAndFetch( array( 'select' => 'member_id', 'from' => 'members', 'where' => "email='test01@test01.pl'" ) );

		$this->email_check['member_id'] = $email_check['member_id'];

		echo $email_check['member_id'];


		return $email_check['member_id'] ? 'Użytkownik istnieje' : 'Brak użytkownika';

		//return $email_check['member_id'];	


	}

}

?>

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

a masz jakiś błąd przy tym returnie ? a spróbuj dać

zamiast

return $email_check['member_id'] ? 'Użytkownik istnieje' : 'Brak użytkownika';
[/code] coś takiego:
[code]
return (string) ($email_check['member_id'] ? 'Użytkownik istnieje' : 'Brak użytkownika');

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

ale co nadal: Fatal error: Using $this when not in object context in ?? bo można zrobić jeszcze trochę inaczej, że w tej metodzie stworzysz obiekt ipsRegistry tylko, że wtedy będzie trzeba za każdym razem w metodach tworzyć ten obiekt

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

ale co nadal: Fatal error: Using $this when not in object context in ?? bo można zrobić jeszcze trochę inaczej, że w tej metodzie stworzysz obiekt ipsRegistry tylko, że wtedy będzie trzeba za każdym razem w metodach tworzyć ten obiekt

tak ten sam (Fatal error: Using $this when not in object context in)

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

no to cofnij te zmiany z przekazywaniem $registry i stwórz obiekt ipsRegistry w tej metodzie. Innej metody chyba nie ma

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

Udało się, zmodyfikowałem, wrzuciłem do jednego pliku całość. Poprawnie działając testowy przykład poniżej.

Pytanko, użyłem w kodzie "global $test;" , jak mogę zmienić, aby nie używać global, chciałbym uniknąć tego typu w dostępie.


<?php

define( 'IPB_THIS_SCRIPT', 'api' );

define( 'IPB_LOAD_SQL'   , 'queries' );


/**

* Matches IP address of requesting API

* Set to 0 to not match with IP address

*/

define( 'CVG_IP_MATCH', 1 );


require_once( '../../initdata.php' );


//===========================================================================

// MAIN PROGRAM

//===========================================================================


define( 'IPS_CLASS_PATH', IPS_ROOT_PATH . 'sources/classes/' );


require_once( IPS_ROOT_PATH . 'sources/base/ipsRegistry.php' );

require_once( IPS_ROOT_PATH . 'sources/base/ipsController.php' );


//-----------------------------------------

// Set up cookie stuff

//-----------------------------------------


$registry = ipsRegistry::instance();

$registry->init();


IPSCookie::$sensitive_cookies = array( 'session_id', 'ipb_admin_session_id', 'member_id', 'pass_hash' );


//--------------------------------

//  Set up our vars

//--------------------------------


$registry->DB()->obj['use_shutdown'] = 0;


//--------------------------------

// Set debug mode

//--------------------------------


$registry->DB()->setDebugMode( ipsRegistry::$settings['sql_debug'] == 1 ? intval($_GET['debug']) : 0 );



require_once("lib/nusoap.php");


$test= new gsSopaTest($registry);

$server = new nusoap_server();

$server->soap_defencoding = 'UTF-8';

$server->xml_encoding = 'UTF-8';

$namespace = "http://www.my-service.pl/wsdl";

$server->configureWSDL("gsForumWsdl", $namespace);

$server->wsdl->schemaTargetNamespace = $namespace;

$server->debug_flag = false;


/*** Registry  method *********************/

$server->register(

	// method name:

	'checkMemberExists',    

	// parameter list:

	array('name'=>'xsd:string'), 

	// return value(s):

	array('return'=>'xsd:string'),

	// namespace:

	$namespace,

	// soapaction: (use default)

	false,

	// style: rpc or document

	'rpc',

	// use: encoded or literal

	'encoded',

	// description: documentation for the method

	'Simple Hello World Method');



/*** function HelloComplexWorld ***/

//Register our method using the complex type

$server->register(

	// method name:

	'HelloComplexWorld', 	

	// parameter list:

	array('name'=>'tns:MyComplexType'), 

	// return value(s):

	array('return'=>'tns:MyComplexType'),

	// namespace:

	$namespace,

	// soapaction: (use default)

	false,

	// style: rpc or document

	'rpc',

	// use: encoded or literal

	'encoded',

	// description: documentation for the method

	'Complex Hello World Method');


//Create a complex type

$server->wsdl->addComplexType('MyComplexType','complexType','struct','all','',

    array( 'ID' => array('name' => 'ID','type' => 'xsd:int'),

   'YourName' => array('name' => 'YourName','type' => 'xsd:string')));				






/****************************************************************/


function checkMemberExists($email)

{	

	global $test;

	return $test->checkMemberExists_zKlasy($email);

}



function HelloComplexWorld($mycomplextype)

{

	global $test;

	return $test->HelloComplexWorld($mycomplextype);	

}	


function test() {

	global $test;

	return $test->test();

}



/***********************************************/

$server->decode_utf8  = false;

// Get our posted data if the service is being consumed

// otherwise leave this data blank. 

$HTTP_RAW_POST_DATA = isset($GLOBALS['HTTP_RAW_POST_DATA']) ? $GLOBALS['HTTP_RAW_POST_DATA'] : '';

// pass our posted data (or nothing) to the soap service  

$server->service($HTTP_RAW_POST_DATA);

exit();




class gsSopaTest {


    var $registry;


	function __construct( ipsRegistry $registry )

		{	

			$this->registry = $registry;

			$this->DB       = $this->registry->DB();

			$this->settings =& $this->registry->fetchSettings();

			$this->request  =& $this->registry->fetchRequest();

		}


	function checkMemberExists_zKlasy($email)

		{	

			//$this->DB->update( 'members',	array( 'allow_admin_mails' => 1 ), "member_id='".$email."'" );

			$email_check = $this->registry->DB()->buildAndFetch( array( 'select' => 'member_id', 'from' => 'members', 'where' => "email='".$email."'" ) );

			return $email_check['member_id'] ? 'Użytkownik istnieje' : 'Brak użytkownika';

			//return $email_check['member_id'];

		}


	function HelloComplexWorld($mycomplextype)

		{

			return $mycomplextype;	

		}	


}


?>

Edytowano przez gregoriii

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

Jak dla mnie to już lepiej robić w każdej metodzie

$registry = ipsRegistry::instance();
$registry->init();
[/code]

Udostępnij ten post


Link to postu
Udostępnij na innych stronach

  • Kto przegląda   0 użytkowników

    Brak zalogowanych użytkowników przeglądających tę stronę.

×

Ważne informacje

Kontynuując przeglądanie strony, wyrażasz zgodę na używanie przez nas plików cookies.