包含:登录失败锁定、90天密码有效期、30分钟会话超时、 强制改密、登录审计日志、屏幕水印、企业背景图、 备案信息固定底部、favicon、登录页JS修复等全部改动
This commit is contained in:
@@ -0,0 +1,416 @@
|
||||
<?php
|
||||
declare(strict_types=1);
|
||||
namespace MRBS;
|
||||
|
||||
require "defaultincludes.inc";
|
||||
|
||||
use MRBS\Form\Form;
|
||||
|
||||
// Check the CSRF token.
|
||||
Form::checkToken();
|
||||
|
||||
// Check the user is authorised for this page
|
||||
checkAuthorised(this_page());
|
||||
|
||||
|
||||
// Get non-standard form variables
|
||||
$form_vars = array(
|
||||
'sort_key' => 'string',
|
||||
'area_name' => 'string',
|
||||
'area_disabled' => 'string',
|
||||
'area_timezone' => 'string',
|
||||
'area_admin_email' => 'string',
|
||||
'area_start_first_slot' => 'string',
|
||||
'area_start_last_slot' => 'string',
|
||||
'area_res_mins' => 'int',
|
||||
'area_def_duration_mins' => 'int',
|
||||
'area_def_duration_all_day' => 'string',
|
||||
'area_min_create_ahead_enabled' => 'string',
|
||||
'area_min_create_ahead_value' => 'int',
|
||||
'area_min_create_ahead_units' => 'string',
|
||||
'area_max_create_ahead_enabled' => 'string',
|
||||
'area_max_create_ahead_value' => 'int',
|
||||
'area_max_create_ahead_units' => 'string',
|
||||
'area_min_delete_ahead_enabled' => 'string',
|
||||
'area_min_delete_ahead_value' => 'int',
|
||||
'area_min_delete_ahead_units' => 'string',
|
||||
'area_max_delete_ahead_enabled' => 'string',
|
||||
'area_max_delete_ahead_value' => 'int',
|
||||
'area_max_delete_ahead_units' => 'string',
|
||||
'area_max_duration_enabled' => 'string',
|
||||
'area_max_duration_periods' => 'int',
|
||||
'area_max_duration_value' => 'int',
|
||||
'area_max_duration_units' => 'string',
|
||||
'area_private_enabled' => 'string',
|
||||
'area_private_default' => 'int',
|
||||
'area_private_mandatory' => 'string',
|
||||
'area_private_override' => 'string',
|
||||
'area_approval_enabled' => 'string',
|
||||
'area_reminders_enabled' => 'string',
|
||||
'area_enable_periods' => 'string',
|
||||
'area_periods' => 'array',
|
||||
'area_confirmation_enabled' => 'string',
|
||||
'area_confirmed_default' => 'string',
|
||||
'area_default_type' => 'string',
|
||||
'area_times_along_top' => 'string',
|
||||
'custom_html' => 'string',
|
||||
'period_starts' => 'array',
|
||||
'period_ends' => 'array'
|
||||
);
|
||||
|
||||
foreach($form_vars as $var => $var_type)
|
||||
{
|
||||
$$var = get_form_var($var, $var_type);
|
||||
|
||||
// Trim the strings and truncate them to the maximum field length
|
||||
if (is_string($$var))
|
||||
{
|
||||
$$var = trim($$var);
|
||||
$$var = truncate($$var, "area.$var");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (!isset($area_default_type))
|
||||
{
|
||||
$area_default_type = $area_defaults['default_type'];
|
||||
}
|
||||
|
||||
// Get the max_per_interval form variables
|
||||
foreach ($interval_types as $interval_type)
|
||||
{
|
||||
$var = "area_max_per_$interval_type";
|
||||
$$var = get_form_var($var, 'int');
|
||||
$var = "area_max_per_{$interval_type}_enabled";
|
||||
$$var = get_form_var($var, 'string');
|
||||
$var = "area_max_secs_per_$interval_type";
|
||||
$$var = get_form_var($var, 'int');
|
||||
$var = "area_max_secs_per_{$interval_type}_units";
|
||||
$$var = get_form_var($var, 'string');
|
||||
$var = "area_max_secs_per_{$interval_type}_enabled";
|
||||
$$var = get_form_var($var, 'string');
|
||||
}
|
||||
|
||||
// UPDATE THE DATABASE
|
||||
// -------------------
|
||||
|
||||
if (empty($area))
|
||||
{
|
||||
throw new \Exception('$area is empty');
|
||||
}
|
||||
|
||||
// Initialise the error array
|
||||
$errors = array();
|
||||
|
||||
// Check the name hasn't been used in another area
|
||||
$id = get_area_id($area_name);
|
||||
if (isset($id) && ($id != $area))
|
||||
{
|
||||
$errors[] = 'invalid_area_name';
|
||||
}
|
||||
|
||||
// Clean up the address list replacing newlines by commas and removing duplicates
|
||||
$area_admin_email = clean_address_list($area_admin_email);
|
||||
// Validate email addresses
|
||||
if (!validate_email_list($area_admin_email))
|
||||
{
|
||||
$errors[] = 'invalid_email';
|
||||
}
|
||||
|
||||
// Check that the time formats are correct (hh:mm). They should be, because
|
||||
// the HTML5 element or polyfill will force them to be, but just in case ...
|
||||
// (for example if we are relying on a polyfill and JavaScript is disabled)
|
||||
|
||||
if (!preg_match(REGEX_HHMM, $area_start_first_slot) ||
|
||||
!preg_match(REGEX_HHMM, $area_start_last_slot))
|
||||
{
|
||||
$errors[] = 'invalid_time_format';
|
||||
}
|
||||
else
|
||||
{
|
||||
// Get morningstarts and eveningends
|
||||
list($area_morningstarts, $area_morningstarts_minutes) = explode(':', $area_start_first_slot);
|
||||
list($area_eveningends, $area_eveningends_minutes) = explode(':', $area_start_last_slot);
|
||||
|
||||
// Convert the book ahead times into seconds
|
||||
fromTimeString($area_min_create_ahead_value, $area_min_create_ahead_units);
|
||||
fromTimeString($area_max_create_ahead_value, $area_max_create_ahead_units);
|
||||
fromTimeString($area_min_delete_ahead_value, $area_min_delete_ahead_units);
|
||||
fromTimeString($area_max_delete_ahead_value, $area_max_delete_ahead_units);
|
||||
|
||||
fromTimeString($area_max_duration_value, $area_max_duration_units);
|
||||
|
||||
// If we are using periods, round these down to the nearest whole day
|
||||
// (anything less than a day is meaningless when using periods)
|
||||
if ($area_enable_periods)
|
||||
{
|
||||
$vars = array('area_min_create_ahead_value',
|
||||
'area_max_create_ahead_value',
|
||||
'area_min_delete_ahead_value',
|
||||
'area_max_delete_ahead_value');
|
||||
|
||||
foreach ($vars as $var)
|
||||
{
|
||||
if (isset($$var))
|
||||
{
|
||||
$$var -= $$var % SECONDS_PER_DAY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Convert booleans into 0/1 (necessary for PostgreSQL)
|
||||
$vars = array(
|
||||
'area_disabled',
|
||||
'area_def_duration_all_day',
|
||||
'area_min_create_ahead_enabled',
|
||||
'area_max_create_ahead_enabled',
|
||||
'area_min_delete_ahead_enabled',
|
||||
'area_max_delete_ahead_enabled',
|
||||
'area_max_duration_enabled',
|
||||
'area_private_enabled',
|
||||
'area_private_default',
|
||||
'area_private_mandatory',
|
||||
'area_approval_enabled',
|
||||
'area_reminders_enabled',
|
||||
'area_enable_periods',
|
||||
'area_confirmation_enabled',
|
||||
'area_confirmed_default',
|
||||
'area_times_along_top'
|
||||
);
|
||||
|
||||
foreach ($interval_types as $interval_type)
|
||||
{
|
||||
$vars[] = "area_max_per_{$interval_type}_enabled";
|
||||
$vars[] = "area_max_secs_per_{$interval_type}_enabled";
|
||||
}
|
||||
|
||||
foreach ($vars as $var)
|
||||
{
|
||||
$$var = (!empty($$var)) ? 1 : 0;
|
||||
}
|
||||
|
||||
// TODO: This is a kludge until we store use_period_times in the database.
|
||||
// We need to make sure that the period start times correspond to the correct periods.
|
||||
if (count($area_periods) == count($period_starts) + 1)
|
||||
{
|
||||
array_unshift($period_starts, null);
|
||||
}
|
||||
// Assemble the periods as an object.
|
||||
$periods_tmp = new Periods($area);
|
||||
for ($i = 0; $i < count($area_periods); $i++)
|
||||
{
|
||||
$periods_tmp->add(new Period(
|
||||
$area_periods[$i],
|
||||
$period_starts[$i] ?? null,
|
||||
$period_ends[$i] ?? null
|
||||
));
|
||||
}
|
||||
|
||||
// Validate the periods, but only if we are using periods with period times.
|
||||
if ($area_enable_periods && isset($period_starts[0]) && (true !== ($result = $periods_tmp->validate())))
|
||||
{
|
||||
$errors[] = $result;
|
||||
}
|
||||
|
||||
// Convert the periods to a value suitable for the database.
|
||||
$area_periods = $periods_tmp->toDbValue();
|
||||
|
||||
// Validate times mode settings
|
||||
if (!$area_enable_periods)
|
||||
{
|
||||
// Avoid divide by zero errors
|
||||
if ($area_res_mins == 0)
|
||||
{
|
||||
$errors[] = 'invalid_resolution';
|
||||
}
|
||||
else
|
||||
{
|
||||
// Check morningstarts, eveningends, and resolution for consistency
|
||||
$start_first_slot = ($area_morningstarts*60) + $area_morningstarts_minutes; // minutes
|
||||
$start_last_slot = ($area_eveningends*60) + $area_eveningends_minutes; // minutes
|
||||
|
||||
// If eveningends is before morningstarts then it's really on the next day
|
||||
if (hm_before(array('hours' => $area_eveningends, 'minutes' => $area_eveningends_minutes),
|
||||
array('hours' => $area_morningstarts, 'minutes' => $area_morningstarts_minutes)))
|
||||
{
|
||||
$start_last_slot += MINUTES_PER_DAY;
|
||||
}
|
||||
|
||||
$start_difference = ($start_last_slot - $start_first_slot); // minutes
|
||||
|
||||
if ($start_difference%$area_res_mins != 0)
|
||||
{
|
||||
$errors[] = 'invalid_resolution';
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Errors in the form data - go back to the form
|
||||
if (!empty($errors))
|
||||
{
|
||||
$query_string = "area=$area";
|
||||
foreach ($errors as $error)
|
||||
{
|
||||
$query_string .= "&errors[]=$error";
|
||||
}
|
||||
location_header("edit_area.php?$query_string");
|
||||
}
|
||||
|
||||
// Everything is OK, update the database
|
||||
|
||||
$sql = "UPDATE " . _tbl('area') . " SET ";
|
||||
$sql_params = array();
|
||||
$assign_array = array();
|
||||
$assign_array[] = "area_name=?";
|
||||
$sql_params[] = $area_name;
|
||||
$assign_array[] = "sort_key=?";
|
||||
$sql_params[] = $sort_key;
|
||||
$assign_array[] = "disabled=?";
|
||||
$sql_params[] = $area_disabled;
|
||||
$assign_array[] = "timezone=?";
|
||||
$sql_params[] = $area_timezone;
|
||||
$assign_array[] = "area_admin_email=?";
|
||||
$sql_params[] = $area_admin_email;
|
||||
|
||||
if (isset($custom_html))
|
||||
{
|
||||
// The custom HTML field won't be present if it has been
|
||||
// disabled in the config file
|
||||
$assign_array[] = "custom_html=?";
|
||||
$sql_params[] = $custom_html;
|
||||
}
|
||||
|
||||
if (!$area_enable_periods)
|
||||
{
|
||||
$assign_array[] = "resolution=?";
|
||||
$sql_params[] = $area_res_mins * 60;
|
||||
if (!$area_def_duration_all_day)
|
||||
{
|
||||
// If the default duration is all day, then this value will have
|
||||
// been disabled on the form, so don't change it.
|
||||
$assign_array[] = "default_duration=?";
|
||||
$sql_params[] = $area_def_duration_mins * 60;
|
||||
}
|
||||
$assign_array[] = "default_duration_all_day=?";
|
||||
$sql_params[] = $area_def_duration_all_day;
|
||||
$assign_array[] = "morningstarts=?";
|
||||
$sql_params[] = $area_morningstarts;
|
||||
$assign_array[] = "morningstarts_minutes=?";
|
||||
$sql_params[] = $area_morningstarts_minutes;
|
||||
$assign_array[] = "eveningends=?";
|
||||
$sql_params[] = $area_eveningends;
|
||||
$assign_array[] = "eveningends_minutes=?";
|
||||
$sql_params[] = $area_eveningends_minutes;
|
||||
}
|
||||
|
||||
// only update the min and max *_ahead_secs fields if the form values
|
||||
// are set; they might be NULL because they've been disabled by JavaScript
|
||||
$assign_array[] = "min_create_ahead_enabled=?";
|
||||
$sql_params[] = $area_min_create_ahead_enabled;
|
||||
$assign_array[] = "max_create_ahead_enabled=?";
|
||||
$sql_params[] = $area_max_create_ahead_enabled;
|
||||
$assign_array[] = "min_delete_ahead_enabled=?";
|
||||
$sql_params[] = $area_min_delete_ahead_enabled;
|
||||
$assign_array[] = "max_delete_ahead_enabled=?";
|
||||
$sql_params[] = $area_max_delete_ahead_enabled;
|
||||
$assign_array[] = "max_duration_enabled=?";
|
||||
$sql_params[] = $area_max_duration_enabled;
|
||||
|
||||
if (isset($area_min_create_ahead_value))
|
||||
{
|
||||
$assign_array[] = "min_create_ahead_secs=?";
|
||||
$sql_params[] = $area_min_create_ahead_value;
|
||||
}
|
||||
if (isset($area_max_create_ahead_value))
|
||||
{
|
||||
$assign_array[] = "max_create_ahead_secs=?";
|
||||
$sql_params[] = $area_max_create_ahead_value;
|
||||
}
|
||||
if (isset($area_min_delete_ahead_value))
|
||||
{
|
||||
$assign_array[] = "min_delete_ahead_secs=?";
|
||||
$sql_params[] = $area_min_delete_ahead_value;
|
||||
}
|
||||
if (isset($area_max_delete_ahead_value))
|
||||
{
|
||||
$assign_array[] = "max_delete_ahead_secs=?";
|
||||
$sql_params[] = $area_max_delete_ahead_value;
|
||||
}
|
||||
if (isset($area_max_duration_value))
|
||||
{
|
||||
$assign_array[] = "max_duration_secs=?";
|
||||
$sql_params[] = $area_max_duration_value;
|
||||
$assign_array[] = "max_duration_periods=?";
|
||||
$sql_params[] = $area_max_duration_periods;
|
||||
}
|
||||
|
||||
foreach($interval_types as $interval_type)
|
||||
{
|
||||
$var = "max_per_{$interval_type}_enabled";
|
||||
$area_var = "area_" . $var;
|
||||
$assign_array[] = "$var=" . $$area_var;
|
||||
|
||||
$var = "max_per_$interval_type";
|
||||
$area_var = "area_" . $var;
|
||||
if (isset($$area_var))
|
||||
{
|
||||
// only update these fields if they are set; they might be NULL because
|
||||
// they have been disabled by JavaScript
|
||||
$assign_array[] = "$var=?";
|
||||
$sql_params[] = $$area_var;
|
||||
}
|
||||
|
||||
// Now do the max_secs variables (limits on the total length of bookings)
|
||||
$var = "max_secs_per_{$interval_type}_enabled";
|
||||
$area_var = "area_" . $var;
|
||||
$assign_array[] = "$var=" . $$area_var;
|
||||
|
||||
$var = "max_secs_per_$interval_type";
|
||||
$area_var = "area_" . $var;
|
||||
|
||||
if (isset($$area_var))
|
||||
{
|
||||
// only update these fields if they are set; they might be NULL because
|
||||
// they have been disabled by JavaScript
|
||||
// Need to convert back into seconds
|
||||
$units_var = "area_max_secs_per_{$interval_type}_units";
|
||||
fromTimeString($$area_var, $$units_var);
|
||||
$assign_array[] = "$var=?";
|
||||
$sql_params[] = $$area_var;
|
||||
}
|
||||
}
|
||||
|
||||
$assign_array[] = "private_enabled=?";
|
||||
$sql_params[] = $area_private_enabled;
|
||||
$assign_array[] = "private_default=?";
|
||||
$sql_params[] = $area_private_default;
|
||||
$assign_array[] = "private_mandatory=?";
|
||||
$sql_params[] = $area_private_mandatory;
|
||||
$assign_array[] = "private_override=?";
|
||||
$sql_params[] = $area_private_override;
|
||||
$assign_array[] = "approval_enabled=?";
|
||||
$sql_params[] = $area_approval_enabled;
|
||||
$assign_array[] = "reminders_enabled=?";
|
||||
$sql_params[] = $area_reminders_enabled;
|
||||
$assign_array[] = "enable_periods=?";
|
||||
$sql_params[] = $area_enable_periods;
|
||||
$assign_array[] = "periods=?";
|
||||
$sql_params[] = $area_periods;
|
||||
$assign_array[] = "confirmation_enabled=?";
|
||||
$sql_params[] = $area_confirmation_enabled;
|
||||
$assign_array[] = "confirmed_default=?";
|
||||
$sql_params[] = $area_confirmed_default;
|
||||
$assign_array[] = "default_type=?";
|
||||
$sql_params[] = $area_default_type;
|
||||
$assign_array[] = "times_along_top=?";
|
||||
$sql_params[] = $area_times_along_top;
|
||||
|
||||
$sql .= implode(",", $assign_array) . " WHERE id=?";
|
||||
$sql_params[] = $area;
|
||||
|
||||
db()->command($sql, $sql_params);
|
||||
|
||||
|
||||
// Go back to the admin page
|
||||
location_header("admin.php?day=$day&month=$month&year=$year&area=$area");
|
||||
Reference in New Issue
Block a user