誰でもユーザーを登録できるようにする

メッセージ

誰でもユーザーを登録できるようにし、 Wikipediaにあるような利用者ページと下書きのような機能が欲しいです。 (BugTrack/2554に分離) 登録ユーザーへ個別に権限の設定ができるといいと思ってます XD

ユーザー登録システムの実装案 (はいふん)

lib/auth.php
ユーザー登録に関する関数をつくってみました。
私はform_auth関数の次に埋め込んでます。
/**
 * Check if username can be used
 *
 * @param String username
 * @return true is usable username
 */
function is_usable_username($username)
{
	global $auth_users;
	if (in_array($username, array_keys($auth_users))) {
		return false;
	}
	return true;
}

function exist_user($username) {
	return !is_usable_username($username);
}

/**
 * User registration
 */
function user_registration()
{
	global $user_registration;
	global $auth_users, $created_users;
	if ($user_registration) {
		if (file_exists(PKWK_USERLIST_CACHE)) {
			$lines = file(PKWK_USERLIST_CACHE);
			foreach ($lines as $line) {
				list($user, $pass) = explode("\t", rtrim($line));
				$created_users[$user] = array(
					'edit_auth_pages' => $pass,
					'password' => $pass,
				);
				$created_auth_users[$user] = $pass;
			}
			if ($created_auth_users) {
				$auth_users += $created_auth_users;
				unset($created_auth_users);
			}
		}
	}
}

/**
 * Create user
 *
 * @param String username
 * @param String password
 * @param boolean check
 * @return true is created user
 */
function create_user($username, $password, $check)
{
	global $user_registration, $created_users;
	if (!$user_registration)
		die_message('User registration is disabled.');
	if ($username == '' || $password == '') return false;
	if ($check) {
		if (exist_user($username)) {
			return false;
		}
	}
	$created_users[$username] = array(
		'password' => $password,
	); 
	$file = PKWK_USERLIST_CACHE;
	pkwk_touch_file($file);
	$fp = fopen($file, 'r+') or
		die_message('Cannot open ' . $file);
	set_file_buffer($fp, 0);
	flock($fp, LOCK_EX);
	ftruncate($fp, 0);
	rewind($fp);
	foreach ($created_users as $user=>$data)
		fputs($fp, $user . "\t" . $data['password'] . "\n");
	flock($fp, LOCK_UN);
	fclose($fp);
	return true;
}
form_auth関数の変更箇所
function form_auth($username, $password)
{
	global $ldap_user_account, $auth_users;
	$user = $username;
	if ($ldap_user_account) {
		// LDAP account
		return ldap_auth($username, $password);
	} else {
		// Defined users in pukiwiki.ini.php
-		if (in_array($user, array_keys($auth_users))) {
+		if (exist_user($user)) {
			if (pkwk_hash_compute(
				$password,
				$auth_users[$user]) === $auth_users[$user]) {
				session_start();
				session_regenerate_id(true); // require: PHP5.1+
				$_SESSION['authenticated_user'] = $user;
				$_SESSION['authenticated_user_fullname'] = $user;
				return true;
			}
		}
	}
	return false;
}
定数の定義
/////////////////////////////////////////////////
// User registration
define('PKWK_USERLIST_CACHE', DATA_HOME . 'userlist.dat');
lib/pukiwiki.php
/////////////////////////////////////////////////
// Main
if ($vars['page'] === FALSE) {
	die_invalid_pagename();
	exit;
}
if (manage_page_redirect()) {
	exit;
}
$retvars = array();
$is_cmd = FALSE;
if (isset($vars['cmd'])) {
	$is_cmd  = TRUE;
	$plugin = & $vars['cmd'];
} else if (isset($vars['plugin'])) {
	$plugin = & $vars['plugin'];
} else {
	$plugin = '';
}
if ($plugin != '') {
+	user_registration();
	ensure_valid_auth_user();
plugin/loginform.inc.php
function plugin_loginform_action()
{
	global $auth_user, $auth_type, $_loginform_messages;
	$page = isset($_GET['page']) ? $_GET['page'] : '';
	$pcmd = isset($_GET['pcmd']) ? $_GET['pcmd'] : '';
	$url_after_login = isset($_GET['url_after_login']) ? $_GET['url_after_login'] : '';
	$page_after_login = $page;
	if (!$url_after_login) {
		$page_after_login = $page;
	}
-	$action_url = get_base_uri() . '?plugin=loginform'
-		. '&page=' . rawurlencode($page)
-		. ($url_after_login ? '&url_after_login=' . rawurlencode($url_after_login) : '')
-		. ($page_after_login ? '&page_after_login=' . rawurlencode($page_after_login) : '');
	$username = isset($_POST['username']) ? $_POST['username'] : '';
	$password = isset($_POST['password']) ? $_POST['password'] : '';
	$isset_user_credential = $username || $password ;
	if ($username && $password && form_auth($username, $password)) {
		// Sign in successfully completed
		form_auth_redirect($url_after_login, $page_after_login);
		exit; // or 'return FALSE;' - Don't double check for FORM_AUTH
	}
	if ($pcmd === 'logout') {
		// logout
		switch ($auth_type) {
			case AUTH_TYPE_BASIC:
				header('WWW-Authenticate: Basic realm="Please cancel to log out"');
				header('HTTP/1.0 401 Unauthorized');
				break;
			case AUTH_TYPE_FORM:
			case AUTH_TYPE_EXTERNAL:
			case AUTH_TYPE_SAML:
			default:
				$_SESSION = array();
				session_regenerate_id(true); // require: PHP5.1+
				session_destroy();
				break;
		}
		$auth_user = '';
		return array(
			'msg' => 'Log out',
			'body' => 'Logged out completely<br>'
				. '<a href="'. get_page_uri($page) . '">'
				. $page . '</a>'
		);
+	} else if ($pcmd === 'registration') {
+		// registration
+		$password_confirm = isset($_POST['password_confirm']) ? $_POST['password_confirm'] : '';
+		$match_password = $password == $password_confirm;
+		$usable_username = is_usable_username($username);
+		if ($usable_username && $match_password) {
+			if (create_user($username, $password, false)) {
+			}
+		}
+		$action_url = get_base_uri() . '?plugin=loginform&pcmd=registration'
+		. '&page=' . rawurlencode($page)
+		. ($url_after_login ? '&url_after_login=' . rawurlencode($url_after_login) : '')
+		. ($page_after_login ? '&page_after_login=' . rawurlencode($page_after_login) : '');
+		ob_start();
+?>
+<style>
+  .registrationformcontainer {
+    text-align: center;
+  }
+  .registrationform table {
+    margin-top: 1em;
+	margin-left: auto;
+	margin-right: auto;
+  }
+  .registrationform tbody td {
+    padding: .5em;
+  }
+  .registrationform .label {
+    text-align: right;
+  }
+  .registrationform .registration-button-container {
+    text-align: right;
+  }
+  .registrationform .registrationbutton {
+    margin-top: 1em;
+  }
+  .registrationform .errormessage {
+    color: red;
+  }
+</style>
+<div class="registrationformcontainer">
+<form name="loginform" class="registrationform" action="<?php echo htmlsc($action_url) ?>" method="post">
+<div>
+<table style="border:0">
+  <tbody>
+  <tr>
+    <td class="label"><label for="_plugin_registrationform_username"><?php echo htmlsc($_loginform_messages['username']) ?></label></td>
+    <td><input type="text" name="username" value="<?php echo htmlsc($username) ?>" id="_plugin_registrationform_username" autoComplete="name"></td>
+  </tr>
+  <tr>
+  <td class="label"><label for="_plugin_registrationform_form_password"><?php echo htmlsc($_loginform_messages['password']) ?></label></td>
+  <td><input type="password" name="password" id="_plugin_registrationform_form_password" autoComplete="new-password"></td>
+  </tr>
+  <tr>
+  <td class="label"><label for="_plugin_registrationform_password_confirm"><?php echo htmlsc($_loginform_messages['password_confirm']) ?></label></td>
+  <td><input type="password" name="password_confirm" id="_plugin_registrationform_password_confirm"></td>
+  </tr>
+<?php if (!$usable_username): ?>
+  <tr>
+    <td></td>
+    <td class="errormessage"><?php echo $_loginform_messages['unavailable_username'] ?></td>
+  </tr>
+<?php endif ?>
+<?php if (!$match_password): ?>
+  <tr>
+    <td></td>
+    <td class="errormessage"><?php echo $_loginform_messages['not_match_password'] ?></td>
+  </tr>
+<?php endif ?>
+  <tr>
+    <td></td>
+    <td class="registration-button-container"><input type="submit" value="<?php echo htmlsc($_loginform_messages['register']) ?>" class="registrationbutton"></td>
+  </tr>
+  </tbody>
+</table>
+</div>
+<div>
+</div>
+</form>
+</div>
+<script><!--
+window.addEventListener && window.addEventListener("DOMContentLoaded", function() {
+  var f = window.document.forms.loginform;
+  if (f && f.username && f.password) {
+    if (f.username.value) {
+     f.password.focus && f.password.focus();
+	} else {
+     f.username.focus && f.username.focus();
+	}
+  }
+});
+//-->
+</script>
+<?php
+		$body = ob_get_contents();
+		ob_end_clean();
+		return array(
+			'msg' => $_loginform_messages['register'],
+			'body' => $body,
+			);
+
	} else {
		// login
+		$action_url = get_base_uri() . '?plugin=loginform'
+		. '&page=' . rawurlencode($page)
+		. ($url_after_login ? '&url_after_login=' . rawurlencode($url_after_login) : '')
+		. ($page_after_login ? '&page_after_login=' . rawurlencode($page_after_login) : '');
		ob_start();
?>
<style>
  .loginformcontainer {
    text-align: center;
  }
pukiwiki.ini.php
私はUser definitionの近くに埋め込んでみました。
/////////////////////////////////////////////////
// User registration (0:Disable, 1:Enable)
$user_registration = 1;
.htaccess
# Prohibit direct access
-<FilesMatch "\.(ini\.php|lng\.php|txt|gz|tgz|zip)$">
+<FilesMatch "\.(ini\.php|lng\.php|txt|gz|tgz|zip|dat)$">
  Require all denied
</FilesMatch>

ユーザー登録とはまた別だと思いますが、ユーザーのみ編集できる制限を実装してみました。

ja.lng.php
Page titlesの箇所へ追加
$_title_cannotedit_not_login = 'ログインしていないため $1 は編集できません';
Skinの箇所へ追加
$_LANG['skin']['registration'] = 'ユーザー登録';
差分
///////////////////////////////////////
// loginform.inc.php
$_loginform_messages = array(
	'username' => 'ユーザー名:',
	'password' => 'パスワード:',
+	'password_confirm' => 'パスワード (確認):',
	'login' => 'ログイン',
+	'register' => 'ユーザー登録',
-	'invalid_username_or_password' => 'ユーザー名またはパスワードが違います'
+	'invalid_username_or_password' => 'ユーザー名またはパスワードが違います',
+	'unavailable_username' => '既にそのユーザー名は使われています',
+	'not_match_password' => 'パスワードが確認と一致しません'
);
skin/pukiwiki.skin.php
 <?php if ($enable_login) { ?>
 	[
-	<?php _navigator('login') ?>
+	<?php _navigator('login') ?> |
+	<?php _navigator('registration') ?>
	]
 <?php } ?>
lib/html.php
	$_LINK['upload']   = "$script?plugin=attach&amp;pcmd=upload&amp;page=$r_page";
+	$_LINK['registration']   = "$script?cmd=loginform&amp;pcmd=registration&amp;page=$r_page";
	$_LINK['canonical_url'] = $canonical_url;
en.lng.php
Page titlesの箇所へ追加
$_title_cannotedit_not_login = '$1 is not editable because you are not log in';
Skinの箇所へ追加
$_LANG['skin']['registration'] = 'User registration';
差分
///////////////////////////////////////
// loginform.inc.php
$_loginform_messages = array(
	'username' => 'Username',
	'password' => 'Password',
+	'password_confirm' => 'Password (Confirm):',
	'login' => 'Log in',
+	'register' => 'User registration',
-	'invalid_username_or_password' => 'The username or password you entered is incorrect'
+	'invalid_username_or_password' => 'The username or password you entered is incorrect',
+	'unavailable_username' => 'The username is already in use',
+	'not_match_password' => 'Password and confirmed password is not match'
);
plugin/edit.inc.php
定数定義
// ユーザーだけがページを編集できるようにする
define('PLUGIN_EDIT_WRITE_USER_ONLY', FALSE);
plugin_edit_action関数
function plugin_edit_action()
{
-	global $vars, $_title_edit;
+	global $vars, $_title_edit, $auth_user, $_title_cannotedit_not_login;

	if (PKWK_READONLY) die_message('PKWK_READONLY prohibits editing');

	// Create initial pages
	plugin_edit_setup_initial_pages();

	$page = isset($vars['page']) ? $vars['page'] : '';
	check_editable($page, true, true);
	check_readable($page, true, true);
	
+	if (PLUGIN_EDIT_WRITE_USER_ONLY && !$auth_user) {
+		$body = $title = str_replace('$1',
+			htmlsc(strip_bracket($page)), $_title_cannotedit_not_login);
+		$page = str_replace('$1', make_search($page), $_title_cannotedit_not_login);
+		catbody($title, $page, $body);
+		exit;
+	}

userlist.datに登録されたユーザーのデータが保存されます。

関連




トップ   編集 凍結 差分 履歴 添付 複製 名前変更 リロード   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS
Last-modified: 2022-05-10 (火) 22:05:10
Site admin: PukiWiki Development Team

PukiWiki 1.5.4+ © 2001-2022 PukiWiki Development Team. Powered by PHP 5.6.40-0+deb8u12. HTML convert time: 0.420 sec.

OSDN