{"id":28951581,"url":"https://github.com/invokable/laravel-line-project","last_synced_at":"2025-06-23T15:05:55.414Z","repository":{"id":37827026,"uuid":"302325676","full_name":"invokable/laravel-line-project","owner":"invokable","description":null,"archived":false,"fork":false,"pushed_at":"2025-06-21T10:07:13.000Z","size":1934,"stargazers_count":9,"open_issues_count":1,"forks_count":1,"subscribers_count":3,"default_branch":"main","last_synced_at":"2025-06-21T11:20:02.310Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"PHP","has_issues":false,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/invokable.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null},"funding":{"github":["invokable"],"patreon":null,"open_collective":null,"ko_fi":null,"tidelift":null,"community_bridge":null,"liberapay":null,"issuehunt":null,"lfx_crowdfunding":null,"polar":null,"buy_me_a_coffee":null,"thanks_dev":null,"custom":null}},"created_at":"2020-10-08T11:59:21.000Z","updated_at":"2025-06-21T10:07:16.000Z","dependencies_parsed_at":"2024-01-04T05:22:39.749Z","dependency_job_id":"d44096a1-e590-4628-96cb-15e299731391","html_url":"https://github.com/invokable/laravel-line-project","commit_stats":null,"previous_names":["invokable/laravel-line-project"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/invokable/laravel-line-project","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/invokable%2Flaravel-line-project","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/invokable%2Flaravel-line-project/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/invokable%2Flaravel-line-project/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/invokable%2Flaravel-line-project/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/invokable","download_url":"https://codeload.github.com/invokable/laravel-line-project/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/invokable%2Flaravel-line-project/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":261500667,"owners_count":23168071,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2025-06-23T15:05:50.755Z","updated_at":"2025-06-23T15:05:55.385Z","avatar_url":"https://github.com/invokable.png","language":"PHP","funding_links":["https://github.com/sponsors/invokable"],"categories":[],"sub_categories":[],"readme":"# LINE SDK for Laravel sample project\n\nhttps://github.com/invokable/laravel-line-sdk\n\n## Sample Code Explanations\n\nThis project demonstrates the main features of LINE integration with Laravel applications. The following sections explain the key components with code examples.\n\n### 1. OAuth Authentication with LINE Accounts\n\nThe application uses Laravel Socialite to handle LINE OAuth authentication. Users can log in with their LINE accounts and the system stores their profile information.\n\n#### Routes Configuration (`routes/web.php`)\n```php\nRoute::get('login', [LoginController::class, 'login'])-\u003ename('login');\nRoute::get('callback', [LoginController::class, 'callback']);\nRoute::post('logout', [LoginController::class, 'logout'])-\u003ename('logout');\n```\n\n#### Login Controller (`app/Http/Controllers/LoginController.php`)\n```php\n\u003c?php\n\nnamespace App\\Http\\Controllers;\n\nuse App\\Models\\User;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Support\\Facades\\Log;\nuse Laravel\\Socialite\\Facades\\Socialite;\n\nclass LoginController extends Controller\n{\n    public function login()\n    {\n        return Socialite::driver('line-login')-\u003ewith([\n            'prompt' =\u003e 'consent',\n            'bot_prompt' =\u003e 'normal',\n        ])-\u003eredirect();\n    }\n\n    public function callback(Request $request)\n    {\n        if ($request-\u003emissing('code')) {\n            Log::info('Login callback called without code parameter', [\n                'request_data' =\u003e $request-\u003eall(),\n                'ip' =\u003e $request-\u003eip(),\n                'user_agent' =\u003e $request-\u003euserAgent(),\n            ]);\n\n            return redirect()-\u003eroute('welcome')-\u003ewith('error', 'Authorization failed. Please try logging in again.');\n        }\n\n        $user = Socialite::driver('line-login')-\u003euser();\n\n        $loginUser = User::updateOrCreate([\n            'line_id' =\u003e $user-\u003eid,\n        ], [\n            'name' =\u003e 'User',\n            'avatar' =\u003e $user-\u003eavatar,\n            'access_token' =\u003e $user-\u003etoken,\n            'refresh_token' =\u003e $user-\u003erefreshToken,\n        ]);\n\n        auth()-\u003elogin($loginUser, true);\n\n        return to_route('dashboard');\n    }\n\n    public function logout()\n    {\n        auth()-\u003elogout();\n        return redirect('/');\n    }\n}\n```\n\nThe `login()` method redirects users to LINE's OAuth authorization page with specific parameters:\n- `prompt =\u003e 'consent'`: Forces the consent screen to appear\n- `bot_prompt =\u003e 'normal'`: Allows users to add the bot as a friend\n\nThe `callback()` method handles the OAuth response, creates or updates the user record, and logs them into the application.\n\n### 2. LINE Notifications using Laravel Notifications\n\nLaravel's notification system is used to send messages through LINE. This approach provides a clean, object-oriented way to handle LINE messaging.\n\n#### Notification Controller (`app/Http/Controllers/NotificationController.php`)\n```php\n\u003c?php\n\nnamespace App\\Http\\Controllers;\n\nuse App\\Notifications\\LineTest;\nuse Illuminate\\Http\\Request;\n\nclass NotificationController extends Controller\n{\n    public function __invoke(Request $request)\n    {\n        $request-\u003euser()-\u003enotify(new LineTest('Notification from LINE Messaging API'));\n\n        return back();\n    }\n}\n```\n\n#### LINE Notification Class (`app/Notifications/LineTest.php`)\n```php\n\u003c?php\n\nnamespace App\\Notifications;\n\nuse Illuminate\\Bus\\Queueable;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Illuminate\\Notifications\\Notification;\nuse Revolution\\Line\\Notifications\\LineChannel;\nuse Revolution\\Line\\Notifications\\LineMessage;\n\nclass LineTest extends Notification\n{\n    use Queueable;\n\n    public function __construct(protected string $message)\n    {\n        //\n    }\n\n    public function via(object $notifiable): array\n    {\n        return [\n            LineChannel::class,\n        ];\n    }\n\n    public function toLine(object $notifiable): LineMessage\n    {\n        return LineMessage::create()\n            -\u003etext($this-\u003emessage)\n            -\u003esticker(446, random_int(1988, 2027));\n    }\n\n    public function getMessage(): string\n    {\n        return $this-\u003emessage;\n    }\n}\n```\n\nThe notification system allows you to:\n- Send text messages with `-\u003etext()`\n- Include stickers with `-\u003esticker(packageId, stickerId)`\n- Queue notifications for better performance using the `Queueable` trait\n- Target specific users through the `routeNotificationForLine()` method in the User model\n\n### 3. Sending Messages with PushMessage\n\nFor direct message sending without using the notification system, you can use LINE's PushMessage API directly through the Bot facade.\n\n#### Push Controller (`app/Http/Controllers/PushController.php`)\n```php\n\u003c?php\n\nnamespace App\\Http\\Controllers;\n\nuse Illuminate\\Http\\RedirectResponse;\nuse Illuminate\\Http\\Request;\nuse LINE\\Clients\\MessagingApi\\Model\\PushMessageRequest;\nuse LINE\\Clients\\MessagingApi\\Model\\TextMessage;\nuse LINE\\Constants\\MessageType;\nuse Revolution\\Line\\Facades\\Bot;\n\nclass PushController extends Controller\n{\n    public function __invoke(Request $request): RedirectResponse\n    {\n        $message = new TextMessage(['text' =\u003e 'PushMessage test', 'type' =\u003e MessageType::TEXT]);\n\n        $push = new PushMessageRequest([\n            'to' =\u003e $request-\u003euser()-\u003eline_id,\n            'messages' =\u003e [$message],\n        ]);\n\n        Bot::pushMessage($push);\n\n        return back();\n    }\n}\n```\n\nPushMessage is useful when you need to:\n- Send messages immediately without going through the notification system\n- Have fine-grained control over message construction\n- Send messages to users who haven't interacted with your bot recently\n\n### 4. Receiving Messages from LINE\n\nThe webhook functionality for receiving messages from LINE is provided by the `laravel-line-sdk` package. You should customize the `MessageListener.php` file for your specific project needs.\n\n#### Message Listener (`app/Listeners/Line/MessageListener.php`)\n```php\n\u003c?php\n\nnamespace App\\Listeners\\Line;\n\nuse LINE\\Clients\\MessagingApi\\ApiException;\nuse LINE\\Webhook\\Model\\MessageEvent;\nuse LINE\\Webhook\\Model\\StickerMessageContent;\nuse LINE\\Webhook\\Model\\TextMessageContent;\nuse Revolution\\Line\\Facades\\Bot;\n\nclass MessageListener\n{\n    protected string $token;\n\n    public function handle(MessageEvent $event): void\n    {\n        $message = $event-\u003egetMessage();\n        $this-\u003etoken = $event-\u003egetReplyToken();\n\n        match ($message::class) {\n            TextMessageContent::class =\u003e $this-\u003etext($message),\n            StickerMessageContent::class =\u003e $this-\u003esticker($message),\n        };\n    }\n\n    protected function text(TextMessageContent $message): void\n    {\n        Bot::reply($this-\u003etoken)-\u003etext($message-\u003egetText());\n    }\n\n    protected function sticker(StickerMessageContent $message): void\n    {\n        Bot::reply($this-\u003etoken)-\u003esticker(\n            $message-\u003egetPackageId(),\n            $message-\u003egetStickerId()\n        );\n    }\n}\n```\n\n**Important Notes:**\n- The webhook endpoint is automatically provided by the `laravel-line-sdk` package\n- This sample implementation simply echoes back received messages\n- For more complex message processing, consider dispatching a Job from the listener:\n\n```php\npublic function handle(MessageEvent $event): void\n{\n    // Dispatch a job for complex processing\n    ProcessLineMessage::dispatch($event);\n    \n    // Send immediate acknowledgment if needed\n    Bot::reply($event-\u003egetReplyToken())-\u003etext('Message received! Processing...');\n}\n```\n\nThis approach prevents webhook timeouts while allowing complex business logic to run in the background.\n\n## LICENSE\nMIT\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Finvokable%2Flaravel-line-project","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Finvokable%2Flaravel-line-project","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Finvokable%2Flaravel-line-project/lists"}