eesyphp/example/includes/db.php
2024-01-23 19:23:10 +01:00

390 lines
9.5 KiB
PHP

<?php
use EesyPHP\App;
use EesyPHP\Db;
use EesyPHP\Hook;
use EesyPHP\Log;
use Unidecode\Unidecode;
$db = new Db(
App::get('db.dsn', null, 'string'),
App::get('db.user', null, 'string'),
App::get('db.password', null, 'string'),
App::get('db.options', array(), 'array'),
App::get('db.date_format', null, 'string'),
App::get('db.datetime_format', null, 'string'),
);
/*
* Methods to handle items
*/
function get_items($orderby='id', $raw_values=false) {
global $db;
try {
$info = $db -> get_many('item', null, null, $orderby);
if (!is_array($info))
return;
if ($raw_values)
return $info;
$items = array();
foreach ($info as $item)
$items[$item['id']] = $db -> format_row_info($item, array('date'));
return $items;
}
catch (Exception $e) {
Log :: error("Error retrieving items info from database : ".$e->getMessage());
}
return false;
}
function get_item($id, $raw_values=false) {
global $db;
try {
$info = $db -> get_one('item', array('id' => $id));
if (!is_array($info))
return false;
if ($raw_values)
return $info;
return $db -> format_row_info($info, array('date'));
}
catch (Exception $e) {
Log :: error("Error retrieving item #$id info from database : ".$e->getMessage());
}
return false;
}
function add_item($values) {
global $db;
$values['date'] = $db -> time2datetime(time());
try {
$result = $db -> fpdo -> insertInto('item')
-> values($values)
-> execute();
if ($result !== false) {
$item = get_item($result);
Log :: info("New item #$result added");
Hook :: trigger('item_added', $item);
return $item;
}
}
catch (Exception $e) {
Log :: error("Error creating item in database : ".$e->getMessage());
}
return false;
}
function update_item($id, $changes) {
global $db;
if (!is_array($changes))
return false;
if (empty($changes))
return true;
$item = get_item($id, true);
if (!is_array($item)) return false;
if (isset($changes['date']) && $changes['date'])
$changes['date'] = $db -> time2datetime($changes['date']);
try {
$result = $db -> fpdo -> update('item')
-> set($changes)
-> where('id', $id)
-> execute();
if ($result !== false) {
Log :: info("Item #$id updated");
Hook :: trigger('item_updated', $item);
return true;
}
}
catch (Exception $e) {
Log :: error("Error updating item #$id in database : ".$e->getMessage());
}
return false;
}
function change_item_status($id, $status) {
if (update_item($id, array('status' => $status))) {
Log :: info("Status of item #$id changed to $status.");
return true;
}
return false;
}
function archive_item($id) {
return change_item_status($id, 'archived');
}
function delete_item($id) {
global $db;
try {
$result = $db -> fpdo -> deleteFrom('item')
-> where('id', $id)
-> execute();
if ($result !== false) {
Log :: info("Item #$id deleted");
return True;
}
}
catch (Exception $e) {
Log :: error("Error deleting item #$id from database : ".$e->getMessage());
}
return false;
}
function search_items($params) {
global $db;
// Detect PgSQL backend
$is_pgsql = (strpos(App::get('db.dsn', '', 'string'), "pgsql:") === 0);
$where = array();
if (isset($params['status']) && $params['status'] && $params['status'] != 'all')
$where['status'] = $params['status'];
$patterns_where = array();
if (isset($params['pattern']) && $params['pattern']) {
foreach(preg_split('/\s+/', trim($params['pattern'])) as $word) {
if (!$word) continue;
$patterns_word=array();
// If numeric pattern ?
if (preg_match('/^[0-9]+$/', $word)) {
// Numeric pattern
$word = intval($word);
$patterns_word['id = ?'] = $word;
}
else {
// Text pattern
foreach (array('name', 'description') as $field) {
if ($is_pgsql) {
$word = Unidecode::unidecode($word);
$patterns_word["unaccent($field) ILIKE ?"] = "%$word%";
}
else
$patterns_word["$field LIKE ?"] = "%$word%";
}
}
$patterns_where[] = $patterns_word;
}
}
$order='id';
$orders=array('id', 'name', 'date', 'status', 'description');
if (isset($params['order'])) {
if (!in_array($order, $orders))
return -1;
$order=$params['order'];
}
$order_direction='DESC';
if (isset($params['order_direction']) && $params['order_direction']) {
if (!in_array($params['order_direction'], array('ASC', 'DESC')))
return -1;
$order_direction=$params['order_direction'];
}
$orderby="$order $order_direction";
$limit = "";
$page = 1;
$nb_by_page = 10;
$offset = 0;
if (!isset($params['all'])) {
if (isset($params['page']) && $params['page']>0) {
if (isset($params['nb_by_page']) && $params['nb_by_page']>0) {
$nb_by_page = intval($params['nb_by_page']);
}
$page = intval($params['page']);
}
$offset = ($page-1)*$nb_by_page;
$limit = $nb_by_page;
}
try {
$query = $db -> fpdo -> from('item');
if (!empty($where))
$query -> where($where);
foreach ($patterns_where as $patterns_word)
call_user_func_array(
array($query, 'where'),
array_merge(
array('('.implode(' OR ', array_keys($patterns_word)).')'),
array_values($patterns_word)
)
);
$result = $query -> orderBy($orderby)
-> limit($limit)
-> offset($offset)
-> execute();
if ($result === false) {
Log :: error('search_items() : search in DB return false');
return false;
}
$rows = $result -> fetchAll();
$items = array();
foreach ($rows as $row) {
$items[] = $db -> format_row_info($row, array('date'));
}
if (isset($params['all'])) {
return array(
'count' => count($items),
'first' => 1,
'last' => count($items),
'nb_pages' => 1,
'page' => 1,
'items' => $items
);
}
$query_count = $db -> fpdo -> from('item')
-> select(null)
-> select('count(*) as count');
if (!empty($where))
$query_count -> where($where);
foreach ($patterns_where as $patterns_word)
call_user_func_array(
array($query_count, 'where'),
array_merge(
array('('.implode(' OR ', array_keys($patterns_word)).')'),
array_values($patterns_word)
)
);
$result_count = $query_count -> execute();
if ($result_count === false) {
Log :: debug('search_items() : search for count in DB return false');
return False;
}
$count = $result_count -> fetch();
return array(
'count' => $count['count'],
'first' => $offset+1,
'last' => (
$offset+$nb_by_page<$count['count']?
$offset+$nb_by_page:$count['count']),
'nb_pages' => ceil($count['count']/$nb_by_page),
'page' => $page,
'items' => $items,
);
}
catch (Exception $e) {
Log :: exception(
$e, "An exception occurred searching items with params %s infos from database : ",
preg_replace("/\n[ \t]*/", " ", print_r($params, true))
);
}
return false;
}
function export_items($fd=null) {
if (!$fd) $fd = fopen('php://output', 'w');
fputcsv(
$fd,
array (
'id',
'name',
'date',
'status',
'description',
)
);
$items = get_items();
foreach($items as $item) {
fputcsv(
$fd,
array(
$item['id'],
$item['name'],
$item['date'],
$item['status'],
$item['description'],
)
);
}
return True;
}
function restore_items($fd=null) {
global $db;
if (!$fd) $fd = fopen('php://stdin', 'r');
try {
$result = $db -> fpdo -> deleteFrom('item')
-> execute();
if ($result === false) {
Log :: error("An unknown error occurred truncating item table in database.");
return false;
}
}
catch (Exception $e) {
Log :: error("Error truncating item table in database : ".$e->getMessage());
return false;
}
$first_row = false;
$line = 0;
$restored = 0;
$error = false;
$datetime_fields = array (
'date',
);
// Map fields to support hold CSV files format
$mapping = array (
'creation_date' => 'date',
'desc' => 'description',
);
while (($row = fgetcsv($fd)) !== FALSE) {
$line++;
if ($first_row === false) {
$first_row = $row;
continue;
}
try {
$values = array();
for ($i=0; $i < count($first_row); $i++) {
if (!$row[$i]) continue;
$field = (
array_key_exists($first_row[$i], $mapping)?
$mapping[$first_row[$i]]:
$first_row[$i]);
$value = (in_array($field, $datetime_fields)?$db -> time2datetime($row[$i]):$row[$i]);
$values[$field] = $value;
}
$result = $db -> fpdo -> insertInto('item')
-> values($values)
-> execute();
if ($result !== false) {
$restored++;
}
else {
Log :: error("Unknown error occurred restoring item from line #$line :\n".print_r($values, true));
$error = true;
}
}
catch (Exception $e) {
Log :: error(
"Error restoring item from line #$line : ".$e->getMessage()."\n".print_r($values, true));
$error = true;
}
}
Log :: info("$restored items restored");
// Trigger hooks
Hook :: trigger('items_restored');
return !$error;
}
# vim: tabstop=2 shiftwidth=2 softtabstop=2 expandtab