PageRenderTime 50ms CodeModel.GetById 6ms RepoModel.GetById 1ms app.codeStats 0ms

/elgg/mod/openid_client/openid_include.php

https://bitbucket.org/rhizomatik/lorea_production/
PHP | 542 lines | 396 code | 98 blank | 48 comment | 55 complexity | 784d29601c0fa88dfacd0d2c46c31ad3 MD5 | raw file
Possible License(s): GPL-3.0, GPL-2.0, BSD-3-Clause, LGPL-2.1
  1. <?php
  2. /**
  3. * An Elgg 1.x compatible store implementation
  4. */
  5. /**
  6. * Require base class for creating a new interface.
  7. */
  8. require_once 'Auth/Yadis/Email.php';
  9. require_once 'Auth/OpenID.php';
  10. require_once 'Auth/OpenID/Interface.php';
  11. require_once 'Auth/OpenID/Consumer.php';
  12. try {
  13. include_once "Auth/OpenID/HMACSHA1.php";
  14. } catch(Exception $e) {
  15. // new way :P
  16. require_once "Auth/OpenID/HMAC.php";
  17. }
  18. require_once 'Auth/OpenID/Nonce.php';
  19. require_once 'Auth/OpenID/SReg.php';
  20. class OpenID_ElggStore extends Auth_OpenID_OpenIDStore {
  21. function resetAssociations () {
  22. openid_client_delete_entities('object', 'openid_client::association');
  23. }
  24. function resetNonces () {
  25. openid_client_delete_entities('object', 'openid_client::nonce');
  26. }
  27. function getAssociation ($server_url, $handle = null) {
  28. if (isset($handle)) {
  29. $meta_array = array(
  30. 'server_url' => $server_url,
  31. 'handle' => $handle
  32. );
  33. $assocs = get_entities_from_metadata_multi($meta_array, 'object', 'openid_client::association');
  34. } else {
  35. $assocs = get_entities_from_metadata('server_url', $server_url, 'object','openid_client::association');
  36. }
  37. if (!$assocs || (count($assocs) == 0)) {
  38. return null;
  39. } else {
  40. $associations = array();
  41. foreach ($assocs as $assoc_row) {
  42. $assoc = new Auth_OpenID_Association($assoc_row->handle,
  43. base64_decode($assoc_row->secret),
  44. $assoc_row->issued,
  45. $assoc_row->lifetime,
  46. $assoc_row->assoc_type);
  47. if ($assoc->getExpiresIn() == 0) {
  48. OpenID_ElggStore::removeAssociation($server_url, $assoc->handle);
  49. } else {
  50. $associations[] = array($assoc->issued, $assoc);
  51. }
  52. }
  53. if ($associations) {
  54. $issued = array();
  55. $assocs = array();
  56. foreach ($associations as $key => $assoc) {
  57. $issued[$key] = $assoc[0];
  58. $assocs[$key] = $assoc[1];
  59. }
  60. array_multisort($issued, SORT_DESC, $assocs, SORT_DESC,
  61. $associations);
  62. // return the most recently issued one.
  63. list($issued, $assoc) = $associations[0];
  64. return $assoc;
  65. } else {
  66. return null;
  67. }
  68. }
  69. }
  70. function removeAssociation ($server_url, $handle) {
  71. if (isset($handle)) {
  72. $meta_array = array(
  73. 'server_url' => $server_url,
  74. 'handle' => $handle
  75. );
  76. $entities = get_entities_from_metadata_multi($meta_array, 'object', 'openid_client::association');
  77. } else {
  78. $entities = get_entities_from_metadata('server_url', $server_url, 'object','openid_client::association');
  79. }
  80. foreach ($entities as $entity) {
  81. openid_client_delete_entity($entity);
  82. }
  83. }
  84. function reset () {
  85. OpenID_ElggStore::resetAssociations ();
  86. OpenID_ElggStore::resetNonces ();
  87. }
  88. function storeAssociation ($server_url, $association) {
  89. // Initialise a new ElggObject
  90. $association_obj = new ElggObject();
  91. $association_obj->subtype = 'openid_client::association';
  92. $association_obj->owner_guid = 0;
  93. $association_obj->container_guid = 0;
  94. $association_obj->title = 'association';
  95. $association_obj->access_id = 2;
  96. if ($association_obj->save()) {
  97. $association_obj->server_url = $server_url;
  98. $association_obj->handle = $association->handle;
  99. $association_obj->secret = base64_encode($association->secret);
  100. $association_obj->issued = $association->issued;
  101. $association_obj->lifetime = $association->lifetime;
  102. $association_obj->assoc_type = $association->assoc_type;
  103. return true;
  104. } else {
  105. return false;
  106. }
  107. }
  108. function useNonce ( $server_url, $timestamp, $salt) {
  109. global $Auth_OpenID_SKEW;
  110. if ( abs($timestamp - time()) > $Auth_OpenID_SKEW ) {
  111. return false;
  112. }
  113. // check to see if the nonce already exists
  114. $meta_array = array(
  115. 'server_url' => $server_url,
  116. 'timestamp' => $timestamp,
  117. 'salt' => $salt
  118. );
  119. $entities = get_entities_from_metadata_multi($meta_array, 'object', 'openid_client::nonce');
  120. if ($entities) {
  121. // bad - this nonce is already in use
  122. return false;
  123. } else {
  124. // Initialise a new ElggObject
  125. $nonce_obj = new ElggObject();
  126. $nonce_obj->subtype = 'openid_client::nonce';
  127. $nonce_obj->owner_guid = 0;
  128. $nonce_obj->container_guid = 0;
  129. $nonce_obj->title = 'nonce';
  130. $nonce_obj->access_id = 2;
  131. if ($nonce_obj->save()) {
  132. $nonce_obj->server_url = $server_url;
  133. $nonce_obj->timestamp = $timestamp;
  134. $nonce_obj->salt = $salt;
  135. return true;
  136. } else {
  137. return false;
  138. }
  139. }
  140. }
  141. function getNoSyncStatus($user) {
  142. if (isset($user) && isset($user->openid_client_nosync_status)) {
  143. return $user->openid_client_nosync_status;
  144. } else {
  145. return false;
  146. }
  147. }
  148. function addNoSyncStatus($user) {
  149. $user->openid_client_nosync_status = 1;
  150. }
  151. }
  152. function openid_client_create_invitation($prefix,$username,$ident,$email,$fullname) {
  153. error_log("start create invitation");
  154. $invite = new ElggObject();
  155. $invite->subtype = "openid_invitation";
  156. $invite->owner_guid = 0;
  157. $invite->container_guid = 0;
  158. $invite->title = 'invitation';
  159. $invite->access_id = 2;
  160. error_log("middle create invitation");
  161. if ($invite->save()) {
  162. error_log("end create invitation");
  163. $invite->new_owner = $ident;
  164. $invite->name = $fullname;
  165. $invite->email = $email;
  166. $invite->username = $username;
  167. $invite->code = $prefix . substr(base_convert(md5(time() . $username), 16, 36), 0, 7);
  168. $invite->added = time();
  169. return $invite;
  170. } else {
  171. return null;
  172. }
  173. }
  174. function openid_client_get_invitation($code) {
  175. $invitations = get_entities_from_metadata('code', $code, 'object','openid_invitation');
  176. if ($invitations) {
  177. return $invitations[0];
  178. } else {
  179. return null;
  180. }
  181. }
  182. function openid_client_remove_invitation($code) {
  183. $invitations = get_entities_from_metadata('code', $code, 'object','openid_invitation');
  184. if ($invitations) {
  185. foreach ($invitations as $invitation) {
  186. openid_client_delete_entity($invitation);
  187. }
  188. }
  189. }
  190. function openid_client_get_invitation_by_username($username) {
  191. $invitations = get_entities_from_metadata('username', $username, 'object','openid_invitation');
  192. if ($invitations) {
  193. return $invitations[0];
  194. } else {
  195. return null;
  196. }
  197. }
  198. function openid_client_send_activate_confirmation_message($details) {
  199. global $CONFIG;
  200. // not sure where these should really come from
  201. $from_name = $CONFIG->site->name;
  202. $from_email = $CONFIG->site->email;
  203. $subject = sprintf(elgg_echo('openid_client:activate_confirmation_subject'),$CONFIG->sitename);
  204. $url = $CONFIG->wwwroot . "mod/openid_client/actions/confirm.php?code=" . $details->code;
  205. $message = wordwrap(sprintf(elgg_echo('openid_client:activate_confirmation_body'),$details->name,$CONFIG->sitename,$url, $CONFIG->sitename));
  206. openid_client_email_user($details->name, $details->email, $from_name, $from_email, $subject,$message);
  207. }
  208. function openid_client_send_change_confirmation_message($details) {
  209. global $CONFIG;
  210. // not sure where these should really come from
  211. $from_name = 'System administrator';
  212. $from_email = 'kevin@radagast.biz';
  213. $subject = sprintf(elgg_echo('openid_client:change_confirmation_subject'),$CONFIG->sitename);
  214. $url = $CONFIG->wwwroot . "mod/openid_client/actions/confirm.php?code=" . $details->code;
  215. $message = wordwrap(sprintf(elgg_echo('openid_client:change_confirmation_body'),
  216. $details->name,$CONFIG->sitename,$url, $CONFIG->sitename));
  217. openid_client_email_user($details->name, $details->email, $from_name, $from_email, $subject,$message);
  218. }
  219. $emailLabel = elgg_echo('openid_client:email_label');
  220. $nameLabel = elgg_echo('openid_client:name_label');
  221. $submitLabel = elgg_echo('openid_client:submit_label');
  222. $cancelLabel = elgg_echo('openid_client:cancel_label');
  223. function openid_client_generate_sync_form($new_email,$new_name, $user, $email_confirmation) {
  224. return elgg_view_layout('one_column',elgg_view_title(elgg_echo('openid_client:sync_title')) . elgg_view("openid_client/forms/sync",
  225. array(
  226. 'userid' => $user->getGUID(),
  227. 'new_email' => $new_email,
  228. 'new_name' => $new_name,
  229. 'email_confirmation' => $email_confirmation
  230. )));
  231. }
  232. function openid_client_generate_missing_data_form($openid_url,$email,$fullname,$email_confirmation,$details) {
  233. return elgg_view_layout('one_column',elgg_view_title(elgg_echo('openid_client:missing_title')) . elgg_view("openid_client/forms/missing",
  234. array(
  235. 'openid_url' => $openid_url,
  236. 'email' => $email,
  237. 'fullname' => $fullname,
  238. 'email_confirmation' => $email_confirmation,
  239. 'openid_code' => $details->code
  240. )));
  241. }
  242. function openid_client_check_email_confirmation($openid_url) {
  243. global $CONFIG;
  244. $done = false;
  245. $email_confirmation = false;
  246. $greenlist = datalist_get('openid_client_greenlist');
  247. $yellowlist = datalist_get('openid_client_yellowlist');
  248. if ($greenlist) {
  249. foreach (explode("\n",$greenlist) as $entry ) {
  250. if (fnmatch($entry,$openid_url)) {
  251. $email_confirmation = false;
  252. $done = true;
  253. break;
  254. }
  255. }
  256. }
  257. if (!$done && $yellowlist) {
  258. foreach (explode("\n",$yellowlist) as $entry ) {
  259. if (fnmatch($entry,$openid_url)) {
  260. $email_confirmation = true;
  261. break;
  262. }
  263. }
  264. }
  265. return $email_confirmation;
  266. }
  267. function openid_client_create_openid_user($openid_url,$email, $fullname, $email_confirmation) {
  268. global $messages;
  269. if ($email && openid_client_get_user_by_email($email)) {
  270. register_error(sprintf(elgg_echo('openid_client:create_email_in_use'),$email));
  271. return null;
  272. } else {
  273. $user = new ElggUser();
  274. $user->email = $email;
  275. $user->name = $fullname;
  276. $user->access_id = 2;
  277. $user->subtype = 'openid';
  278. $user->username = randomString(8);
  279. if ($user->save()) {
  280. $id = $user->getGUID();
  281. $user = get_user($id);
  282. $user->alias = $openid_url;
  283. $user->username = "openid_".$id;
  284. if ($email_confirmation) {
  285. $user->active = 'no';
  286. } else {
  287. $user->active = 'yes';
  288. }
  289. create_metadata($id, 'contactemail', $email, 'text', $id, ACCESS_PRIVATE);
  290. $r = $user->save();
  291. // Turn on email notifications by default
  292. set_user_notification_setting($user->getGUID(), 'email', true);
  293. return $user;
  294. } else {
  295. register_error(elgg_echo('openid_client:user_creation_failed'));
  296. forward();
  297. return null;
  298. }
  299. }
  300. }
  301. /**
  302. * Send a notification via email.
  303. */
  304. function openid_client_email_user($to_name, $to_email, $from_name, $from_email, $subject, $message)
  305. {
  306. $to = "$to_name <$to_email>";
  307. $headers = "From: $from_name <$from_email>\r\n";
  308. return mail($to, $subject, $message, $headers);
  309. }
  310. // should really be added to users.php
  311. /**
  312. * Get user by email
  313. *
  314. * @param string $email The user's email address
  315. * @return ElggUser|false Depending on success
  316. */
  317. function openid_client_get_user_by_email($email)
  318. {
  319. global $CONFIG;
  320. $email = sanitise_string($email);
  321. $row = get_data_row("SELECT * from {$CONFIG->dbprefix}users_entity where email='$email'");
  322. if ($row)
  323. return new ElggUser($row);
  324. return false;
  325. }
  326. // modified from Elgg 1.0 sessions.php
  327. /**
  328. * Log in
  329. *
  330. * @param user entity $user
  331. * @param true|false $persistent
  332. * @return true|false
  333. */
  334. function do_login($user, $persistent = false) {
  335. $_SESSION['user'] = $user;
  336. $_SESSION['guid'] = $user->getGUID();
  337. $_SESSION['id'] = $_SESSION['guid'];
  338. $_SESSION['username'] = $user->username;
  339. $_SESSION['name'] = $user->name;
  340. $code = (md5($user->name . $user->username . time() . rand()));
  341. $user->code = md5($code);
  342. $user->save();
  343. $_SESSION['code'] = $code;
  344. //if (!empty($persistent)) {
  345. setcookie("elggperm", $code, (time()+(86400 * 30)),"/");
  346. //}
  347. // set_login_fields($user->id);
  348. return true;
  349. }
  350. // copied over from old elgglib
  351. /**
  352. * Validates an email to make sure it makes sense and adheres
  353. * to the email filter if it's set.
  354. *
  355. * @param string $address The email address to validate.
  356. * @return boolean
  357. */
  358. function openid_validate_email($address) {
  359. global $CONFIG;
  360. if (ereg('^[-!#$%&\'*+\\./0-9=?A-Z^_`a-z{|}~]+'.
  361. '@'.
  362. '[-!#$%&\'*+\\/0-9=?A-Z^_`a-z{|}~]+\.'.
  363. '[-!#$%&\'*+\\./0-9=?A-Z^_`a-z{|}~]+$',
  364. $address)) {
  365. if ($CONFIG->emailfilter != "") {
  366. $domain = substr($address,strpos($address,"@")+1);
  367. if (substr_count($CONFIG->emailfilter, $domain) == 0) {
  368. return false;
  369. }
  370. }
  371. return true;
  372. } else {
  373. return false;
  374. }
  375. }
  376. function randomString($length)
  377. {
  378. // Generate random 32 charecter string
  379. $string = md5(time());
  380. // Position Limiting
  381. $highest_startpoint = 32-$length;
  382. // Take a random starting point in the randomly
  383. // Generated String, not going any higher then $highest_startpoint
  384. $randomString = substr($string,rand(0,$highest_startpoint),$length);
  385. return $randomString;
  386. }
  387. function openid_client_delete_entities($type = "", $subtype = "", $owner_guid = 0)
  388. {
  389. $entities = get_entities($type, $subtype, $owner_guid, "time_created desc", 0);
  390. foreach ($entities as $entity) {
  391. openid_client_delete_entity($entity);
  392. }
  393. return true;
  394. }
  395. function openid_client_delete_entity($entity)
  396. {
  397. global $CONFIG;
  398. $entity->clearMetadata();
  399. $entity->clearAnnotations();
  400. $guid = $entity->getGUID();
  401. delete_data("DELETE from {$CONFIG->dbprefix}entities where guid={$guid}");
  402. }
  403. function is_admin($user_id = 0) {
  404. if (!$user_id) {
  405. if (isloggedin()) {
  406. $user_id = $_SESSION['user']->getGUID();
  407. } else {
  408. return false;
  409. }
  410. }
  411. return get_metadata_byname($user_id, 'admin');
  412. }
  413. if (!function_exists('fnmatch')) {
  414. function fnmatch($pattern, $string) {
  415. for ($op = 0, $npattern = '', $n = 0, $l = strlen($pattern); $n < $l; $n++) {
  416. switch ($c = $pattern[$n]) {
  417. case '\\':
  418. $npattern .= '\\' . @$pattern[++$n];
  419. break;
  420. case '.': case '+': case '^': case '$': case '(': case ')': case '{': case '}': case '=': case '!': case '<': case '>': case '|':
  421. $npattern .= '\\' . $c;
  422. break;
  423. case '?': case '*':
  424. $npattern .= '.' . $c;
  425. break;
  426. case '[': case ']': default:
  427. $npattern .= $c;
  428. if ($c == '[') {
  429. $op++;
  430. } else if ($c == ']') {
  431. if ($op == 0) return false;
  432. $op--;
  433. }
  434. break;
  435. }
  436. }
  437. if ($op != 0) return false;
  438. return preg_match('/' . $npattern . '/i', $string);
  439. }
  440. }
  441. ?>