Listing 16-8 (Continued) foreach ($lines as $str) { $index++; if (preg_match(‘/To:\s*(.+)/i’, $str, $match ) ) { $to = $match[1]; } else if (preg_match(‘/From:\s*(.+)/i’, $str, $match ) ) { array_push($headers, “From: $match[1] \r\n”); } else if (preg_match(‘/Subject:\s*(.+)/i’, $str, $match ) ) { $subject = $match[1]; } else if (preg_match(‘/^CC:\s*(.+)/i’, $str, $match)) { array_push($headers, “Cc: $match[1] \r\n”); } else if (preg_match(‘/Bcc:\s*(.+)/i’, $str, $match)) { array_push($headers, “Bcc: $match[1] \r\n”); } else if (preg_match(‘/Content-Type:\s*(.+)/i’, $str, $match ) ) { if (preg_match(‘/html/’, $match[1])) { array_push($headers, 576 Part IV: Using PHP for Sysadmin Tasks 21 549669 ch16.qxd 4/4/03 9:27 AM Page 576 “Content-Type: text/html\r\n”); } else { array_push($headers, “Content-Type: text/plain\n”); } $contentTypeSet = TRUE; } else if (preg_match(‘/MIME-Version:\s*(.+)/i’, $str, $match ) ) { array_push($headers, “MIME-Version: $match[1] \r\n”); } else { array_push($message, $str); } } if (! $contentTypeSet) array_push($headers, “Content-Type: text/plain\r\n”); $subject = preg_replace( ‘/<%TODAY%>/i’, $today, $subject); $body = implode(‘’, $message); $body = preg_replace(‘/<%TODAY%>/i’, $today, $body); $headerStr = implode(‘’, $headers); if (DEBUG) echo “Sending mail to: $to (subject: $subject)\n”; return mail($to, $subject, $body, $headerStr); } function getRemindersForToday($list = null, $logFile = null) { Continued Chapter 16: Command-Line PHP Utilities 577 21 549669 ch16.qxd 4/4/03 9:27 AM Page 577 Listing 16-8 (Continued) $reminders = array(); $logEntries = array(); // Get today’s date $thisMonth = date(‘M’); $thisMM = date(‘m’); $thisDay = strtolower(date(‘D’)); $thisDD = date(‘d’); $MMDD = sprintf(“%02d-%02d”, $thisMM, $thisDD); $lineNumber = 0; // Parse each line in the user’s reminder file foreach ($list as $line) { // Count line number (needed for error reporting) $lineNumber++; // Ignore lines starting with # as comments if (preg_match(‘/^#/’, $line)) continue; // Ignore lines that are blank $line = ltrim($line); if (preg_match(‘/^$/’, $line)) continue; $line = substr($line,0, strlen($line)-1); list ($type,$when,$what) = explode(‘:’, $line); if (preg_match(‘/daily/i’, $type)) { // daily reminders have only 2 parts daily:file // so $when will have what we want in $what // Daily reminder array_push($reminders, $when); } else if ( preg_match(‘/weekly/i’, $type) && !strcmp($thisDay, strtolower($when)) && !empty($what) ) { 578 Part IV: Using PHP for Sysadmin Tasks 21 549669 ch16.qxd 4/4/03 9:27 AM Page 578 // Weekly reminder array_push($reminders, $what); } else if ( preg_match(‘/monthly/i’, $type) && ($thisDD == $when) && !empty($what) ) { // Monthly reminder array_push($reminders, $what); } else if ( preg_match(‘/yearly/i’, $type) && (!strcmp($MMDD, $when)) && !empty($what) ) { // Yearly reminder array_push($reminders, $what); } else if (empty($what)) { array_push($logEntries, “error in line $lineNumber ($line)”); } } // Write log entries writeLog($logFile, $logEntries); // Remove duplicates from reminder list return array_values(array_unique($reminders)); } function writeLog($logFile = null, $entries = null) { if (count($entries) <1) return FALSE; $logFD = fopen($logFile, ‘a+’); $today = date(‘M-d-Y h:i:s A’); if (! $logFD) return FALSE; Continued Chapter 16: Command-Line PHP Utilities 579 21 549669 ch16.qxd 4/4/03 9:27 AM Page 579 Listing 16-8 (Continued) foreach ($entries as $logRecord) { fputs($logFD, “$today: $logRecord\n”); } fclose($logFD); return TRUE; } function getUsers($userFile = null) { $users = array(); if (!file_exists($userFile)) { return $users; } // For each line in the file // create a entry in users array // as: $users[username] = home_dir foreach ( file($userFile) as $line) { $userInfo = explode(‘:’,$line); $users[$userInfo[0]] = $userInfo[5]; } return $users; } ?> Here is how this script works: ◆ It first gets a list of users by calling the getUsers() function. This func- tion is given the PASSWD_FILE file name, which is configured in reminder.conf. The user list is returned into $userList. ◆ For each user in $userList, the script calls the doRemind() function, which processes the reminders for the user. Now let’s examine each of the functions used in this script. 580 Part IV: Using PHP for Sysadmin Tasks 21 549669 ch16.qxd 4/4/03 9:27 AM Page 580 . $str, $match ) ) { if (preg_match(‘/html/’, $match[1])) { array_push($headers, 576 Part IV: Using PHP for Sysadmin Tasks 21 549669 ch16.qxd 4/4/03 9:27 AM Page 576 “Content-Type: text/html ”); }. $headerStr); } function getRemindersForToday($list = null, $logFile = null) { Continued Chapter 16: Command-Line PHP Utilities 577 21 549669 ch16.qxd 4/4/03 9:27 AM Page 577 Listing 16-8 (Continued) $reminders. && !strcmp($thisDay, strtolower($when)) && !empty($what) ) { 578 Part IV: Using PHP for Sysadmin Tasks 21 549669 ch16.qxd 4/4/03 9:27 AM Page 578 // Weekly reminder array_push($reminders,