PNewCode Posted October 10 Share Posted October 10 (edited) Hello everyone. I am wanting to prevent duplicate entries. This task is using laravel which I know little to nothing about. I'm putting this in PHP help because the file has php at the top of it. If this is the wrong place for this, then I apologize. The issue is that I googled for days and either I can't find the answer, or I can't translate what I find to fit what I need to do. The goal here is to prevent new users that sign up, to choose a username or screen name that already exists. I'm putting the code down below that I have to register the new users. The reason for this is because lately, I've had too many people replicating the same user names to make new accounts, either because they don't feel like asking for help when they forget the password or because they don't remember the answer to the question they created, or because they think making a new account gets them something new. So what I want to do is prevent duplicate user and screen names This laravel stuff is so far over my head that it's like trying to translate ancient egyptian cymbals for me. It took me over a week just to find where this file was haha Andy and all help is appreciated greatly NOTE: I didn't try to add any code to it yet because I'm incredibly nervous to destroy what is built because I don't understand this at all. <?php namespace App\Http\Controllers\Auth; use App\Models\User; use Illuminate\Http\Request; use Illuminate\Http\JsonResponse; use App\Http\Controllers\Controller; use App\Services\ImageUploadService; use Illuminate\Support\Facades\Hash; use Illuminate\Auth\Events\Registered; use App\Providers\RouteServiceProvider; use Illuminate\Support\Facades\Validator; use Illuminate\Foundation\Auth\RegistersUsers; class RegisterController extends Controller { /* |-------------------------------------------------------------------------- | Register Controller |-------------------------------------------------------------------------- | | This controller handles the registration of new users as well as their | validation and creation. By default this controller uses a trait to | provide this functionality without requiring any additional code. | */ use RegistersUsers; /** * Where to redirect users after registration. * * @var string */ protected $redirectTo = RouteServiceProvider::HOME; /** * Create a new controller instance. * * @return void */ public function __construct() { $this->middleware('guest'); } /** * Get a validator for an incoming registration request. * * @param array $data * @return \Illuminate\Contracts\Validation\Validator */ protected function validator(array $data) { return Validator::make($data, [ 'fname' => ['required', 'string', 'max:255', 'alpha'], 'username' => ['required', 'string', 'max:255', 'alpha_num'], //'lname' => ['required', 'string', 'max:255'], 'password' => ['required', 'string', 'min:8'], 'image' => ['image', 'mimes:jpg,jpeg,png','mimetypes:image/jpg,image/jpeg,image/png'], 'question' => ['required', 'string', 'max:255'], 'answer' => ['required', 'string', 'max:255'], 'ip_address' => ['required', 'string', 'max:255'], ]); } /** * Create a new user instance after a valid registration. * * @param array $data * @return \App\Models\User */ protected function create(array $data) { return User::create([ 'fname' => $data['fname'], //'lname' => $data['lname'], 'email' => $data['username'], 'question' => $data['question'], 'answer' => $data['answer'], 'password' => Hash::make($data['password']), 'unique_id' => rand(time(), 100000000), 'ip_address' => $data['ip_address'], // Save the user's IP address ]); } /** * Handle a registration request for the application. * * @param \Illuminate\Http\Request $request * @return \Illuminate\Http\RedirectResponse|\Illuminate\Http\JsonResponse */ public function register(Request $request) { $this->validator($request->all())->validate(); $user = $this->create($request->all()); event(new Registered($user)); /*$filename = now().$request->file('image')->getClientOriginalName(); $request->image->storeAs('images',$filename,'public');*/ //$filename = (new ImageUploadService())->upload($request->file('image'), 'images'); //$user->update(['img'=>$filename]); $users = User::where('id','!=',$user->id)->get()->modelKeys(); foreach($users as $u){ $user->conversations()->create()->users()->attach($u); } $this->guard()->login($user); if ($response = $this->registered($request, $user)) { return $response; } return $request->wantsJson() ? new JsonResponse([], 201) : redirect('login.php'); //: redirect($this->redirectPath()); } } Edited October 10 by PNewCode Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/ Share on other sites More sharing options...
Barand Posted October 10 Share Posted October 10 The best way is to define the username as a unique key in your user table. That way you can't add another with the same name (an exception with be thrown if you attempt to add a second). Then check for duplicate key errors when adding users in you code. Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1637270 Share on other sites More sharing options...
PNewCode Posted October 10 Author Share Posted October 10 43 minutes ago, Barand said: The best way is to define the username as a unique key in your user table. Thank you. The column name is "fname". Is that what you mean? In regular php I know how to check for duplicates and list them but thats as far as my knowledge goes. Laravel is a wild mess to me haha Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1637271 Share on other sites More sharing options...
Barand Posted October 10 Share Posted October 10 The basic code is /* Current user data +----+----------+--------------+ | id | username | fullname | +----+----------+--------------+ | 1 | lucy | Lucy Lastik | | 2 | hugh | Hugh Jass | | 3 | tom | Tom DiCanari | +----+----------+--------------+ */ try { $stmt = $pdo->prepare("INSERT INTO user (username, fullname) VALUES (?, ?) "); $stmt->execute( [ 'lucy', 'Lucy Smith' ] ); // attempt duplicate insert } catch (PDOException $e) { if ($stmt->errorInfo()[1] == 1062) { // duplicate key error code $_SESSION['errors']['username'] = 'username already exists'; // error message to display to user when form redisplayed } else throw $e; // let php handle the error } Just convert it to Laravelese. Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1637276 Share on other sites More sharing options...
maxxd Posted October 11 Share Posted October 11 Even better, Laravel will throw an Illuminate\Database\UniqueConstraintViolationException when you try to insert a record that violates the SQL unique constraint. Just catch that before the PDOException or general Exception and you can handle it. Looking at your code, you don't have a username column in your create method. The POST['username'] field is assigned to the email column in the table, which is a bit confusing. Either way, heed Barand's advice to add a unique constraint on whatever your username column is, wrap your create() statement in a try...catch() that catches the UniqueConstraintViolationException, and make sure your create() method is inserting data into that column. Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1637298 Share on other sites More sharing options...
PNewCode Posted November 11 Author Share Posted November 11 @Barand and @maxxd thank you for that info. Unfortunately I have no idea how to convert that to "Laravelese" as you said. Though that was a cool way of putting it haha. And yes the email is the username, because after getting a lot of grief from users in todays world of paranoid entries (and for good reason for many cases) I just changed it to entering a username instead of an email so that no email addresses are stored. There were already a few hundred pages that relied on it for other functions so I just left the column name in the database the same. I can't make heads or tales out of Laravel no matter how much I study it. It's like car mechanics to me... I can change the oil but rebuilding a motor is something my brain doesn't want me to know. Laravel, as it seems, is the motor. Spent the last month trying to comprehend this. No luck. I don't suppose either of you are for hire to make this function for me? Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1639866 Share on other sites More sharing options...
Barand Posted November 11 Share Posted November 11 No hablo Laravelese. Sorry, I've never used it. Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1639868 Share on other sites More sharing options...
maxxd Posted November 12 Share Posted November 12 (edited) I get the username -> email thing; it's one of those wonderful side effects of tech debt and the mitigation thereof. As far as the Laravelese, yeah - laravel is a very opinionated framework. What you can easily do for the validation on username/email is this: https://laravel.com/docs/11.x/validation#rule-unique So if I'm not mistaken (and it's late and I've had some wine so I may very well be mistaken) you can use 'username' => ['required', 'string', 'max:255', 'alpha_num', 'unique:App\Models\User,email'], PS - I'm not for hire, but if your timeline is very slow I'd be glad to help out when I've got time. Post here or DM me, but I can't guarantee I'll be able to respond quickly. Edited November 12 by maxxd Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1639879 Share on other sites More sharing options...
gizmola Posted Monday at 09:27 AM Share Posted Monday at 09:27 AM You should be able to use the unique constraint in the validator. return Validator::make($data, [ 'fname' => ['required', 'string', 'max:255', 'alpha'], 'username' => ['required', 'string', 'max:255', 'alpha_num', 'unique:User,email'], etc... What this does in Laravel, is that at validation time, Laravel will query the table to test for a row that exists with the same email that the user is trying to provide for this new registration. With that said, it is never a bad idea to enforce your desired database rules in the database, as Barand advised. Assuming this is mysql, you would do this for the email column of the user table, would be to create a unique index on the email column. Given that the system will be looking up users by the email column (as the username) there should be an index on that column anyways, but in this case the index should be unique. With mysql KEY and indexes are two ways of accomplishing the exact same thing. Quote Link to comment https://forums.phpfreaks.com/topic/324725-php-and-laravel-prevent-duplicate-entries-help-please/#findComment-1640968 Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.