Kotchasan Framework Documentation
Csv Class - การจัดการไฟล์ CSV
Csv Class - การจัดการไฟล์ CSV
คลาส Csv เป็นเครื่องมือสำหรับการนำเข้าและส่งออกข้อมูล CSV ในกรอบงาน Kotchasan
namespace
Kotchasan\Csv;คุณสมบัติ
คลาส Csv รองรับการอ่านและเขียนไฟล์ CSV พร้อมกับการจัดการ character encoding และการตรวจสอบข้อมูล
คุณสมบัติสำคัญ
private $charset; // การเข้ารหัสตัวอักษร
private $columns; // ข้อมูลคอลัมน์
private $datas; // ข้อมูลที่นำเข้า
private $keys; // คอลัมน์สำหรับตรวจสอบข้อมูลซ้ำ;เมธอดหลัก
import()
นำเข้าข้อมูล CSV
class ExampleClass {
<?php
public static function import($csv, $columns, $keys = null, $charset = 'UTF-8'): array;
}Parameters:
$csv- ที่อยู่ไฟล์ CSV$columns- อาร์เรย์ข้อมูลคอลัมน์array('column1' => 'data type', 'column2' => 'data type')$keys- ชื่อคอลัมน์สำหรับตรวจสอบข้อมูลซ้ำ (null = ไม่ตรวจสอบ)$charset- การเข้ารหัสไฟล์ (ค่าเริ่มต้น UTF-8)
Returns: อาร์เรย์ข้อมูลที่นำเข้า
ตัวอย่างการใช้งาน:
use Kotchasan\Csv;
// นำเข้าข้อมูลสมาชิก
$columns = [
'name' => 'string',
'email' => 'string',
'age' => 'int',
'salary' => 'double',
'phone' => 'number',
'join_date' => 'date'
];
$data = Csv::import('/path/to/members.csv', $columns);
foreach ($data as $row) {
echo "ชื่อ: {$row['name']}, อีเมล: {$row['email']}, อายุ: {$row['age']}\n";
}
// นำเข้าข้อมูลพร้อมตรวจสอบซ้ำตาม email
$keys = ['email']; // ตรวจสอบซ้ำตาม email
$data = Csv::import('/path/to/members.csv', $columns, $keys);
// นำเข้าข้อมูลจากไฟล์ที่เป็น TIS-620
$data = Csv::import('/path/to/thai_data.csv', $columns, null, 'TIS-620');
// นำเข้าข้อมูลผลิตภัณฑ์
$productColumns = [
'product_code' => 'en', // ตัวอักษรอังกฤษและตัวเลขเท่านั้น
'product_name' => 'string',
'price' => 'float',
'stock' => 'int',
'created_date' => 'datetime'
];
$products = Csv::import('/path/to/products.csv', $productColumns, ['product_code']);
// นำเข้าข้อมูลการขายรายวัน
$salesColumns = [
'sale_date' => 'date',
'amount' => 'double',
'customer_id' => 'int',
'sale_time' => 'time'
];
$sales = Csv::import('/path/to/daily_sales.csv', $salesColumns);
// ใช้ฟังก์ชันแบบกำหนดเองสำหรับการประมวลผลข้อมูล
$customColumns = [
'email' => function($value) {
return filter_var(trim($value), FILTER_VALIDATE_EMAIL) ?: null;
},
'phone' => function($value) {
return preg_replace('/[^0-9]/', '', $value);
},
'name' => function($value) {
return ucwords(trim($value));
}
];
$cleanData = Csv::import('/path/to/contacts.csv', $customColumns);read()
อ่านไฟล์ CSV และประมวลผลแต่ละแถวข้อมูล
public static function read(
$file,
$onRow,
$headers = null,
$charset = 'UTF-8',
$onBeforeRead = null,
$args = null
): void;Parameters:
$file- ที่อยู่ไฟล์ CSV$onRow- ฟังก์ชัน callback ที่จะทำงานกับแต่ละแถวfunction($row, $args)$headers- อาร์เรย์หัวข้อที่คาดหวัง (ไม่บังคับ)$charset- การเข้ารหัสไฟล์ (ค่าเริ่มต้น UTF-8)$onBeforeRead- ฟังก์ชัน callback ก่อนอ่านข้อมูลfunction($columns, $args)(ไม่บังคับ)$args- ข้อมูลเพิ่มเติมที่จะส่งไปยัง callbacks (ไม่บังคับ)
Throws: Exception หากเกิดข้อผิดพลาด
ตัวอย่างการใช้งาน:
use Kotchasan\Database;
<?php
use Kotchasan\Csv;
// อ่านไฟล์ CSV และแสดงผลแต่ละแถว
Csv::read('/path/to/data.csv', function($row) {
echo "ประมวลผลแถว: " . print_r($row, true);
});
// อ่านไฟล์พร้อมตรวจสอบหัวข้อ
$expectedHeaders = ['name', 'email', 'phone'];
Csv::read('/path/to/contacts.csv', function($row) {
// บันทึกข้อมูลลงฐานข้อมูล
$db = \Kotchasan\Database::create();
$db->table('contacts')->insert($row);
}, $expectedHeaders);
// ระบบนำเข้าข้อมูลขนาดใหญ่แบบ batch
$batchSize = 1000;
$batch = [];
$count = 0;
Csv::read('/path/to/large_file.csv', function($row) use (&$batch, &$count, $batchSize) {
$batch[] = $row;
$count++;
if (count($batch) >= $batchSize) {
// บันทึก batch
$db = \Kotchasan\Database::create();
$db->table('large_table')->insert($batch);
echo "ประมวลผล {$count} แถว\n";
$batch = []; // รีเซ็ต batch
}
});
// บันทึก batch สุดท้าย
if (!empty($batch)) {
$db = \Kotchasan\Database::create();
$db->table('large_table')->insert($batch);
echo "ประมวลผลเสร็จสิ้น รวม {$count} แถว\n";
}
// ระบบตรวจสอบและทำความสะอาดข้อมูล
Csv::read('/path/to/user_data.csv', function($row) {
$errors = [];
// ตรวจสอบอีเมล
if (!filter_var($row['email'], FILTER_VALIDATE_EMAIL)) {
$errors[] = "อีเมลไม่ถูกต้อง: {$row['email']}";
}
// ตรวจสอบเบอร์โทร
if (!preg_match('/^[0-9]{10}$/', $row['phone'])) {
$errors[] = "เบอร์โทรไม่ถูกต้อง: {$row['phone']}";
}
if (empty($errors)) {
// ข้อมูลถูกต้อง บันทึกลงฐานข้อมูล
echo "บันทึกข้อมูล: {$row['name']}\n";
} else {
// ข้อมูลไม่ถูกต้อง บันทึก log
error_log("ข้อมูลไม่ถูกต้อง: " . implode(', ', $errors));
}
});send()
สร้างและส่งไฟล์ CSV เป็นการดาวน์โหลด
public static function send(
$file,
$header,
$datas,
$charset = 'UTF-8',
$bom = true
): void;Parameters:
$file- ชื่อไฟล์ (ไม่รวมนามสกุล)$header- อาร์เรย์หัวข้อของไฟล์ CSV$datas- อาร์เรย์ข้อมูลแถวของไฟล์ CSV$charset- การเข้ารหัสไฟล์ (ค่าเริ่มต้น UTF-8)$bom- ใส่ Byte Order Mark หรือไม่ (ค่าเริ่มต้น true)
Returns: void (ส่งไฟล์และ exit)
ตัวอย่างการใช้งาน:
use Kotchasan\Database;
<?php
use Kotchasan\Csv;
// ส่งออกข้อมูลสมาชิก
$headers = ['ชื่อ', 'นามสกุล', 'อีเมล', 'เบอร์โทร'];
$memberData = [
['สมชาย', 'ใจดี', 'somchai@example.com', '0812345678'],
['สมหญิง', 'รักดี', 'somying@example.com', '0823456789'],
['สมศักดิ์', 'มั่นคง', 'somsak@example.com', '0834567890']
];
Csv::send('members', $headers, $memberData);
// ส่งออกข้อมูลจากฐานข้อมูล
$db = \Kotchasan\Database::create();
$users = $db->table('users')
->select('name', 'email', 'created_at')
->toArray();
$headers = ['ชื่อ', 'อีเมล', 'วันที่สมัคร'];
$userData = [];
foreach ($users as $user) {
$userData[] = [
$user['name'],
$user['email'],
date('Y-m-d', strtotime($user['created_at']))
];
}
Csv::send('user_report', $headers, $userData);
// ส่งออกข้อมูลเป็น TIS-620 สำหรับโปรแกรมไทย
Csv::send('thai_report', $headers, $userData, 'TIS-620');
// ส่งออกข้อมูลขายรายเดือน
function exportMonthlySales($year, $month) {
$db = \Kotchasan\Database::create();
$sales = $db->table('sales s')
->join('products p', 'p.id = s.product_id')
->select('p.name', 's.quantity', 's.price', 's.total', 's.sale_date')
->where('YEAR(s.sale_date)', $year)
->where('MONTH(s.sale_date)', $month)
->toArray();
$headers = ['ชื่อสินค้า', 'จำนวน', 'ราคาต่อหน่วย', 'ยอดรวม', 'วันที่ขาย'];
$salesData = [];
foreach ($sales as $sale) {
$salesData[] = [
$sale['name'],
$sale['quantity'],
number_format($sale['price'], 2),
number_format($sale['total'], 2),
$sale['sale_date']
];
}
$filename = "sales_{$year}_{$month}";
return Csv::send($filename, $headers, $salesData);
}
// ส่งออกรายงานผู้ใช้งานระบบ
function exportUserActivity() {
$db = \Kotchasan\Database::create();
$activities = $db->table('user_logs ul')
->join('users u', 'u.id = ul.user_id')
->select('u.name', 'u.email', 'ul.action', 'ul.ip_address', 'ul.created_at')
->order('ul.created_at DESC')
->limit(10000)
->toArray();
$headers = ['ชื่อผู้ใช้', 'อีเมล', 'การกระทำ', 'IP Address', 'เวลา'];
$activityData = [];
foreach ($activities as $activity) {
$activityData[] = [
$activity['name'],
$activity['email'],
$activity['action'],
$activity['ip_address'],
$activity['created_at']
];
}
return Csv::send('user_activity_log', $headers, $activityData);
}ตัวอย่างการใช้งานขั้นสูง
use Kotchasan\Csv;
use Kotchasan\Database;
// ระบบจัดการ CSV แบบครบชุด
class CsvManager
{
// นำเข้าข้อมูลผู้ใช้จาก CSV
public static function importUsers($csvFile) {
$columns = [
'username' => 'en',
'email' => function($value) {
$email = trim($value);
return filter_var($email, FILTER_VALIDATE_EMAIL) ? $email : null;
},
'name' => 'string',
'phone' => 'number',
'birthdate' => 'date',
'salary' => 'double'
];
$keys = ['username', 'email']; // ไม่ให้ username หรือ email ซ้ำ
try {
$users = Csv::import($csvFile, $columns, $keys);
$db = Kotchasan\Database::create();
$imported = 0;
$errors = [];
foreach ($users as $user) {
// ตรวจสอบข้อมูลที่จำเป็น
if (empty($user['username']) || empty($user['email'])) {
$errors[] = "ข้อมูลไม่ครบ: " . json_encode($user);
continue;
}
// ตรวจสอบว่ามีในระบบแล้วหรือไม่
$exists = $db->table('users')
->where('username', $user['username'])
->orWhere('email', $user['email'])
->first();
if ($exists) {
$errors[] = "ผู้ใช้ซ้ำ: {$user['username']} / {$user['email']}";
continue;
}
// เพิ่มข้อมูลเพิ่มเติม
$user['password'] = password_hash('123456', PASSWORD_DEFAULT);
$user['status'] = 1;
$user['created_at'] = date('Y-m-d H:i:s');
// บันทึกลงฐานข้อมูล
$db->table('users')->insert($user);
$imported++;
}
return [
'success' => true,
'imported' => $imported,
'total' => count($users),
'errors' => $errors
];
} catch (Exception $e) {
return [
'success' => false,
'message' => $e->getMessage()
];
}
}
// ส่งออกรายงานการขาย
public static function exportSalesReport($startDate, $endDate) {
$db = Kotchasan\Database::create();
$sales = $db->table('sales s')
->join('products p', 'p.id = s.product_id')
->join('users u', 'u.id = s.user_id')
->select(
's.id',
'p.name as product_name',
'p.code as product_code',
'u.name as customer_name',
's.quantity',
's.unit_price',
's.total_price',
's.sale_date',
's.status'
)
->whereBetween('s.sale_date', [$startDate, $endDate])
->order('s.sale_date DESC')
->toArray();
$headers = [
'รหัสการขาย',
'รหัสสินค้า',
'ชื่อสินค้า',
'ลูกค้า',
'จำนวน',
'ราคาต่อหน่วย',
'ยอดรวม',
'วันที่ขาย',
'สถานะ'
];
$salesData = [];
$totalAmount = 0;
foreach ($sales as $sale) {
$statusText = $sale['status'] == 1 ? 'สำเร็จ' : 'ยกเลิก';
$salesData[] = [
$sale['id'],
$sale['product_code'],
$sale['product_name'],
$sale['customer_name'],
$sale['quantity'],
number_format($sale['unit_price'], 2),
number_format($sale['total_price'], 2),
$sale['sale_date'],
$statusText
];
if ($sale['status'] == 1) {
$totalAmount += $sale['total_price'];
}
}
// เพิ่มแถวสรุป
$salesData[] = ['', '', '', '', '', '', '', '', ''];
$salesData[] = ['', '', '', 'ยอดรวมทั้งหมด', '', '', number_format($totalAmount, 2), '', ''];
$filename = "sales_report_{$startDate}_to_{$endDate}";
return Csv::send($filename, $headers, $salesData);
}
// นำเข้าข้อมูลสินค้า
public static function importProducts($csvFile) {
$result = [
'total' => 0,
'imported' => 0,
'updated' => 0,
'errors' => []
];
Csv::read($csvFile, function($row) use (&$result) {
$result['total']++;
try {
$db = Kotchasan\Database::create();
// ทำความสะอาดข้อมูล
$productData = [
'code' => trim($row['code'] ?? ''),
'name' => trim($row['name'] ?? ''),
'price' => (float)($row['price'] ?? 0),
'cost' => (float)($row['cost'] ?? 0),
'stock' => (int)($row['stock'] ?? 0),
'category_id' => (int)($row['category_id'] ?? 0),
'description' => trim($row['description'] ?? ''),
'updated_at' => date('Y-m-d H:i:s')
];
// ตรวจสอบข้อมูลที่จำเป็น
if (empty($productData['code']) || empty($productData['name'])) {
$result['errors'][] = "ข้อมูลไม่ครบ: รหัสสินค้าหรือชื่อสินค้าไม่มี";
return;
}
// ตรวจสอบว่ามีสินค้านี้อยู่แล้วหรือไม่
$existing = $db->table('products')
->where('code', $productData['code'])
->first();
if ($existing) {
// อัพเดทข้อมูล
$db->table('products')
->where('code', $productData['code'])
->update($productData);
$result['updated']++;
} else {
// เพิ่มข้อมูลใหม่
$productData['created_at'] = date('Y-m-d H:i:s');
$db->table('products')->insert($productData);
$result['imported']++;
}
} catch (Exception $e) {
$result['errors'][] = "บรรทัดที่ {$result['total']}: " . $e->getMessage();
}
});
return $result;
}
// ส่งออกเทมเพลต CSV
public static function exportTemplate($type) {
$templates = [
'users' => [
'filename' => 'user_import_template',
'headers' => ['username', 'email', 'name', 'phone', 'birthdate', 'salary'],
'sample' => [
['john_doe', 'john@example.com', 'John Doe', '0812345678', '1990-01-15', '50000'],
['jane_smith', 'jane@example.com', 'Jane Smith', '0823456789', '1985-05-20', '45000']
]
],
'products' => [
'filename' => 'product_import_template',
'headers' => ['code', 'name', 'price', 'cost', 'stock', 'category_id', 'description'],
'sample' => [
['P001', 'สินค้า A', '100.00', '80.00', '50', '1', 'รายละเอียดสินค้า A'],
['P002', 'สินค้า B', '200.00', '150.00', '30', '2', 'รายละเอียดสินค้า B']
]
]
];
if (!isset($templates[$type])) {
return false;
}
$template = $templates[$type];
return Csv::send(
$template['filename'],
$template['headers'],
$template['sample']
);
}
}
// ระบบ Controller สำหรับจัดการ CSV
class CsvController extends \Kotchasan\Controller
{
public function import() {
if ($this->request->getMethod() === 'POST') {
$uploadedFile = $this->request->getUploadedFile('csv_file');
$type = $this->request->getParsedBodyParam('type');
if ($uploadedFile && $uploadedFile->getError() === UPLOAD_ERR_OK) {
$tempFile = $uploadedFile->getTempName();
switch ($type) {
case 'users':
$result = CsvManager::importUsers($tempFile);
break;
case 'products':
$result = CsvManager::importProducts($tempFile);
break;
default:
$result = ['success' => false, 'message' => 'ประเภทไม่ถูกต้อง'];
}
header('Content-Type: application/json');
echo json_encode($result);
}
} else {
// แสดงฟอร์มอัพโหลด
include ROOT_PATH . 'modules/csv/views/import.php';
}
}
public function export() {
$type = $this->request->getQueryParam('type');
$format = $this->request->getQueryParam('format', 'data');
switch ($type) {
case 'sales':
$startDate = $this->request->getQueryParam('start_date');
$endDate = $this->request->getQueryParam('end_date');
CsvManager::exportSalesReport($startDate, $endDate);
break;
case 'users':
if ($format === 'template') {
CsvManager::exportTemplate('users');
} else {
// ส่งออกข้อมูลผู้ใช้จริง
}
break;
case 'products':
if ($format === 'template') {
CsvManager::exportTemplate('products');
} else {
// ส่งออกข้อมูลสินค้าจริง
}
break;
}
}
}หมายเหตุการใช้งาน
- การเข้ารหัส: รองรับ UTF-8, TIS-620 และ character encoding อื่นๆ
- ประเภทข้อมูล: string, int, double, float, number, en, date, datetime, time
- ฟังก์ชันกำหนดเอง: สามารถใช้ callback function สำหรับการประมวลผลข้อมูล
- BOM: รองรับการเพิ่ม Byte Order Mark สำหรับ UTF-8
- ข้อมูลขนาดใหญ่: ใช้ read() สำหรับการประมวลผลแบบ streaming
คลาส Csv เป็นเครื่องมือที่ทรงพลังสำหรับการจัดการไฟล์ CSV ในกรอบงาน Kotchasan รองรับการนำเข้าและส่งออกข้อมูลในรูปแบบต่างๆ และเหมาะสำหรับการใช้งานในระบบเว็บแอปพลิเคชัน