]> git.mxchange.org Git - quix0rs-gnu-social.git/blob - plugins/RequireValidatedEmail/RequireValidatedEmailPlugin.php
[TRANSLATION] Update license and copyright notice in translation files
[quix0rs-gnu-social.git] / plugins / RequireValidatedEmail / RequireValidatedEmailPlugin.php
1 <?php
2 /**
3  * StatusNet, the distributed open-source microblogging tool
4  *
5  * Plugin that requires the user to have a validated email address before they
6  * can post notices
7  *
8  * PHP version 5
9  *
10  * LICENCE: This program is free software: you can redistribute it and/or modify
11  * it under the terms of the GNU Affero General Public License as published by
12  * the Free Software Foundation, either version 3 of the License, or
13  * (at your option) any later version.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Affero General Public License for more details.
19  *
20  * You should have received a copy of the GNU Affero General Public License
21  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
22  *
23  * @category  Plugin
24  * @package   StatusNet
25  * @author    Craig Andrews <candrews@integralblue.com>
26  * @author    Brion Vibber <brion@status.net>
27  * @author    Evan Prodromou <evan@status.net>
28  * @copyright 2011 StatusNet Inc. http://status.net/
29  * @copyright 2009 Free Software Foundation, Inc http://www.fsf.org
30  * @license   http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
31  * @link      http://status.net/
32  */
33
34 if (!defined('STATUSNET') && !defined('LACONICA')) {
35     exit(1);
36 }
37
38 /**
39  * Plugin for requiring a validated email before posting.
40  *
41  * Enable this plugin using addPlugin('RequireValidatedEmail');
42  *
43  * @category  Plugin
44  * @package   StatusNet
45  * @author    Craig Andrews <candrews@integralblue.com>
46  * @author    Brion Vibber <brion@status.net>
47  * @author    Evan Prodromou <evan@status.net>
48  * @author    Mikael Nordfeldth <mmn@hethane.se>
49  * @copyright 2009-2013 Free Software Foundation, Inc http://www.fsf.org
50  * @copyright 2009-2010 StatusNet, Inc.
51  * @license   http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
52  * @link      http://status.net/
53  */
54 class RequireValidatedEmailPlugin extends Plugin
55 {
56     const PLUGIN_VERSION = '2.0.0';
57
58     /**
59      * Users created before this time will be grandfathered in
60      * without the validation requirement.
61      */
62     public $grandfatherCutoff = null;
63
64     /**
65      * If OpenID plugin is installed, users with a verified OpenID
66      * association whose provider URL matches one of these regexes
67      * will be considered to be sufficiently valid for our needs.
68      *
69      * For example, to trust WikiHow and Wikipedia OpenID users:
70      *
71      * addPlugin('RequireValidatedEmailPlugin', array(
72      *    'trustedOpenIDs' => array(
73      *        '!^http://\w+\.wikihow\.com/!',
74      *        '!^http://\w+\.wikipedia\.org/!',
75      *    ),
76      * ));
77      */
78     public $trustedOpenIDs = array();
79
80     /**
81      * Whether or not to disallow login for unvalidated users.
82      */
83     public $disallowLogin = false;
84
85     public function onRouterInitialized(URLMapper $m)
86     {
87         $m->connect('main/confirmfirst/:code',
88                     array('action' => 'confirmfirstemail'));
89         return true;
90     }
91
92     /**
93      * Event handler for notice saves; rejects the notice
94      * if user's address isn't validated.
95      *
96      * @param Notice $notice The notice being saved
97      *
98      * @return bool hook result code
99      */
100     public function onStartNoticeSave(Notice $notice)
101     {
102         $author = $notice->getProfile();
103         if (!$author->isLocal()) {
104             // remote notice
105             return true;
106         }
107         $user = $author->getUser();
108         if (!$this->validated($user)) {
109             // TRANS: Client exception thrown when trying to post notices before validating an e-mail address.
110             $msg = _m('You must validate your email address before posting.');
111             throw new ClientException($msg);
112         }
113         return true;
114     }
115
116     /**
117      * Event handler for registration attempts; rejects the registration
118      * if email field is missing.
119      *
120      * @param Action $action Action being executed
121      *
122      * @return bool hook result code
123      */
124     function onStartRegisterUser(&$user, &$profile)
125     {
126         $email = $user->email;
127
128         if (empty($email)) {
129             // TRANS: Client exception thrown when trying to register without providing an e-mail address.
130             throw new ClientException(_m('You must provide an email address to register.'));
131         }
132
133         return true;
134     }
135
136     /**
137      * Check if a user has a validated email address or has been
138      * otherwise grandfathered in.
139      *
140      * @param User $user User to valide
141      *
142      * @return bool
143      */
144     protected function validated(User $user)
145     {
146         // The email field is only stored after validation...
147         // Until then you'll find them in confirm_address.
148         $knownGood = !empty($user->email) ||
149           $this->grandfathered($user) ||
150           $this->hasTrustedOpenID($user);
151
152         // Give other plugins a chance to override, if they can validate
153         // that somebody's ok despite a non-validated email.
154
155         // @todo FIXME: This isn't how to do it! Use Start*/End* instead
156         Event::handle('RequireValidatedEmailPlugin_Override',
157                       array($user, &$knownGood));
158
159         return $knownGood;
160     }
161
162     /**
163      * Check if a user was created before the grandfathering cutoff.
164      * If so, we won't need to check for validation.
165      *
166      * @param User $user User to check
167      *
168      * @return bool true if user is grandfathered
169      */
170     protected function grandfathered(User $user)
171     {
172         if ($this->grandfatherCutoff) {
173             $created = strtotime($user->created . " GMT");
174             $cutoff  = strtotime($this->grandfatherCutoff);
175             if ($created < $cutoff) {
176                 return true;
177             }
178         }
179         return false;
180     }
181
182     /**
183      * Override for RequireValidatedEmail plugin. If we have a user who's
184      * not validated an e-mail, but did come from a trusted provider,
185      * we'll consider them ok.
186      *
187      * @param User $user User to check
188      *
189      * @return bool true if user has a trusted OpenID.
190      */
191     function hasTrustedOpenID(User $user)
192     {
193         if ($this->trustedOpenIDs && class_exists('User_openid')) {
194             foreach ($this->trustedOpenIDs as $regex) {
195                 $oid = new User_openid();
196
197                 $oid->user_id = $user->id;
198
199                 $oid->find();
200                 while ($oid->fetch()) {
201                     if (preg_match($regex, $oid->canonical)) {
202                         return true;
203                     }
204                 }
205             }
206         }
207         return false;
208     }
209
210     /**
211      * Add version information for this plugin.
212      *
213      * @param array &$versions Array of associative arrays of version data
214      *
215      * @return boolean hook value
216      */
217     function onPluginVersion(array &$versions)
218     {
219         $versions[] =
220           array('name' => 'Require Validated Email',
221                 'version' => self::PLUGIN_VERSION,
222                 'author' => 'Craig Andrews, '.
223                 'Evan Prodromou, '.
224                 'Brion Vibber',
225                 'homepage' =>
226                 'https://git.gnu.io/gnu/gnu-social/tree/master/plugins/RequireValidatedEmail',
227                 'rawdescription' =>
228                 // TRANS: Plugin description.
229                 _m('Disables posting without a validated email address.'));
230
231         return true;
232     }
233
234     /**
235      * Show an error message about validating user email before posting
236      *
237      * @param string $tag    Current tab tag value
238      * @param Action $action action being shown
239      * @param Form   $form   object producing the form
240      *
241      * @return boolean hook value
242      */
243     function onStartMakeEntryForm($tag, $action, &$form)
244     {
245         $user = common_current_user();
246         if (!empty($user)) {
247             if (!$this->validated($user)) {
248                 $action->element('div', array('class'=>'error'), _m('You must validate an email address before posting!'));
249             }
250         }
251         return true;
252     }
253
254     /**
255      * Prevent unvalidated folks from creating spam groups.
256      *
257      * @param Profile $profile User profile we're checking
258      * @param string $right rights key
259      * @param boolean $result if overriding, set to true/false has right
260      * @return boolean hook result value
261      */
262     function onUserRightsCheck(Profile $profile, $right, &$result)
263     {
264         if ($right == Right::CREATEGROUP ||
265             ($this->disallowLogin && ($right == Right::WEBLOGIN || $right == Right::API))) {
266             $user = User::getKV('id', $profile->id);
267             if ($user && !$this->validated($user)) {
268                 $result = false;
269                 return false;
270             }
271         }
272         return true;
273     }
274
275     function onLoginAction($action, &$login)
276     {
277         if ($action == 'confirmfirstemail') {
278             $login = true;
279             return false;
280         }
281         return true;
282     }
283 }