iT邦幫忙

2023 iThome 鐵人賽

DAY 21
0
Modern Web

Laravel實作 —系列 第 21

[Day 21] Laravel實作 -- 我把生死簿當死亡筆記本在寫

  • 分享至 

  • xImage
  •  

前兩天認識完多對多,今天我們要來寫報名的基本功能,那我們也是先從新增開始寫。
首先我們一樣先到web去新增我們的路徑,讓之後使用時更容易。
routes\web.php

Route::resource('joiners',\App\Http\Controllers\JoinerController::class)
    ->except('index')
    ->middleware(['auth', 'verified']);

這次我們不會使用到index,所以在建立時我們先就將他鎖起來。

那寫完路徑之後我們還需要一個入口進到我們的報名頁面,所以我們先到article的show去新增一個按鈕,讓別人可以清楚的知道如何報名。那我們就到blade中去新增我們的按鈕,resources\views\articles\show.blade.php

    <div class="max-w-7xl mx-auto sm:px-6 lg:px-8 py-6">
        <button type = "submit" class="px-3 py-1 rounded bg-gray-800 text-white hover:bg-gray-700">
            <a href = "{{route('joiners.create', $article)}}"> 新增活動</a>
        </button>
    </div>

寫完入口後我們就要到controller中去迎接這位客人,那我們到app\Http\Controllers\JoinerController.php

    /**
     * Show the form for creating a new resource.
     */
    public function create(Request $request)
    {
        $article = Article::find($request -> article);   
        return view('joiners.create', ['article' => $article]);

    }

因為前面我們已經建過article的create了,所以知道這邊我們需要將我們的blade寫出來,那我們就先到resources\views中新建一個資料夾然後放入我們的blade的檔案就開始寫程式吧。

<x-app-layout>
    <x-slot name="header">
        <h2 class="font-semibold text-xl text-gray-800 leading-tight">
            {{$article->title}}
        </h2>
    </x-slot>
	
    <div class="py-12">
        <div class="max-w-7xl mx-auto sm:px-6 lg:px-8">
            <div class="bg-white overflow-hidden shadow-sm sm:rounded-lg">
                <div class="p-6 text-gray-900 m-6 text-center">
                     @if($errors->any())
						<div class = "error p-3 bg-red-600 text-white font-thin rounded">
							<ul>
								@foreach($errors -> all() as $error)
									<li>{{ $error }}</li>
								@endforeach
							</ul>
						</div>

					@endif

                    
                    <div class = "text-lg text-gray-700 py-2 px-6 whitespace-pre-wrap leading-relaxed text-left">
                        {{ $article -> summary }}
                    </div>
                    
					<form action = "{{ route('joiners.store') }}" method = "post">  
						@csrf
						<div class="field my-2 ">
							<lable for=""> {{__("生日")}} </lable>
							<input type = "date" value="{{ old('birthday') }}" name = "birthday" class = "border-gray-300 p-2 mx-2">

						</div>

						<div class="flex-auto ">
							<div class="field my-2" ><p>{{__("身分證字號")}}</p></div>
							<div class="field my-2 ">
								<lable for="" class="mb-2"> {{__("")}}</lable>
								<input type = "text" value="{{ old('ID_number') }}" name = "ID_number" class = "w-2/5 border-gray-300 p-2 mx-2">

							</div>
						</div>
						
						<div class="flex-auto ">
							<div class="field my-2" ><p>{{__("電話號碼")}}</p></div>
							<div class="field my-2 ">
								<lable for="" class="mb-2" > {{__("")}}</lable>
								<input type = "text" value="{{ old('phone') }}" name = "phone" class = "w-2/5 border-gray-300 p-2 mx-2 placeholder-gray-300" placeholder="{{ __('ex:0912345678') }}">

							</div>
						</div>

                        <div class="flex-auto ">
							<div class="field my-2" ><p>{{__("備註")}}</p></div>
							<div class="field my-2" >
								<lable for="" class="mb-2"> {{__("")}} </lable>
								<textarea name = "note" rows = "5" class = "w-4/5 m-auto border-gray-300 p-2 placeholder-gray-300" placeholder="{{ __('有甚麼話想對主辦方說的嗎...') }}">{{ old('note') }}</textarea>

							</div>

						</div>


						<div class="flex mt-4 space-x-6 justify-center">
							<div class="actions">
								<button type = "submit" name="article_id" value="{{ $article -> id }}" class="px-3 py-1 rounded bg-indigo-150 text-white hover:bg-indigo-250"> {{__("確定報名!")}} </button>
							</div>
							<div class="px-3 py-1 rounded bg-gray-200 hover:bg-gray-300 ">	
								<a href = "{{route('dashboard')}}" > {{__("取消報名")}} </a>
							</div>
						</div>
					</form>
                </div>
            </div>
        </div>
    </div>
</x-app-layout>

接著我們到controller中去補足store的程式碼,完成store我們今天的工作也完成了。

    /**
     * Store a newly created resource in storage.
     */
    public function store(Request $request)
    {
        $content = $request->validate([
            'note' => 'max:255',
            'phone' => 'required|numeric:10',
            'birthday' => 'required',
            'ID_number' => 'required|min:10|max:10',
        ]);

        auth()->user()->joinArticles()->syncWithoutDetaching([$request->article_id => $content]);

        return redirect() -> route('dashboard');
    }

這邊是不是有人發現,欸?怎麼和article之前的store有些不一樣?為甚麼有用到syncWithoutDetaching這又是甚麼?
這是專門用來儲存多對多表格的方式,其實他總共有四種:attach、detach、sync、syncWithoutDetaching。
我們來一一了解他是什麼吧:

  • attach
    他的用法是直接插入一筆新的資料,並不會去檢查這筆資料是否曾經存在。
    arrary=[1,2,3]
    attach([3,4,5])
    => arrary=[1,2,3,3,4,5]

  • detach
    負責的是多對多關係的刪除,他和attach一樣並不會檢查資料是否存在,如果有就會刪除,沒有也不會報錯。
    arrary=[1,2,3]
    detach([3,4,5])
    => arrary=[1,2]

  • sync
    sync只會儲存當下array裡有的資料,原本存在資料庫裡的資料,如果不在array裡,便會被刪除。
    arrary=[1,2,3]
    sync([3,4,5])
    => arrary=[1,2,3]

  • syncWithoutDetaching
    這個是我們比較常用的函式,sync會幫我們檢查有沒有重複的關聯,但是我們希望只更新原本不存在的關係。
    array=[1,2,3]
    syncWithoutDetaching([3,4,5])
    => array=[1,2,3,4,5]

那我們今天了解了如何新增一筆多對多的資料,並且瞭解了多對多是怎麼儲存的,大家看我們這樣輕輕鬆鬆地就介紹完多對多的儲存,我們當時可是哀號了好幾個晚上到白天,最後才發現用如此簡單的方法就可以將資料存入。雖然這看似簡簡單單的程式碼,卻是多對多不可或缺的用法,大家還是要花些時間去了解喔,那我們今天就先到這裡,我們明天要來學前端,我們明天見,掰掰!


上一篇
[Day 20] Laravel實作 -- 比米諾斯人生還亂的是多對多
下一篇
[Day 22] Laravel實作 -- 現在的我也可以畫出地獄變
系列文
Laravel實作 —30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言