<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>aip solutions developer's blog &#187; PHP</title>
	<atom:link href="http://blog.aip-solutions.com/tag/php/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.aip-solutions.com</link>
	<description>aip solutions developer's blog</description>
	<lastBuildDate>Thu, 15 Jul 2010 10:46:36 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Table abstraction with DList &#8211; part 1</title>
		<link>http://blog.aip-solutions.com/50/table-abstraction-with-dlist-patr-1/</link>
		<comments>http://blog.aip-solutions.com/50/table-abstraction-with-dlist-patr-1/#comments</comments>
		<pubDate>Tue, 10 Feb 2009 17:21:52 +0000</pubDate>
		<dc:creator>Peter Mihailov</dc:creator>
				<category><![CDATA[PHP]]></category>
		<category><![CDATA[class]]></category>
		<category><![CDATA[database abstraction]]></category>
		<category><![CDATA[DList]]></category>
		<category><![CDATA[lib]]></category>
		<category><![CDATA[server-side]]></category>
		<category><![CDATA[table]]></category>

		<guid isPermaLink="false">http://blog.aip-solutions.com/?p=50</guid>
		<description><![CDATA[It is well-known that programmers are lazy people. Thanks to this fact a lot of good stuff are written. The same is the story with DList. It starts on one sunny day near the old office of AIP Solutions. The server-side team of the company, represented by Me and Mr. Marin Todorov, decided to have [...]]]></description>
			<content:encoded><![CDATA[<p>It is well-known that programmers are lazy people. Thanks to this fact a lot of good stuff are written. The same is the story with DList. It starts on one sunny day near the old office of AIP Solutions. The server-side team of the company, represented by <a href="http://www.waynblog.com/" target="_blank">Me</a> and <a href="http://underplot.com/" target="_blank">Mr. Marin Todorov</a>, decided to have a lunch in the restaurant near the office. We was outside and the weather was so pleasant so we decided that it will be one very very long lunch. But we needed an excuse. Our idea was to say our colleagues that we had done some work. So we took a couple of napkins and started our software design work.</p>
<p>Ok I finished the introduction. So I&#8217;ll try to explain something about DList.</p>
<p>After we analysed our server-side programming work. We found that all the time we do the same. We add, edit and remove some items in database tables. Then we retrieve the content of those tables. So we decided to create a generic class which will implement all the stuff we need. It&#8217;s called DList (DataList). DList is an abstraction for list with items. The constructor of the class takes an object as an argument. The type of this object is &#8220;DListConf&#8221; (DList Configuration) or also known as DLC. The DLC object contains all the information DList needs to know about the table in database, which DList have to manage. After DList class is instantiated we have an object which implements so called DList interface. That means the object has this list of methods:</p>
<pre>DList|array static DList::Make('DLC Name [,DLC name1 ...]')
void  DList::setOrderMethod($orderString);
void  DList::setFilter($filterString);
void  DList::setPaging($pagingObject);
array DList::add($info)
void  DList::edit($Id, $info)
bool  DList::remove($Id)
array DList::getInfo($Id, $langId)
array DList::getList($langId)
array DList::getFullList($langId)
int   DList::getCount()</pre>
<p>When we have this methods we can do most ot our work without writing SQL queries. So this class provide some kind of database abstraction layer. It increases the level of predictability of the code written from any member of our team. And one very important thing, it saves time, a lot of time. Of course I&#8217;m not saying that everyting could be done with DList, but it does very good work in most of the cases.</p>
<p><strong>DList usage</strong></p>
<p>There are two ways for creating instance of DList. The classic approach with new keyword in PHP.</p>
<pre>$products = new DList($productsDLC);</pre>
<p>In this case $productsDLC is our DList Configuration  object and $products is the DList object.</p>
<p>If we need more DList objects, we can use the Make static method.</p>
<pre>list($products, $categories, $news) = DList::Make('productsDLC, categoriesDLC, newsDLC');</pre>
<p>In this example I use the Make method to create three DList objects at once. This method returns an array with DList objects inside. Make method has an other very useful feature, it automatically includes the files with DLC definitions. This files should be in <code>aip.conf</code> folder and its names should be like in this example: <code>productsDLC.php, categoriesDLC.php, newsDLC.php</code>.</p>
<p>Before I continue with DList features I&#8217;d like to write something more about DListConf or DLC. It is very important, because withour properly configured DLC you won&#8217;t have an operational DList object. DListConf is configuration container. Our convention is make DLC objects in files with the same name. For example:</p>
<pre>$productsDLC = DListConf('productsList');</pre>
<p>We create object called <code>$productsDLC</code> in a file called <code>productsDLC.php</code>. This is not required, but it makes things easy and clear and for the staff of AIP Solutions it is <strong>obligatory</strong>. Also this convention is required for static method <code>Make()</code>. The constructor of DListConf takes only one argument and it should be the name of the table in database, which Dlist should manage. This is an example of a real DLC file &#8211; <code>productsDLC.php</code>:</p>
<pre>$productsDLC = new DListConf('productsList'); 	<span>/* name of the table */</span>
$productsDLC-&gt;setLangCount(2);		 	<span>/* default:1 */</span>
$productsDLC-&gt;setTextKey('name'); 	  		<span>/* default:name */</span>
$productsDLC-&gt;setLangKey('langId');  	  	<span>/* default:langId, false for none */</span>
$productsDLC-&gt;setParentKey('parentId');  		<span>/* default:parentId, false for none */</span>
$productsDLC-&gt;setOrderMethod('orderId ASC'); 	<span>/* default:Id ASC */</span>

$productsDLC-&gt;addField('parentId', 'int');
$productsDLC-&gt;addField('imageId', 'int');
$productsDLC-&gt;addField('price', 'price');		<span>/* in DList we have standard datatype 'price' */</span>
$productsDLC-&gt;addField('descr', 'rtf');
$productsDLC-&gt;addField('abstract', 'rtf');
$productsDLC-&gt;addField('orderId', 'int');</pre>
<p>The first method in this example is <code>setLangCount(int $languageCount);</code>. We use this method to tell to DList that the data it will manage will be translated in 2 languages. In this case DList knows that for each item added to the table it has to make 2 records &#8211; one record for each language. In other words if you add 1 product into the database and you have <code>setLangCount(2);</code> in you <code>$productsDLC</code>, DList will insert 2 rows in <code>productsList</code> table.</p>
<p>The next method is <code>setTextKey(string $fieldName)</code>. This tells which field in the table can be defined as a &#8220;name&#8221; of the items saved in this table. In our case with <code>productsList</code> table we use the filed <code>name</code>, which is the name of the product. This parameter is used in <code>DList::getList()</code> method, which will be discussed later.</p>
<p>The other main method is <code>setLangKey(string fieldName)</code>. It shows which field in DB table should be used for storing the language ID of each record. So in our example this is <code>langId</code> field. Which means that if we add 1 product to the database DList will make 1 record with langId = 1 and 1 record with langId = 2.</p>
<p>The method <code>setParentKey(string fieldName)</code> also takes the name of a field in DB table as an argument. This field should be used when we need parent-child relation between two tables managed by DList. An example for this case is when we have products, which are grouped in different categories. So in products we make DB table field called <code>parentId</code> and use <code>setParentKey('parentId')</code>.Then when we have to add product we have to write its parent category ID in this field.</p>
<p>Method called <code>setOrderMethod(string $orderSqlString)</code> is used to set the default order of items recorded in the table. The parameter which method takes is the ORDER BY clause in SQL. But without ORDER BY at the begging. For example: <code>name ASC</code>. In this case when we retrieve a list of items from the table using <code>DList::getList()</code> or <code>DList::getFullList()</code> methods, the result will be ordered by product name in ascending sort.</p>
<p>The last method in our example is <code>addField(string $fieldName, string $dataType)</code>. We use this method for describing the fields in the table. Every field (well,there are some exceptions) in the DB table should be defined with this method. The first argument is the name of the field and the second argument is its data type. In fact we don&#8217;t use the standard data types in SQL. Dlist uses the following data types:<br />
<code>int, string, rtf, file, date, price, enum</code>. </p>
<p><code>int</code> type is for integer data &#8211; numbers</p>
<p><code>string</code> is used for strings. it is important that DList perform some operations on data defined as a string. It replaces the quotes and slashes with its HTML codes.</p>
<p><code>rtf</code> is like a string but DList doesn&#8217;t make any changes on the strings. It should be used for textareas with rich text formatted texts.</p>
<p><code>file</code> &#8211; this data type should be used when the information is file name.</p>
<p><code>date</code> &#8211; data type for storing dates.</p>
<p><code>price</code> &#8211; store decimal prices with this data type.</p>
<p><code>price</code> &#8211; it should be used for enum MySQL fields.</p>
<p>The fields that should not be defined with  <code>addField(string $fieldName, string $dataType)</code> method are fields defined as an <code>Text Key</code> and <code>Language Key</code> with <code>setTextKey()</code> and <code>setLangKey()</code> methods. In our example this are <code>name</code> and <code>langId</code> fields. In fact if some field is not defined in the DLC, Dlist will work well, but this field will stay &#8220;invisible&#8221; for the object. You will not be able to add, edit or even read the information in this field.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.aip-solutions.com/50/table-abstraction-with-dlist-patr-1/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>PayPal Integration</title>
		<link>http://blog.aip-solutions.com/5/paypal-integration/</link>
		<comments>http://blog.aip-solutions.com/5/paypal-integration/#comments</comments>
		<pubDate>Thu, 05 Feb 2009 11:33:39 +0000</pubDate>
		<dc:creator>Peter Mihailov</dc:creator>
				<category><![CDATA[PHP]]></category>
		<category><![CDATA[development]]></category>
		<category><![CDATA[e-commerce]]></category>
		<category><![CDATA[eshops]]></category>
		<category><![CDATA[orders]]></category>
		<category><![CDATA[PayPal]]></category>
		<category><![CDATA[server-side]]></category>
		<category><![CDATA[shopping cart]]></category>

		<guid isPermaLink="false">http://blog.aip-solutions.com/?p=5</guid>
		<description><![CDATA[The idea of this post is not to try teach somebody how to make integration between his site and Paypal. In fact Paypal has really good development center and everything is very well documented. I strongly recommend getting  familiar with Paypal development docs  to anyone. I just hope this post will be useful to [...]]]></description>
			<content:encoded><![CDATA[<p>The idea of this post is not to try teach somebody how to make integration between his site and Paypal. In fact Paypal has really good development center and everything is very well documented. I strongly recommend getting  familiar with Paypal development docs  to anyone. I just hope this post will be useful to may colleagues in their very first steps in paypal integration.</p>
<p>When we are talking about PayPal integration in e-commerce sites there are two main methods that we have to use. <strong>Payment Data Transfer</strong> (<strong>PDT</strong>) and <strong>Instant Payment Notification</strong> (<strong>IPN</strong>) are both ways PayPal to inform you system about the payments.</p>
<p><strong>PDT</strong>&#8217;s primary function is to display payment details to buyers when they are automatically redirected back to your site after payment completion. However there cases where the site will not receive notification, such as with pending transactions or if the buyer closes the browser before redirection to your site is complete. This is why PDT should NOT be used to confirm the shipment.  Also PDT requires <strong>Auto Return</strong> to be enabled.  So in a few words PDT should be used for retrieving appropriate information for showing the <em>Thank You</em> page at the end of the payment.</p>
<p>In a few words I&#8217;ll try to explain how PDT works. For more information please refer to <a href="https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/howto_html_paymentdatatransfer">Paypal development central</a>. The buyer clicks on the button <em>Pay</em> on your web site. The site redirects to Paypal page, sending information like amount that should be payed and some other account details. After payment Paypal&#8217;s site redirects back to your site and sends you some useful information like transaction ID. You have to use this transaction ID and make so called synchronization. To do that you have to send post request back to Paypal gateway with a proper set of variables including transaction ID. Then you will receive success or fail response  At the end you have to use this information to show the buyer that everything is OK and the his order will be processed. For details about variables that can be passed you should check <a href="https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/e_howto_html_IPNandPDTVariables">here</a>.</p>
<p><strong>IPN </strong>is a different approach receiving payment information. It is an asynchronous POST request to provided by page (URL) on your server. The system will receive the request no matter if the buyer&#8217;s browser is closed. Also it is not required <strong>Auto Return</strong> to be enabled. The other benefit is the fact that credit card and bank information is not transmitted in IPN and Secure Sockets Layer (SSL) is not required. IPN is the way I use to mark the orders in our systems as payed as soon as payment is confirmed by Paypal.  To use IPN you have to supply a page which is going to receive the notifications.  The URL to this page can be set in you Paypal account or you can send this URL each time when your site redirects the buyer to Paypal site.  When payment is completed payment system will send a post request to notification URL you have supplied. After that you must confirm that this notification is authentic. It is called <em>notification validation</em>. In fact there are two ways for this validation. First one which is also the better one is so called <em>shared secrets.</em> The problem with this approach if that your site has to support SSL and dedicated hosting with high enough level of security. The alternative solution for notification validation is postback. It means you have to make a post request to Paypal&#8217;s gateway which have to include exactly the same variables in same order as variables paypal have sent it to you. To the list of name value pairs you have to add <em>cmd=_notify-validate</em>. After this you will receive response VERIFIED or INVALID. Then after a few checks that you have to make and which are very well documented <a href="https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/howto_html_instantpaymentnotif">here</a>. You can be sure that payment is completed. I&#8217;m posting a link to my class for handling IPN with <em>notification validation</em> written in PHP5. The class is not 100% ready yet, but it is a good starting point for future development.</p>
<p><a href="http://blog.aip-solutions.com/wp-content/uploads/2009/02/IpnHandler.txt" target="_blank">IpnHandler.php</a></p>
<p>This is a simple example of the class usage:</p>
<p>$payPalConfig = array(    &#8216;gatewayUrl&#8217;=&gt;&#8221;www.sandbox.paypal.com&#8217;,<br />
&#8216;gatewayPort&#8217;=&gt;&#8217;443&#8242;,<br />
&#8216;receiverEmail&#8217;=&gt;&#8217;test@tes.com&#8217;,     // the email of  merchant account in Paypal<br />
);</p>
<p>$ipn = new IpnHandler();<br />
$ipn-&gt;setConfiguration($payPalConfig);<br />
$result = $ipn-&gt;handle();</p>
<p>In fact PDT and IPN doesn&#8217;t exclude each other so both should be used simultaneous web site&#8217;s order systems.</p>
<p>Some useful links for goodbye :</p>
<p><a href="https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/home_US" target="_blank">https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/home_US</a></p>
<p><a href="https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/library_documentation#wps" target="_blank">https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/library_documentation#wps</a></p>
<p><a href="https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/howto_html_instantpaymentnotif" target="_blank">https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/howto_html_instantpaymentnotif</a></p>
<p><a href="https://www.paypal.com/us/cgi-bin/?cmd=p/xcl/rec/ipn-code-outside" target="_blank">https://www.paypal.com/us/cgi-bin/?cmd=p/xcl/rec/ipn-code-outside</a></p>
<p><a href="https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/howto_html_paymentdatatransfer" target="_blank">https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&amp;content_ID=developer/howto_html_paymentdatatransfer</a></p>
<p><a href="https://www.paypal.com/us/cgi-bin/?cmd=p/xcl/rec/pdt-code-outside" target="_blank">https://www.paypal.com/us/cgi-bin/?cmd=p/xcl/rec/pdt-code-outside</a></p>
<p>Ciao ciao</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.aip-solutions.com/5/paypal-integration/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
