beego開發輕部落格——第七講 文章的顯示、修改與刪除
【小雞創作】beego開發輕部落格
本章目標:新增“文章的顯示、修改與刪除”功能
github: 開啟後,點選右上角star按鈕
視訊教程: B站地址
文章顯示
1. 功能分析
文章的顯示功能,首先我們需要新增路由,約定文章顯示的路由路徑為"/details/[文章的key]",再新增路由對應的控制器,我們需要根據key查詢到文章的記錄,返回給頁面。
根據文字的key查詢文章的資料庫方法,我們之前在新增文章的時候已經新增。
2. 控制器邏輯調整
2.1 修改controllers->index.go新增GetDetails,查詢文章資訊返回給頁面,程式碼如下(請留意程式碼中的註解,都是邏輯說明):
//@router /details/:key [get] func (this *IndexController) GetDetails() { //得到頁面傳過來的文章的key key:= this.Ctx.Input.Param(":key") //到資料庫中根據key查詢文章 note,err:=models.QueryNoteByKey(key) if err!=nil{ //查詢有問題,就提示頁面文章不存在 this.Abort500(syserror.New("文章不存在",err)) } //將文章的資訊放回給頁面 this.Data["note"] = note this.TplName="details.html" }
3. 前臺頁面調整
3.1 我們修改views->index.html 頁面,修改跳轉文章詳情的連結,改成我們定義好的路由路徑。修改程式碼如下
... <div class="item-boxlayer-photos-demo1 layer-photos-demo"> <!-- 此處拼寫 文章詳情路由路徑 --> <h3><a href="details/{{.Key}}">{{.Title}}</a></h3> <h5>釋出於:<span>{{date .UpdatedAt "Y-m-d H:i:s"}}</span></h5> ...
3.1 我們修改views->index.html 頁面,將文章摘要資訊顯示的部分抽取出來儲存為模版,並且新增檔案views->comm->note_summary_tpl.html。
3.1.1 views->index.html 修改程式碼如下
{{ range .notes}} <div class="item"> {{template "comm/note_summary_tpl.html" .}} <div class="comment count"> ... </div> {{end}}
3.1.2 views->comm->note_summary_tpl.html修改程式碼如下
<div class="item-boxlayer-photos-demo1 layer-photos-demo"> <h3><a href="details/{{.Key}}">{{.Title}}</a></h3> <h5>釋出於:<span>{{date .UpdatedAt "Y-m-d H:i:s"}}</span></h5> <p>{{.Summary}}</p> </div>
3.2 我們複製檔案views->comm->note_summary_tpl.html儲存為views->comm->note_tpl.html修改其中的程式碼將顯示文章摘要改成顯示文章的內容,修改程式碼如下
... <!--原始碼是:<p>{{.Summary}}</p>--> <!--go的html模版輸出預設是對html標籤轉義的--> <!--str2html是beego提供的方法,可以將字串直接輸出不轉義--> <p>{{str2html .Content}}</p> ...
3.3 我們修改views->details.html 頁面,嵌入views->comm->note_tpl.html模版頁面,顯示文章內容,修改程式碼如下
... <div class="item-boxlayer-photos-demo1 layer-photos-demo"> <!--此處為修改--> <!--請注意 後面傳的是.note作為通道傳給模版--> {{template "comm/note_tpl.html" .note }} <div class="count layui-clear"> ...
文章的顯示功能已經實現
文章修改
1. 功能分析
1、我們需要給文章修改功能新增操作入口,我們使用layui提供的fixbar作為操作按鈕。
2、頁面需要的資料:我們要判斷使用者是否登陸,使用者是否有修改文章的許可權,同時我們也有判斷當前的使用者id是否和當前文章所屬使用者的id相等,只有滿足這些條件才能對文章進行修改和刪除的操作。修改文章時我們需要帶入文章的key。因此我們要拿到當前登陸的使用者的資訊,還要拿到當前文章詳情頁面的文章的所屬使用者的id和文章的key值。
3、頁面要拿到當前登陸的使用者的資訊,我們要將使用者資訊儲存到html頁面中型別為json物件的user變數。為了得到user的json物件,我們需要定義“gorm定義表結構的結構體”的json輸出的格式。
4、我們定義修改文章的路由路徑為:/edit/[當前文章的key],然後路由對應的控制器方法的邏輯是:根據key和當前登陸的使用者找到文章資料(這兒我們需要新增資料庫方法),指定渲染模版note_new.html,修改note_new.html,使其能夠顯示文章具體資訊。而note_new.html模版,在文章新增的時候,我們就已經支援文章修改的功能,我們只需修改文章儲存的控制器方法,新增儲存後返回的跳轉頁面路徑,跳轉到文章詳情頁面。
2. 資料庫邏輯調整
2.1 新增根據使用者id和文章的key查詢文章的方法,修改models->note.go檔案,新增QueryNoteByKeyAndUserId方法,程式碼如下:
func QueryNoteByKeyAndUserId(key string, userid int) (note Note, err error) { return note, db.Where("key = ? and user_id = ? ", key, userid).Take(¬e).Error }
2.2 目前定義資料庫表結構的結構體都是繼承gorm自帶的model結構體,而gorm的model的結構體,沒法重新定義json輸出的格式,因此,我們重新定義model的結構體並定義json的格式。修改models->core.go檔案,新增程式碼如下
// `json:"name"` 這句是定義json輸出的格式 type Model struct { IDuint `gorm:"primary_key" json:"id"` CreatedAt time.Time `json:"created_at"` UpdatedAt time.Time `json:"updated_at"` DeletedAt *time.Time `sql:"index" json:"deleted_at"` }
2.3 修改models->note.go,修改程式碼如下
type Note struct { Model//這兒的Model是我們上面定義的Model不是gorm.Model ... }
2.4 修改models->user.go,優化使用者結構體的json輸出的格式,修改程式碼如下
type User struct { Model //這兒的Model是我們上面定義的Model不是gorm.Model Name string `gorm:"unique_index" json:"name"` Email string `gorm:"unique_index" json:"email"` Pwd string `json:"-"`//“-” 代表不輸出,密碼不能輸出到頁面。 Avatar string `json:"avatar"` Role int`json:"role"` }
3. 控制器邏輯調整
3.1 新增編輯頁面的路由/edit/:key,新增控制器邏輯:查詢文章並顯示文章修改頁面。修改controllers->note.go檔案,新增如下程式碼:
// @router /edit/:key [get] func (this *NoteController) EditPage() { // 獲取頁面傳過來key key := this.Ctx.Input.Param(":key") //根據當前文章的key和登陸使用者id查詢出,文章資訊。 note, err := models.QueryNoteByKeyAndUserId(key, int(this.User.ID)) if err != nil { //查詢有問題,就提示文章不存在。 this.Abort500(syserror.New("文章不存在!", err)) } //將文章的資訊以及key傳到頁面。 this.Data["note"] = note this.Data["key"] = key //"note_new.html" 是文章新增的頁面,之前實現文章新增功能的時候 this.TplName = "note_new.html" }
3.2 修改文章儲存的控制器邏輯,讓頁面儲存成功後跳轉頁面到文章詳情頁面。修改controllers->note.go中的Save方法。
// @router /save/:key [post] func (this *NoteController) Save() { ... //原始碼:this.JSONOkH("儲存成功", H{}) this.JSONOk("儲存成功", fmt.Sprintf("/details/%s", key)) }
4. 前臺頁面調整
4.1 在文章詳情頁面中,我們將當前登陸的使用者資訊,文章的使用者所屬id,以及文章的key,儲存到js變數中。修改views->details.html頁面新增如下程式碼
<script> var user = {{.User}};//這兒輸出直接就是json物件 //這兒將文章的資訊拼成json物件賦值給note變數 var note = { userid:{{.note.UserID}},key:{{.note.Key}} }; </script>
4.2 在文章詳情頁面新增修改和刪除的操作按鈕,我們採用layui提供的fixbar控制元件,同時我們根據當前登陸的使用者和當前文章詳情頁的文章的所屬使用者來判斷是否顯示按鈕,修改views->details.html頁面新增如下程式碼
<script> ... layui.use(['util','jquery'], function(){ var util = layui.util,$= layui.jquery; //使用者必須登陸, //登陸的使用者的role必須為0,可以修改文章 //登陸的使用者的id,必須等於當前文章詳情頁的文章所屬使用者的id if(user&& user.id >0&&user.role===0&&user.id ===note.userid){ util.fixbar({ bar1: '',//編輯的圖示 bar2:''//刪除的圖示 ,click: function(type){ console.log(type); if(type === 'bar1'){ //跳轉到修改文章的頁面 window.location.href="/note/edit/"+note.key } if(type === 'bar2'){ //刪除的邏輯,等待實現。 } } }); } }); </script>
4.3 文章修改的頁面views-note_new.html頁面,雖然之前實現了修改文章的功能。頁面模版沒有根據傳過來的文章內容來填充文章的內容。我們修改views-note_new.html 修改程式碼如下
... <form class="layui-form layui-form-pane" action=""> ... <!--{{/* 修改程式碼為: value="{{.note.Title}}" */}}--> <div class="layui-input-block"> <input type="text" name="title" required="" value="{{.note.Title}}" lay-verify="required" placeholder="請輸入標題" autocomplete="off" class="layui-input"> ... <!--{{/* 修改程式碼為: {{if .note}}{{str2html .note.Content}}{{end}} */}}--> <div id="edit" style="background: #fff;"> {{if .note}}{{str2html .note.Content}}{{end}} </div> </div> </div> ... </form>
文章修改功能已經實現
文章刪除
1. 功能分析
我們需要定義文章刪除功能的路由定義:/del/[文章的key] 為post請求。我們要新增根據使用者id和文章的key去刪除文章的資料庫方法。再新增路由對應的控制器邏輯,呼叫刪除文章的資料庫方法來刪除文章。修改文章詳情頁面,當點選刪除按鈕的時候,後臺傳送post請求,成功提示刪除成功,頁面跳轉到首頁。失敗就提示刪除失敗。
2. 資料庫邏輯調整
2.1 修改models-note.go檔案,我們新增根據使用者id和文章的key,刪除文章的方法,程式碼如下
func DeleteNoteByUserIdAndKey(key string, userid int) error { return db.Delete(&Note{}, "key = ? and user_id = ?", key, userid).Error }
3. 控制器邏輯調整
3.1 修改controllers-note.go檔案,新增根據傳過來的key和當前登陸的使用者id 去呼叫刪除文章的控制器方法,程式碼如下
// @router /del/:key [post] func (this *NoteController) Del() { //獲取頁面傳過來的key值 key := this.Ctx.Input.Param(":key") //呼叫資料庫方法刪除文章 if err := models.DeleteNoteByUserIdAndKey(key, int(this.User.ID)); err != nil { //刪除失敗,提示頁面刪除失敗 this.Abort500(syserror.New("刪除失敗", err)) } //返回刪除成功,並跳轉到首頁 this.JSONOk("刪除成功", "/") }
4. 前臺頁面調整
4.1 修改views->details.html檔案,新增向後臺傳送刪除文章的請求的邏輯,新增程式碼如下
layui.use(['util','jquery'], function(){ ... if(type === 'bar2'){ $.post("/note/del/"+note.key,function (data) { if (data.code === 0) { layer.msg("刪除成功"); if (data.action) { setTimeout(function () { window.location.href = data.action; }, 300); } } else { layer.msg("刪除失敗:" + data.msg); } }, "json").error(function () { layer.msg("網路異常") }); } ... });
文章刪除的功能已經實現。
這兒可以考慮優化一下刪除文章的時候提示是否刪除
貼個頁面效果圖

文章顯示效果圖