เราสามารถใช้คำสั่งสำหรับส่ง Email ใน CI
โดยไม่ต้องติดตั้ง Library ใดๆ เพิ่มอีก เพียงแค่
ใช้งาน Email Library ที่มีมาให้อยู่แล้ว รองรับ
การตั้งค่าการส่งแบบ SMTP และมีรูปแบบการใช้งาน
ที่ง่ายไม่ซับซ้อน
การส่งอีเมลใน CI รองรับการกำหนดใช้งานใน 3 protocal
ได้แก่ Mail, Sendmail และ SMTP ซึ่งจริงๆ แล้วการส่งทั้งหมด
ก็จะผ่าน SMTP ซึ่งเป็น protocal หลักในการส่งอีเมล เพียงแค่
ถูกแยกด้วยรูปแบบการส่ง เช่น แบบ Mail ก็เป็นการใช้งานฟังก์ชั่น mail()
ของ PHP ปกติแล้วส่งค่าไปที่ SMTP Server ซึ่งผู้ดูแลระบบของ server นั้น
ได้กำหนดการตั้ง SMTP ไว้อยู่แล้ว เช่นเดียวกันกับ sendmail ก็ทำงานในลักษณะ
เดียวกัน เพียงแต่แทนที่จะใช้คำสั่ง mail() ปกติ ก็ไปใช้คำสั่งใน sendmail library
แทน Sendmail Library ก็ทำการส่งค่าไป SMTP Server เพื่อส่งอีเมล
ในบางกรณีหากคำสั่ง mail() ไม่ได้เปิดใช้งาน หรือบาง server ก็อาจจะส่งค่าไปใช้งาน
sendmail library แทนคำสั่ง mail() ก็ได้ หากเรียกใช้งานผ่าน Mail protocal
สำหรับ SMTP protocal เป็นเหมือนการกำหนด SMTP ที่ใช้ส่งอีเมลแบบกำหนดเอง แทนที่เรา
จะใช้ค่าของระบบ ที่ server กำหนดไว้ ก็ใช้ค่า SMTP ที่เราสามารถกำหนด host ,username,
password และ port เองได้ การใช้งานแบบ SMTP ช่วยได้มากหากไม่ต้องการให้อีเมลของเรา
ถูกมองเป็น spam ถ้าเราเลือกใช้งาน SMTP Host ที่น่าเชื่อถือ เราสามารถทดลองใช้ค่า Free
SMTP server เพื่อทดสอบการใช้งานได้ เช่น MailJet หรือ Gmail
เราสามารถทดสอบการทำงาน การส่งอีเมลในเครื่อง โดยใช้เครื่องมือของ xampp จำลองเป็น
Mail Server ตามตัวอย่างเนื้อหาด้านล่าง ผู้เขียนจะใช้วิธีข้างต้นในการทดสอบประกอบการอธิบาย
การตั้งค่า mercury ใน xampp สำหรับทดสอบส่งอีเมล บน localhost http://niik.in/681
https://www.ninenik.com/content.php?arti_id=681 via @ninenik
การเรียกใช้งาน Email Library
ในการใช้งานการส่งอีเมลใน CI เราสามารถเรียกใช้งาน Email Library ด้วยคำสั่งง่าย 2 รูปแบบ
ด้านล่าง ดังนี้
$email = \Config\Services::email(); // หรือ $email = service('email');
เตรียมส่วนของไฟล์ทดสอบ
ให้เราเตรียมส่วนของไฟล์ทดสอบตามรูปแบบดังนี้
app/Controllers/Helloworld.php
<?php namespace App\Controllers; use CodeIgniter\Controller; // เรียกใช้งาน Controller class class Helloworld extends Controller { public function index() { $email = service('email'); // เรียกใช้งาน email library } }
เราจะจำลองการใช้งานง่ายๆ เพียงแค่เรียกมายัง /helloworld ก็ให้ส่งอีเมลตามรูปแบบที่กำหนด
ข้างต้นเราจะได้ $email เป็นตัวแปร instance ของ Email Library ไว้ใช้งาน
คำสั่งต่างๆ สำหรับส่ง Email
ก่อนใช้งาน เรามาดูคำสั่งต่างๆ สำหรับเรียกใช้งานการส่งอีเมล ดังนี้
$email->setFrom() // สำหรับกำหนด อีเมล ชื่อ ผู้ส่ง $email->setReplyTo() // สำหรับกำหนดอีเมล ชื่อ ที่ต้องการให้ตอบกลับ $email->setTo() // สำหรับกำหนดอีเมลที่จะส่งถึง กำหนดหลายค่าให้คั่นด้วย คอมม่า (,) $email->setCC() // คล้ายกับ setTo() อีเมลเพิ่มเติม นอกเหนือจากที่กำหนดใน To โดยตรง $email->setBCC() // คล้าย To และ CC เพียงแต่ผู้รับอีเมลคนอื่นๆ จะไม่รู้ว่าส่งมายังอีเมลนี้ด้วย $email->setSubject() // กำหนดหัวเรื่องอีเมล $email->setMessage() // กำหนดเนื้อหาอีเมล เป็นข้อความปกติ หรือเป็น html ก็ได้ $email->setAltMessage() // สำหรับข้อความอีเมลทางเลือก ที่แสดงเฉพาะข้อความได้อย่างเดียว $email->setHeader() // กำหนดค่า header ของอีเมลเพิ่มเติม $email->clear() // ล้างค้าเพื่อเริ่มต้น การกำหนดการส่งอีเมลใหม่ $email->send() // สำหรับทำคำสั่งส่งอีเมล ตามค่าที่กำหนด $email->attach() // สำหรับแนบไฟล์ไปในอีเมล $email->setAttachmentCID() // สำหรับแนบรูปไปในข้อความอีเมล
การตั้งค่าการส่งอีเมล
เราสามารถกำหนดการตั้งค่าการส่งอีเมล ตามรูปแบบการใช้งาน protocal ได้ โดยเฉพาะการส่งแบบ SMTP
ซึ่งมีการตั้งค่าต่างๆ วิธีที่ดีที่สุดคือ ให้เราไปกำหนดในไฟล์ app/Config/Email.php โดย protocal หลักจะเป็น
mail ตัวอย่างการกำหนดแบบ SMTP ใน Email.php
app/Config/Email.php (บางส่วน)
public $protocol = 'smtp'; public $SMTPHost = 'in-v3.mailjet.com'; public $SMTPUser = '8e3086sdffdsfsf41e051fe9'; public $SMTPPass = 'c45cffdsfdsfdsds90fea'; public $SMTPPort = 587; public $SMTPCrypto = 'tls';
ข้างต้นเป็นการกำหนดการส่งอีเมลหลักในระบบใช้เป็นแบบ SMTP ตามค่าที่กำหนด ข้อมูลด้านบนเป็นข้อมูลค่า
สำหรับทดสอบเท่านั้น นำไปใช้ไม่ได้ หากเราใช้ SMTP ค่าใด ก็ให้กำหนดตามค่านั้นๆ
สังเกตว่า ถ้าเรากำหนดใช้งาน protocal เป็น แบบ smtp เราต้องกำหนดค่าเพิ่มเติมตามด้านบน แต่ถ้าเราใช้
เป็นแบบ mail หรือใช้ค่าเดิม เราไม่ต้องกำหนดค่าใดๆ เพิ่มอีก
public $protocol = 'mail';
สำหรับการกำหนดเป็นแบบ sendmail เราต้องดูการกำหนดในส่วนของ mailPath ด้วย เป็นการระบุ path ของ
sendmail library ใน server สำหรับเรียกใช้งาน
public $protocol = 'sendmail'; public $mailPath = '/usr/sbin/sendmail';
การตั้งค่าใน Email.php จะสะดวกสำหรับค่าที่จะใช้งานเป็นค่าหลักในระบบ โดยเฉพาะถ้าใช้เป็นแบบ smtp
ที่จะต้องมีการตั้งค่าต่างๆ เพิ่มเติมมากกว่าปกติ และถ้าเราจะไปตั้งค่าในแต่ละหน้าก็อาจจะไม่สะดวกนัก
สำหรับค่าอีกค่า ที่เราอาจจะต้องการปรับก็คือ
public $mailType = 'text';
ถ้าเราส่งอีเมลส่วนใหญ่เป็นแบบ html ไม่ใช่ text ให้เราเปลี่ยนเป็น html แทน หรือถ้าใช้ค่าใดๆ เป็นส่วนใหญ่
ให้กำหนดเป็นค่านั้นๆ ไว้ก่อน เพราะเราสามารถปรับเปลี่ยนเพิ่มเติม ในขึ้นตอนเรียกใช้ ถ้าจำเป็น
การตั้งค่าในขั้นตอนการเรียกใช้งาน
นอกจากเราจะสามารถกำหนดการตั้งค่าหลักที่ไฟล์ Email.php ตามที่กล่าวไปแล้วด้านบน เรายังสามารถกำหนด
รูปแบบการตั้งค่าเฉพาะการเรียกใช้งานในหน้านั้นๆ ได้ดังนี้
รูปแบบ smtp
$email = service('email'); // เรียกใช้งาน email library $config['protocol'] = 'smtp'; $config['SMTPHost'] = 'in-v3.mailjet.com'; $config['SMTPUser'] = '8e308660xxxxxxxxxx1e051fe9'; $config['SMTPPass'] = 'c45cff79fxxxxxxxxxx674990fea'; $config['SMTPPort'] = 587; // 25 $config['SMTPCrypto'] = 'tls'; $config['mailType'] = 'html'; $email->initialize($config);
รูปแบบ mail
$email = service('email'); // เรียกใช้งาน email library $config['protocol'] = 'mail'; $config['mailType'] = 'html'; $email->initialize($config);
รูปแบบ sendmail
$email = service('email'); // เรียกใช้งาน email library $config['protocol'] = 'sendmail'; $config['mailType'] = 'html'; $email->initialize($config);
จำไว้ว่า หากเราใช้ค่าจากการกำหนดใน Email.php โดยตรง เราไม่ต้องใช้คำสั่ง
$email->initialize($config);
แต่ถ้าเรามีการกำหนดการตั้งค่าเพิ่มเติมในหน้าใช้งาน เราต้องเรียกใช้คำสั่ง initialize($config)
เพื่อปรับการใช้งานการตั้งค่า เป็นตามที่กำหนดในขณะเรียกใช้งาน
ตัวอย่างการส่ง Email
เรามาดูตัวอย่างรูปแบบการส่งอีเมล และการใช้คำสั่งต่างๆ ดังนี้
$email = service('email'); // เรียกใช้งาน email library // กำหนดการตั้งค่า หากใช้รูปแบบใน Email.php ไม่ต้องกำหนดเพิ่มส่วนนี้ $config['protocol'] = 'smtp'; $config['SMTPHost'] = 'in-v3.mailjet.com'; $config['SMTPUser'] = '8e308660xxxxxxx051fe9'; $config['SMTPPass'] = 'c45cff79xxxxxxxxxx674990fea'; $config['SMTPPort'] = 587; $config['SMTPCrypto'] = 'tls'; $config['mailType'] = 'html'; $email->initialize($config); // กำหนดผู้ส่ง $email->setFrom('ninenik@gmail.com', 'Ninenik Narkdee'); // กำหนดผู้รับ $email->setTo('ninenik@gmail.com'); // ทดสอบส่งหาตัวเอง // $email->setTo('demo@localhost.com'); // $email->setCC('another@another-example.com'); // $email->setBCC('them@their-example.com');*/ // กำหนดหัวเรื่อง $email->setSubject('Email Test'); // กำหนดตัวแปรข้อความอีเมล แบบ HTML $body="รายละเอียดอีเมล ทดสอบส่ง <br>"; $body.="ใช้งาน mercury/32 ใน xampp ส่งอีเมลใน localhost <br>"; $body.="จากเว็บไซต์ <a href='https://www.ninenik.com'>www.ninenik.com</a> <br>"; $body.="<img src='https://www.ninenik.com/images/logo_01_Sat.gif' /><br>"; // กำหนดข้อความ // $email->setMessage('Testing the email class.'); $email->setMessage($body); // ใช้จากตัวแปร // การแนบไฟล์ $email->attach(ROOTPATH.'public/uploads/photo/for-line-1.png','inline'); $email->attach(ROOTPATH.'public/uploads/photo/for-line-2.png'); $email->attach('https://i.imgur.com/nKLtn0j.png'); // แนบไฟล์จาก URL // ทำคำสั่งส่งอีเมล if($email->send()){ echo "Successfull"; }
การกำหนดค่า และใช้งานคำสั่งอื่นๆ เพิ่มเติม
การกำหนดอีเมลผู้ส่ง เราจะกำหนดอีเมลเป็น ค่าแรก และกำหนดชื่อที่ต้องการแสดงเป็นค่าที่ 2
$email->setFrom('you@example.com', 'Your Name');
เวลาเราส่งอีเมลไป หากผู้รับต้องการตอบกลับ หรือกดปุ่ม reply ในโปรแกรมอีเมล ก็จะหมายถึง
การตอบกลับมายังอีเมลของผู้ส่ง แต่ถ้าเราต้องการให้ผู้รับ ตอบกลับไปอีกอีเมลหนึ่งแทนอีเมลที่ส่งไป
เราก็สามารถกำหนดในคำสั่งนี้ได้
$email->setReplyTo('you@example.com', 'Your Name');
กรณีต้องการส่งอีเมลไปให้ผู้รับหลายๆ คน สามารถกำหนดในรูปแบบดังนี้ได้
// แบบ string ข้อความคั่นด้วย comma (,) $email->setTo('one@example.com, two@example.com, three@example.com'); // แบบ array เช่น กรณีเรามีรายการอีเมลเป็นแบบ array ก็ส่งค่าตัวแปร array // เข้ามาในคำสั่ง setTo($arr_emailList) ได้ $email->setTo(['one@example.com', 'two@example.com', 'three@example.com']);
กรณีถ้าปกติเราส่งอีเมลเป็นแบบ HTML เป็นหลัก แต่ในบางครั้ง เป็นไปได้ที่ฝั่งผู้รับอีเมล จะใช้งาน
โปรแแกรม หรือเครื่องมือจัดการอีเมล ที่อาจจะไม่รองรับการแสดงผลในรูปแบบ HTML ตัว CI ก็จะทำ
การจัดแท็ก HTML แล้วส่งเป็นเฉพาะข้อความไป แต่ถ้าเราอยากได้รูปแบบข้อความเฉพาะสำหรับกรณี
ดังกล่าว โดยไม่ต้องแยกหรือตัดจากข้อความ HTML เราก็สามารถใช้คำสั่งดังนี้ได้
// เนื้อหาอีเมลที่เป็นแบบข้อความอย่างเดียว $email->setAltMessage('This is the alternative message');
การเพิ่มความน่าเชื่อถือของอีเมล ในบางครั้ง จำเป็นต้องส่งข้อมูลบางอย่าง ไปใน header ของ
อีเมล เพื่อไม่ให้อีเมลถูกมองว่าเป็น spam หรือเพื่อตรวจสอบความถูกต้องของอีเมล เราก็สามารถ
กำหนดส่วนของ header ของอีเมล เพิ่มเติม ด้วยคำสั่งดังนี้
$email->setHeader('Header1', 'Value1'); $email->setHeader('Header2', 'Value2');
ในกรณีที่เราต้องส่งอีเมลไปให้หลายๆ คน และแต่ละคนก็อาจจะมีเนื้อหาภายในที่แตกต่างกันไปบ้าง
ไม่มากก็น้อย ดังนั้น การวนลูปสำหรับส่งอีเมล เราจำเป็นต้องให้มั่นใจว่า รูปแบบที่กำหนดให้กับแต่ละคน
จะต้องไม่ซ้ำกัน โดยใช้คำสัง clear() ตามรูปแบบดังนี้
foreach ($list as $name => $address) { $email->clear(); $email->setTo($address); $email->setFrom('your@example.com'); $email->setSubject('Here is your info '.$name); $email->setMessage('Hi ' . $name . ' Here is the info you requested.'); $email->send(); }
ก่อนที่จะเริ่มกำหนดค่าส่งใหม่ เราใช้คำสั่ง clear() เพื่อให้มั่นใจว่า ค่าต่างๆ ที่กำหนดก่อนหน้าถูก reset
เป็นค่าว่าง ให้พร้อมสำหรับกำหนดค่าใหม่อีกครั้ง
กรณีที่มีการแนบไฟล์ เราสามารถกำหนด ค่าเป็น clear(true) เพื่อล้างค่าการกำหนดการแนบไฟล์ด้วยได้
การแนบไฟล์เราสามารถกำหนดรุปแบบเพิ่มเติมดังนี้ได้
กรณีเช่น ถ้าเป็นรูปภาพ และเราต้องการแสดงในอีเมลเลย สามารถใช้เป็น
$email->attach(ROOTPATH.'public/uploads/photo/for-line-1.png','inline');
ค่า parameter แรกเป็น path ของไฟล์บน server ของเรา และค่าที่สองเป็นรูปแแบบการแนบไฟล์
โดยค่าเริ่มต้นจะเป็นคำว่า 'attachment' หากเราต้องการแค่แนบไฟล์ ก็สามารถกำหนดในรูปแบบที่สอง
ได้เลย
$email->attach(WRITEPATH.'uploads/photo/for-line-2.png'); // มีค่าเท่ากับ $email->attach(WRITEPATH.'uploads/photo/for-line-2.png','attachment');
ถ้าเราต้องการเปลี่ยนชื่อไฟล์ที่แนบ เป็นชื่ออื่น ให้เรากำหนดใน parameter ตัวที่ 3 ประมาณนี้
$email->attach(WRITEPATH.'uploads/photo/for-line-2.png','attachment','newfile.png');
กรณีเราต้องการแนบไฟล์จากข้อมูลที่ส่งมา เช่นจากไฟล์ที่อัพโหลด เราสามารถใช้ค่า buffer หรือค่า
จากตัวแปรข้อมูลนั้นเป็น parameter แรก และกำหนด parameter ที่ 4 เป็น MIME type ของไฟล์นั้น
ตัวอย่างการประยุกต์ใช้งานก็เช่น เราไม่ต้องการเก็บไฟล์ไว้บน server อยากให้ผู้อัพโหลดไฟล์ที่จะส่ง
แล้ว เราก็ใช้ค่าข้อมูล buffer ของไฟล์นั้นเป็นค่าสำหรับแนบเป็นไฟล์เลย ดังนี้
$email->attach($buffer, 'attachment', 'report.pdf', 'application/pdf');
เราสามารถกำหนด ไฟล์ที่จะแนบเป็น url ได้ ดังนี้
$email->attach('https://i.imgur.com/nKLtn0j.png'); // แนบไฟล์จาก URL
เราสามารถแนบไฟล์รูปแบบแสดงในเนื้อหาอีเมล ด้วยคำสั่งดังนี้
$email->attach(ROOTPATH.'public/uploads/photo/for-line-2.png'); $cid = $email->setAttachmentCID(ROOTPATH.'public/uploads/photo/for-line-2.png'); $body="รายละเอียดอีเมล ทดสอบส่ง <br>"; $body.="ใช้งาน mercury/32 ใน xampp ส่งอีเมลใน localhost <br>"; $body.="จากเว็บไซต์ <a href='https://www.ninenik.com'>www.ninenik.com</a> <br>"; $body.="<img src='cid:". $cid."' /><br>"; $email->setMessage($body);
ใช้สำหรับรูปภาพที่ต้องการแนบไปเนื้อหาอีเมลเท่านั้น ถ้าส่งหลายๆ คน ให้เรากำหหนดการเรียกใช้งาน
คำสั่ง attach() ไว้นอกลูป ตามนี้
$filename = '/img/photo1.jpg'; $email->attach($filename); foreach ($list as $address) { $email->setTo($address); $cid = $email->setAttachmentCID($filename); $email->setMessage('<img src="cid:'. $cid .'" alt="photo1" />'); $email->send(); }
เนื้อหาเกี่ยวกับการส่งอีเมล ก็มีประมาณนี้ เราสามารถจัดการกับการส่งอีเมลในโปรเจ็คของเราโดยไม่จำเป็น
ต้องโหลด library เพิ่มเติม สามารถใช้งาน Email Library ที่มีมาให้ได้ง่ายและสะดวก
หวังว่าเนื้อหานี้จะเป็นประโยชน์ สามารถนำไปประยุกต์ใช้งานต่อไปได้