So i was working on a project and decided... "heyy, why not add a referral system and encourage users to share the application". Searched the web but all solutions weren't what i wanted, I mean referral systems aren't new to me but this is going to be my first time building one with laravel and this is also my going to be my first blog post ๐. So lets get to it,
The referral is going to work like this:
A user signs up and a code gets auto generated as their referral code which they can give to others
When a user registers, they're prompted to add a referral code
The user whose referral code was used would be notified that someone registered with their code
We are going to be creating 2 migration tables. The user table and the referral table.
Our eloquent Model should be a case where a user can be refered by another user and a user can refer many users but it's going to be (One to One) while we have a column that adds each time a new user uses an existing user referral code.
First of, we create our laravel application
laravel new referral-app
After installing laravel, we make the referral model, migration and controller
php artisan make:model Referral -mc
Now we edit our migration table, first the users table ๐
public function up(): void
{
Schema::create('users', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('email')->unique();
$table->string('referral_status')->default('off');
$table->string('referral_by')->nullable();
$table->timestamp('email_verified_at')->nullable();
$table->string('password');
$table->rememberToken();
$table->timestamps();
});
}
Now we edit the referral table
public function up(): void
{
Schema::create('referrals', function (Blueprint $table) {
$table->id();
$table->foreignId('user_id')->constrained()->cascadeOnDelete();
$table->string('referral_code')->unique()->nullable();
$table->integer('total_referred_users')->default(0);
$table->timestamps();
});
}
We are using foreignId cause of our Eloquent relationship with the users table One-To-Many
.
Let's not forget our auth ๐
composer require laravel/ui
php artisan ui bootstrap
php artisan ui bootstrap --auth
Let's edit our models, starting with the User Model
protected $fillable = [
'name',
'email',
'password',
'referral_status',
'referral_by'
];
public function referral(){
return $this->hasOne(Referral::class);
}
We did we just do?
First we added
referral_status
andreferral_by
to the $fillable in the User modelThen we specified the eloquent relationship
hasOne
On the other hand the Referral model eloquent relationship should belongsTo
the User model and we add user_id
, referral_code
and total_referred_users
to the Referral model $fillable
protected $fillable = [
'user_id',
"referral_code",
"total_referred_users"
];
public function user(){
return $this->belongsTo(User::class);
}
Using MySql, we're going to create a database referral_app
and link it to through our .env file.
Now we migrate and the add Auth route
to our routes/web.php
file
php artisan migrate
In the web.php file add this๐
Auth::routes();
Now let's add referral code to every user who signs up but first we need a page for users to enter their referral code after signing up. We would create a new file in our view/auth folder called referral.blade.php
and place this code below in it
@extends('layouts.app')
@section('content')
<div class="container">
<div class="row justify-content-center">
<div class="col-md-8">
<div class="card">
<div class="card-header">{{ __('Referral') }}</div>
<div class="card-body">
<form method="POST" action="{{ route('referral.verify') }}">
@csrf
@method('PATCH')
<div class="row mb-3">
<label for="referral" class="col-md-4 col-form-label text-md-end">{{ __('Referral Code') }}</label>
<div class="col-md-6">
<input id="referral" type="text" class="form-control @error('referral') is-invalid @enderror" name="referral" value="{{ old('referral') }}" required autocomplete="referral" autofocus>
@error('referral')
<span class="invalid-feedback" role="alert">
<strong>{{ $message }}</strong>
</span>
@enderror
</div>
</div>
<div class="row mb-0">
<div class="col-md-8 offset-md-4">
<button type="submit" class="btn btn-primary">
{{ __('Proceed') }}
</button>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
@endsection
The form is being submitted to a patch route referral.store
which we are going to add the web.php
file later on, for now let's add this to the web.php
Route::get('/referral', function(){ return view('auth.referral');})->name('referral');
Now we let's get back to generating a referral code to every user who signs up
Locate the RegisterController
in App\Http\Controllers\Auth
.
We're going to edit the protected function create(array $data)
Replace the function with this edited version
protected function create(array $data)
{
$user = User::create([
'name' => $data['name'],
'email' => $data['email'],
'password' => Hash::make($data['password']),
]);
Referral::create([
'user_id'=> $user->id,
'referral_code'=>Str::random(6),
]);
return $user;
}
Also in your view/home.blade.php replace the existing code with this
@extends('layouts.app')
@section('content')
<div class="container">
<div class="row justify-content-center">
<div class="col-md-8">
<div class="card">
<div class="card-header">{{ __('Dashboard') }}</div>
<div class="card-body">
@if (session('status'))
<div class="alert alert-success" role="alert">
{{ session('status') }}
</div>
@endif
<p>Your referral code is {{ auth()->user()->referral->referral_code }}</p>
</div>
</div>
</div>
</div>
</div>
@endsection
Now let's add the referral part. First locate App/Providers/RouteServiceProvider
and edit
Change from this:
public const HOME = '/home';
To this:
public const HOME = '/referral';
Now it's time to add our route referral.store
and verify referrals.
In your web.php
file, add the patch route for storing the referrals
Route::patch('/referral/store', [App\Http\Controllers\ReferralController::class, 'store'])->name('referral.store');
In the ReferralController add the store function
public function store(Request $request){
$user = User::find(Referral::where("referral_code", $request->referral)->first()->user_id);
$total_referred_users = $user->referral->total_referred_users + 1;
$user->referral->update(['total_referred_users'=> $total_referred_users]);
DB::table('users')->where('id', auth()->user()->id)->update(['referral_by' => $request->referral]);
Notification::route('mail', $user->email)->notify(new UserNotification());
return redirect()->action([HomeController::class,'index']);
}
Let me explain the code
First we got the user using the referral code that was submitted then we added to it counts of user
We then proceeded to update the new user's
referral_by
column to add a referral codeFinally, we send a notification to the user who referred that someone signed up with their referral code
Don't forget to make:notification to generate the email notification
php artisan make:notification UserNotification
Edit the contents and replace with this code
<?php
namespace App\Notifications;
use Illuminate\Bus\Queueable;
use App\Models\User;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Notifications\Messages\MailMessage;
use Illuminate\Notifications\Notification;
class UserNotification extends Notification
{
use Queueable;
/**
* Create a new notification instance.
*/
public function __construct()
{
//
}
/**
* Get the notification's delivery channels.
*
* @return array<int, string>
*/
public function via(object $notifiable): array
{
return ['mail'];
}
/**
* Get the mail representation of the notification.
*/
public function toMail(object $notifiable): MailMessage
{
return (new MailMessage)
->line("A user just joined ".getenv('APP_NAME')." using your referral code")
->line('Thank you for using our application!');
}
/**
* Get the array representation of the notification.
*
* @return array<string, mixed>
*/
public function toArray(object $notifiable): array
{
return [
//
];
}
}
Our Laravel referral system using referral code is now done, don't forget
php artisan serve
npm install
npm run dev
You can check the code out on my github.
https://github.com/hen8y/laravel-referral-system
In case you want to make the notifcation mail send faster, make sure to check laravel queue
Follow me on X(Twitter) Twitter
Top comments (0)