first sql source implementation
[bdrem.git] / src / bdrem / Source / Sql.php
1 <?php
2 namespace bdrem;
3
4 /**
5  * Fetch data from an SQL database
6  */
7 class Source_Sql
8 {
9     protected $dsn;
10     protected $user;
11     protected $password;
12     protected $table;
13     protected $fields ;
14
15     public function __construct($config)
16     {
17         $this->dsn      = $config['dsn'];
18         $this->user     = $config['user'];
19         $this->password = $config['password'];
20         $this->table    = $config['table'];
21         $this->fields   = $config['fields'];
22     }
23
24     /**
25      * @param string $strDate Date the events shall be found for, YYYY-MM-DD
26      */
27     public function getEvents($strDate, $nDaysBefore, $nDaysAfter)
28     {
29         $dbh = new \PDO($this->dsn, $this->user, $this->password);
30         $arDays = $this->getDates($strDate, $nDaysBefore, $nDaysAfter);
31         $arEvents = array();
32
33         foreach ($this->fields['date'] as $field => $typeName) {
34             $fieldSql = 'CONCAT('
35                 . 'EXTRACT(MONTH FROM ' . $field . '),'
36                 . '"-",'
37                 . 'EXTRACT(DAY FROM ' . $field . ')'
38                 . ') = ';
39
40             $parts = array();
41             foreach ($arDays as $day) {
42                 $parts[] = $fieldSql . $dbh->quote($day);
43             }
44             $sql = 'SELECT ' . $field . ' AS e_date'
45                 . ', ' . $this->fields['name'] . ' AS e_name'
46                 . ' FROM ' . $this->table
47                 . ' WHERE '
48                 . implode(' OR ', $parts);
49
50             $res = $dbh->query($sql);
51             if ($res === false) {
52                 $errorInfo = $dbh->errorInfo();
53                 throw new \Exception(
54                     'SQL error #' . $errorInfo[0]
55                     . ': ' . $errorInfo[1]
56                     . ': ' . $errorInfo[2],
57                     (int) $errorInfo[1]
58                 );
59             }
60             while ($row = $res->fetchObject()) {
61                 $event = new Event(
62                     $row->e_name, $typeName, 
63                     str_replace('0000', '????', $row->e_date)
64                 );
65                 if ($event->isWithin($strDate, $nDaysBefore, $nDaysAfter)) {
66                     $arEvents[] = $event;
67                 }
68             }
69         }
70         return $arEvents;
71     }
72
73     protected function getDates($strDate, $nDaysBefore, $nDaysAfter)
74     {
75         $ts = strtotime($strDate) - 86400 * $nDaysBefore;
76         $numDays = $nDaysBefore + $nDaysAfter;
77
78         $arDays = array();
79         do {
80             $arDays[] = date('n-j', $ts);
81             $ts += 86400;
82         } while (--$numDays >= 0);
83         return $arDays;
84     }
85 }
86 ?>