🫢Triển khai dự án Pi bằng Laravel 12

Để thuận tiện cho dự án được chạy

composer run dev
composer require laravel/ui --dev
php artisan ui bootstrap --auth

Tích hợp tailwind css vào

vite.config.js

import { defineConfig } from 'vite';
import laravel from 'laravel-vite-plugin';
import tailwindcss from '@tailwindcss/vite'
export default defineConfig({
  plugins: [
    tailwindcss(),
    laravel({
      input: [
        'resources/sass/app.scss',
        'resources/js/app.js',
      ],
      refresh: true,
    }),
  ],
});

Tích hợp template bootstrap admin vào auth Laravel

composer require laravel/breeze --dev
php artisan breeze:install
# Chọn "Blade" khi được hỏi (mặc định là 0)
# Bạn có thể chọn có hoặc không hỗ trợ dark mode
npm install
npm run dev
php artisan migrate

Tạo cho tôi migrations \nPost, Category, Page có các trường để làm seo ví dụ description ... với đa ngôn ngữ và một admin để nhập dữ liệu để tôi chuẩn bị làm api cho đa ngôn ngữ

composer require spatie/laravel-translatable
php artisan make:migration create_categories_table
php artisan make:migration create_posts_table
php artisan make:migration create_pages_table
php artisan make:model Post
php artisan make:model Page
php artisan make:model Category
php artisan make:controller Admin/PostController --resource
php artisan make:controller Admin/PageController --resource
php artisan make:controller Admin/CategoryController --resource

database\migrations\2025_05_29_220715_create_categories_table.php

<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
  /**
   * Run the migrations.
   */
  public function up(): void
  {
    Schema::create('categories', function (Blueprint $table) {
      $table->id();
      $table->json('name');             // đa ngôn ngữ
      $table->json('slug')->nullable(); // seo-friendly URL
      $table->json('description')->nullable();
      $table->timestamps();
    });
  }
  /**
   * Reverse the migrations.
   */
  public function down(): void
  {
    Schema::dropIfExists('categories');
  }
};

database\migrations\2025_05_29_220758_create_pages_table.php

<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
  /**
   * Run the migrations.
   */
  public function up(): void
  {
    Schema::create('pages', function (Blueprint $table) {
      $table->id();
      $table->json('title');
      $table->json('slug')->nullable();
      $table->json('content')->nullable();
      $table->json('meta_title')->nullable();
      $table->json('meta_description')->nullable();
      $table->json('meta_keywords')->nullable();
      $table->timestamps();
    });
  }
  /**
   * Reverse the migrations.
   */
  public function down(): void
  {
    Schema::dropIfExists('pages');
  }
};

database\migrations\2025_05_29_220812_create_posts_table.php

<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
  /**
   * Run the migrations.
   */
  public function up(): void
  {
    Schema::create('posts', function (Blueprint $table) {
      $table->id();
      $table->foreignId('category_id')->constrained()->cascadeOnDelete();
      $table->json('title');
      $table->json('slug')->nullable();
      $table->json('excerpt')->nullable();
      $table->json('content');
      $table->json('meta_title')->nullable();
      $table->json('meta_description')->nullable();
      $table->json('meta_keywords')->nullable();
      $table->timestamps();
    });
  }
  /**
   * Reverse the migrations.
   */
  public function down(): void
  {
    Schema::dropIfExists('posts');
  }
};

app\Models\Category.php

<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Spatie\Translatable\HasTranslations;
class Category extends Model
{
  use HasTranslations;
  protected $translatable = ['name', 'slug', 'description'];
}

app\Models\Page.php

<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Spatie\Translatable\HasTranslations;
class Page extends Model
{
  use HasTranslations;
  protected $translatable = [
    'title',
    'slug',
    'content',
    'meta_title',
    'meta_description',
    'meta_keywords',
  ];
}

app\Models\Post.php

<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Spatie\Translatable\HasTranslations;
class Post extends Model
{
  use HasTranslations;
  protected $translatable = [
    'title',
    'slug',
    'excerpt',
    'content',
    'meta_title',
    'meta_description',
    'meta_keywords',
  ];
  public function category()
  {
    return $this->belongsTo(Category::class);
  }
}

Hãy tạo cho tôi seeders hiện tại tôi đã có

php artisan make:seed CategorySeeder
php artisan make:seed PostSeeder
php artisan make:seed PageSeeder

database\seeders\CategorySeeder.php

<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
use App\Models\Category;
class CategorySeeder extends Seeder
{
  public function run(): void
  {
    Category::create(
      [
        'name' => [
          'en' => 'Technology 1',
          'vi' => 'Công nghệ 1',
        ],
        'slug' => [
          'en' => 'technology-1',
          'vi' => 'cong-nghe-1',
        ],
        'description' => [
          'en' => 'All about tech 1',
          'vi' => 'Tất cả về công nghệ 1',
        ],
      ],
      [
        'name' => [
          'en' => 'Technology 2',
          'vi' => 'Công nghệ 2',
        ],
        'slug' => [
          'en' => 'technology-2',
          'vi' => 'cong-nghe-2',
        ],
        'description' => [
          'en' => 'All about tech 2',
          'vi' => 'Tất cả về công nghệ 2',
        ],
      ]
    );
    Category::create(
      [
        'name' => [
          'en' => 'Health 1',
          'vi' => 'Sức khỏe 1',
        ],
        'slug' => [
          'en' => 'health-1',
          'vi' => 'suc-khoe-1',
        ],
        'description' => [
          'en' => 'Tips for better health 1',
          'vi' => 'Mẹo cho sức khỏe tốt hơn 1',
        ],
      ],
      [
        'name' => [
          'en' => 'Health 2',
          'vi' => 'Sức khỏe 2',
        ],
        'slug' => [
          'en' => 'health-2',
          'vi' => 'suc-khoe-2',
        ],
        'description' => [
          'en' => 'Tips for better health 2',
          'vi' => 'Mẹo cho sức khỏe tốt hơn 2',
        ],
      ]
    );
  }
}

database\seeders\PageSeeder.php

<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
use App\Models\Page;
class PageSeeder extends Seeder
{
  public function run(): void
  {
    Page::create(
      [
        'title' => [
          'en' => 'About Us 1',
          'vi' => 'Về chúng tôi 1',
        ],
        'slug' => [
          'en' => 'about-us-1',
          'vi' => 've-chung-toi-1',
        ],
        'content' => [
          'en' => '<p>We are a leading company in tech... 1</p>',
          'vi' => '<p>Chúng tôi là công ty hàng đầu trong lĩnh vực công nghệ... 1</p>',
        ],
        'meta_title' => [
          'en' => 'About Our Company 1',
          'vi' => 'Thông tin về công ty 1',
        ],
        'meta_description' => [
          'en' => 'Learn more about what we do. 1',
          'vi' => 'Tìm hiểu thêm về công việc của chúng tôi. 1',
        ],
        'meta_keywords' => [
          'en' => 'about, company 1',
          'vi' => 'về, công ty 1',
        ],
      ],
      [
        'title' => [
          'en' => 'About Us 2',
          'vi' => 'Về chúng tôi 2',
        ],
        'slug' => [
          'en' => 'about-us-2',
          'vi' => 've-chung-toi-2',
        ],
        'content' => [
          'en' => '<p>We are a leading company in tech... 2</p>',
          'vi' => '<p>Chúng tôi là công ty hàng đầu trong lĩnh vực công nghệ... 2</p>',
        ],
        'meta_title' => [
          'en' => 'About Our Company 2',
          'vi' => 'Thông tin về công ty 2',
        ],
        'meta_description' => [
          'en' => 'Learn more about what we do. 2',
          'vi' => 'Tìm hiểu thêm về công việc của chúng tôi. 2',
        ],
        'meta_keywords' => [
          'en' => 'about, company 2',
          'vi' => 'về, công ty 2',
        ],
      ]
    );
  }
}

database\seeders\PostSeeder.php

<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
use App\Models\Post;
use App\Models\Category;
class PostSeeder extends Seeder
{
  public function run(): void
  {
    $category = Category::first(); // Giả sử có ít nhất 1 category
    Post::create(
      [
        'category_id' => $category->id,
        'title' => [
          'en' => 'The Rise of AI 1',
          'vi' => 'Sự trỗi dậy của AI 1',
        ],
        'slug' => [
          'en' => 'rise-of-ai-1',
          'vi' => 'su-troi-day-cua-ai-1',
        ],
        'excerpt' => [
          'en' => 'An overview of AI evolution 1',
          'vi' => 'Tổng quan về sự phát triển của AI 1',
        ],
        'content' => [
          'en' => '<p>AI is transforming industries... 1</p>',
          'vi' => '<p>Trí tuệ nhân tạo đang thay đổi các ngành công nghiệp... 1</p>',
        ],
        'meta_title' => [
          'en' => 'AI Evolution 1',
          'vi' => 'Sự phát triển của AI 1',
        ],
        'meta_description' => [
          'en' => 'Discover how AI is shaping the world. 1',
          'vi' => 'Khám phá cách AI định hình thế giới. 1',
        ],
        'meta_keywords' => [
          'en' => 'AI, technology 1',
          'vi' => 'AI, công nghệ 1',
        ],
      ],
      [
        'category_id' => $category->id,
        'title' => [
          'en' => 'The Rise of AI 2',
          'vi' => 'Sự trỗi dậy của AI 2',
        ],
        'slug' => [
          'en' => 'rise-of-ai-2',
          'vi' => 'su-troi-day-cua-ai-2',
        ],
        'excerpt' => [
          'en' => 'An overview of AI evolution 2',
          'vi' => 'Tổng quan về sự phát triển của AI 2',
        ],
        'content' => [
          'en' => '<p>AI is transforming industries... 2</p>',
          'vi' => '<p>Trí tuệ nhân tạo đang thay đổi các ngành công nghiệp... 2</p>',
        ],
        'meta_title' => [
          'en' => 'AI Evolution 2',
          'vi' => 'Sự phát triển của AI 2',
        ],
        'meta_description' => [
          'en' => 'Discover how AI is shaping the world. 2',
          'vi' => 'Khám phá cách AI định hình thế giới. 2',
        ],
        'meta_keywords' => [
          'en' => 'AI, technology 2',
          'vi' => 'AI, công nghệ 2',
        ],
      ]
    );
  }
}

database\seeders\DatabaseSeeder.php

<?php
namespace Database\Seeders;
use App\Models\User;
// use Illuminate\Database\Console\Seeds\WithoutModelEvents;
use Illuminate\Database\Seeder;
class DatabaseSeeder extends Seeder
{
  /**
   * Seed the application's database.
   */
  public function run(): void
  {
    // User::factory(10)->create();
    // User::factory()->create([
    //   'name'  => 'Admin',
    //   'email' => 'admin@example.com',
    // ]);
    $this->call([
      CategorySeeder::class,
      PostSeeder::class,
      PageSeeder::class,
    ]);
  }
}
php artisan db:seed hoặc php artisan migrate --seed
php artisan make:view admin.categories.index
php artisan make:view admin.categories.create
php artisan make:view admin.categories.edit
php artisan make:controller FrontendController
 php artisan make:controller CKEditorController

Last updated

Was this helpful?