Laravel入门教程: 实现简单的AJAX的CRUD页面

介绍

这段时间在写一个考试系统ChemLab,期间用到了AJAX实现增删查改(CRUD)页面,现在写一个Laravel入门教程吧,一步步实现最基本的CRUD页面。

项目地址,求Star:Laravel_AJAX_CRUD

演示地址:http://115.159.147.250/task

博文地址:Laravel入门教程: 实现简单的AJAX的CRUD页面

先来看看效果图:
Laravel入门教程: 实现简单的AJAX的CRUD页面_第1张图片

这个教程需要安装homestead环境,关于homestead可以参考我的另一篇博文:windows下安装Homestead开发环境

创建项目

vagrant@homestead:~/Code$ laravel new AJAX_CRUD
vagrant@homestead:~/Code$ cd AJAX_CRUD/

修改配置

修改数据库

打开.env,主要是修改数据库方面的,我们选择task数据库,如下:

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=task
DB_USERNAME=homestead
DB_PASSWORD=secret

然后在数据库中创建task数据库。

修改网址映射

注意这部分是在主机下进行的,不是在虚拟机homestead中进行的,后面我提到主机应该注意。
修改homestead的配置文件:~/.homestead/Homestead.yaml,增加如下内容:

sites:
    - map: crud.app
      to: /home/vagrant/Code/AJAX_CRUD/public

修改C:\Windows\System32\drivers\etc\hosts,增加一条记录:

192.168.10.10  crud.app

重启homestead虚拟机:

homestead reload --provision

访问项目

浏览器访问crud.app,应该能见到如下页面:
Laravel入门教程: 实现简单的AJAX的CRUD页面_第2张图片

引入Bootstrap、JQuery、Toastr

刚创建的项目什么都没有,在resources/welcome.blade.php中加入bootstrapJQueryToastr

<title>Task Managertitle>

<link href="http://cdn.bootcss.com/bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet">
<link href="http://cdn.bootcss.com/toastr.js/2.1.3/toastr.min.css" rel="stylesheet">
<script src="http://cdn.bootcss.com/jquery/3.1.0/jquery.min.js">script>
<script src="http://cdn.bootcss.com/bootstrap/3.3.7/js/bootstrap.min.js">script>
<script src="http://cdn.bootcss.com/toastr.js/2.1.3/toastr.min.js">script>

将如下内容删除:

<style>
    html, body {
        height: 100%;
    }

    body {
        margin: 0;
        padding: 0;
        width: 100%;
        display: table;
        font-weight: 100;
        font-family: 'Lato', sans-serif;
    }

    .container {
        text-align: center;
        display: table-cell;
        vertical-align: middle;
    }

    .content {
        text-align: center;
        display: inline-block;
    }

    .title {
        font-size: 96px;
    }
style>
...
<div class="content">
    <div class="title">Laravel 5div>
div>

创建Eloquent模型、数据表

vagrant@homestead:~/Code/AJAX_CRUD$ php artisan make:model Task -m
Model created successfully.
Created Migration: 2016_08_17_033029_create_tasks_table

编辑模型:app/Task.php,如下:

class Task extends Model
{
    protected $fillable = ['name', 'content'];
}

编辑database/migrations/2016_08_17_033029_create_tasks_table.php,如下

...
public function up()
{
    Schema::create('tasks', function (Blueprint $table) {
        $table->increments('id');
        $table->text('name');
        $table->text('content');
        $table->timestamps();
    });

    App\Task::create([
        'name' => '任务1',
        'content' => '完成crud'
    ]);
    App\Task::create([
        'name' => '任务1',
        'content' => '完成教程'
    ]);
}
...

创建数据表:

vagrant@homestead:~/Code/AJAX_CRUD$ php artisan migrate
Migration table created successfully.
Migrated: 2014_10_12_000000_create_users_table
Migrated: 2014_10_12_100000_create_password_resets_table
Migrated: 2016_08_17_033029_create_tasks_table

到数据库中查看,你会发现task数据库中多了一些表和记录。

构建页面

创建控制器

vagrant@homestead:~/Code/AJAX_CRUD$ php artisan make:controller TaskController
Controller created successfully.

修改路由

编辑app/Http/routes.php

Route::get('/', function () {
    return redirect('/task');
});

Route::resource('/task', 'TaskController');

这样所有动作都由我们刚刚创建的控制器来执行了。

这里的Route::resource方法可以看这个:RESTful Resource Controllers,它默认帮你创建这几个http verb
* GET
* POST
* PUT
* DELETE

这样就不用自己写路由了。

修改控制器

编辑app/Http/Controllers/TaskController.php,在类中增加如下方法:

use App\Task;
...
public function index() {
    return view('welcome', [
        'tasks' => Task::all()
    ]);
}

编辑页面

编辑resources/welcome.blade.php,如下

<div class="container">
    {{--task list--}}
    <div class="panel panel-default">
        <div class="panel-heading">
            任务管理器
        div>
        <div class="panel-body">
            <button class="btn btn-primary" id="add">添加任务button>
        div>
        <table class="table table-striped">
            <thead>
            <tr>
                <th>idth>
                <th>Nameth>
                <th>Contentth>
                <th>Created_atth>
                <th>Actionth>
            tr>
            thead>
            <tbody id="task-list">
            @foreach($tasks as $task)
                <tr id="task{{ $task->id }}">
                    <td>{{ $task->id }}td>
                    <td>{{ $task->name }}td>
                    <td>{{ $task->content }}td>
                    <td>{{ $task->created_at }}td>
                    <td>
                        <button  class="btn btn-info edit" value="{{ $task->id }}">编辑button>
                        <button class="btn btn-warning delete" value="{{ $task->id }}">删除button>
                    td>
                tr>
            @endforeach
            tbody>
        table>
    div>
    {{--Modal--}}
    <div class="modal fade" id="taskModal" tabindex="-1" role="dialog">
        <div class="modal-dialog" role="document">
            <div class="modal-content">
                <div class="modal-header">
                    <button type="button" class="close" data-dismiss="modal"><span >×span>button>
                    <h4 class="modal-title" id="task-title">编辑任务h4>
                div>
                <div class="modal-body">
                    <form id="task">
                        <div class="form-group">
                            <label for="tname" class="control-label">Name:label>
                            <input id="tname" class="form-control" type="text">
                        div>
                        <div class="form-group">
                            <label for="tcontent" class="control-label">Content:label>
                            <textarea class="form-control" id="tcontent">textarea>
                        div>
                        {!! csrf_field() !!}
                    form>
                div>
                <div class="modal-footer">
                    <button type="button" id="tsave" class="btn btn-primary" value="update">提交button>
                    <input type="hidden" id="tid" name="tid" value="-1">
                div>
            div>
        div>
    div>

div>

中插入:

<script src="{{ asset('js/app.js') }}">script>

创建public/js/app.js

好了目前页面如图:
Laravel入门教程: 实现简单的AJAX的CRUD页面_第3张图片

增删查改CRUD

下面我们来实现核心功能:增删查改。

在实现之前,我们记得添加CSRF_TOKEN,不然ajax的时候会出现500错误。

编辑resources/welcome.blade.php,在

中添加如下代码:

...
    div>
    {!! csrf_field() !!}
form>
...

增加

Task控制器中添加函数:

public function store(Request $request) {
    $this->validate($request, [
        'name' => 'required',
        'content' => 'required'
    ]);
    $task = new Task();
    $task->name = $request->get('name');
    $task->content = $request->get('content');
    $task->save();
    return response()->json($task);
}

删除

Task控制器中增加函数:

public function destroy($id) {
    $task = Task::find($id);
    $task->delete();
    return response()->json(['success']);
}

查、改

Task控制器中增加函数:

public function show($id) {
    $task = Task::find($id);
    return response()->json($task);
}
public function update(Request $request, $id) {
    $this->validate($request, [
        'name' => 'required',
        'content' => 'required'
    ]);
    $task = Task::find($id);
    $task->name = $request->get('name');
    $task->content = $request->get('content');
    $task->save();
    return response()->json($task);
}

app.js

最后的public/js/app.js如下:

$(document).ready(function () {
    url = '/task/';
    $.ajaxSetup({
        headers: {
            'X-CSRF-TOKEN': $('#task input[name="_token"]').val()
        }
    });

    $('#add').click(function () {
        $('#task-title').text('添加任务');
        $('#tsave').val('add');
        $('#taskModal').modal('show');
    });

    $('body').on('click', 'button.delete', function() {
        var tid = $(this).val();
        $.ajax({
            type: 'DELETE',
            url: url+tid,
            success: function (data) {
                console.log(data);
                $('#task'+tid).remove();
                toastr.success('删除成功!');
            },
            error: function (data, json, errorThrown) {
                console.log(data);
                var errors = data.responseJSON;
                var errorsHtml= '';
                $.each( errors, function( key, value ) {
                    errorsHtml += '
  • ' + value[0] + '
  • '
    ; }); toastr.error( errorsHtml , "Error " + data.status +': '+ errorThrown); } }); }); $('body').on('click', 'button.edit', function() { $('#task-title').text('编辑任务'); $('#tsave').val('update'); var tid = $(this).val(); $('#tid').val(tid); $.get(url+tid, function (data) { console.log(url+tid); console.log(data); $('#tname').val(data.name); $('#tcontent').val(data.content); }); $('#taskModal').modal('show'); }); $('#tsave').click(function () { if($('#tsave').val() == 'add') { turl = url; var type = "POST"; // add } else { turl = url + $('#tid').val(); var type = "PUT"; // edit } var data = { name: $('#tname').val(), content: $('#tcontent').val() }; $.ajax({ type: type, url: turl, data: data, dataType: 'json', success: function (data) { console.log(data); $('#taskModal').modal('hide'); $('#task').trigger('reset'); var task = ''">' + ''+ data.id +'' + ''+ data.name +'' + ''+ data.content +'' + ''+ data.created_at +'' + ' '+ '' + ''; console.log(task); if(type == 'POST') { $('#task-list').append(task); toastr.success('添加成功!'); } else { // edit $('#task'+data.id).replaceWith(task); toastr.success('编辑成功!'); } }, error: function (data, json, errorThrown) { console.log(data); var errors = data.responseJSON; var errorsHtml= ''; $.each( errors, function( key, value ) { errorsHtml += '
  • ' + value[0] + '
  • '
    ; }); toastr.error( errorsHtml , "Error " + data.status +': '+ errorThrown); } }); }); });

    问题记录

    写这个教程遇到的问题也蛮大的,记录下来。

    路由问题

    之前路由是这样的:

    Route::resource('/', 'TaskController');

    但是会出现404问题,于是只好重定向到/task中,问题解决。

    Route::get('/', function () {
        return redirect('/task');
    });
    
    Route::resource('/task', 'TaskController');

    新元素事件绑定问题

    之前是这样绑定事件的:

    $('.delete').click(function () {
        ...
    }

    但是会出现增加记录,无法点击触发事件的问题,将事件绑定到body解决:

    $('body').on('click', 'button.delete', function() {
        ...
    }

    参考链接:Event binding on dynamically created elements?

    响应Json

    Laravel返回模型的时候默认以json方式返回,所以无需response()->json()

    你可能感兴趣的:(Web)