Trik untuk Menguji Aplikasi Web Laravel Menggunakan Pabrik Model

pengantar


Mari kita bayangkan bahwa kita sedang mengembangkan aplikasi web kecil pada versi Laravel lebih tinggi dari 6 dan kami ingin menulis tes untuk itu.


Isi artikel diberikan di bawah ini:


  1. Deskripsi Domain
  2. Pembuatan aplikasi
  3. Penciptaan Entitas
  4. Tes menulis
  5. Masalah
  6. Keputusan

Deskripsi Domain


Kami akan mengembangkan toko online tempat pengguna tertentu dapat melakukan pemesanan tertentu. Dari penjelasan di atas, kita dapat mengetahui bahwa entitas utama dari area subjek adalah pengguna, pesanan, dan barang. Ada hubungan satu-ke-banyak antara pengguna dan pesanan, yaitu pengguna dapat memiliki banyak pesanan, dan pesanan hanya memiliki satu pengguna (pengguna diperlukan untuk pesanan). Ada hubungan banyak-ke-banyak antara pesanan dan barang, karena barang dapat dalam pesanan berbeda dan pesanan dapat terdiri dari banyak barang. Untuk kesederhanaan, kami mengabaikan produk dan hanya fokus pada pengguna dan pesanan.


Pembuatan aplikasi


Aplikasi Laravel sangat mudah dibangun menggunakan paket pembuat aplikasi . Setelah menginstalnya, membuat aplikasi baru sesuai dengan satu perintah:


laravel new shop

Penciptaan Entitas


, — . Laravel , . , . :


php artisan make:model Order -m -f

App/, database/migrations/ database/factories/.


. , . - :


<?php

use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateOrdersTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('orders', function (Blueprint $table) {
            $table->id();
            $table->unsignedBigInteger('user_id');
            $table->timestamps();

            $table->foreign('user_id')->references('id')->on('users')
                ->onDelete('cascade');
        });
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::dropIfExists('orders');
    }
}

. fillable :


<?php

namespace App;

use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;

class Order extends Model
{
    protected $fillable = ['user_id'];

    /**
     * Relation to user
     * @return BelongsTo
     */
    public function user(): BelongsTo
    {
        return $this->belongsTo(User::class);
    }
}

. , , id.


<?php

/** @var \Illuminate\Database\Eloquent\Factory $factory */

use App\Order;
use App\User;
use Faker\Generator as Faker;

$factory->define(Order::class, function (Faker $faker) {
    return [
        'user_id' => factory(User::class)->create()->id
    ];
});

, .



, Laravel PHPUnit . :


php artisan make:test OrderTest

tests/Feature/. RefreshDatabase.


№1.


<?php

namespace Tests\Feature;

use App\Order;
use App\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Foundation\Testing\WithFaker;
use Tests\TestCase;

class OrderTest extends TestCase
{
    use RefreshDatabase;

    /** @test */
    public function order_factory_can_create_order()
    {
        // When we use Order factory
        $order = factory(Order::class)->create();
        // Then we should have new Order::class instance
        $this->assertInstanceOf(Order::class, $order);
    }
}

!


№2.


/** @test */
public function order_should_have_user_relation()
{
    // When we use Order factory
    $order = factory(Order::class)->create();
    // Then we should have new Order::class instance with user relation
    $this->assertNotEmpty($order->user_id);
    $this->assertInstanceOf(User::class, $order->user);
}

!


№3. ,


/** @test */
public function we_can_provide_user_id_to_order_factory()
{
    // Given user
    $user = factory(User::class)->create();
    // When we use Order factory and provide user_id parameter
    $order = factory(Order::class)->create(['user_id' => $user->id]);
    // Then we should have new Order::class instance with provided user_id
    $this->assertEquals($user->id, $order->user_id);
}

!


, , . , , .


№4. ,


/** @test */
public function when_we_create_one_order_one_user_should_be_created()
{
    // Given user
    $user = factory(User::class)->create();
    // When we use Order factory and provide user_id parameter
    $order = factory(Order::class)->create(['user_id' => $user->id]);
    // Then we should have new Order::class instance with provided user_id
    $this->assertEquals($user->id, $order->user_id);
    // Let's check that system has one user in DB
    $this->assertEquals(1, User::count());
}

! , . ? .



, , — . , , . . , , . , .



, . PHP , n- — func_get_arg(), . , () Faker, — , create() . , , () . , , . :


$factory->define(Order::class, function (Faker $faker) {
    //    
    $passedArguments = func_get_arg(1);
    return [
        'user_id' => function () use ($passedArguments) {
            //    user_id,   
            if (! array_key_exists('user_id', $passedArguments)) {
                return factory(User::class)->create()->id;
            }
        }
    ];
});

№4 — !


Hanya itu yang ingin saya bagikan. Saya sering menghadapi masalah yang perlu untuk mengontrol jumlah entitas setelah beberapa tindakan di dalam sistem, dan penerapan standar pabrik tidak benar-benar mengatasi hal ini.


Saya akan senang mendengar trik Anda yang Anda gunakan saat berkembang di Laravel atau PHP.


All Articles