Code Monkey home page Code Monkey logo

fk-adder's Introduction

FkAdder for Laravel Migration

Lets you add foreign keys smart and easy! Foreign key adder for laravel migration. For Laravel 4.2 and 5.*.

The purpose of FkAdder is to simplify declaration of foreign key columns in migration.

Things that FkAdder do for you:
  • Remembers the data type of a foreign key, and it will provide the correct data type for you, so that you don't have to recall the data type of foreign key column whenever you need that particular foreign key.
  • Lets you create migration tables in any order. This solves the problem when your table is created prior than the reference table. Usually this may cause error like Reference table some_table does not exist, this happens when referencing the table which are to be migrated on last part of migrations.
  • Speeds up laravel migration development.

Installation

composer require ajcastro/fk-adder

Alias

Add alias into config/app.php file. You can skip this because of laravel's auto-discovery.

 'Fk' => FkAdder\Fk::class

Configuration

Create a config file named config/fk_adder.php

<?php

return [
    // For simple string-based declaration
    'fk_datatypes_path' => base_path('database/foreign_keys/fk_datatypes.php')
    // For class-based declaration, used for special cases and more control. You don't need this for simple cases .
    'fk_namespace' => 'Your\Fk\Namespace',
];

Setup

There are two ways to setup your foreign keys: string-based declaration and class-based declaration. String-based is preferred for simpler datatype declaration.

String-based declaration

Open your fk_datatypes_path file and add the foreign key declaration in the array. The array keys are the foreign key columns and its values are the datatypes. The reference tables are smartly guessed already by remove the _id and pluralizing the foreign key names e.g. user_id -> users.

<?php

return [
    'user_id'       => 'unsignedInteger',
    'group_id'      => 'unsignedInteger',
    'preference_id' => 'unsignedBigInteger',
];

Since version 1.2, you can now also define the reference table. This is helpful for foreign keys which has custom table names.

<?php

return [
    'user_id'       => 'unsignedInteger, custom_users',
    'group_id'      => 'unsignedInteger, custom_groups',
];
Class-based declaration

Create classes of foreign keys declaration inside your fk_namespace directory path.

Naming Convention

If the foreign key is e.g. user_id, then the class name should be UserId.

Example:

<?php

namespace Your\Fk\Namespace;

use FkAdder\BaseFk;

class UserId extends BaseFk
{
    protected $referenceTable = 'users';

    public function createFkColumn($column)
    {
        return $this->table->unsignedInteger($column);
    }
}

Sample Usage, Before vs After

Before

<?php

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

class CreateUsersTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('users', function(Blueprint $table) {
            $table->increments('id');
            $table->unsignedInteger('group_id')->nullable()->comment('Group of the user');
            $table->unsignedBigInteger('preference_id')->nullable()->comment('Preference of the user');

            $table->foreign('group_id')->references('id')->on('groups');
            $table->foreign('preference_id')->references('id')->on('preferences')
                ->onDelete('cascade')>onUpdate('cascade');
        });
    }
}

After

<?php

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

class CreateUsersTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('users', function(Blueprint $table) {
            $table->increments('id');

            Fk::make($table)->add('group_id')->nullable()->comment('Group of the user');

            Fk::make($table)
                ->onDelete('cascade')
                ->onUpdate('cascade')
                ->add('preference_id')
                ->nullable()
                ->comment('Preference of the user');
        });

        Fk::migrate();
    }
}

More Features, Benefits and Explanations

<?php

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

class CreateUsersTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('users', function(Blueprint $table) {
            $table->increments('id');

            // Foreign key declaration is one-liner, simpler and more compact.
            // You dont have to type what datatype it is. You will just declare it once.
            Fk::make($table)->add('group_id')->nullable()->comment('Group of the user');
            Fk::make($table)->onDelete('cascade')->add('preference_id')
                ->nullable()->comment('Preference of the user');

            // After you call the method `add()`, it will return an instance of the usual \Illuminate\Support\Fluent,
            // so that you can chain more column declaration like `nullable()` and `comment()`

            // If ever you need a different column name from the foreign key, just pass a second parameter
            // to `add()` method e.g.
            Fk::make($table)->add('group_id', 'new_group_id')->nullable()->comment('New group of the user');

            // The default `onDelete` settings is `restrict` and `onUpdate` is `cascade`.
            Fk::make($table)->onDelete('restrict')->onUpdate('cascade')->add('group_id', 'new_group_id');

            // You can also pass the key name for the foreign key.
            Fk::make($table)->keyName('users_new_group_id_foreign_key')->add('group_id', 'new_group_id');

            // Take note that those foreign key modifiers should be called prior or before the `add()` method.
        });

        // Finally, you may now migrate and persist foreign keys in mysql database.
        // You can call this once at the very end of migration,
        // so all your foreign key declarations accross different migration files will be persisted.
        Fk::migrate();
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Fk::rollback(); // delete foreign keys persisted by Fk::migrate(), (coming soon...)
        Schema::dropIfExists('users');
    }
}

License

Released under MIT License.

fk-adder's People

Contributors

ajcastro avatar monrealryan avatar

Stargazers

 avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar

Forkers

monrealryan

fk-adder's Issues

Create a json file containing data needed to drop a foreign key

For example we are developing a blog app. The tables involved are users, tags and posts tables.
Migration Files:
20180101_create_users_table

$table->increments('id');
$table->string('name');

20180101_create_tags_table

$table->increments('id');
$table->string('name');

20180101_create_posts_table

  $table->increments('id');
  Fk::make($table)->add('user_id');
  Fk::make($table)->add('tag_id');
  $table->string('title');
  $table->string('body');

This should generate a json of data that is needed when deleting the foreign key.
Those json files will be saved in directory database/foreign_keys/ and the json filename would be the migration_file_name.json.
So when we run the above migration it will create a file database/foreign_keys/20180101_create_posts_table.json. One json file per migration file. Only 20180101_create_posts_table.json is created because it is the only migration file that calls Fk::make().

The data needed to drop a foreign key is the:

  • table
  • foreign key name.
    Sample Dropping of foreign key :
Schema::table('posts', function ($table) {
  $table->dropForeignKey('the_foreign_key_name');
});

Sample json file format:

[{
"table" : "posts",
"foreign_key_names: ["posts_user_id_foreign_key", "posts_tag_id_foreign_key"]
}]

It is an array of objects, because it can be possible that one migration file can involve many tables.

The code will be placed in the Fk::migrate() method.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.