<?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>jQuery, Ajax, PHP, JSON, XML, Web Technologies &#187; Uncategorized</title>
	<atom:link href="http://blog.chonla.com/category/uncategorized/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.chonla.com</link>
	<description>คุยกันเรื่อง jQuery, Ajax, PHP, JSON, XML และ Web Technologies เป็นภาษาไทยกันดีกว่า</description>
	<lastBuildDate>Tue, 17 Jan 2012 18:27:02 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>Magic Methods เรียกใช้พี่สิจ๊ะ แล้วน้องจะสบาย</title>
		<link>http://blog.chonla.com/2011/11/magic-methods-%e0%b9%80%e0%b8%a3%e0%b8%b5%e0%b8%a2%e0%b8%81%e0%b9%83%e0%b8%8a%e0%b9%89%e0%b8%9e%e0%b8%b5%e0%b9%88%e0%b8%aa%e0%b8%b4%e0%b8%88%e0%b9%8a%e0%b8%b0-%e0%b9%81%e0%b8%a5%e0%b9%89%e0%b8%a7/</link>
		<comments>http://blog.chonla.com/2011/11/magic-methods-%e0%b9%80%e0%b8%a3%e0%b8%b5%e0%b8%a2%e0%b8%81%e0%b9%83%e0%b8%8a%e0%b9%89%e0%b8%9e%e0%b8%b5%e0%b9%88%e0%b8%aa%e0%b8%b4%e0%b8%88%e0%b9%8a%e0%b8%b0-%e0%b9%81%e0%b8%a5%e0%b9%89%e0%b8%a7/#comments</comments>
		<pubDate>Wed, 23 Nov 2011 10:38:54 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[Object Oriented]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Magic Methods]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=339</guid>
		<description><![CDATA[Magic methods คืออะไร ทำไมผมถึงเกริ่นหัวว่ามันจำอำนวยความสะดวกสบายขนาดนั้น Magic method เป็น method ใน class ทั่วไปที่จะถูกเรียกก็ต่อเมื่อเกิดเงื่อนไขอย่างใดอย่างหนึ่งที่ตรงกับ method นั้น ๆ ในความเป็นจริงแล้ว magic methods นั้น ไม่ได้มีอะไรวิเศษไปกว่า method ธรรมดาเลย เรียกให้ง่ายก็คือจริง ๆ แล้ว ตัว magic method ก็คือ method ธรรมดานี่แหละ เพียงแค่ว่า มันไม่ได้ถูกเรียกตรง ๆ เหมือนกับการเรียกใช้งาน method อื่น ๆ แต่อย่างที่บอกตอนต้น คือเมื่อเกิดเหตุการณ์ที่มีเงื่อนไขตรงแล้ว method นี้จะถูกเรียกโดยอัตโนมัติ ตัว magic methods เองจะขึ้นต้นด้วยตัว underscore สองตัวติดกัน ( __ ) ดังนั้นเราควรหลีกเลี่ยงการตั้งชื่อ method ที่ขึ้นต้นด้วย __ นะครับ [...]]]></description>
			<content:encoded><![CDATA[<p>Magic methods คืออะไร ทำไมผมถึงเกริ่นหัวว่ามันจำอำนวยความสะดวกสบายขนาดนั้น</p>
<p>Magic method เป็น method ใน class ทั่วไปที่จะถูกเรียกก็ต่อเมื่อเกิดเงื่อนไขอย่างใดอย่างหนึ่งที่ตรงกับ method นั้น ๆ ในความเป็นจริงแล้ว magic methods นั้น ไม่ได้มีอะไรวิเศษไปกว่า method ธรรมดาเลย เรียกให้ง่ายก็คือจริง ๆ แล้ว ตัว magic method ก็คือ method ธรรมดานี่แหละ เพียงแค่ว่า มันไม่ได้ถูกเรียกตรง ๆ เหมือนกับการเรียกใช้งาน method อื่น ๆ แต่อย่างที่บอกตอนต้น คือเมื่อเกิดเหตุการณ์ที่มีเงื่อนไขตรงแล้ว method นี้จะถูกเรียกโดยอัตโนมัติ</p>
<p><span id="more-339"></span>ตัว magic methods เองจะขึ้นต้นด้วยตัว underscore สองตัวติดกัน ( __ ) ดังนั้นเราควรหลีกเลี่ยงการตั้งชื่อ method ที่ขึ้นต้นด้วย __ นะครับ</p>
<p>เรามารู้จัก magic methods ที่ php เตรียมไว้ให้เรากัน</p>
<p><strong><span style="color: #0000ff;">__sleep()</span></strong> และ <strong><span style="color: #0000ff;">__wakeup()</span></strong></p>
<p>จะถูกเรียกเมื่อมีการเรียกใช้งานคำสั่ง serialize() และ unserialize() โดยเมื่อเราเรียก serialize() กับ object ของ class ที่มี method __sleep() มันจะทำการเรียกใช้งาน method __sleep() ก่อนที่จะทำการ serialize object ของเรา และจะเอาค่าที่ return จาก __sleep() ไป serialize() (ถ้าไม่มีการคืนค่าอะไรกลับไป คำสั่ง serialize จะทำการ serialize ค่า NULL)</p>
<p>ในทำนองเดียวกัน คำสั่ง unserialize() จะไปเรียกคำสั่ง __wakeup() ก่อนที่จะทำการ unserialize(); นั่นเอง</p>
<p><span style="color: #0000ff;"><strong>__tostring()</strong></span></p>
<p>ชื่อ method ค่อนข้างชัดเจน method นี้เอาไว้ใช้สำหรับการประมวลผล object แบบ string เช่น เรามี object ตัวหนึ่ง คือ $obj เราสามารถใช้คำสั่ง echo $obj ได้เลย โดยที่มันจะไปเรียก magic method __tostring อัตโนมัติ ค่าที่ส่งกลับจาก method นี้จะถูกส่งต่อให้ echo อีกทีหนึ่งนั่นเอง</p>
<p><span style="color: #0000ff;"><strong>__invoke()</strong></span></p>
<p>magic method __invoke() นี้จะถูกเรียกเมื่อมีการเรียกใช้งาน object ของเราเป็น function เช่น เรามี object ชื่อ $obj เราสามารถเรียกใช้เป็น $obj(&#8216;test&#8217;) ได้เลย โดยที่ค่า &#8216;test&#8217; จะถูกส่งผ่านไปให้ __invoke() นั่นเอง</p>
<p><span style="color: #0000ff;"><strong>__set_state()</strong></span></p>
<p>เป็น method ที่ถูกเรียกเมื่อมีการเรียกใช้งานคำสั่ง var_export กับ object ของ class ค่าที่ถูกส่งคืนกลับมาจะถูกส่งไปให้ var_export อีกทีหนึ่ง</p>
<p><span style="color: #0000ff;"><strong>__construct()</strong></span></p>
<p>สำหรับคนที่เขียน object oriented น่าจะรู้จัก method นี้ดี method นี้จะถูกเรียกเมื่อ class ของเราถูก instantiate เป็น object ครับ</p>
<p><span style="color: #0000ff;"><strong>__destruct()</strong></span></p>
<p>จะถูกเรียกเมื่อ object ของเราถูกทำลาย (ทำลายแบบทั้ง implicit คือ ถูกทำลายไปเอง ไม่ได้สั่งทำลาย เช่น ออกจาก variable scope และทำลายแบบ explicit คือ ทำลายด้วยคำสั่ง unset)</p>
<p><span style="color: #0000ff;"><strong>__call()</strong></span></p>
<p>จะถูกเรียกเมื่อมีการเรียกใช้ method ที่ใช้งานไม่ได้ (ไม่มี method นั้นใน class หรือ method นั้นเข้าถึงไม่ได้ เช่น private method)</p>
<p><strong><span style="color: #0000ff;">__callStatic()</span></strong></p>
<p>เหมือน __call() เพียงแค่ใช้กับ static method ครับ</p>
<p><span style="color: #0000ff;"><strong>__get()</strong></span></p>
<p>ถูกเรียกเมื่อมีการอ้างถึง property ที่เข้าถึงไม่ได้ของ class (ไม่มี property นั้น หรือเข้าถึงไม่ได้จากสาเหตุอื่น เช่น private property)</p>
<p><span style="color: #0000ff;"><strong>__set()</strong></span></p>
<p>ถูกเรียกเมื่อมีการกำหนดค่าให้กับ property ที่เข้าถึงไม่ได้ของ class</p>
<p><span style="color: #0000ff;"><strong>__isset()</strong></span></p>
<p>ถูกเรียกเมื่อมีการเช็คค่า property ที่เข้าถึงไม่ได้ ของ class ว่าถูกกำหนดค่าไว้หรือไม่ผ่านคำสั่ง isset()</p>
<p><span style="color: #0000ff;"><strong>__unset()</strong></span></p>
<p>ถูกเรียกเมื่อมีการทำลาย property ที่เข้าถึงไม่ได้ ของ class ผ่านคำสั่ง unset()</p>
<p><span style="color: #0000ff;"><strong>__clone()</strong></span></p>
<p>ถูกเรียกเมื่อมีการสั่ง clone object ผ่าน คำสั่ง clone</p>
<p>ตัวอย่างการนำ magic methods มาประยุกต์ใช้คือการทำ data binding แบบง่าย ๆ ครับ</p>
<pre class="js">&lt;?php
class DataBind {
	public $buffer;

	public function __construct() {
		$buffer = array();
	}

	public function __call($fn, $args) {
		if (preg_match('/^Get([A-Z][a-zA-Z0-9]*)$/', $fn, $m)) {
			return $this-&gt;buffer[$m[1]];
		} elseif (preg_match('/^Set([A-Z][a-zA-Z0-9]*)$/', $fn, $m)) {
			$this-&gt;buffer[$m[1]] = $args[0];
		} else {
			echo 'No method found: ' . $fn . "\n";
		}
	}
}

$data = new DataBind();
$data-&gt;SetBook('Harry Potter');
$data-&gt;SetName('John Doe');
$data-&gt;NoMethod();
echo "My name is " . $data-&gt;GetName() . ".\n";
echo "I love a book titled " . $data-&gt;GetBook() . ".\n";
?&gt;</pre>
<p>จะได้ output เป็น</p>
<pre class="js">No method found: NoMethod
My name is John Doe.
I love a book titled Harry Potter.</pre>
<pre class="js">ลองเอาไปประยุกต์ใช้กันดูนะครับ <img src='http://blog.chonla.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </pre>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2011%2F11%2Fmagic-methods-%25e0%25b9%2580%25e0%25b8%25a3%25e0%25b8%25b5%25e0%25b8%25a2%25e0%25b8%2581%25e0%25b9%2583%25e0%25b8%258a%25e0%25b9%2589%25e0%25b8%259e%25e0%25b8%25b5%25e0%25b9%2588%25e0%25b8%25aa%25e0%25b8%25b4%25e0%25b8%2588%25e0%25b9%258a%25e0%25b8%25b0-%25e0%25b9%2581%25e0%25b8%25a5%25e0%25b9%2589%25e0%25b8%25a7%2F&amp;title=Magic%20Methods%20%E0%B9%80%E0%B8%A3%E0%B8%B5%E0%B8%A2%E0%B8%81%E0%B9%83%E0%B8%8A%E0%B9%89%E0%B8%9E%E0%B8%B5%E0%B9%88%E0%B8%AA%E0%B8%B4%E0%B8%88%E0%B9%8A%E0%B8%B0%20%E0%B9%81%E0%B8%A5%E0%B9%89%E0%B8%A7%E0%B8%99%E0%B9%89%E0%B8%AD%E0%B8%87%E0%B8%88%E0%B8%B0%E0%B8%AA%E0%B8%9A%E0%B8%B2%E0%B8%A2" id="wpa2a_2"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2011/11/magic-methods-%e0%b9%80%e0%b8%a3%e0%b8%b5%e0%b8%a2%e0%b8%81%e0%b9%83%e0%b8%8a%e0%b9%89%e0%b8%9e%e0%b8%b5%e0%b9%88%e0%b8%aa%e0%b8%b4%e0%b8%88%e0%b9%8a%e0%b8%b0-%e0%b9%81%e0%b8%a5%e0%b9%89%e0%b8%a7/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Transaction ใน Database นั้นสำคัญไฉน</title>
		<link>http://blog.chonla.com/2011/07/transaction-%e0%b9%83%e0%b8%99-database-%e0%b8%99%e0%b8%b1%e0%b9%89%e0%b8%99%e0%b8%aa%e0%b8%b3%e0%b8%84%e0%b8%b1%e0%b8%8d%e0%b9%84%e0%b8%89%e0%b8%99/</link>
		<comments>http://blog.chonla.com/2011/07/transaction-%e0%b9%83%e0%b8%99-database-%e0%b8%99%e0%b8%b1%e0%b9%89%e0%b8%99%e0%b8%aa%e0%b8%b3%e0%b8%84%e0%b8%b1%e0%b8%8d%e0%b9%84%e0%b8%89%e0%b8%99/#comments</comments>
		<pubDate>Thu, 28 Jul 2011 18:41:28 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[Database]]></category>
		<category><![CDATA[MySQL]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[ACID]]></category>
		<category><![CDATA[Transaction]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=332</guid>
		<description><![CDATA[โพสนี้ว่าด้วยเรื่องทฤษฎีเกี่ยวกับ transaction ใน database ล้วน ๆ พร้อมตัวอย่างประกอบให้เห็นนิดหน่อยครับ สืบเนื่องจากโพสก่อนหน้านี้ผมพูดถึง database engine ใน MySQL ไป โดยอธิบายไปว่า บางชนิดจะสนับสนุน transaction แต่บางชนิดไม่สนับสนุน แถมยังเอาลิงก์เกี่ยวกับ transaction ทิ้งไว้ให้ไปอ่านเองอีกด้วย โพสนี้เลยจะขออนุญาตมาขยายความเรื่องเกี่ยวกับ transaction ให้เห็นภาพชัดเจนมากขึ้นกันดีกว่า Transaction (ทรานแซคชั่น) หมายถึงการดำเนินการธุรกรรมอะไรซักอย่าง แล้วแต่เนื้อหาที่นำไปใช้ เช่น ไปธนาคารถอนเงิน 1 ครั้ง ก็เรียกได้ว่าเกิด 1 transaction หรือโอนเงินให้เพื่อน 1 ครั้ง ก็เรียกว่า 1 transaction ได้เช่นกัน แล้วความสำคัญของ transaction มันอยู่ตรงไหน?&#8230; ลองพิจารณากระบวนการโอนเงินดูครับ (ตัวอย่างคลาสสิคมาก) ผมโอนเงินจากบัญชี A ไปบัญชี B กระบวนการย่อยที่เกิดขึ้นคือ ถอนเงินจาก A และฝากเข้าไปที่ B [...]]]></description>
			<content:encoded><![CDATA[<p>โพสนี้ว่าด้วยเรื่องทฤษฎีเกี่ยวกับ transaction ใน database ล้วน ๆ พร้อมตัวอย่างประกอบให้เห็นนิดหน่อยครับ</p>
<p>สืบเนื่องจากโพสก่อนหน้านี้ผมพูดถึง database engine ใน MySQL ไป โดยอธิบายไปว่า บางชนิดจะสนับสนุน transaction แต่บางชนิดไม่สนับสนุน แถมยังเอาลิงก์เกี่ยวกับ transaction ทิ้งไว้ให้ไปอ่านเองอีกด้วย โพสนี้เลยจะขออนุญาตมาขยายความเรื่องเกี่ยวกับ transaction ให้เห็นภาพชัดเจนมากขึ้นกันดีกว่า</p>
<p><span id="more-332"></span>Transaction (ทรานแซคชั่น) หมายถึงการดำเนินการธุรกรรมอะไรซักอย่าง แล้วแต่เนื้อหาที่นำไปใช้ เช่น ไปธนาคารถอนเงิน 1 ครั้ง ก็เรียกได้ว่าเกิด 1 transaction หรือโอนเงินให้เพื่อน 1 ครั้ง ก็เรียกว่า 1 transaction ได้เช่นกัน แล้วความสำคัญของ transaction มันอยู่ตรงไหน?&#8230; ลองพิจารณากระบวนการโอนเงินดูครับ (ตัวอย่างคลาสสิคมาก) ผมโอนเงินจากบัญชี A ไปบัญชี B กระบวนการย่อยที่เกิดขึ้นคือ ถอนเงินจาก A และฝากเข้าไปที่ B ดังนั้นเราจะเห็นได้ว่า ในธุรกรรมการโอนเงิน 1 transaction จะมี 2 operation ย่อยเกิดขึ้นคือ ถอนเงิน และฝากเงิน</p>
<p>ปัญหาคือ ในกรณีที่ระบบล่มระหว่าง transaction ยังไม่เสร็จสิ้นล่ะ (จากตัวอย่าง เช่น ถอนเงินจาก A มาแล้ว แต่ยังไม่ได้ฝากเข้าไปที่ B) จะเกิดอะไรขึ้น&#8230; งานงอกไงครับ</p>
<p>ดังนั้น ไอ้เจ้า transaction เนี่ย อย่างน้อยจำเป็นต้องมีคุณสมบัติที่จะทำให้เรามั่นใจได้ว่า กระบวนการย่อย ๆ ที่เกิดใน transaction เนี่ย ทำงานได้อย่างสมบูรณ์นะ คุณสมบัติพวกนี้ถ้าเอาเฉพาะตัวอักษรตัวแรกของชื่อภาษาอังกฤษมาเรียงกัน จะเขียนได้เป็น ACID ดังนั้น คุณสมบัติของ transaction นี้ก็จะเรียกง่าย ๆ กันว่า ACID properties ของ transaction นั่นเอง โดยที่ ACID properties นี้จะประกอบด้วย</p>
<blockquote><p><span style="color: #808080;">ก่อนที่จะทำความรู้จัก ACID properties &#8230; ผมขอแนะนำให้รู้จักคำ 2 คำที่ใช้กันใน transaction ก่อน คือ rollback และ commit &#8230; การ <em><strong>rollback</strong></em> หมายถึงการยกเลิกสิ่งที่ทำมาทั้งหมดใน transaction นั้น ๆ ส่วนการ <em><strong>commit</strong></em> คือการยอมรับและบันทึกค่าที่เปลี่ยนแปลงทั้งหมดใน transaction นั้น ๆ</span></p></blockquote>
<p>1. Atomicity &#8211; คุณสมบัตินี้จะสอดคล้องกับตัวอย่างที่ผมพูดไปก่อนหน้านี้ โดยจะมีหลักง่าย ๆ ที่ชัดเจนคือ transaction ที่ถูกกระทำนี้มี operation ย่อย ๆ หลายคำสั่ง ถ้าทำได้ ก็หมายถึงทำได้ทั้งหมด ถ้าทำอันใดอันหนึ่งไม่ได้ จะหมายถึงทำไม่ได้เลยตั้งแต่คำสั่งแรก (All or nothing)</p>
<p>2. Consistency &#8211; คุณสมบัตินี้หมายถึงว่า ความสอดคล้องของข้อมูลจะต้องถูกต้องเสมอ ถ้าไม่ถูกต้องระบบจะต้องทำการ rollback กลับไปยังจุดที่ข้อมูลทั้งหมดสอดคล้องกันอยู่ ยกตัวอย่างเช่น จำนวนเงินที่ก่อนที่จะทำการโอนของทั้ง 2 บัญชีรวมกันจะต้องเท่ากันกับหลักจากทำการโอนแล้ว หรือข้อมูลที่เก็บเฉพาะ integer แต่เราใส่ข้อมูลที่เป็นทศนิยมเข้าไป ข้อมูลทั้งเรคอร์ดนี้ก็ไม่ควรถูกบันทึก หรือในระบบฐานข้อมูลที่มีการกำหนดฟิลด์อ้างอิงได้ (ว่าฟิลด์นี้อ้างถึงฟิลด์ไหนในตารางอื่น) การลบเรคอร์ดที่มีฟิลด์ที่ถูกอ้างอิงก็ควรจะก่อให้เกิด &#8230;</p>
<ul>
<li>ยกเลิก transaction และ rollback กลับไปยังจุดที่สอดคล้องล่าสุด&#8230;หรือ</li>
<li>ลบเรคอร์ดที่มีการอ้างถึงข้อมูลนี้&#8230;หรือ</li>
<li>ทำฟิลด์ที่อ้างถึงข้อมูลนี้ให้เป็น NULL ซะ</li>
</ul>
<p>3. Isolation &#8211; หมายถึงว่า การประมวลผล transaction หนึ่ง ๆ ถ้ามันยังไม่เสร็จ transaction อื่น ๆ จะต้องไม่เห็นผลจากการกระทำของ transaction นี้ เช่น transaction ที่ 1 โอนเงินจากบัญชี A ไป B จำนวน 200 บาท และ transaction ที่ 2 คือ ถอนเงินจาก A 100 บาท กำหนดให้ในขั้นตอนของ transaction ที่ 2 เกิดขึ้นหลังจากที่ถอนเงินออกจาก A ไป 200 เพื่อที่จะนำไปฝากเข้า B แล้ว จากคุณสมบัติของ Isolation นี้จะทำให้ transaction ที่ 2 ยังไม่เห็นว่า A เงินหายไปแล้ว 200 หรือ B ได้รับเงินแล้ว 200</p>
<p>4. Durability &#8211; หมายถึง transaction ใด ๆ ก็ตามที่ทำการ commit แล้ว ข้อมูลจะต้องอยู่แบบนั้น ไม่ว่าระบบจะล่มยังไง เมื่อกู้คืนมาได้ transaction นั้นก็จะยังถือว่า commit และประมวลผลเสร็จสิ้นแล้ว</p>
<p>ครบ 4 อย่างแล้ว&#8230; พอเห็นภาพความสำคัญของ transaction ใน database มากขึ้นแล้วหรือยังครับ</p>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2011%2F07%2Ftransaction-%25e0%25b9%2583%25e0%25b8%2599-database-%25e0%25b8%2599%25e0%25b8%25b1%25e0%25b9%2589%25e0%25b8%2599%25e0%25b8%25aa%25e0%25b8%25b3%25e0%25b8%2584%25e0%25b8%25b1%25e0%25b8%258d%25e0%25b9%2584%25e0%25b8%2589%25e0%25b8%2599%2F&amp;title=Transaction%20%E0%B9%83%E0%B8%99%20Database%20%E0%B8%99%E0%B8%B1%E0%B9%89%E0%B8%99%E0%B8%AA%E0%B8%B3%E0%B8%84%E0%B8%B1%E0%B8%8D%E0%B9%84%E0%B8%89%E0%B8%99" id="wpa2a_4"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2011/07/transaction-%e0%b9%83%e0%b8%99-database-%e0%b8%99%e0%b8%b1%e0%b9%89%e0%b8%99%e0%b8%aa%e0%b8%b3%e0%b8%84%e0%b8%b1%e0%b8%8d%e0%b9%84%e0%b8%89%e0%b8%99/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>ทำความรู้จักกับ Storage Engine ของ MySQL กันหน่อย</title>
		<link>http://blog.chonla.com/2011/07/%e0%b8%97%e0%b8%b3%e0%b8%84%e0%b8%a7%e0%b8%b2%e0%b8%a1%e0%b8%a3%e0%b8%b9%e0%b9%89%e0%b8%88%e0%b8%b1%e0%b8%81%e0%b8%81%e0%b8%b1%e0%b8%9a-storage-engine-%e0%b8%82%e0%b8%ad%e0%b8%87-mysql-%e0%b8%81/</link>
		<comments>http://blog.chonla.com/2011/07/%e0%b8%97%e0%b8%b3%e0%b8%84%e0%b8%a7%e0%b8%b2%e0%b8%a1%e0%b8%a3%e0%b8%b9%e0%b9%89%e0%b8%88%e0%b8%b1%e0%b8%81%e0%b8%81%e0%b8%b1%e0%b8%9a-storage-engine-%e0%b8%82%e0%b8%ad%e0%b8%87-mysql-%e0%b8%81/#comments</comments>
		<pubDate>Tue, 26 Jul 2011 16:01:11 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[MySQL]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Database Engines]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=327</guid>
		<description><![CDATA[MySQL พูดชื่อนี้ ผมว่า developer หลาย ๆ คน ก็คงต้องรู้จักฐานข้อมูลยอดนิยมตัวนี้ แต่จะมีใครรู้บ้างว่า MySQL เนี่ย มันมี storage engine ให้เลือกใช้หลายแบบนะ แล้วแบบไหนที่เหมาะกับงานของเราล่ะ? (ใครไม่รู้จักว่า storage engine นั้นหมายถึงอะไร database engine เรียกง่าย ๆ ก็เหมือนชนิดของฐานข้อมูล สาเหตุที่เราต้องเลือกชนิด engine ให้เหมาะสมนั้น เปรียบเทียบง่าย ๆ ว่า มันก็เหมือนกับเสื้อผ้า เสื้อผ้ามีหลายประเภท เราใส่ออกไปนอกบ้านได้ทุกแบบ แต่แบบไหนที่เหมาะกับกาลเทศะ และงานที่ทำ อย่างเช่น ชุดกันไฟกับงานนักดับเพลิง จะให้ใส่สูทไปดับไฟก็ได้ แต่มันไม่ถนัด&#8230;) การที่เราจะรู้ว่า storage engine แบบไหนเหมาะกับเรานั้น เราก็ต้องมาทำความรู้จักกับ storage engine แต่ละชนิดกันก่อน เพื่อไม่ให้เป็นการเสียเวลา เรามาทำความรู้จักกับ storage engine แต่ละตัวกันดีกว่า (เราสามารถกำหนดให้แต่ละตารางใช้ engine ต่างกันได้ตามความเหมาะสมในการใช้งาน) ISAM เป็น storage engine ที่ถูกออกแบบมาโดยที่มีแนวคิดที่ว่า ตารางมักจะถูกอ่านมากกว่าอัพเดท [...]]]></description>
			<content:encoded><![CDATA[<p>MySQL พูดชื่อนี้ ผมว่า developer หลาย ๆ คน ก็คงต้องรู้จักฐานข้อมูลยอดนิยมตัวนี้ แต่จะมีใครรู้บ้างว่า MySQL เนี่ย มันมี storage engine ให้เลือกใช้หลายแบบนะ แล้วแบบไหนที่เหมาะกับงานของเราล่ะ? (ใครไม่รู้จักว่า storage engine นั้นหมายถึงอะไร database engine เรียกง่าย ๆ ก็เหมือนชนิดของฐานข้อมูล สาเหตุที่เราต้องเลือกชนิด engine ให้เหมาะสมนั้น เปรียบเทียบง่าย ๆ ว่า มันก็เหมือนกับเสื้อผ้า เสื้อผ้ามีหลายประเภท เราใส่ออกไปนอกบ้านได้ทุกแบบ แต่แบบไหนที่เหมาะกับกาลเทศะ และงานที่ทำ อย่างเช่น ชุดกันไฟกับงานนักดับเพลิง จะให้ใส่สูทไปดับไฟก็ได้ แต่มันไม่ถนัด&#8230;)</p>
<p>การที่เราจะรู้ว่า storage engine แบบไหนเหมาะกับเรานั้น เราก็ต้องมาทำความรู้จักกับ storage engine แต่ละชนิดกันก่อน เพื่อไม่ให้เป็นการเสียเวลา เรามาทำความรู้จักกับ storage engine แต่ละตัวกันดีกว่า (เราสามารถกำหนดให้แต่ละตารางใช้ engine ต่างกันได้ตามความเหมาะสมในการใช้งาน)</p>
<p><span id="more-327"></span></p>
<ul>
<li>ISAM เป็น storage engine ที่ถูกออกแบบมาโดยที่มีแนวคิดที่ว่า ตารางมักจะถูกอ่านมากกว่าอัพเดท ทำให้ storage engine ชนิดนี้สามารถประมวลผลคำสั่งที่เป็นการอ่านได้อย่างรวดเร็วมาก ๆ แต่มีข้อเสียใหญ่ ๆ คือการไม่สนับสนุนการทำงานแบบ transaction (คือไม่สามารถ rollback ได้ ถ้าเกิดกรณีการทำงานไม่สมบูรณ์ ทางทฤษฎีเรียกว่า ACID transaction properties : สามารถอ่านเพิ่มเติมได้จากที่ <a href="http://en.wikipedia.org/wiki/ACID">http://en.wikipedia.org/wiki/ACID</a>)  และไม่รองรับระบบ fault-tolerant (คือถ้าระบบล่ม ก็อาจจะไม่สามารถที่จะกู้ข้อมูลกลับขึ้นมาได้เลย) ดังนั้นถ้าจะใช้ engine นี้ในงานสำคัญ ก็แนะนำว่าหมั่น backup บ่อย ๆ ครับ</li>
<li>MyISAM เป็น engine ยอดนิยมสำหรับเว็บทั่ว ๆ ไป พัฒนาต่อเนื่องมาจาก ISAM ทำให้ความเร็วในการอ่านยังเป็นเรื่องที่โดดเด่นอยู่เหมือนเดิม นอกจากนี้แล้วยังมีการเพิ่มส่วนของการทำ indexing และ operation สำหรับ field บางอย่างลงไปด้วย ข้อดีอีกอย่างคือ ใน MyISAM นี้ มี tool ที่ใช้ในการกู้ข้อมูลในกรณีที่ตารางมีปัญหาด้วย (MyISAMChk) แต่ข้อเสียที่สำคัญก็ยังคงอยู่คือ ไม่สนับสนุนการทำงานแบบ transaction และคำสั่ง update ยังส่งผลให้เกิดขยะที่ไม่จำเป็นอีกด้วย ทำให้เราต้องใช้คำสั่ง OPTIMIZE เพื่อจัดการขยะพวกนี้ให้หายไปจากตาราง</li>
<li>HEAP (หรือ Memory) เป็น engine ที่ไม่ได้สร้างตารางขึ้นมาเป็นไฟล์จริง ๆ เหมือนกับ engine อื่น ๆ แต่จะสร้างตารางลงใน Memory ของเครื่อง ทำให้การเข้าถึงทำได้รวดเร็วยิ่งกว่า ISAM และ MyISAM แต่ข้อเสียคือ มันไม่อยู่ถาวร ถ้ามีการปิดเครื่องหรือระบบล่มโดยที่ยังไม่ได้บันทึกค่าในตารางลงไฟล์ ข้อมูลใน Memory ขณะนั้นก็จะหายไปทั้งหมด ไม่สามารถกู้คืนได้ และทุกครั้งที่ใช้งานตารางที่ใช้ engine นี้เสร็จ ก็จะต้องลบตารางนี้ทิ้งด้วย ไม่เช่นนั้นแล้วจะเกิดขยะใน Memory อาจจะทำให้ Memory ไม่พอในการทำงานได้</li>
<li>InnoDB และ Berkley DB (BDB) เป็นฐานข้อมูลที่ถูกพัฒนามาให้สนับสนุน transaction และแถมด้วยการสนับสนุน Foreign Key แต่ก็มีข้อเสียคือมันช้ากว่า ISAM และ MyISAM แต่สำหรับผู้ที่จำเป็นจะต้องใช้ transaction แล้ว ก็คงเลี่ยงไม่ได้ที่จะใช้ engine ชนิดนี้</li>
<li>Cluster ถูกพัฒนาขึ้นเพื่อเพิ่ม High Availability และ High Performance (ประมาณว่าใช้งานได้นาน ๆ และมีประสิทธิภาพดี) แต่ก็จะต้องใช้ resource ในการ implement ค่อนข้างมากเช่นเดียวกัน โดยที่ engine สำหรับ Cluster นี้มีชื่อว่า NDB หรือ NDBCLUSTER (NDB = Network Database)</li>
</ul>
<div>(จริง ๆ แล้วมี storage engine อีกมากมายที่ถูกพัฒนาขึ้นมาใช้กับ MySQL แต่ผมขอไม่พูดถึง เพราะมันเยอะมาก และเราก็ไม่ค่อยได้ใช้งานเท่าไรนัก ผู้ที่สนใจ เข้าไปดูรายละเอียดได้ที่ <a href="http://en.wikipedia.org/wiki/MySQL">http://en.wikipedia.org/wiki/MySQL</a>)</div>
<div>ถึงตอนนี้ ผมว่าเราคงสามารถที่จัดตัดสินใจได้ง่ายขึ้นแล้วว่าจะใช้ engine แบบไหนกับตารางของเราดี</div>
<div>อ้างอิง</div>
<div>
<ul>
<li><a href="http://www.techrepublic.com/article/a-fast-and-furious-guide-to-mysql-database-engines/1058872">http://www.techrepublic.com/article/a-fast-and-furious-guide-to-mysql-database-engines/1058872</a></li>
<li><a href="http://en.wikipedia.org/wiki/MySQL">http://en.wikipedia.org/wiki/MySQL</a></li>
<li><a href="http://en.wikipedia.org/wiki/MySQL_Cluster">http://en.wikipedia.org/wiki/MySQL_Cluster</a></li>
</ul>
</div>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2011%2F07%2F%25e0%25b8%2597%25e0%25b8%25b3%25e0%25b8%2584%25e0%25b8%25a7%25e0%25b8%25b2%25e0%25b8%25a1%25e0%25b8%25a3%25e0%25b8%25b9%25e0%25b9%2589%25e0%25b8%2588%25e0%25b8%25b1%25e0%25b8%2581%25e0%25b8%2581%25e0%25b8%25b1%25e0%25b8%259a-storage-engine-%25e0%25b8%2582%25e0%25b8%25ad%25e0%25b8%2587-mysql-%25e0%25b8%2581%2F&amp;title=%E0%B8%97%E0%B8%B3%E0%B8%84%E0%B8%A7%E0%B8%B2%E0%B8%A1%E0%B8%A3%E0%B8%B9%E0%B9%89%E0%B8%88%E0%B8%B1%E0%B8%81%E0%B8%81%E0%B8%B1%E0%B8%9A%20Storage%20Engine%20%E0%B8%82%E0%B8%AD%E0%B8%87%20MySQL%20%E0%B8%81%E0%B8%B1%E0%B8%99%E0%B8%AB%E0%B8%99%E0%B9%88%E0%B8%AD%E0%B8%A2" id="wpa2a_6"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2011/07/%e0%b8%97%e0%b8%b3%e0%b8%84%e0%b8%a7%e0%b8%b2%e0%b8%a1%e0%b8%a3%e0%b8%b9%e0%b9%89%e0%b8%88%e0%b8%b1%e0%b8%81%e0%b8%81%e0%b8%b1%e0%b8%9a-storage-engine-%e0%b8%82%e0%b8%ad%e0%b8%87-mysql-%e0%b8%81/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>ปลั๊กอิน BBCode สำหรับ jQuery</title>
		<link>http://blog.chonla.com/2009/11/%e0%b8%9b%e0%b8%a5%e0%b8%b1%e0%b9%8a%e0%b8%81%e0%b8%ad%e0%b8%b4%e0%b8%99-bbcode-%e0%b8%aa%e0%b8%b3%e0%b8%ab%e0%b8%a3%e0%b8%b1%e0%b8%9a-jquery/</link>
		<comments>http://blog.chonla.com/2009/11/%e0%b8%9b%e0%b8%a5%e0%b8%b1%e0%b9%8a%e0%b8%81%e0%b8%ad%e0%b8%b4%e0%b8%99-bbcode-%e0%b8%aa%e0%b8%b3%e0%b8%ab%e0%b8%a3%e0%b8%b1%e0%b8%9a-jquery/#comments</comments>
		<pubDate>Mon, 16 Nov 2009 10:33:23 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[Homemade Plugin]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jQuery]]></category>
		<category><![CDATA[Plugins]]></category>
		<category><![CDATA[Souce Code]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[BBCode]]></category>
		<category><![CDATA[Plugin]]></category>
		<category><![CDATA[Regular Expression]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=245</guid>
		<description><![CDATA[วันนี้ผมลองเขียน plugin แก้ขัดที่หายหน้าหายตาไปนานมาให้ลองกันครับ นั่นก็คือปลั๊กอินที่ใช้ render BBCode ครับ ใครที่เป็นนักโพสเว็บบอร์ดคงจะรู้จักกันดีว่า BBCode คืออะไร สำหรับใครที่ยังไม่รู้จักก็อ่านย่อหน้าถัดไปได้เลยครับ BBCode เราเรียกได้ว่าเป็น lightweighted markup language ใช้สำหรับจัดรูปแบบข้อความตามเว็บบอร์ดต่าง ๆ ครับ มีลักษณะของแท็กอยู่ในเครื่องหมายก้ามปู เช่น [b]ตัวหนา[/b] ครับ เจ้าตัว BBCode นี่เว็บบราวเซอร์มันไม่รู้จักครับ ต้องทำการแปลไปเป็น markup language ที่ใช้ทั่ว ๆ ไปก่อนครับ นั่นก็คือ HTML หรือ XHTML ครับ เช่น จาก [b]ตัวหนา[/b] จะถูกแปลงไปเป็น &#60;b&#62;ตัวหนา&#60;/b&#62; แล้วค่อยนำไปแสดงผลครับ จุดประสงค์หลัก ๆ ของ BBCode คือ เพื่อให้ผู้ใช้สามารถจัดรูปแบบข้อความได้ง่ายขึ้น รวมไปถึงเพื่อความปลอดภัยของการแสดงผลข้อความที่โพสโดยผู้ใช้ด้วยครับ เช่น การควบคุมการใช้งาน javascript การควบคุมให้ใช้ tag [...]]]></description>
			<content:encoded><![CDATA[<p>วันนี้ผมลองเขียน plugin แก้ขัดที่หายหน้าหายตาไปนานมาให้ลองกันครับ นั่นก็คือปลั๊กอินที่ใช้ render BBCode ครับ ใครที่เป็นนักโพสเว็บบอร์ดคงจะรู้จักกันดีว่า BBCode คืออะไร สำหรับใครที่ยังไม่รู้จักก็อ่านย่อหน้าถัดไปได้เลยครับ</p>
<p>BBCode เราเรียกได้ว่าเป็น lightweighted markup language ใช้สำหรับจัดรูปแบบข้อความตามเว็บบอร์ดต่าง ๆ ครับ มีลักษณะของแท็กอยู่ในเครื่องหมายก้ามปู เช่น [b]ตัวหนา[/b] ครับ เจ้าตัว BBCode นี่เว็บบราวเซอร์มันไม่รู้จักครับ ต้องทำการแปลไปเป็น markup language ที่ใช้ทั่ว ๆ ไปก่อนครับ นั่นก็คือ HTML หรือ XHTML ครับ เช่น จาก [b]ตัวหนา[/b] จะถูกแปลงไปเป็น &lt;b&gt;ตัวหนา&lt;/b&gt; แล้วค่อยนำไปแสดงผลครับ<br />
<span id="more-245"></span><br />
จุดประสงค์หลัก ๆ ของ BBCode คือ เพื่อให้ผู้ใช้สามารถจัดรูปแบบข้อความได้ง่ายขึ้น รวมไปถึงเพื่อความปลอดภัยของการแสดงผลข้อความที่โพสโดยผู้ใช้ด้วยครับ เช่น การควบคุมการใช้งาน javascript การควบคุมให้ใช้ tag ภายในข้อกำหนด เป็นต้น</p>
<p>เจ้าตัว BBCode เนี่ย มันไม่มีข้อกำหนดเป็นมาตรฐาน เพียงแค่มีการใช้งานโดยทั่วไปตามเว็บบอร์ดเวอร์ชั่นใหม่ ๆ ทั่วไปครับ รายละเอียดรูปแบบคำสั่ง สามารถตามไปดูในหัวข้ออ้างอิงท้ายบทความได้เลยครับ</p>
<p>ทีนี้มาดูกันว่าปลั๊กอินตัวนี้จะทำงานยังไงครับ</p>
<p>ง่าย ๆ ครับ แค่เรียก $(&lt;selector&gt;).bbcode(); เท่านั้นครับ เช่น</p>
<pre class="js">$("div").bbcode();</pre>
<p>ไอเดียของปลั๊กอินตัวนี้ผมได้มาจากตอนเขียนแก้บักการแสดงผล BBCode ให้เก็บเว็บไซต์หนึ่งครับ ปกติแล้วการ render จาก BBCode ไปเป็น HTML นั้น มักจะทำที่ Server และส่ง HTML ที่ได้มาให้บราวเซอร์แสดงผล แต่ผมต้องการที่จะลดโหลดฝั่ง Server ลง โดยจะย้ายการทำงานจากฝั่ง Server มาทำที่บราวเซอร์แทน</p>
<p>หลักการทำงานก็ไม่มีอะไรมากครับ ผมใช้วิธีการกำหนดค่า Pattern ในรูปแบบ Regular Expression และใช้ Regular Expression Engine ของ JavaScript ในการแสดงผลให้ถูกต้องเท่านั้นครับ</p>
<p>ลองไปดูที่ <a title="BBCode Plugin for jQuery" href="http://sandbox.chonla.com/bbcode/" target="_blank">LIVE DEMO</a> กันเลยครับ</p>
<p><span style="text-decoration: underline;">อ้างอิง</span></p>
<ul>
<li><span style="background-color: #ffffff;"><a title="BBCode" href="http://en.wikipedia.org/wiki/BBCode" target="_blank">http://en.wikipedia.org/wiki/BBCode</a></span></li>
</ul>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2009%2F11%2F%25e0%25b8%259b%25e0%25b8%25a5%25e0%25b8%25b1%25e0%25b9%258a%25e0%25b8%2581%25e0%25b8%25ad%25e0%25b8%25b4%25e0%25b8%2599-bbcode-%25e0%25b8%25aa%25e0%25b8%25b3%25e0%25b8%25ab%25e0%25b8%25a3%25e0%25b8%25b1%25e0%25b8%259a-jquery%2F&amp;title=%E0%B8%9B%E0%B8%A5%E0%B8%B1%E0%B9%8A%E0%B8%81%E0%B8%AD%E0%B8%B4%E0%B8%99%20BBCode%20%E0%B8%AA%E0%B8%B3%E0%B8%AB%E0%B8%A3%E0%B8%B1%E0%B8%9A%20jQuery" id="wpa2a_8"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2009/11/%e0%b8%9b%e0%b8%a5%e0%b8%b1%e0%b9%8a%e0%b8%81%e0%b8%ad%e0%b8%b4%e0%b8%99-bbcode-%e0%b8%aa%e0%b8%b3%e0%b8%ab%e0%b8%a3%e0%b8%b1%e0%b8%9a-jquery/feed/</wfw:commentRss>
		<slash:comments>11</slash:comments>
		</item>
		<item>
		<title>Method Chaining ใน PHP ทำเองก็ได้ง่ายจัง</title>
		<link>http://blog.chonla.com/2009/09/method-chaining-%e0%b9%83%e0%b8%99-php-%e0%b8%97%e0%b8%b3%e0%b9%80%e0%b8%ad%e0%b8%87%e0%b8%81%e0%b9%87%e0%b9%84%e0%b8%94%e0%b9%89%e0%b8%87%e0%b9%88%e0%b8%b2%e0%b8%a2%e0%b8%88%e0%b8%b1%e0%b8%87/</link>
		<comments>http://blog.chonla.com/2009/09/method-chaining-%e0%b9%83%e0%b8%99-php-%e0%b8%97%e0%b8%b3%e0%b9%80%e0%b8%ad%e0%b8%87%e0%b8%81%e0%b9%87%e0%b9%84%e0%b8%94%e0%b9%89%e0%b8%87%e0%b9%88%e0%b8%b2%e0%b8%a2%e0%b8%88%e0%b8%b1%e0%b8%87/#comments</comments>
		<pubDate>Wed, 02 Sep 2009 19:03:09 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[jQuery]]></category>
		<category><![CDATA[Object Oriented]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Chainability]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=228</guid>
		<description><![CDATA[บทความนี้ได้แรงบันดาลใจมาจาก chainability ของ jQuery และ query builder ของ kohana (จริง ๆ ผมเข้าใจว่า query builder มีอยู่ใน php framework ตัวอื่นด้วย แต่พอดีท่านรุ่งจากบ้าน PHP.DeeServer.net ซึ่งแนะนำให้ผมรู้จักกับ kohana เค้าแนะนำตัวที่อยู่ใน kohana มาครับ) ไอเดียหลัก ๆ ของการทำ chaining ก็คือ การทำให้มันสามารถเรียกต่อกันได้เป็นทอด ๆ นั่นเอง ยกตัวอย่างใน jQuery ซึ่งมีคุณสมบัติที่เรียกว่า chainability อยู่ ทำให้เราสามารถเรียกคำสั่งได้แบบนี้ $("#submenu").addClass("whitemenu").show("slow"); จะเห็นได้ว่า เราสามารถเรียก .show ต่อเนื่องได้เลย นี่เองที่ทำให้เกิดการเรียกอย่างต่อเนื่อง หรือ การทำ Method chaining นั่นเอง ใน PHP เราสามารถทำให้ object มีคุณสมบัติเดียวกันนี้ได้เช่นกัน [...]]]></description>
			<content:encoded><![CDATA[<p>บทความนี้ได้แรงบันดาลใจมาจาก <a href="http://blog.chonla.com/2008/11/เมื่อฟ้าส่ง-chainability-มาให้กับ-jquery/" target="_blank" title="เมื่อฟ้าส่ง Chainability มาให้กับ jQuery">chainability</a> ของ <a href="http://www.jquery.com" target="_blank" title="jQuery - The Write Less, Do More, JavaScript Library">jQuery</a> และ query builder ของ <a href="http://www.kohanaphp.com/" target="_blank" title="Kohana - The swift PHP Framework">kohana</a> (จริง ๆ ผมเข้าใจว่า query builder มีอยู่ใน php framework ตัวอื่นด้วย แต่พอดีท่านรุ่งจากบ้าน <a href="http://php.deeserver.net" target="_blank" title="PHP.DeeServer.Net">PHP.DeeServer.net</a> ซึ่งแนะนำให้ผมรู้จักกับ kohana เค้าแนะนำตัวที่อยู่ใน kohana มาครับ)</p>
<p>ไอเดียหลัก ๆ ของการทำ chaining ก็คือ การทำให้มันสามารถเรียกต่อกันได้เป็นทอด ๆ นั่นเอง ยกตัวอย่างใน jQuery ซึ่งมีคุณสมบัติที่เรียกว่า chainability อยู่ ทำให้เราสามารถเรียกคำสั่งได้แบบนี้</p>
<pre name="code" class="js">
$("#submenu").addClass("whitemenu").show("slow");
</pre>
<p>จะเห็นได้ว่า เราสามารถเรียก .show ต่อเนื่องได้เลย นี่เองที่ทำให้เกิดการเรียกอย่างต่อเนื่อง หรือ การทำ Method chaining นั่นเอง<br />
<span id="more-228"></span></p>
<p>ใน PHP เราสามารถทำให้ object มีคุณสมบัติเดียวกันนี้ได้เช่นกัน เพียงแต่น่าเสียดายที่คุณสมบัตินี้ มีอยู่ใน PHP ตั้งแต่เวอร์ชั่น 5 ขึ้นไปเท่านั้น สำหรับคนที่ยังใช้ PHP4 อยู่ ผมต้องขอแสดงความเสียใจด้วยครับ ฮ่า ๆ และคาดว่าเหตุนี้เองที่ทำให้ kohana สามารถใช้งานได้กับ PHP5 ขึ้นไปเท่านั้น</p>
<p>หลักการง่าย ๆ ที่ทำให้เราสามารถทำ Method chaining ได้ก็คือ การเขียน class และทำการคืนค่าของ object มันเองกลับออกมาหลังจากที่จบ method ทำนองเดียวกับใน jQuery ตอนที่เขียน plugin </p>
<p>ตอนจบ เราก็จะทำการ return jQuery object กลับออกมาให้เช่นเดียวกัน</p>
<p>ลองมาดูตัวอย่างใน PHP กันดีกว่าครับ</p>
<pre name="code" class="js">
// php5 only
class Database
{
	private $link;

	private $table;
	private $field;
	private $condition;
	private $order;
	private $result;

	// connection functions
	function __construct($config)
	{
		$this->flush();
		$this->link = null;
		$this->connect($config["hostname"],
				$config["username"],
				$config["password"],
				$config["database"]);
	}

	function __destruct()
	{
		$this->disconnect();
	}

	function connect($host = "",
				$user = "",
				$password = "",
				$db = "")
	{
		if ($this->link !== null)
			$this->disconnect();

		$this->link = mysql_connect($host, $user, $password);

		if ($this->link === FALSE)
		{
			echo $this->err();
		}
		else
		{
			if ($db !== "")
			{
				return $this->db($db);
			}
		}
		return $this;
	}

	function disconnect()
	{	// break chain
		if ($this->link !== null)
			mysql_close($this->link);
		$this->link = null;
	}

	function db($db)
	{
		if (mysql_select_db($db, $this->link) === FALSE)
			echo $this->err();
		return $this;
	}

	function errno()
	{
		return mysql_errno($this->link);
	}

	function ok()
	{
		return ($this->errno() == 0);
	}

	function err()
	{	// break chain
		return mysql_error($this->link);
	}

	function execute($sql)
	{
		$this->result = mysql_query($sql, $this->link);
		return $this;
	}

	function records()
	{
		$result = array();
		if ($this->result !== FALSE)
		{
			while (($row = mysql_fetch_assoc($this->result)) !== FALSE)
			{
				$result[] = $row;
			}
		}
		return $result;
	}

	function flush()
	{
		$this->table = "";
		$this->field = "";
		$this->condition = "";
		$this->order = "";
		$this->result = null;
		return $this;
	}

	function safe($value)
	{
		if (!get_magic_quotes_gpc())
		{
			$value = addslashes($value);
		}
		return "'$value'";
	}

	function table($table)
	{
		$this->table = $table;
		return $this;
	}

	function field($field)
	{
		$this->field = $field;
		return $this;
	}

	function condition($condition)
	{
		if (is_array($condition))
		{
			$cond = array();
			foreach ($condition as $f => $v)
			{
				$cond[] = "($f = " . $this->safe($v) . ")";
			}
			$condition = implode(" AND ", $cond);
		}
		$this->condition = $condition;
		return $this;
	}

	function top($num = 1)
	{
		$field = $this->field;
		if ($field == "") $field = "*";
		$sql = "SELECT {$field} FROM {$this->table}";
		if ($this->condition !== "")
			$sql .= " WHERE {$this->condition}";
		if ($this->order !== "")
			$sql .= " ORDER BY {$this->order}";
		$sql .= " LIMIT 0, {$num}";
		return $this->execute($sql)->records();
	}

	function all()
	{
		$field = $this->field;
		if ($field == "") $field = "*";
		$sql = "SELECT {$field} FROM {$this->table}";
		if ($this->condition !== "")
			$sql .= " WHERE {$this->condition}";
		if ($this->order !== "")
			$sql .= " ORDER BY {$this->order}";
		return $this->execute($sql)->records();
	}

	function order($order)
	{
		$this->order = $order;
		return $this;
	}
}
</pre>
<p>code ด้านบนนี้ เป็น code ที่ผมทดสอบ โดยทำเป็นไอเดียเริ่มต้นง่าย ๆ สำหรับการทำ query builder จะเห็นได้ว่า หลาย ๆ method จะมีการ return ตัว object มันเอง ($this) ไอเดียหลักในการกำหนดว่า method ไหนที่ผม return หรือไม่ return $this ก็คือ มีความจำเป็นในการเรียก method ต่อจากนี้หรือไม่นั่นเอง</p>
<p>การใช้งานก็ไม่ได้ยุ่งยากอะไร</p>
<pre name="code" class="js">
$dbconf = array(
	"hostname" => "localhost",
	"username" => "root",
	"password" => "123456",
	"database" => "test"
);
$db = new Database($dbconf);
$rows = $db->table("products")
		->field("product_id, product_name")
		->condition(array(
				"product_group"=>"tyre",
				"product_model"=>"Eagle"))
		->top();
print_r($rows);
</pre>
<p>จากตัวอย่างด้านบน เป็นการ select หา product จาก table products โดยกำหนด criteria ในการค้นหาเป็น product_group = &#8216;tyre&#8217; และ product_model = &#8216;Eagle&#8217; โดยจะเลือกเอาเฉพาะ record แรกสุดเท่านั้น</p>
<p>เห็นมั๊ยครับ หลักการง่าย ๆ แค่ return $this เองครับ ที่สำคัญ อย่าลืมนะครับ PHP5 ขึ้นไปนะครับ</p>
<p>ขอให้สนุกกับการเขียนโปรแกรมครับ</p>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2009%2F09%2Fmethod-chaining-%25e0%25b9%2583%25e0%25b8%2599-php-%25e0%25b8%2597%25e0%25b8%25b3%25e0%25b9%2580%25e0%25b8%25ad%25e0%25b8%2587%25e0%25b8%2581%25e0%25b9%2587%25e0%25b9%2584%25e0%25b8%2594%25e0%25b9%2589%25e0%25b8%2587%25e0%25b9%2588%25e0%25b8%25b2%25e0%25b8%25a2%25e0%25b8%2588%25e0%25b8%25b1%25e0%25b8%2587%2F&amp;title=Method%20Chaining%20%E0%B9%83%E0%B8%99%20PHP%20%E0%B8%97%E0%B8%B3%E0%B9%80%E0%B8%AD%E0%B8%87%E0%B8%81%E0%B9%87%E0%B9%84%E0%B8%94%E0%B9%89%E0%B8%87%E0%B9%88%E0%B8%B2%E0%B8%A2%E0%B8%88%E0%B8%B1%E0%B8%87" id="wpa2a_10"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2009/09/method-chaining-%e0%b9%83%e0%b8%99-php-%e0%b8%97%e0%b8%b3%e0%b9%80%e0%b8%ad%e0%b8%87%e0%b8%81%e0%b9%87%e0%b9%84%e0%b8%94%e0%b9%89%e0%b8%87%e0%b9%88%e0%b8%b2%e0%b8%a2%e0%b8%88%e0%b8%b1%e0%b8%87/feed/</wfw:commentRss>
		<slash:comments>15</slash:comments>
		</item>
		<item>
		<title>jTemplates, Template Engine ของ jQuery</title>
		<link>http://blog.chonla.com/2009/05/jtemplates-template-engine-%e0%b8%82%e0%b8%ad%e0%b8%87-jquery/</link>
		<comments>http://blog.chonla.com/2009/05/jtemplates-template-engine-%e0%b8%82%e0%b8%ad%e0%b8%87-jquery/#comments</comments>
		<pubDate>Tue, 19 May 2009 17:10:30 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jQuery]]></category>
		<category><![CDATA[JSON]]></category>
		<category><![CDATA[Plugins]]></category>
		<category><![CDATA[Souce Code]]></category>
		<category><![CDATA[Template Engine]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[jTemplate]]></category>
		<category><![CDATA[Plugin]]></category>
		<category><![CDATA[Template]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=149</guid>
		<description><![CDATA[ได้ไปอ่านบทความเกี่ยวกับ Template Engine ที่เว็บ jquerytips เป็น Template Engine ที่เป็น plugin ของ jQuery น่าสนใจดีครับ เลยเอามาแบ่งปันกัน jTemplate เป็น Template Engine ที่มีลักษณะการเขียน (Syntax) ที่เรียกได้ว่าลอกแบบกันมาจาก Smarty เลยทีเดียว ทำให้คนที่มีพื้นฐานของ Smarty อยู่แล้ว สามารถเรียนรู้ jTemplate ได้โดยง่าย ส่วนรูปแบบของข้อมูลที่รองรับก็จะอยู่ในรูปแบบของ JSON มาดูตัวอย่างการเขียนกันครับ ขั้นแรก ผมจะกำหนด data ที่จะใช้งานก่อนครับ var data = { id: 4, name: "User List", table: [ {id: 1, name: 'Anne', age: 22, mail: 'anne@domain.com'}, [...]]]></description>
			<content:encoded><![CDATA[<p>ได้ไปอ่านบทความเกี่ยวกับ Template Engine ที่เว็บ <a href="http://www.jquerytips.com" target="_blank">jquerytips</a> เป็น Template Engine ที่เป็น plugin ของ jQuery น่าสนใจดีครับ เลยเอามาแบ่งปันกัน<br />
<span id="more-149"></span><br />
jTemplate เป็น Template Engine ที่มีลักษณะการเขียน (Syntax) ที่เรียกได้ว่าลอกแบบกันมาจาก Smarty เลยทีเดียว ทำให้คนที่มีพื้นฐานของ Smarty อยู่แล้ว สามารถเรียนรู้ jTemplate ได้โดยง่าย ส่วนรูปแบบของข้อมูลที่รองรับก็จะอยู่ในรูปแบบของ JSON มาดูตัวอย่างการเขียนกันครับ</p>
<p>ขั้นแรก ผมจะกำหนด data ที่จะใช้งานก่อนครับ</p>
<pre class="js">var data = {
    id: 4,
    name: "User List",
    table: [
        {id: 1, name: 'Anne', age: 22, mail: 'anne@domain.com'},
        {id: 2, name: 'Amelie', age: 24, mail: 'amelie@domain.com'},
        {id: 3, name: 'Polly', age: 18, mail: 'polly@domain.com'},
        {id: 4, name: 'Alice', age: 26, mail: 'alice@domain.com'},
        {id: 5, name: 'Martha', age: 25, mail: 'martha@domain.com'}
    ],
    toString: function() {
        return this.name.bold() + ' (count: ' + this.table.length + ')';
    }
};</pre>
<p>เสร็จแล้วก็มากำหนด Template</p>
<pre class="js">{#template MAIN}
&lt;div id="header"&gt;{$T.name}&lt;/div&gt;
&lt;table&gt;
{#foreach $T.table as r}
    {#include row root=$T.r}
{#/for}
&lt;/table&gt;
{#/template MAIN}

{#template row}
&lt;tr bgcolor="{#cycle values=['#AAAAEE','#CCCCFF']}"&gt;
    &lt;td&gt;{$T.name.bold()}&lt;/td&gt;
    &lt;td&gt;{$T.age}&lt;/td&gt;
    &lt;td&gt;{$T.mail.link('mailto:'+$T.mail)}&lt;/td&gt;
&lt;/tr&gt;
{#/template row}</pre>
<p>ที่เหลือก็แค่เรียกใช้งาน plugin ตัวนี้เท่านั้นเองครับ ง่าย ๆ</p>
<pre class="js">$("#result").setTemplate($("textarea").text()).processTemplate(data);</pre>
<p>ลองไปดูตัวอย่างที่ <a title="LIVE DEMO : jTemplate for jQuery" href="http://sandbox.chonla.com/jtemplate" target="_blank">LIVE DEMO</a> ได้เลยครับ</p>
<p>แหล่งอ้างอิงและ API</p>
<ul>
<li><a href="http://jtemplates.tpython.com/">http://jtemplates.tpython.com/</a></li>
<li><a href="http://www.jquerytips.com/2008/12/07/jtemplate-template-engine-in-javascript/">http://www.jquerytips.com/2008/12/07/jtemplate-template-engine-in-javascript/</a></li>
</ul>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2009%2F05%2Fjtemplates-template-engine-%25e0%25b8%2582%25e0%25b8%25ad%25e0%25b8%2587-jquery%2F&amp;title=jTemplates%2C%20Template%20Engine%20%E0%B8%82%E0%B8%AD%E0%B8%87%20jQuery" id="wpa2a_12"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2009/05/jtemplates-template-engine-%e0%b8%82%e0%b8%ad%e0%b8%87-jquery/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>ไอเดีย Template Engine แบบ Basic</title>
		<link>http://blog.chonla.com/2009/05/%e0%b9%84%e0%b8%ad%e0%b9%80%e0%b8%94%e0%b8%b5%e0%b8%a2-template-%e0%b9%81%e0%b8%9a%e0%b8%9a-basic/</link>
		<comments>http://blog.chonla.com/2009/05/%e0%b9%84%e0%b8%ad%e0%b9%80%e0%b8%94%e0%b8%b5%e0%b8%a2-template-%e0%b9%81%e0%b8%9a%e0%b8%9a-basic/#comments</comments>
		<pubDate>Thu, 14 May 2009 15:41:49 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[PHP]]></category>
		<category><![CDATA[Souce Code]]></category>
		<category><![CDATA[Template Engine]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Template]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=171</guid>
		<description><![CDATA[ใน framework ที่มีการแยก View ออกมาอย่างชัดเจน อย่างเช่น MVC จะมีการใช้ Template เข้ามาเป็นตัวช่วยในการช่วยแสดงผล ไม่ว่าจะเป็นการใช้ Template Engine อย่างเช่น smarty เป็นต้น ทีนี้ ผมก็มาคิด ๆ ดูว่าไอ้เจ้า Template เนี่ย มันมีไอเดียการทำงานยังไง ลองมาดูกัน หลักการง่าย ๆ ของการทำ Template คือ การแยกแนวคิดให้ตัว Template ทำหน้าที่แสดงผลอย่างเดียว โดยไม่มี Logic อื่น ๆ มาเกี่ยวข้อง เราอาจจะมี condition บางอย่างอยู่ใน template ได้ แต่ก็เฉพาะในส่วนที่เกี่ยวข้องกับการแสดงผลเท่านั้น ดังนั้น สิ่งที่จำเป็นก่อนการแสดงผลนั่นก็คือ การเตรียมข้อมูลที่จะแสดงให้พร้อมนั่นเอง ต่อจากนั้นเราก็นำข้อมูลที่เราเตรียมไว้ ไปยัดใส่ template ที่เราเตรียมไว้ เป็นอันเรียบร้อย เรามาสร้าง template engine แบบง่ายที่สุดในโลกกันดีกว่า function [...]]]></description>
			<content:encoded><![CDATA[<p>ใน framework ที่มีการแยก View ออกมาอย่างชัดเจน อย่างเช่น MVC จะมีการใช้ Template เข้ามาเป็นตัวช่วยในการช่วยแสดงผล ไม่ว่าจะเป็นการใช้ Template Engine อย่างเช่น <a title="Smarty Template Engine" href="http://www.smarty.net/" target="_blank">smarty</a> เป็นต้น</p>
<p>ทีนี้ ผมก็มาคิด ๆ ดูว่าไอ้เจ้า Template เนี่ย มันมีไอเดียการทำงานยังไง ลองมาดูกัน</p>
<p><span id="more-171"></span>หลักการง่าย ๆ ของการทำ Template คือ การแยกแนวคิดให้ตัว Template ทำหน้าที่แสดงผลอย่างเดียว โดยไม่มี Logic อื่น ๆ มาเกี่ยวข้อง เราอาจจะมี condition บางอย่างอยู่ใน template ได้ แต่ก็เฉพาะในส่วนที่เกี่ยวข้องกับการแสดงผลเท่านั้น ดังนั้น สิ่งที่จำเป็นก่อนการแสดงผลนั่นก็คือ การเตรียมข้อมูลที่จะแสดงให้พร้อมนั่นเอง ต่อจากนั้นเราก็นำข้อมูลที่เราเตรียมไว้ ไปยัดใส่ template ที่เราเตรียมไว้ เป็นอันเรียบร้อย</p>
<p>เรามาสร้าง template engine แบบง่ายที่สุดในโลกกันดีกว่า</p>
<pre name="code" class="js">
function apply_template($data, $template)
{
    ob_start();
    include ($template);
    $output = ob_get_clean();
    return $output;
} 
</pre>
<p>ดูเหมือนง่ายมั๊ยครับ แค่ไม่กี่บรรทัดเอง ส่วนของ template file เราก็จะมีตัวแปรไว้ใช้งานตัวนึง ชื่อว่า $data นั่นเองครับ เวลาเราส่งค่าเข้า template ก็ให้ส่งผ่านตัวแปรตัวเดียวครับ (อาจจะทำเป็น array หรือ object ก็ได้ครับ)</p>
<p>ลองดูตัวอย่างใน <a title="LIVE DEMO : Basic Template Engine" href="http://sandbox.chonla.com/template/" target="_blank">LIVE DEMO</a> นะครับ</p>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2009%2F05%2F%25e0%25b9%2584%25e0%25b8%25ad%25e0%25b9%2580%25e0%25b8%2594%25e0%25b8%25b5%25e0%25b8%25a2-template-%25e0%25b9%2581%25e0%25b8%259a%25e0%25b8%259a-basic%2F&amp;title=%E0%B9%84%E0%B8%AD%E0%B9%80%E0%B8%94%E0%B8%B5%E0%B8%A2%20Template%20Engine%20%E0%B9%81%E0%B8%9A%E0%B8%9A%20Basic" id="wpa2a_14"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2009/05/%e0%b9%84%e0%b8%ad%e0%b9%80%e0%b8%94%e0%b8%b5%e0%b8%a2-template-%e0%b9%81%e0%b8%9a%e0%b8%9a-basic/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>หมายเลขบัตรประชาชน? สร้างเองดีกว่า</title>
		<link>http://blog.chonla.com/2009/04/%e0%b8%ab%e0%b8%a1%e0%b8%b2%e0%b8%a2%e0%b9%80%e0%b8%a5%e0%b8%82%e0%b8%9a%e0%b8%b1%e0%b8%95%e0%b8%a3%e0%b8%9b%e0%b8%a3%e0%b8%b0%e0%b8%8a%e0%b8%b2%e0%b8%8a%e0%b8%99-%e0%b8%aa%e0%b8%a3%e0%b9%89%e0%b8%b2/</link>
		<comments>http://blog.chonla.com/2009/04/%e0%b8%ab%e0%b8%a1%e0%b8%b2%e0%b8%a2%e0%b9%80%e0%b8%a5%e0%b8%82%e0%b8%9a%e0%b8%b1%e0%b8%95%e0%b8%a3%e0%b8%9b%e0%b8%a3%e0%b8%b0%e0%b8%8a%e0%b8%b2%e0%b8%8a%e0%b8%99-%e0%b8%aa%e0%b8%a3%e0%b9%89%e0%b8%b2/#comments</comments>
		<pubDate>Wed, 01 Apr 2009 08:14:57 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[Algorithm]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Souce Code]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Utility]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=155</guid>
		<description><![CDATA[สาเหตุที่ผมเขียนบทความนี้ขึ้นมา เพราะว่ามันจะมีบางช่วงเวลาที่ผมจำเป็นต้องใช้หมายเลขบัตรประชาชนในการทำอะไรหลาย ๆ อย่าง ไม่ว่าจะเป็นเรื่องของการทำระบบ verify หมายเลขบัตรประชาชน หรือเอาไปใช้สมัครโน่นสมัครนี่ บางครั้งผมแค่อยากลองเฉย ๆ แต่ไม่ได้อยากใช้หมายเลขบัตรของผมจริง ๆ ด้วยเหตุผลด้านความปลอดภัยของผมเอง ผมเลยลองสร้างหมายเลขบัตรประชาชนจากอัลกอริธึมในการตรวจสอบหมายเลขบัตรประชาชนขึ้นมา อัลกอริธึมในการตรวจสอบหมายเลขบัตรประชาชน สามารถหาได้ตามเว็บทั่ว ๆ ไป ที่ผมได้มาก็จะประมาณนี้ครับ (Javascript) function validate_thai_citizen_id(id) { var b = 0; if (id.length &#60; 13) return false; checksum = id.substring(12, 13); for (var i = 0; i &#60; 12; i++) { b += parseInt(id.substring(i, i+1)) * (13 - i); [...]]]></description>
			<content:encoded><![CDATA[<p>สาเหตุที่ผมเขียนบทความนี้ขึ้นมา เพราะว่ามันจะมีบางช่วงเวลาที่ผมจำเป็นต้องใช้หมายเลขบัตรประชาชนในการทำอะไรหลาย ๆ อย่าง ไม่ว่าจะเป็นเรื่องของการทำระบบ verify หมายเลขบัตรประชาชน หรือเอาไปใช้สมัครโน่นสมัครนี่ บางครั้งผมแค่อยากลองเฉย ๆ แต่ไม่ได้อยากใช้หมายเลขบัตรของผมจริง ๆ ด้วยเหตุผลด้านความปลอดภัยของผมเอง ผมเลยลองสร้างหมายเลขบัตรประชาชนจากอัลกอริธึมในการตรวจสอบหมายเลขบัตรประชาชนขึ้นมา</p>
<p><span id="more-155"></span>อัลกอริธึมในการตรวจสอบหมายเลขบัตรประชาชน สามารถหาได้ตามเว็บทั่ว ๆ ไป ที่ผมได้มาก็จะประมาณนี้ครับ (Javascript)</p>
<pre name="code" class="js">
function validate_thai_citizen_id(id)
{
    var b = 0;
    if (id.length &lt; 13) return false;
    checksum = id.substring(12, 13);
    for (var i = 0; i &lt; 12; i++)
    {
        b += parseInt(id.substring(i, i+1)) * (13 - i);
    }
    tmp = 11 - (b % 11);
    switch(tmp)
    {
        case 11: check = 1; break;
        case 10: check = 0; break;
        default: check = tmp;
    }
    return (check == checksum);
}
</pre>
<p>จาก code ด้านบน เราจะเห็นได้ว่าส่วนที่สำคัญที่สุดคือ digit สุดท้าย ซึ่งจะทำหน้าที่เป็น checksum digit ซึ่งเราสามารถคำนวณได้จาก 12 digits แรก</p>
<p>เมื่อเราเอามาจัดการเขียนให้เป็นเรื่องเป็นราวจะได้แบบนี้ครับ</p>
<pre name="code" class="php">
function generate_thai_citizen_id()
{
	$checksum = 0;
	$b = 0;
	$r = 0;
	$t = "";
	mt_srand();
	for ($i = 0; $i < 12; $i ++)
	{
		$r = mt_rand(0, 9);
		$b += $r * (13 - $i);
		$t .= "$r";
	}
	$tmp = 11 - ($b % 11);
	switch($tmp)
	{
		case 11: $check = 1; break;
		case 10: $check = 0; break;
		default: $check = $tmp;
	}
	$t .= $check;
	return $t;
}
</pre>
<p>Code ด้านบนนี้ผมพอร์ตมาจาก Javascript version ที่ผมทำไว้ให้เป็น PHP ครับ</p>
<p>ลองดูหน้าที่ทำเสร็จแล้ว (PHP) ได้ที่ <a title="LIVE DEMO: Randomly create citizen ID" href="http://sandbox.chonla.com/citizenid/" target="_blank">LIVE DEMO</a> เลยครับ</p>
<p>ปล. หมายเลขบัตรประชาชนที่สร้างจาก <a title="LIVE DEMO: Randomly create citizen ID" href="http://sandbox.chonla.com/citizenid/" target="_blank">LIVE DEMO</a> สามารถนำไปใช้ได้จริงนะครับ ใช้ให้ถูกที่ถูกกฏหมายนะครับ<br />
ปล. อีกที วันที่ 9 ก.ย. 52 ผมแก้ไข code ที่เป็น เวอร์ชั่น php ให้ถูกต้องครับ มีบักนิดหน่อย</p>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2009%2F04%2F%25e0%25b8%25ab%25e0%25b8%25a1%25e0%25b8%25b2%25e0%25b8%25a2%25e0%25b9%2580%25e0%25b8%25a5%25e0%25b8%2582%25e0%25b8%259a%25e0%25b8%25b1%25e0%25b8%2595%25e0%25b8%25a3%25e0%25b8%259b%25e0%25b8%25a3%25e0%25b8%25b0%25e0%25b8%258a%25e0%25b8%25b2%25e0%25b8%258a%25e0%25b8%2599-%25e0%25b8%25aa%25e0%25b8%25a3%25e0%25b9%2589%25e0%25b8%25b2%2F&amp;title=%E0%B8%AB%E0%B8%A1%E0%B8%B2%E0%B8%A2%E0%B9%80%E0%B8%A5%E0%B8%82%E0%B8%9A%E0%B8%B1%E0%B8%95%E0%B8%A3%E0%B8%9B%E0%B8%A3%E0%B8%B0%E0%B8%8A%E0%B8%B2%E0%B8%8A%E0%B8%99%3F%20%E0%B8%AA%E0%B8%A3%E0%B9%89%E0%B8%B2%E0%B8%87%E0%B9%80%E0%B8%AD%E0%B8%87%E0%B8%94%E0%B8%B5%E0%B8%81%E0%B8%A7%E0%B9%88%E0%B8%B2" id="wpa2a_16"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2009/04/%e0%b8%ab%e0%b8%a1%e0%b8%b2%e0%b8%a2%e0%b9%80%e0%b8%a5%e0%b8%82%e0%b8%9a%e0%b8%b1%e0%b8%95%e0%b8%a3%e0%b8%9b%e0%b8%a3%e0%b8%b0%e0%b8%8a%e0%b8%b2%e0%b8%8a%e0%b8%99-%e0%b8%aa%e0%b8%a3%e0%b9%89%e0%b8%b2/feed/</wfw:commentRss>
		<slash:comments>7</slash:comments>
		</item>
		<item>
		<title>MVC Design Pattern (MVC ไม่ได้ย่อจากการ์ตูน Mavel Comic นะเฟ้ย)</title>
		<link>http://blog.chonla.com/2009/01/mvc-design-pattern-%e0%b9%84%e0%b8%a1%e0%b9%88%e0%b9%83%e0%b8%8a%e0%b9%88%e0%b8%81%e0%b8%b2%e0%b8%a3%e0%b9%8c%e0%b8%95%e0%b8%b9%e0%b8%99-mavel-comic-%e0%b8%99%e0%b8%b0%e0%b9%80%e0%b8%9f%e0%b9%89/</link>
		<comments>http://blog.chonla.com/2009/01/mvc-design-pattern-%e0%b9%84%e0%b8%a1%e0%b9%88%e0%b9%83%e0%b8%8a%e0%b9%88%e0%b8%81%e0%b8%b2%e0%b8%a3%e0%b9%8c%e0%b8%95%e0%b8%b9%e0%b8%99-mavel-comic-%e0%b8%99%e0%b8%b0%e0%b9%80%e0%b8%9f%e0%b9%89/#comments</comments>
		<pubDate>Thu, 15 Jan 2009 16:10:41 +0000</pubDate>
		<dc:creator>chonla</dc:creator>
				<category><![CDATA[MVC]]></category>
		<category><![CDATA[Object Oriented]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Software Engineering]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Design Pattern]]></category>

		<guid isPermaLink="false">http://blog.chonla.com/?p=142</guid>
		<description><![CDATA[MVC ที่ผมจะพูดถึงนี้ ย่อมาจาก Model-View-Controller ครับ เป็นรูปแบบการออกแบบระบบ โดยหลักการคือ จะแบ่งระบบที่เราออกแบบเป็น 3 ส่วนประกอบหลัก ๆ คือ Model, View และ Controller โดยที่แต่ละส่วนจะมีความสำคัญดังนี้ Model  จะหมายถึง Object ที่แทนข้อมูล หรือกิจกรรมต่าง ๆ ในระบบ เช่น ตารางใน database หรือจะเป็นโพรเซสงานหนึ่ง ๆ ก็ได้ครับ เราจะไม่นับข้อมูลดิบในระบบเป็น Model เพราะข้อมูลเหล่านั้นจะถูกครอบ (Encapsulated) ด้วย Model นั่นเองครับ ถ้าใครเคยเรียน Object Oriented มาน่าจะพอเข้าใจได้ดีนะครับ View จะหมายถึงการแสดงผลข้อมูลต่าง ๆ ที่ได้รับมาจาก Model ครับ ไม่ว่าจะอยู่ในรูปแบบของรูปภาพกราฟิคต่าง ๆ หรือข้อความก็ตาม นอกจากนี้เรายังสามารถแสดงผลที่ได้รับจาก Model หนึ่ง ๆ ได้หลายรูปแบบอีกด้วย Controller จะหมายถึง [...]]]></description>
			<content:encoded><![CDATA[<p>MVC ที่ผมจะพูดถึงนี้ ย่อมาจาก Model-View-Controller ครับ เป็นรูปแบบการออกแบบระบบ โดยหลักการคือ จะแบ่งระบบที่เราออกแบบเป็น 3 ส่วนประกอบหลัก ๆ คือ Model, View และ Controller โดยที่แต่ละส่วนจะมีความสำคัญดังนี้</p>
<p><span id="more-142"></span></p>
<ol>
<li>Model  จะหมายถึง Object ที่แทนข้อมูล หรือกิจกรรมต่าง ๆ ในระบบ เช่น ตารางใน database หรือจะเป็นโพรเซสงานหนึ่ง ๆ ก็ได้ครับ เราจะไม่นับข้อมูลดิบในระบบเป็น Model เพราะข้อมูลเหล่านั้นจะถูกครอบ (Encapsulated) ด้วย Model นั่นเองครับ ถ้าใครเคยเรียน Object Oriented มาน่าจะพอเข้าใจได้ดีนะครับ</li>
<li>View จะหมายถึงการแสดงผลข้อมูลต่าง ๆ ที่ได้รับมาจาก Model ครับ ไม่ว่าจะอยู่ในรูปแบบของรูปภาพกราฟิคต่าง ๆ หรือข้อความก็ตาม นอกจากนี้เรายังสามารถแสดงผลที่ได้รับจาก Model หนึ่ง ๆ ได้หลายรูปแบบอีกด้วย</li>
<li>Controller จะหมายถึง กิจกรรม การกระทำ หรือการตอบสนองต่อเหตุการณ์ต่าง ๆ ที่เกิดขึ้น โดยอาจจะมีผลทำให้ข้อมูลใน Model เปลี่ยนสถานะไปได้ครับ</li>
</ol>
<div id="attachment_144" class="wp-caption aligncenter" style="width: 294px"><a href="http://blog.chonla.com/wp-content/uploads/2009/01/model-view-controller-01.png"><img class="size-full wp-image-144" title="model-view-controller-01" src="http://blog.chonla.com/wp-content/uploads/2009/01/model-view-controller-01.png" alt="MVC diagram" width="284" height="340" /></a><p class="wp-caption-text">MVC diagram</p></div>
<p>รูปภาพด้านบนจะแสดงให้เห็นถึงความสัมพันธ์ระหว่าง Model, View และ Controller ในรูปแบบ Diagram (ขอบคุณภาพจาก <a href="http://www.tonymarston.net/php-mysql/model-view-controller.html">http://www.tonymarston.net/php-mysql/model-view-controller.html</a> ด้วยครับ)</p>
<p><strong>ข้อดีของการออกแบบระบบด้วย MVC Pattern</strong></p>
<ul>
<li><strong>การออกแบบที่ชัดเจน</strong> เมื่อเรากำหนดให้ Model อยู่ในรูปแบบของ Object ในระบบ ส่งผลให้เราสามารถมองภาพระบบโดยรวมได้ชัดเจนมากขึ้นว่า Model ใด สัมพันธ์กับ Model ใดในลักษณะใด รวมไปถึงคำสั่งต่าง ๆ ใน Object ที่เราสามารถเรียกใช้งานได้ จะทำให้เรามองเห็นภาพของพฤติกรรมของ Model นั้น ๆ อีกด้วย</li>
<li><strong>การปรับปรุง/แก้ไขได้โดยง่าย</strong> เมื่อเราออกแบบตาม MVC Pattern ทำให้เราสามารถปรับปรุง แก้ไขส่วนใด ๆ ได้อย่างง่ายดายโดยที่ไม่กระทบกับส่วนที่เหลือ เนื่องจากทั้ง 3 ส่วนต่างอิสระต่อกัน เพียงเรากำหนด Interface ของแต่ละส่วนให้ชัดเจน และทำการพัฒนา แก้ไข หรือปรับปรุงภายใต้ Interface ที่กำหนดเท่านั้น</li>
<li><strong>View ที่หลากหลาย</strong> หลังจากที่เราแยก View กับ Model ออกจากกัน ทำให้เราสามารถออกแบบ View ได้หลายรูปแบบ เปรียบเทียบได้กับ Model หนึ่งที่คอย Generate XML Data รายงานดัชนีหุ้น และมี View ที่นำข้อมูล XML ไปใช้สร้างเป็นกราฟ หรือตารางนั้นเอง</li>
<li><strong>Maintain ระบบได้ง่าย</strong> เพราะเราได้ออกแบบระบบที่มีโครงสร้างชัดเจน ทำให้ยืดหยุ่นต่อการเพิ่มเติม รวมไปถึงการนำส่วนใด ๆ กลับมาใช้ซ้ำได้อีกด้วย (Reusability)</li>
</ul>
<p><strong>แล้วข้อเสียล่ะ?</strong></p>
<p>เมื่อพูดถึงข้อดีแล้ว ต่อไปเราก็มาพูดถึงข้อเสียกันบ้าง ข้อเสียหนึ่งที่เห็นได้ชัดเลยคือ มันซับซ้อนเกินไป ถ้าเราจะนำมาใช้กับระบบขนาดเล็ก เทียบง่าย ๆ มันก็คงไม่ต่างจากภาษิตที่ว่า ขี่ช้างจับตั๊กแตน นั่นเองครับ</p>
<p><strong>นอกจากนี้แล้ว</strong></p>
<p>นอกจากนี้แล้ว ทางฝั่งภาษา PHP เองก็มี Framework ที่สนับสนุนการพัฒนาระบบที่มีพื้นฐาน MVC design pattern อยู่หลายตัวครับ ผมขออนุญาตลอกมาจาก Wiki ให้ดูกัน (<a href="http://en.wikipedia.org/wiki/Model-view-controller#PHP">http://en.wikipedia.org/wiki/Model-view-controller#PHP)</a></p>
<ul>
<li></li>
<li>Akelos PHP Framework &#8211; a Ruby on Rails port to PHP4/5.</li>
<li>CakePHP &#8211; webapplication framework modeled after the concepts of Ruby on Rails.</li>
<li>CodeIgniter &#8211; A PHP MVC framework.</li>
<li>FUSE &#8211; A powerful but easy-to-use PHP 5 Framework for MVC development modeled after the concepts of Ruby on Rails.</li>
<li>Jelix (web framework)</li>
<li>Jaws &#8211; is a Framework and Content Management System for building dynamic web sites.</li>
<li>Joomla v1.5.x &#8211; is an open source Content Management System that employs the MVC model for its extensions, called components and modules.</li>
<li>Kohana &#8211; is an open source MVC oriented framework, originally forked from CodeIgniter.</li>
<li>LISA MVC &#8211; is an open source object oriented web application framework.</li>
<li>Odin Assemble &#8211; Small footprint PHP based MVC Framework.</li>
<li>Orinoco Framework &#8211; is a full-stack yet lightweight framework written in PHP5. It implements the Model 2 design paradigm.</li>
<li>PHPonTrax &#8211; A PHP 5 MVC framework modeled after Ruby on Rails.</li>
<li>phpXCore &#8211; A MVC design pattern based PHP content management framework compatible with PHP4 and PHP5.</li>
<li>Prado &#8211; A PHP 5 MVC framework modeled after ASP.NET web forms.</li>
<li>Qcodo &#8211; is an open-source PHP 5 web application framework</li>
<li>SilverStripe &#8211; contains a fully fledged PHP 5.2 ORM/MVC Framework focused on building websites. Much like Ruby on Rails.</li>
<li>Solar</li>
<li>Switch board (framework) &#8211; with Routing PHP 5 MVC Framework with Routing.</li>
<li>Symfony Framework- PHP 5 MVC Framework modeled after the concepts of Ruby on Rails.</li>
<li>Zend Framework &#8211; A PHP 5-based MVC framework modeled after the concepts of Ruby on Rails.</li>
<li>ZNF &#8211; PHP5 MVC framework for enterprise web applications</li>
<li>Zoop &#8211; Framework A Mature PHP 4/5 MVC framework.</li>
<li>PureMVC &#8211; Framework for PHP</li>
</ul>
<p><strong>เอกสารอ้างอิง</strong> </p>
<ul>
<li><a href="http://en.wikipedia.org/wiki/Model-view-controller">http://en.wikipedia.org/wiki/Model-view-controller</a></li>
<li><a href="http://www.tonymarston.net/php-mysql/model-view-controller.html">http://www.tonymarston.net/php-mysql/model-view-controller.html</a></li>
<li><a href="http://cristobal.baray.com/indiana/projects/mvc.html">http://cristobal.baray.com/indiana/projects/mvc.html</a></li>
<li><a href="http://aspalliance.com/1562_Implementing_the_MVC_Design_Pattern_in_ASPNET.1">http://aspalliance.com/1562_Implementing_the_MVC_Design_Pattern_in_ASPNET.1</a></li>
</ul>
<p><a class="a2a_dd a2a_target addtoany_share_save" href="http://www.addtoany.com/share_save#url=http%3A%2F%2Fblog.chonla.com%2F2009%2F01%2Fmvc-design-pattern-%25e0%25b9%2584%25e0%25b8%25a1%25e0%25b9%2588%25e0%25b9%2583%25e0%25b8%258a%25e0%25b9%2588%25e0%25b8%2581%25e0%25b8%25b2%25e0%25b8%25a3%25e0%25b9%258c%25e0%25b8%2595%25e0%25b8%25b9%25e0%25b8%2599-mavel-comic-%25e0%25b8%2599%25e0%25b8%25b0%25e0%25b9%2580%25e0%25b8%259f%25e0%25b9%2589%2F&amp;title=MVC%20Design%20Pattern%20%28MVC%20%E0%B9%84%E0%B8%A1%E0%B9%88%E0%B9%84%E0%B8%94%E0%B9%89%E0%B8%A2%E0%B9%88%E0%B8%AD%E0%B8%88%E0%B8%B2%E0%B8%81%E0%B8%81%E0%B8%B2%E0%B8%A3%E0%B9%8C%E0%B8%95%E0%B8%B9%E0%B8%99%20Mavel%20Comic%20%E0%B8%99%E0%B8%B0%E0%B9%80%E0%B8%9F%E0%B9%89%E0%B8%A2%29" id="wpa2a_18"><img src="http://blog.chonla.com/wp-content/plugins/add-to-any/share_save_171_16.gif" width="171" height="16" alt="Share"/></a></p>]]></content:encoded>
			<wfw:commentRss>http://blog.chonla.com/2009/01/mvc-design-pattern-%e0%b9%84%e0%b8%a1%e0%b9%88%e0%b9%83%e0%b8%8a%e0%b9%88%e0%b8%81%e0%b8%b2%e0%b8%a3%e0%b9%8c%e0%b8%95%e0%b8%b9%e0%b8%99-mavel-comic-%e0%b8%99%e0%b8%b0%e0%b9%80%e0%b8%9f%e0%b9%89/feed/</wfw:commentRss>
		<slash:comments>13</slash:comments>
		</item>
	</channel>
</rss>

