about summary refs log tree commit diff stats
path: root/wiki/inc/subscription.php
diff options
context:
space:
mode:
authorahriman <ahriman@falte.red>2019-01-02 04:57:35 +0000
committerahriman <ahriman@falte.red>2019-01-02 04:57:35 +0000
commit2bd7f83a6495011ada78ca8a9f2af417caf01760 (patch)
treef9acdb7f09e011c65330ab993d4db3620787dbfb /wiki/inc/subscription.php
parentbcb215c3a7e914d05f166846a33860e48bba64fb (diff)
downloadsite-2bd7f83a6495011ada78ca8a9f2af417caf01760.tar.gz
removed dokuwiki
Diffstat (limited to 'wiki/inc/subscription.php')
-rw-r--r--wiki/inc/subscription.php693
1 files changed, 0 insertions, 693 deletions
diff --git a/wiki/inc/subscription.php b/wiki/inc/subscription.php
deleted file mode 100644
index 74bec65..0000000
--- a/wiki/inc/subscription.php
+++ /dev/null
@@ -1,693 +0,0 @@
-<?php
-/**
- * Class for handling (email) subscriptions
- *
- * @author  Adrian Lang <lang@cosmocode.de>
- * @author  Andreas Gohr <andi@splitbrain.org>
- * @license GPL 2 (http://www.gnu.org/licenses/gpl.html)
- */
-class Subscription {
-
-    /**
-     * Check if subscription system is enabled
-     *
-     * @return bool
-     */
-    public function isenabled() {
-        return actionOK('subscribe');
-    }
-
-    /**
-     * Return the subscription meta file for the given ID
-     *
-     * @author Adrian Lang <lang@cosmocode.de>
-     *
-     * @param string $id The target page or namespace, specified by id; Namespaces
-     *                   are identified by appending a colon.
-     * @return string
-     */
-    protected function file($id) {
-        $meta_fname = '.mlist';
-        if((substr($id, -1, 1) === ':')) {
-            $meta_froot = getNS($id);
-            $meta_fname = '/'.$meta_fname;
-        } else {
-            $meta_froot = $id;
-        }
-        return metaFN((string) $meta_froot, $meta_fname);
-    }
-
-    /**
-     * Lock subscription info
-     *
-     * We don't use io_lock() her because we do not wait for the lock and use a larger stale time
-     *
-     * @author Adrian Lang <lang@cosmocode.de>
-     * @param string $id The target page or namespace, specified by id; Namespaces
-     *                   are identified by appending a colon.
-     * @return bool true, if you got a succesful lock
-     */
-    protected function lock($id) {
-        global $conf;
-
-        $lock = $conf['lockdir'].'/_subscr_'.md5($id).'.lock';
-
-        if(is_dir($lock) && time() - @filemtime($lock) > 60 * 5) {
-            // looks like a stale lock - remove it
-            @rmdir($lock);
-        }
-
-        // try creating the lock directory
-        if(!@mkdir($lock, $conf['dmode'])) {
-            return false;
-        }
-
-        if(!empty($conf['dperm'])) chmod($lock, $conf['dperm']);
-        return true;
-    }
-
-    /**
-     * Unlock subscription info
-     *
-     * @author Adrian Lang <lang@cosmocode.de>
-     * @param string $id The target page or namespace, specified by id; Namespaces
-     *                   are identified by appending a colon.
-     * @return bool
-     */
-    protected function unlock($id) {
-        global $conf;
-        $lock = $conf['lockdir'].'/_subscr_'.md5($id).'.lock';
-        return @rmdir($lock);
-    }
-
-    /**
-     * Construct a regular expression for parsing a subscription definition line
-     *
-     * @author Andreas Gohr <andi@splitbrain.org>
-     *
-     * @param string|array $user
-     * @param string|array $style
-     * @param string|array $data
-     * @return string complete regexp including delimiters
-     * @throws Exception when no data is passed
-     */
-    protected function buildregex($user = null, $style = null, $data = null) {
-        // always work with arrays
-        $user = (array) $user;
-        $style = (array) $style;
-        $data = (array) $data;
-
-        // clean
-        $user = array_filter(array_map('trim', $user));
-        $style = array_filter(array_map('trim', $style));
-        $data = array_filter(array_map('trim', $data));
-
-        // user names are encoded
-        $user = array_map('auth_nameencode', $user);
-
-        // quote
-        $user = array_map('preg_quote_cb', $user);
-        $style = array_map('preg_quote_cb', $style);
-        $data = array_map('preg_quote_cb', $data);
-
-        // join
-        $user = join('|', $user);
-        $style = join('|', $style);
-        $data = join('|', $data);
-
-        // any data at all?
-        if($user.$style.$data === '') throw new Exception('no data passed');
-
-        // replace empty values, set which ones are optional
-        $sopt = '';
-        $dopt = '';
-        if($user === '') {
-            $user = '\S+';
-        }
-        if($style === '') {
-            $style = '\S+';
-            $sopt = '?';
-        }
-        if($data === '') {
-            $data = '\S+';
-            $dopt = '?';
-        }
-
-        // assemble
-        return "/^($user)(?:\\s+($style))$sopt(?:\\s+($data))$dopt$/";
-    }
-
-    /**
-     * Recursively search for matching subscriptions
-     *
-     * This function searches all relevant subscription files for a page or
-     * namespace.
-     *
-     * @author Adrian Lang <lang@cosmocode.de>
-     *
-     * @param string         $page The target object’s (namespace or page) id
-     * @param string|array   $user
-     * @param string|array   $style
-     * @param string|array   $data
-     * @return array
-     */
-    public function subscribers($page, $user = null, $style = null, $data = null) {
-        if(!$this->isenabled()) return array();
-
-        // Construct list of files which may contain relevant subscriptions.
-        $files = array(':' => $this->file(':'));
-        do {
-            $files[$page] = $this->file($page);
-            $page = getNS(rtrim($page, ':')).':';
-        } while($page !== ':');
-
-        $re = $this->buildregex($user, $style, $data);
-
-        // Handle files.
-        $result = array();
-        foreach($files as $target => $file) {
-            if(!file_exists($file)) continue;
-
-            $lines = file($file);
-            foreach($lines as $line) {
-                // fix old style subscription files
-                if(strpos($line, ' ') === false) $line = trim($line)." every\n";
-
-                // check for matching entries
-                if(!preg_match($re, $line, $m)) continue;
-
-                $u = rawurldecode($m[1]); // decode the user name
-                if(!isset($result[$target])) $result[$target] = array();
-                $result[$target][$u] = array($m[2], $m[3]); // add to result
-            }
-        }
-        return array_reverse($result);
-    }
-
-    /**
-     * Adds a new subscription for the given page or namespace
-     *
-     * This will automatically overwrite any existent subscription for the given user on this
-     * *exact* page or namespace. It will *not* modify any subscription that may exist in higher namespaces.
-     *
-     * @param string $id The target page or namespace, specified by id; Namespaces
-     *                   are identified by appending a colon.
-     * @param string $user
-     * @param string $style
-     * @param string $data
-     * @throws Exception when user or style is empty
-     * @return bool
-     */
-    public function add($id, $user, $style, $data = '') {
-        if(!$this->isenabled()) return false;
-
-        // delete any existing subscription
-        $this->remove($id, $user);
-
-        $user  = auth_nameencode(trim($user));
-        $style = trim($style);
-        $data  = trim($data);
-
-        if(!$user) throw new Exception('no subscription user given');
-        if(!$style) throw new Exception('no subscription style given');
-        if(!$data) $data = time(); //always add current time for new subscriptions
-
-        $line = "$user $style $data\n";
-        $file = $this->file($id);
-        return io_saveFile($file, $line, true);
-    }
-
-    /**
-     * Removes a subscription for the given page or namespace
-     *
-     * This removes all subscriptions matching the given criteria on the given page or
-     * namespace. It will *not* modify any subscriptions that may exist in higher
-     * namespaces.
-     *
-     * @param string         $id   The target object’s (namespace or page) id
-     * @param string|array   $user
-     * @param string|array   $style
-     * @param string|array   $data
-     * @return bool
-     */
-    public function remove($id, $user = null, $style = null, $data = null) {
-        if(!$this->isenabled()) return false;
-
-        $file = $this->file($id);
-        if(!file_exists($file)) return true;
-
-        $re = $this->buildregex($user, $style, $data);
-        return io_deleteFromFile($file, $re, true);
-    }
-
-    /**
-     * Get data for $INFO['subscribed']
-     *
-     * $INFO['subscribed'] is either false if no subscription for the current page
-     * and user is in effect. Else it contains an array of arrays with the fields
-     * “target”, “style”, and optionally “data”.
-     *
-     * @param string $id  Page ID, defaults to global $ID
-     * @param string $user User, defaults to $_SERVER['REMOTE_USER']
-     * @return array
-     * @author Adrian Lang <lang@cosmocode.de>
-     */
-    function user_subscription($id = '', $user = '') {
-        if(!$this->isenabled()) return false;
-
-        global $ID;
-        /** @var Input $INPUT */
-        global $INPUT;
-        if(!$id) $id = $ID;
-        if(!$user) $user = $INPUT->server->str('REMOTE_USER');
-
-        $subs = $this->subscribers($id, $user);
-        if(!count($subs)) return false;
-
-        $result = array();
-        foreach($subs as $target => $info) {
-            $result[] = array(
-                'target' => $target,
-                'style' => $info[$user][0],
-                'data' => $info[$user][1]
-            );
-        }
-
-        return $result;
-    }
-
-    /**
-     * Send digest and list subscriptions
-     *
-     * This sends mails to all subscribers that have a subscription for namespaces above
-     * the given page if the needed $conf['subscribe_time'] has passed already.
-     *
-     * This function is called form lib/exe/indexer.php
-     *
-     * @param string $page
-     * @return int number of sent mails
-     */
-    public function send_bulk($page) {
-        if(!$this->isenabled()) return 0;
-
-        /** @var DokuWiki_Auth_Plugin $auth */
-        global $auth;
-        global $conf;
-        global $USERINFO;
-        /** @var Input $INPUT */
-        global $INPUT;
-        $count = 0;
-
-        $subscriptions = $this->subscribers($page, null, array('digest', 'list'));
-
-        // remember current user info
-        $olduinfo = $USERINFO;
-        $olduser = $INPUT->server->str('REMOTE_USER');
-
-        foreach($subscriptions as $target => $users) {
-            if(!$this->lock($target)) continue;
-
-            foreach($users as $user => $info) {
-                list($style, $lastupdate) = $info;
-
-                $lastupdate = (int) $lastupdate;
-                if($lastupdate + $conf['subscribe_time'] > time()) {
-                    // Less than the configured time period passed since last
-                    // update.
-                    continue;
-                }
-
-                // Work as the user to make sure ACLs apply correctly
-                $USERINFO = $auth->getUserData($user);
-                $INPUT->server->set('REMOTE_USER',$user);
-                if($USERINFO === false) continue;
-                if(!$USERINFO['mail']) continue;
-
-                if(substr($target, -1, 1) === ':') {
-                    // subscription target is a namespace, get all changes within
-                    $changes = getRecentsSince($lastupdate, null, getNS($target));
-                } else {
-                    // single page subscription, check ACL ourselves
-                    if(auth_quickaclcheck($target) < AUTH_READ) continue;
-                    $meta = p_get_metadata($target);
-                    $changes = array($meta['last_change']);
-                }
-
-                // Filter out pages only changed in small and own edits
-                $change_ids = array();
-                foreach($changes as $rev) {
-                    $n = 0;
-                    while(!is_null($rev) && $rev['date'] >= $lastupdate &&
-                        ($INPUT->server->str('REMOTE_USER') === $rev['user'] ||
-                            $rev['type'] === DOKU_CHANGE_TYPE_MINOR_EDIT)) {
-                        $pagelog = new PageChangeLog($rev['id']);
-                        $rev = $pagelog->getRevisions($n++, 1);
-                        $rev = (count($rev) > 0) ? $rev[0] : null;
-                    }
-
-                    if(!is_null($rev) && $rev['date'] >= $lastupdate) {
-                        // Some change was not a minor one and not by myself
-                        $change_ids[] = $rev['id'];
-                    }
-                }
-
-                // send it
-                if($style === 'digest') {
-                    foreach($change_ids as $change_id) {
-                        $this->send_digest(
-                            $USERINFO['mail'], $change_id,
-                            $lastupdate
-                        );
-                        $count++;
-                    }
-                } elseif($style === 'list') {
-                    $this->send_list($USERINFO['mail'], $change_ids, $target);
-                    $count++;
-                }
-                // TODO: Handle duplicate subscriptions.
-
-                // Update notification time.
-                $this->add($target, $user, $style, time());
-            }
-            $this->unlock($target);
-        }
-
-        // restore current user info
-        $USERINFO = $olduinfo;
-        $INPUT->server->set('REMOTE_USER',$olduser);
-        return $count;
-    }
-
-    /**
-     * Send the diff for some page change
-     *
-     * @param string   $subscriber_mail The target mail address
-     * @param string   $template        Mail template ('subscr_digest', 'subscr_single', 'mailtext', ...)
-     * @param string   $id              Page for which the notification is
-     * @param int|null $rev             Old revision if any
-     * @param string   $summary         Change summary if any
-     * @return bool                     true if successfully sent
-     */
-    public function send_diff($subscriber_mail, $template, $id, $rev = null, $summary = '') {
-        global $DIFF_INLINESTYLES;
-
-        // prepare replacements (keys not set in hrep will be taken from trep)
-        $trep = array(
-            'PAGE' => $id,
-            'NEWPAGE' => wl($id, '', true, '&'),
-            'SUMMARY' => $summary,
-            'SUBSCRIBE' => wl($id, array('do' => 'subscribe'), true, '&')
-        );
-        $hrep = array();
-
-        if($rev) {
-            $subject = 'changed';
-            $trep['OLDPAGE'] = wl($id, "rev=$rev", true, '&');
-
-            $old_content = rawWiki($id, $rev);
-            $new_content = rawWiki($id);
-
-            $df = new Diff(explode("\n", $old_content),
-                           explode("\n", $new_content));
-            $dformat = new UnifiedDiffFormatter();
-            $tdiff = $dformat->format($df);
-
-            $DIFF_INLINESTYLES = true;
-            $df = new Diff(explode("\n", $old_content),
-                           explode("\n", $new_content));
-            $dformat = new InlineDiffFormatter();
-            $hdiff = $dformat->format($df);
-            $hdiff = '<table>'.$hdiff.'</table>';
-            $DIFF_INLINESTYLES = false;
-        } else {
-            $subject = 'newpage';
-            $trep['OLDPAGE'] = '---';
-            $tdiff = rawWiki($id);
-            $hdiff = nl2br(hsc($tdiff));
-        }
-
-        $trep['DIFF'] = $tdiff;
-        $hrep['DIFF'] = $hdiff;
-
-        $headers = array('Message-Id' => $this->getMessageID($id));
-        if ($rev) {
-            $headers['In-Reply-To'] =  $this->getMessageID($id, $rev);
-        }
-
-        return $this->send(
-            $subscriber_mail, $subject, $id,
-            $template, $trep, $hrep, $headers
-        );
-    }
-
-    /**
-     * Send the diff for some media change
-     *
-     * @fixme this should embed thumbnails of images in HTML version
-     *
-     * @param string   $subscriber_mail The target mail address
-     * @param string   $template        Mail template ('uploadmail', ...)
-     * @param string   $id              Media file for which the notification is
-     * @param int|bool $rev             Old revision if any
-     */
-    public function send_media_diff($subscriber_mail, $template, $id, $rev = false) {
-        global $conf;
-
-        $file = mediaFN($id);
-        list($mime, /* $ext */) = mimetype($id);
-
-        $trep = array(
-            'MIME'  => $mime,
-            'MEDIA' => ml($id,'',true,'&',true),
-            'SIZE'  => filesize_h(filesize($file)),
-        );
-
-        if ($rev && $conf['mediarevisions']) {
-            $trep['OLD'] = ml($id, "rev=$rev", true, '&', true);
-        } else {
-            $trep['OLD'] = '---';
-        }
-
-        $headers = array('Message-Id' => $this->getMessageID($id, @filemtime($file)));
-        if ($rev) {
-            $headers['In-Reply-To'] =  $this->getMessageID($id, $rev);
-        }
-
-        $this->send($subscriber_mail, 'upload', $id, $template, $trep, null, $headers);
-
-    }
-
-    /**
-     * Send a notify mail on new registration
-     *
-     * @author Andreas Gohr <andi@splitbrain.org>
-     *
-     * @param string $login    login name of the new user
-     * @param string $fullname full name of the new user
-     * @param string $email    email address of the new user
-     * @return bool true if a mail was sent
-     */
-    public function send_register($login, $fullname, $email) {
-        global $conf;
-        if(empty($conf['registernotify'])) return false;
-
-        $trep = array(
-            'NEWUSER' => $login,
-            'NEWNAME' => $fullname,
-            'NEWEMAIL' => $email,
-        );
-
-        return $this->send(
-            $conf['registernotify'],
-            'new_user',
-            $login,
-            'registermail',
-            $trep
-        );
-    }
-
-    /**
-     * Send a digest mail
-     *
-     * Sends a digest mail showing a bunch of changes of a single page. Basically the same as send_diff()
-     * but determines the last known revision first
-     *
-     * @author Adrian Lang <lang@cosmocode.de>
-     *
-     * @param string $subscriber_mail The target mail address
-     * @param string $id              The ID
-     * @param int    $lastupdate      Time of the last notification
-     * @return bool
-     */
-    protected function send_digest($subscriber_mail, $id, $lastupdate) {
-        $pagelog = new PageChangeLog($id);
-        $n = 0;
-        do {
-            $rev = $pagelog->getRevisions($n++, 1);
-            $rev = (count($rev) > 0) ? $rev[0] : null;
-        } while(!is_null($rev) && $rev > $lastupdate);
-
-        return $this->send_diff(
-            $subscriber_mail,
-            'subscr_digest',
-            $id, $rev
-        );
-    }
-
-    /**
-     * Send a list mail
-     *
-     * Sends a list mail showing a list of changed pages.
-     *
-     * @author Adrian Lang <lang@cosmocode.de>
-     *
-     * @param string $subscriber_mail The target mail address
-     * @param array  $ids             Array of ids
-     * @param string $ns_id           The id of the namespace
-     * @return bool true if a mail was sent
-     */
-    protected function send_list($subscriber_mail, $ids, $ns_id) {
-        if(count($ids) === 0) return false;
-
-        $tlist = '';
-        $hlist = '<ul>';
-        foreach($ids as $id) {
-            $link = wl($id, array(), true);
-            $tlist .= '* '.$link.NL;
-            $hlist .= '<li><a href="'.$link.'">'.hsc($id).'</a></li>'.NL;
-        }
-        $hlist .= '</ul>';
-
-        $id = prettyprint_id($ns_id);
-        $trep = array(
-            'DIFF' => rtrim($tlist),
-            'PAGE' => $id,
-            'SUBSCRIBE' => wl($id, array('do' => 'subscribe'), true, '&')
-        );
-        $hrep = array(
-            'DIFF' => $hlist
-        );
-
-        return $this->send(
-            $subscriber_mail,
-            'subscribe_list',
-            $ns_id,
-            'subscr_list', $trep, $hrep
-        );
-    }
-
-    /**
-     * Helper function for sending a mail
-     *
-     * @author Adrian Lang <lang@cosmocode.de>
-     *
-     * @param string $subscriber_mail The target mail address
-     * @param string $subject         The lang id of the mail subject (without the
-     *                                prefix “mail_”)
-     * @param string $context         The context of this mail, eg. page or namespace id
-     * @param string $template        The name of the mail template
-     * @param array  $trep            Predefined parameters used to parse the
-     *                                template (in text format)
-     * @param array  $hrep            Predefined parameters used to parse the
-     *                                template (in HTML format), null to default to $trep
-     * @param array  $headers         Additional mail headers in the form 'name' => 'value'
-     * @return bool
-     */
-    protected function send($subscriber_mail, $subject, $context, $template, $trep, $hrep = null, $headers = array()) {
-        global $lang;
-        global $conf;
-
-        $text = rawLocale($template);
-        $subject = $lang['mail_'.$subject].' '.$context;
-        $mail = new Mailer();
-        $mail->bcc($subscriber_mail);
-        $mail->subject($subject);
-        $mail->setBody($text, $trep, $hrep);
-        if(in_array($template, array('subscr_list', 'subscr_digest'))){
-            $mail->from($conf['mailfromnobody']);
-        }
-        if(isset($trep['SUBSCRIBE'])) {
-            $mail->setHeader('List-Unsubscribe', '<'.$trep['SUBSCRIBE'].'>', false);
-        }
-
-        foreach ($headers as $header => $value) {
-            $mail->setHeader($header, $value);
-        }
-
-        return $mail->send();
-    }
-
-    /**
-     * Get a valid message id for a certain $id and revision (or the current revision)
-     *
-     * @param string $id  The id of the page (or media file) the message id should be for
-     * @param string $rev The revision of the page, set to the current revision of the page $id if not set
-     * @return string
-     */
-    protected function getMessageID($id, $rev = null) {
-        static $listid = null;
-        if (is_null($listid)) {
-            $server = parse_url(DOKU_URL, PHP_URL_HOST);
-            $listid = join('.', array_reverse(explode('/', DOKU_BASE))).$server;
-            $listid = urlencode($listid);
-            $listid = strtolower(trim($listid, '.'));
-        }
-
-        if (is_null($rev)) {
-            $rev = @filemtime(wikiFN($id));
-        }
-
-        return "<$id?rev=$rev@$listid>";
-    }
-
-    /**
-     * Default callback for COMMON_NOTIFY_ADDRESSLIST
-     *
-     * Aggregates all email addresses of user who have subscribed the given page with 'every' style
-     *
-     * @author Steven Danz <steven-danz@kc.rr.com>
-     * @author Adrian Lang <lang@cosmocode.de>
-     *
-     * @todo move the whole functionality into this class, trigger SUBSCRIPTION_NOTIFY_ADDRESSLIST instead,
-     *       use an array for the addresses within it
-     *
-     * @param array &$data Containing the entries:
-     *    - $id (the page id),
-     *    - $self (whether the author should be notified,
-     *    - $addresslist (current email address list)
-     *    - $replacements (array of additional string substitutions, @KEY@ to be replaced by value)
-     */
-    public function notifyaddresses(&$data) {
-        if(!$this->isenabled()) return;
-
-        /** @var DokuWiki_Auth_Plugin $auth */
-        global $auth;
-        global $conf;
-        /** @var Input $INPUT */
-        global $INPUT;
-
-        $id = $data['id'];
-        $self = $data['self'];
-        $addresslist = $data['addresslist'];
-
-        $subscriptions = $this->subscribers($id, null, 'every');
-
-        $result = array();
-        foreach($subscriptions as $target => $users) {
-            foreach($users as $user => $info) {
-                $userinfo = $auth->getUserData($user);
-                if($userinfo === false) continue;
-                if(!$userinfo['mail']) continue;
-                if(!$self && $user == $INPUT->server->str('REMOTE_USER')) continue; //skip our own changes
-
-                $level = auth_aclcheck($id, $user, $userinfo['grps']);
-                if($level >= AUTH_READ) {
-                    if(strcasecmp($userinfo['mail'], $conf['notify']) != 0) { //skip user who get notified elsewhere
-                        $result[$user] = $userinfo['mail'];
-                    }
-                }
-            }
-        }
-        $data['addresslist'] = trim($addresslist.','.implode(',', $result), ',');
-    }
-}