خطای Target … is not instantiable while building در لاراول

اگر به این خطا برخوردید. Target [Module\\Doctor\\Contract\\RepositoryInterface] is not instantiable while building واضحه دلیلش بایند نشدن اینترفیس به کلاس اصلیه اونه.

برای حل این مشکل نیازه پیدا کنید کجای پروژه دارین اینترفیس هاتون رو به هسته لاراول بایند میکنین. فایلی که پراویدر هاتون رو داخلش بایند کردید، در متد رجیستر اینترفیسمون رو به کلاس اصلی بایند میکنیم.

در ۵ دقیقه پکیج خودتون رو در فریمورک لاراول بسازید (Laravel 5.8)

سلام، بعد مدتها تصمیم گرفتم سعی کنم این عادت نوشتن رو تمرین کنم و چیزهایی که یاد میگیرم رو به وبلاگم اضافه کنم. اخیرا چند روزی درگیر ایجاد و ساختن پکیج تو لاراول بودم. با اینکه خیلی سادست، چند روز واقعا ذهنمو درگیر کرد، همه ریفرنس ها رو خوندم فارسی و انگلیسی، چیزی از قلم افتاده بود اما نمیدونستم چی، حتی نمیدونستم چی رو سرچ کنم! برای حل مشکل تا میتونستم خواستمو ساده کردم همه چیو حذف کردم تا رسیدم به اینکه فقط یک route داشته باشم و نه بیشتر! حتی اسم وندور رو هم که با دش جدا بود تک کلمه ای کردم. مواردی هم بودن که باعث گمراهی من شدن، جلوتر همه رو میگم. بریم که شروع کنیم.

ایجاد پروژه

اول از همه از کد زیر استفاده کنین و یه پروژه جدید ایجاد کنین، من اینجا از لاراول ۵.۸ استفاده کردم (یا پروژه فعلی خودتون رو انتخاب کنین)

composer create-project --prefer-dist laravel/laravel blog "5.8.*"

۲. ساختار فایل ها

مثل تصویر زیر فولدر هایی رو بصورت تو درتو برای پروژه ایجاد کنین. ساختار به این صورت باید باشه که داخل فولدر پروژه فولدر packages ایجاد میکنیم که همه پکیج های ما داخل این فولدر قرار میگیره. حالا داخل فولدر packages فولدری دیگه که وندور ما هستُ vendor میتونه اسم خودتون، نام کاربریتون در گیت هاب باشه. و در آخر هم فولدری با نام پکیجتون ایجاد کنین. در اینجا من نام پکیجم رو easy-comment گذاشتم و داخل این فولدر هم یک فولدر با نام src که محل قرار گیری همه کد های ماست ایجاد کنید. پس تا اینجا ساختار فولدر های من به این صورته:

larave-blog/packages/hamidreza-mozhdeh/easy-comment/src

ساختار فولدر ها برای ایجاد پکیج در لاراول

۳. راه اندازی کومپوزر

از طریق ترمینال وارد فولدر پکیجتون به آدرس packages/hamidreza-mozhdeh/easy-comment   بشین و دستور composer init   بزنین تا یک فایل کامپوزر جدید ایجاد کنیم. کومپوزر از شما سوالاتی میپرسه که اگر خواستین وارد کنین و اگر نه فقط اینتر بزنین تا آخر. بعدا هم میتونین اطلاعات رو ویرایش و تکمیل کنین. در آخر فایل ما به آدرس زیر ایجاد شده:

سوالاتی که بعد composer init پرسیده میشه

packages/hamidreza-mozhdeh/easy-comment/composer.json

داخل فایل کومپوزر من خیلی سادس و بعدا میخوام تغییرش بدم ولی فعلا به این شکله:

{
    "name": "hamidreza-mozhdeh/easy-comment",
    "authors": [
        {
            "name": "Hamidreza Mozhdeh",
            "email": "hamidreza87m@gmail.com"
        }
    ],
    "require": {}
}

حالا برای اینکه مسیر فولدر منبع (که همه کدهامون داخل اونه) رو به کومپوزر معرفی کنیم کد زیر رو واردش میکنیم

{
    "name": "hamidreza-mozhdeh/easy-comment",
    "authors": [
        {
            "name": "Hamidreza Mozhdeh",
            "email": "hamidreza87m@gmail.com"
        }
    ],
    "autoload": {
        "psr-4": {
            "HamidrezaMozhdeh\\EasyComment\\": "src/"
        }
    },
    "require": {}
}

دقت کنین که بعد نام وندور دابل بک اسلش داریم // و همینطور بعد نام پکیجمون هم دابل بک اسلش داریم // شاید متوجه شده باشین نام فولدر وندورم با نام وندوری که اینجا وارد کردم فرق داره! خب من میخواستم نام فولدرم زیبا باشه و با دش از هم جدا کردم. اما چیزی که اینجا وارد میشه namespace پکیج ما هست و نمیتونیم از دش استفاده کنیم. برای اینکار من کمل کبس نوشتم (و استانداری که رعایت میکنند هم همینه). و باز هم دقت کنین که ما هنوز فایل این namespace رو نساختیم و جلوتر میسازیمش. و در نهایت بعد فولدر src هم انتهاش یک فوروادر اسلش اضافه کنین.

ما تا اینجا composer.json پکیجمون رو ویرایش کردیم حالا نیازه composer.json خود لاراول رو ویرایش کنیم قسمت autoload و psr-4 رو داخل اون پیدا کنین و پکیج خودتون رو معرفی کنین، شبیه این:

  "autoload": {
    "classmap": [
      "database/seeds",
      "database/factories"
    ],
    "psr-4": {
      "App\\": "app/",
      "HamidrezaMozhdeh\\EasyComment\\": "packages/hamidreza-mozhdeh/easy-comment/src/"
    }
  },

 

این قسمت خیلی شبیه composer پکیج بود با این تفاوت که آدرس رو کاملتر دادیم اینجا.

۴. ایجاد سرویس پروایدر Service Provider

حالا ما نیاز داریم یک سرویس پروایدر بسازیم که متد ها کلاس ها و فایل ها و… رو از طریق اون فراخونی کنیم. در اینجا ما فقط میخوایم یک روت تعریف کنیم که آیا پکیجمون کار میکنه یانه. برای ایجاد پرواید به دو صورت دستی یا php artisan میشه کار کرد که من دومی رو ترجیح میدم. پس تو ترمینال بزنین:

php artisan make:provider EasyCommentServiceProvider

حالا فایل رو از app/providers   به packages/hamidreza-mozhdeh/easy-comment/src   منتقل کنین. دقت کنین که باید namespace اون رو هم عوض کنین به چیزی که قبلا تعریف کردیم تو کومپوزر تغییر بدیم، من داخل متند boot این فایل روت جدیدی رو لود کردم. برای لود بقیه چیزها اینجا رو نگاه کنین.

<?php

namespace HamidrezaMozhdeh\EasyComment;

use Illuminate\Support\ServiceProvider;

class EasyCommentServiceProvider extends ServiceProvider
{
    /**
     * Register services.
     *
     * @return void
     */
    public function register()
    {
        //
    }

    /**
     * Bootstrap services.
     *
     * @return void
     */
    public function boot()
    {
        $this->loadRoutesFrom(__DIR__.'/routes.php');
    }
}

کتار همین فایل EasyCommentServiceProvider یک فایل دیگه با نام routes.php ایجاد کنید و یک روت مثل web.php داخلش تعریف میکنیم که میشه به آدرس packages/hamidreza-mozhdeh/easy-comment/src/routes.php

<?php

Route::get('testing-new-package', function () {
    return '<h1>Hello world</h1>';
});

آخرین کار باقی مونده اینه که داخل فایل config/app.php داخل آرایه providers پروایدر خودمونو تعریف کنیم.

HamidrezaMozhdeh\EasyComment\EasyCommentServiceProvider::class,
۵. آخرین مرحله و پایان

در نهایت دستور composer dump-autoload  رو بزنین تا فایل های جدید لود بشن. اگر تا اینجا اومدین و کارهارو انجام دادین پکیجتون ایجاد شده ولی الان فقط تست مونده که خیالمون راحت بشه.

چیزی که من شخصا خیلی سرش گیر کردم و جایی اشاره ای بهش نکرده بود که یادتون باشه در این مرحله حتما php artisan config:clear  هم بزنین.

php artisan serve رو بزنین و روت http://127.0.0.1:8000/testing-new-package  رو باز کنین. اگر تا اینجا همه چیز رو درست انجام داده باشین نتیجه رو میبینین.

سعی کردم تا اینجا ساده ترین و ابتدایی ترین راه برای شروع رو توضیح بدم، بازهم سعی میکنم این مقاله رو با پچ های جدید بروز رسانی کنم و ارتقاش بدم. تا همینجا اصل کار انجام شده و شما میتونین خیلی راحت و سریع توسعش بدین. کافیه یه فولدر بزنین مایگریشن و https://laravel.com/docs/5.8/packages#migrations  رو به پروایدر اضافه کنین یا فولدر ویو های خودتونو بسازین و اینو به پروایدر اضافه کنین (همونجایی که روت هست) https://laravel.com/docs/5.8/packages#views

یا اینکه با کد زیر میتونین امکان رو به کاربر بدین کدو پابلیش بزنه و بیاره تو هسته خودش که بتونه ادیت بزنه:

    $this->publishes([
        __DIR__.'/path/to/views' => resource_path('views/vendor/courier'),
    ]);

 

موفق باشید

منابع:

Laravel 5.8 Package Development

ساخت پکیج‌‌ها در فریم‌ورک لاراول

Build Your Own Laravel Package in 10 Minutes Using Composer

نوشتن سایت چند زبانه با لاراول

لاراول  برای ما شرایطی بوجود آورده که داشتن سایت چند زبانه به سادگی امکان پذیره. یا برای منی که دارم طراحی میکنم میخوام که ابتدا با زبان انگلیسی کار کنم و در آخر سایتت رو فارسی ترجمه کنم. اینکار تو لاراول خیلی راحت و سریعه بطوری که یک راه هم نداریم و چندین راه وجود داره. در ادامه با من همراه باشین تا خیلی خلاصه و سریع در این مورد بهتون آموزش بدم:

ساختار فایل های ترجمه لاراول در روش اول به این صورته:

/resources
    /lang
        /en
            contact.php
        /fa
            contact.php

در فولدر resource فولدر lang یک فولدر با مخفف زبان فارسی fa ایجاد کنید. و داخل اول فایل های ترجمه رو به صورت دسته بندی شده داخل هر فایل قرار میدیم. برای مثال سایت من قسمتی داره با نام  contact و ترجمه های داخل اون متفاوت از سایر قسمت های سایته. برای همین داخل فولدر fa یک فایل با نام contact.php ایجاد میکنم و داخل اون رو به صورت زیر با کلید -> مقدار پر میکنم

<?php

return [
    'title' => 'تماس با ما'
];

همونطور که توجه میکنین فایل فقط یک آرایه از توع associative رو برگشت میزنه که هر کلید یک مقدار ترجمه رو برمیگرونه.

برای استفاده از ترجمه داخل فایل های بلید مثل زیر عمل میکنیم:

{{ __('contact.title') }}

@lang('contact.title')

همونطور که متوجه شدین این روش خیلی با نظم و دقیقه و مناسب سایت های بزرگ با ترجمه های زیاده. در این روش بهتره حتما از fallback_locale با ترجمه انگلیسی استفاده کرده باشین (اگر نمیدونین جلوتر توضیح میدم)

روش دوم که ساده و خلاصه هست، روش stringمحور که با JSON انجام میشه و برای سایت های کوچیک با ترجمه های کم مناسبه. به این صورت که در مسیر resource/lang یک فایل json با نام مخفف زبان خودمون درست میکنیم برای مثال resource/lang/fa.json که همه ترجمه ها داخل اون قرار میگیره.

{
    "I love programming.": "من عاشق برنامه نویسیم"
}

که نمایش اون هم در کد خیلی راحتتره. درون بلید به این صورت استفاده میکنیم:

{{ __('I love programming.') }}

@lang('I love programming.')

برای ترجمه حرفه ای تر منبع رو بخونین. اما بریم سراغ راه اندازیش:

فایل در مسیر config/app.php حاوی تنظیمات ترجمه هست که شما با تنظیم اون میتونین زبان سایت خودتون رو تغییر بدین.

اول از همه fallback_locale زبانیه که اگر ترجمه ای پیدا نشد بصورت جایگزین درنظر گرفته میشه. بهتره مقدارش همون en بمونه.

locale متغیری هست که زبان فعلیه برنامست. من اینو منتقل کردم به فایل .env برای اینکار کدتون رو بصورت زیر تغییر بدین:

'locale' => ,en

'locale' => env('APP_LOCALE', 'en'),

حالا در فایل .env متغیر زیر رو تعریف کنین

APP_LOCALE=fa

یادتون باشه حتما در آخر از دستور زیر برای دوباره تنظیم کردن کش کانفیگ استفاده کنین

php artisan cache:clear

در آخر چند تا از امکاناتی که لاراول بهمون میده رو بگم: میتونیم متغیر وسط متن ترجمه فراخونی کنیم. میشه بصورت داینامیک زبان رو تغییر داد و نیازی نیست داخل کانفیگ تعریف کنین و برای مثال از url پارامتر بگیرین. میتونین بصورت شرطی برای جمع و فرد ترجمه بنویسین و…

منبع :Localization

گرفتن جمع رکورد های برگشتی در لاراول ۵.۸

گاهی لازمه بدونیم یک مدل ما در رابطه با مدل دیگه ای (چند به چند و یک به چند) چه تعداد نتیجه داره؟ برای مثال میخوایم بدونیم این پست من چه تعداد کامنت داره؟ یک عدد میخوام.

برای یک مدل فقط کافیه از متد count بصورت زیر استفاده کنم. (چند نمونه مثال)

نمایش تعداد کامنت های یک کاربر
$user->comments->count();

نمایش تعداد کل پست های یک کاربر در زیر یک پست (برای مثال: تاکنون ۶۵ نوشته از این نویسنده انتشار داده شده)
$post->user->posts->count();

اما وقتی چند مدل/ چند رکورد از دیتابیس رو گرفتیم و میخوایم برای هر کدوم چیزی رو بشماریم از روش زیر استفاده میکنیم:

نمایش تعداد کامنت های هر پست

$posts = App\Post::withCount('comments')->get();

foreach ($posts as $post) {
    echo $post->comments_count;
}

یا شمارنده های با فیلتر بیشتر یا چند شمارنده

use Illuminate\Database\Eloquent\Builder;

$posts = App\Post::withCount(['votes', 'comments' => function (Builder $query) {
    $query->where('content', 'like', 'foo%');
}])->get();

echo $posts[0]->votes_count;
echo $posts[0]->comments_count;

 

منبع: Counting Related Models

متد های PUT PATCH DELETE در لاراول

اول از همه بریم سراغ متد های PUT PATCH DELETE این متد ها روش های انتقال دیتا در کنار POST GET هستن و کمتر استفاده شدن و درموردشون کمتر خوندیم و شنیدیم. اما درواقع لیست متد های تقاضاهای HTTP شامل PUT PATCH DELETE POST GET HEAD OPTIONS TRACE CONNECT میشن. که ما بیشتر از همه با POST GET کار کردیم و حالا در لاراول میخوایم از چند تای دیگشون استفاده کنیم. قبلش یه نگاه سریع بهشون بندازیم که اصلا چی هستن و برای چی استفاده میکنیم؟

حالا این نکته رو تو ذهنتون داشته باشید که CRUD مخفف اول کلمات Create Read Update Delete هست.

متد GET برای نمایش یا گرفتن داده خاص مثل یک محصول، یا یک نوع محصول یا لیست محصولات استفاده میشه.

متد POST برای ارسال یک داده به سرور استفاده میشه و معمولا برای Create کردن.

متد PUT برای ارسال داده و جایگزین کردن آن با مقادیر فعلی استفاده میشه. Update

متد PATCH هم برای ارسال داده و بروزرسانی استفاده میشه. فرقش با بالایی اینه که اون جایگزین میکنه کلا، این ویرایش میکنه. که شامل بخشی از اونه اصظلاحا Modify میکنه. اینم میشه Update

متد DELETE که مشخصه برای حذف کردنه.

میرسیم سراغ متد های فرعی که شامل این مبحثمون نمیشه ولی میگم:

متد HEAD مثل متد GET میمونه اما با فرق اینکه بدنه رو نمیگیره و فقط head رو میگیره. داده هایی که در هد صفحه موجوده.

متد CONNECT برای ایجاد یک تونل به منبعی مشخص

متد OPTIONS برای مشخص کردن گزینه های ارتباط با منبع مورد نظر استفاده میشود. (سخت نگیرید – سرچ کنید)

متد TRACE هم برای بررسی مسیر رفت و برگشت بسته.

همونطور که میدونیم HTML در فرم هاش از متد های PUT PATCH DELETE پشتیبانی نمیکنه، لاراول برای پشتیبانی از این route ها از ما میخواد فیلدی رو در فرممون با نام _method تعریف کنیم و مقدار اون رو برابر متد مورد نظر قرار بدیم. برای مثال کد زیر رو ببینین:

<form action="/foo/bar" method="POST">
    <input type="hidden" name="_method" value="PUT">
    <input type="hidden" name="_token" value="{{ csrf_token() }}">
</form>

در بلید برای سرعت بیشتر میتونیم از @method استفاده کنیم که این کد رو برامون جنریت میکنه و البته، متد فرم همچنان باید POST باشه.

<form action="/foo/bar" method="POST">
    @method('PUT')
    @csrf
</form>

 

منبع:
Form Method Spoofing
HTTP request methods
HTTP Request Methods
متد های http
تفاوت بین متدهای HTTP شامل GET, POST, PUT, PATCH, DELETE

توکن CSRF فرم ها در لاراول

لاراول فرم ها رو در برابر حمله های CSRF محافظت میکنه. درخواست های سایت ها / سرور های دیگر از درخواست های یک کاربر اهراز شده جدا میشن. برای اینکار لاراول یک توکن CSRF برای هر کاربر ایجاد میکنه با اینکار چک میکنه آیا این درخواست برای همین کاربر هست یا نه؟!

برای اینکار هرزمان که ما یک فرم در HTML مینویسیم باید حتما یک توکن CSRF رو در فیلد های HTML از نوع input با مقدار توکن ایجاد کنیم. اینکار به میدلور لاراول این امکان رو میده صحت درخواست مارو بررسی کنه. برای راحتی تنها نیاز به نوشتن @csrf  داخل فرم بلیدمون داریم.

<form method="POST" action="/profile">
    @csrf
    ...
</form>

همچنین میتونیم این توکن رو در هدر صفحه هم ارسال کنیم:

<meta name="csrf-token" content="{{ csrf_token() }}">

یا توسط جاوا اسکریپت:

$.ajaxSetup({
    headers: {
        'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
    }
});

اطلاعات بیشتر درباره CSRF Protection

نمایش و مدیریت کاربران لاگین کرده در لاراول

بنا به دلایل مختلف ممکنه نیاز پیدا کنیم که بدونیم کدوم کاربران ما الان لاگین کردن و چه اطلاعاتی از اونها داریم. برای مثال با چه دستگاه هایی لاگین کردن، از کجا لاگین کردن و… یا حتی محدودیت برای لاگین بخوایم بذاریم! سشن ها در لاراول در جاهای مختلفی میتونن ذخیره بشن مثل فایل ها، دیتابیس، کوکی، memcache / redis و آرایه ها (تنظیمات سشن در لاراول). برای مدیریت بهتر سشن ها اون ها رو در دیتابیس ذخیره میکنیم که امکانات زیادی به ما میده از قبیل مدیریت زمان، دسته بندی، مدیریت دستگاه ها، تعداد دستگاه ها و…

دستورات زیر رو اجرا کنین تا لاراول شما آماده بشه:

php artisan session:table
 
composer dump-autoload
 
php artisan migrate

 

حالا داخل فایل config/session.php  درایور سشن رو به database  تغییر بدین.

ایزی ایزی تمام تمام. همین! برین دیتابیس رو نگاه کنین و راحت کوئری بزنین و کاربران رو همونطور که میخواین لیست کنین، مدیریت کنین.

احتمالا نیاز پیدا کنین که کش کانفیگ رو کلیر کنین پس حتما انجامش بدین.

منبع: Display user devices there application is currently logged in and option to logout in Laravel

افزودن لاگین با جیمیل (گوگل) در لاراول

در این پست بهتون میگم چطور از پکیج Socialite استفاده کنین و به وبسایتتون لاگین با جیمیل یا… رو اضافه کنین. برای شروع نیازه که ما پکیج Socialite رو بوسیله composer نصب کنیم. راهنمای خود لاراول رو اینجا ببینین:  Laravel Socialite

نصب Socialite 

composer require laravel/socialite


کانفیک لاراول

سرویسی که میخواین (گوگل، فیسبوک، لینکداین و…) رو به config/service.php اضافه کنین.

'google' => [
    'client_id'     => env('GOOGLE_CLIENT_ID'),
    'client_secret' => env('GOOGLE_CLIENT_SECRET'),
    'redirect'      => env('GOOGLE_REDIRECT')
],

بعد اینکه پکیج جدید رو نصب کردیم سرویس پرووایدر اون رو هم به config/app.php اضافه میکنیم

/*
* Package Service Providers...
*/
Laravel\Socialite\SocialiteServiceProvider::class,

سرویس پرووایدر جایی برای راه انداری برنامه ها و پکیج هاست، خط بالا به لاراول Socialite رو برای استفاده میشناسونه.

همیشه پای یک alias هم در میونه! برای دسترسی راحتتر آلیاس اون رو هم نصب میکنیم.

'aliases' => [
    // ...
    'Socialite' => Laravel\Socialite\Facades\Socialite::class,
]

تا اینجا شما میبایست ساختار اهراز هویت رو داشته باشید و در این آموزش تصور میکنیم این مرحله رو قبلا انجام دادین.

پروژه خودتون رو در گوگل https://console.developers.google.com/projectcreate درست کنین و بعد هم یک اعتبار نامه در اینجا https://console.developers.google.com/apis/credentials درست کنین.

OAuth clinet id google console
OAuth client ID > Consent > Web application

اطلاعاتی که گرفتین رو در .env فایل خودتون وارد کنین:

GOOGLE_CLIENT_ID=000000000000-XXXXXXXXXXX.apps.googleusercontent.com
GOOGLE_CLIENT_SECRET=XXXXXXXXXXXXX
GOOGLE_REDIRECT=http://localhost:8000/callback

قراردادن آدرس برگشتی

در اینجا باید آدرس کالبک رو وارد کنین.

بعد وارد کردن این آدرس ها وارد وب روت خود بشین و روت های مخصوص ریدارکت به گوگل و بازگشت اون رو ایجاد کنین.

Route::get('/redirect', 'Auth\LoginController@redirectToProvider');
Route::get('/callback', 'Auth\LoginController@handleProviderCallback');

در خط اول رواتی (یا روتی) رو تعریف میکنیم که کاربر رو به گوگل میفرسته و خط دوم برگشت از گوگل با دریافت اطلاعات کاربر هست. حالا در LoginController.php متد هایی که تو روات تعریف کردیم رو وارد میکنیم. متد زیر مارو به گوگل ریدایرکت میکنه برای گرفتن اطلاعات کاربر.

/**
  * Redirect the user to the Google authentication page.
  *
  * @return \Illuminate\Http\Response
  */
public function redirectToProvider()
{
    return Socialite::driver('google')->redirect();
}

و متد بعدی دریافت اطلاعات کاربر از گوگل هست (برگشت از گوگل) که اگر ایمیل قبلا وجود داشته، ثبت نام انجام میشه و اگر وجود نداشته باشه ما اون کاربر رو ایجاد میکنیم و سپس لاگین انجام میشه:

    /**
     * Obtain the user information from Google.
     *
     * @return \Illuminate\Http\Response
     */
    public function handleProviderCallback()
    {
        try {
            $user = Socialite::driver('google')->user();
        } catch (\Exception $e) {
            return redirect('/login');
        }        // only allow people with @company.com to login
        if(explode("@", $user->email)[1] !== 'company.com'){
            return redirect()->to('/');
        }        // check if they're an existing user
        $existingUser = User::where('email', $user->email)->first();        if($existingUser){
            // log them in
            auth()->login($existingUser, true);
        } else {
            // create a new user
            $newUser                  = new User;
            $newUser->name            = $user->name;
            $newUser->email           = $user->email;
            $newUser->google_id       = $user->id;
            $newUser->avatar          = $user->avatar;
            $newUser->avatar_original = $user->avatar_original;
            $newUser->save();            auth()->login($newUser, true);
        }
        return redirect()->to('/home');
    }

 

خب تا اینجای کار شما همه کارو انجام دادین فقط بعد اینکه پکیجی رو نصب کردین حتما دامپ کنین:

php artisan clear-compiled
composer dump-autoload
php artisan optimize

اگر خواستین از آدرس های مختلفی برای کالبک استفاده کنین دستور زیر کمکتون میکنه

public function socialLogin($loginFrom){
  return Socialite::driver('google') >redirectUrl('http://your-domain.com?data=123')->redirect();
}

 

منابع:

Add Login with Google to your Laravel app
Laravel 5.5 socialite integration shows error formatRedirectUrl() must be of the type array, null given
Dynamic callback url laravel socialite

چطور در لاراول از ایمیل یا شماره موبایل برای لاگین استفاده کنیم؟ شایدم نام کاربری

برای اینکه کاربرای سایت بتونن با ایمیل یا نام کاربری یا شماره موبایل بتونن لاگین کنن (یک فیلد نام کاربری باشد که هر کدام از این ۳تا را کاربر وارد کرد بتونه لاگین کنه) تغییر خیلی کوچیکی تو متد کنترلر لاگین میدیم. برای اینکار فایل LoginController.php رو ویرایش میکنیم.

ابتدا کلاس Request رو use کنین

use Illuminate\Http\Request;

 

سپس متد credentials رو بازنویسی میکنیم.

    protected function credentials(Request $request)
    {
        $field = filter_var($request->get($this->username()), FILTER_VALIDATE_EMAIL)
            ? 'email'
            : 'mobile';

        return [
            $field => $request->get($this->username()),
            'password' => $request->password,
        ];
    }

تست شده در لاراول ۵٫۴ ۵٫۷ و ۵٫۸

منبع:
https://stackoverflow.com/questions/42708942/allow-login-using-username-or-email-in-laravel-5-4

راهنمای سریع استفاده از ربات تلگرام در لاراول Laravel Telegram Bot

در این مقاله خیلی سریع وخلاصه میریم سراغ ایجاد ربات و اتصال اون به لاراول.
توسط کد زیر پکیج کار با تلگرام رو به لاراول اضافه کنین:

composer require irazasyed/telegram-bot-sdk

حالا به آرایه providers که در مسیر config/app.php هست اضافه میکنیم.

Telegram\Bot\Laravel\TelegramServiceProvider::class,

حالا به آرایه aliases کد زیر رو اضافه میکنیم تا Telegram به فاساد هامون اضافه بشه.

 'Telegram' => Telegram\Bot\Laravel\Facades\Telegram::class,

حالا که سرویس و فاساد اون رو اضافه کردیم فایل کانفیگ تلگرام رو با دستور زیر انتشار میدیم (میاریم به فولدر config)

php artisan vendor:publish --provider="Telegram\Bot\Laravel\TelegramServiceProvider"

حالا میریم به تلگرام و ربات پدرخانده @BotFather رو استارت میزنیم با دستور /newbot یک ربات جدید ایجاد میکنیم. اول اسم ربات و دوم نام کاربری اون رو وارد میکنیم در آخر هم وقتی ربات به درستی ایجاد شد، تلگرام کد token HTTP API میده که بهش تو فایل .env نیاز داریم و به صورت زیر در این فایل وارد میکنیم:

TELEGRAM_BOT_TOKEN=525012101:AAEwy9R1SCpq0V_Bpkgqm9Z4nbrWZaNt_Kg

خب حالا نیاز به یک کانال تلگرام داریم که رباتمون رو داخلش ادد کنیم.

به فایل config/telegram.php میریم و در قسمت ربات های نام رباتمون رو مینویسیم (قسمت username). کد زیر

'bots' => [
    'mybot' => [
        'username' => 'tutsforwebbot',
        'token' => env('TELEGRAM_BOT_TOKEN', ''),
        'certificate_path' => env('TELEGRAM_CERTIFICATE_PATH', ''),
        'webhook_url' => env('TELEGRAM_WEBHOOK_URL', ''),
        'commands' => [
        ],
    ],
],

برای بروز رسانی کشمون هم از دستور زیر استفاده میکنیم:

php artisan config:cache

در تلگرام هر چت (کانال، چت، گروه پی وی یا…) یه اتاق گفتگو حساب میشه و برای ارسال پیام توسط رباط ما نیاز به شماره اون اتاق داریم که البته اسمش chat_id هست. برای اینکه شماره اتاق گفتگو رو پیدا کنیم و کار با رباط تلگرام یه کنترلر برای رباط تلگرام ایجاد میکنیم:

php artisan make:controller TelegramBotController

و کد های زیر رو به کنترلرمون اضافه میکنیم

<?php
 
namespace App\Http\Controllers;
 
use Telegram\Bot\Laravel\Facades\Telegram;
 
class TelegramBotController extends Controller
{
    public function updatedActivity()
    {
        $activity = Telegram::getUpdates();
        dd($activity);
    }
}

کد بالا پیام های اتاق گفتگو رو بصورت لاگ نمایش میده و همچنین شماره اون رو. با مسیر زیر کنترلرمون رو فعال میکنیم:

Route::get('/updated-activity', 'TelegramBotController@updatedActivity');

حالا به مرورگر میریم و آدرس /updated-activity رو تایپ میکنیم، اگر کانال ما خالی باشه مقدار [] برمیگرده ولی وقتی یک پیام ایجاد کنیم (خودمون یک پیام در کانال منتشر کنیم) و دوباره تست میگیریم. خروجی شبیه این میشه:

array:1 [▼
  ۰ => Update {#348 ▼
    #items: array:2 [▼
      "update_id" => 21432106
      "channel_post" => array:4 [▼
        "message_id" => 12
        "chat" => array:4 [▼
          "id" => -1001361379586
          "title" => "Hamidreza bot test"
          "username" => "hamidrezabot_test"
          "type" => "channel"
        ]
        "date" => 1568741639
        "text" => "SalamDonya"
      ]
    ]
  }
]

اگر قبلا پیامی در گروه فرستاده بودین آخرین ایندکس رو چک کنین. در این آرایه در قسمت ایندکس chat قسمت id یک شماره نوشته شده -۱۰۰۱۳۶۱۳۷۹۵۸۶ این شماره رو کپی میکنیم و در فایل .env متغیر زیر رو اضافه میکنیم

TELEGRAM_CHANNEL_ID=-1001361379586

و سپس کش رو دوباره ریفرش میکنیم

php artisan config:cache

حالا به کنترلر TelegramBotController متد زیر رو اضافه میکنیم

public function sendMessage()
    {
        Telegram::sendMessage([
            'chat_id' => -1001361379586,//env('TELEGRAM_CHANNEL_ID', ''),
            'parse_mode' => 'HTML',
            'text' => 'اولین پیام تست ربات تلگرام'
        ]);
    }

البته من مستقیم شماره chat_id رو وارد کردم ولی شما میتنین از متغیر محیطی .env استفاده کنین که کدشو کامنت کردم.
آدرس sendMessage رو در روت خودمون وارد میکنیم و بعد در مرورگر تست میکنیم.

Route::get('/sendMessage', 'TelegramBotController@sendMessage');

 

منبع: https://tutsforweb.com/sending-notifications-to-telegram-messenger-with-laravel