feat: prevent duplicate membership applications and fees

- Add UNIQUE constraint on membership_application.user_id (one app per user)
- Add UNIQUE constraint on membership_fees.user_id (one fee record per user)
- Add validation checks in process_application.php before inserting
- Improve error messages for duplicate submission attempts
- Add migration script to clean up existing duplicates before constraints
- Update checkMembershipApplication to set session message on redirect
- Add comprehensive documentation of duplicate prevention architecture

Individual payments/EFTs are tracked separately in payments table
This commit is contained in:
twotalesanimation
2025-12-05 09:42:42 +02:00
parent 9133b7bbc6
commit 05f74f1b86
4 changed files with 175 additions and 5 deletions

View File

@@ -18,6 +18,40 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') {
die('Security token validation failed. Please try again.');
}
// Check if user already has a membership application
$check_stmt = $conn->prepare("SELECT COUNT(*) as count FROM membership_application WHERE user_id = ?");
$check_stmt->bind_param("i", $user_id);
$check_stmt->execute();
$check_result = $check_stmt->get_result();
$check_row = $check_result->fetch_assoc();
$check_stmt->close();
if ($check_row['count'] > 0) {
http_response_code(400);
echo json_encode([
'status' => 'error',
'message' => 'You have already submitted a membership application. Please check your email for membership details.'
]);
exit;
}
// Check if user already has a membership fee record
$fee_check_stmt = $conn->prepare("SELECT COUNT(*) as count FROM membership_fees WHERE user_id = ?");
$fee_check_stmt->bind_param("i", $user_id);
$fee_check_stmt->execute();
$fee_result = $fee_check_stmt->get_result();
$fee_row = $fee_result->fetch_assoc();
$fee_check_stmt->close();
if ($fee_row['count'] > 0) {
http_response_code(400);
echo json_encode([
'status' => 'error',
'message' => 'You already have a membership fee record. Please contact support if you need to update your application.'
]);
exit;
}
// Get all the form fields with validation
$first_name = validateName($_POST['first_name'] ?? '');
if ($first_name === false) {
@@ -188,11 +222,20 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') {
// Rollback the transaction in case of error
$conn->rollback();
// Error response
$response = [
'status' => 'error',
'message' => 'Error: ' . $e->getMessage()
];
// Check for duplicate key error
$errorMessage = $e->getMessage();
if (strpos($errorMessage, 'Duplicate') !== false || strpos($errorMessage, '1062') !== false) {
$response = [
'status' => 'error',
'message' => 'You have already submitted a membership application. Please check your email for membership details.'
];
} else {
// Error response
$response = [
'status' => 'error',
'message' => 'Error: ' . $errorMessage
];
}
}
// Return the response in JSON format