構造化されたWebサーバ
メイン
main.go
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 |
<span class="k">パッケージ</span> <span class="n">メイン</span> <span class="k">インポート</span> <span class="p">(</span> <span class="s">"html / template" </span> <span class="s">"io / ioutil" </span> <span class="s">"log" </span> <span class="s">"net / http" </span> <span class="p">)</span> <span class="k">タイプ</span> <span class="n">Page </span> <span class="k">struct </span> <span class="p">{ </span> <span class="n">Title </span> <span class="kt">string </span> <span class="n">Body </span> <span class="p">[] </span><span class="kt">byte </span> <span class="p">}</span> <span class="k">func </span> <span class="p">(</span><span class="n">p </span> <span class="o">* </span><span class="n">Page </span><span class="p">)</span> <span class="n">save </span><span class="p">()</span> <span class="kt">error </span> <span class="p">{ </span> <span class="n">filename </span> <span class="o">:= </span> <span class="n">p </span><span class="o">。</span><span class="n">タイトル</span> <span class="o">+ </span> <span class="s">".txt"は</span> <span class="n">ioutilを</span><span class="k">返し</span> <span class="n">ます</span><span class="o">。</span><span class="n">WriteFile </span><span class="p">(</span><span class="n">ファイル名</span><span class="p">、</span> <span class="n">p </span><span class="o">。</span><span class="n">本文</span><span class="p">、</span> <span class="m">0600 </span><span class="p">)</span> <span class="p">}</span> <span class="k">func </span> <span class="n">loadPage </span><span class="p">(</span><span class="n">title </span> <span class="kt">string </span><span class="p">)</span> <span class="p">(</span><span class="o">* </span><span class="n">Page </span><span class="p">、</span> <span class="kt">error </span><span class="p">)</span> <span class="p">{ </span> <span class="n">filename </span> <span class="o">:= </span> <span class="n">title </span> <span class="o">+ </span> <span class="s">".txt" </span> <span class="n">body </span><span class="p">、</span> <span class="n">err </span> <span class="o">:= </span> <span class="n">ioutil </span><span class="o">。</span><span class="n">ReadFile </span><span class="p">(</span><span class="n">filename </span><span class="p">)</span> <span class="k">if </span> <span class="n">err </span> <span class="o">!= </span> <span class="no">nil </span> <span class="p">{ </span> <span class="k">return </span> <span class="no">nil </span><span class="p">、</span> <span class="n">err </span> <span class="p">} </span> <span class="k">return </span> <span class="o">&</span><span class="n">Page </span><span class="p">{ </span><span class="n">Title </span><span class="o">:</span> <span class="n">title </span><span class="p">、</span> <span class="n">Body </span><span class="o">:</span> <span class="n">body </span><span class="p">}、</span> <span class="no">nil </span> <span class="p">}</span> <span class="c">// HTMLファイルのテンプレートを指定できる</span> <span class="c">//直接書いてもいいけれどソースがわかりにくくなる</span> <span class="k">FUNC </span> <span class="n">renderTemplate </span><span class="p">(</span><span class="n">ワット</span> <span class="n">のhttp </span><span class="o">。</span><span class="n">ResponseWriter </span><span class="p">、</span> <span class="n">TMPL </span> <span class="kt">文字列</span><span class="p">、</span> <span class="n">P </span> <span class="o">* </span><span class="n">ページ</span><span class="p">) </span> <span class="p">{ </span> <span class="c">//ローカルのHTMLファイルを指定</span> <span class="n">トン</span><span class="p">、</span> <span class="n">_ </span> <span class="o">: = </span> <span class="n">テンプレート</span><span class="o">。</span><span class="n">ParseFiles </span><span class="p">(</span><span class="n">TMPL </span> <span class="o">+ </span> <span class="s">".htmlを" </span><span class="p">)</span> <span class="n">トン</span><span class="o">。</span><span class="n">実行</span><span class="p">(</span><span class="n">w </span><span class="p">、</span> <span class="n">p </span><span class="p">)</span> <span class="p">}</span> <span class="k">FUNC </span> <span class="n">のViewHandler </span><span class="p">(</span><span class="n">W </span> <span class="n">HTTP </span><span class="o">。</span><span class="n">ResponseWriter </span><span class="p">、</span> <span class="n">R </span> <span class="o">* </span><span class="n">HTTP </span><span class="o">。</span><span class="n">リクエスト</span><span class="p">)</span> <span class="p">{ </span> <span class="n">タイトル</span> <span class="o">:= </span> <span class="n">R </span><span class="o">。</span><span class="n">URL </span><span class="o">。</span><span class="n">パス</span><span class="p">[ </span><span class="nb">len </span><span class="p">(</span><span class="s">"/ view /" </span><span class="p">)</span><span class="o">:</span><span class="p">] </span> <span class="n">p </span><span class="p">、</span> <span class="n">err </span> <span class="o">:= </span> <span class="n">loadPage </span><span class="p">(</span><span class="n">title </span><span class="p">)</span> <span class="c">// </span> <span class="k">もし</span> <span class="n">エラー</span> <span class="c">(ページがなかったら)editページへリダイレクトされる</span><span class="k">if </span><span class="n">err </span><span class="o">!= </span> <span class="no">nil </span> <span class="p">{ </span> <span class="n">http </span><span class="o">。</span><span class="n">リダイレクト</span><span class="p">(</span><span class="n">W </span><span class="p">、</span> <span class="n">R </span><span class="p">、</span> <span class="s">"/編集/" </span><span class="o">+ </span><span class="n">タイトル</span><span class="p">、</span> <span class="n">HTTP </span><span class="o">。</span><span class="n">StatusFound </span><span class="p">)</span> <span class="k">リターン</span> <span class="p">} </span> <span class="n">renderTemplate </span><span class="p">(</span><span class="n">W </span><span class="p">、</span> <span class="s">"ビュー" </span><span class="p">、</span> <span class="n">P </span><span class="p">)</span> <span class="p">}</span> <span class="k">FUNC </span> <span class="n">editHandler </span><span class="p">(</span><span class="n">W </span> <span class="n">HTTP </span><span class="o">。</span><span class="n">ResponseWriter </span><span class="p">、</span> <span class="n">R </span> <span class="o">* </span><span class="n">HTTP </span><span class="o">。</span><span class="n">リクエスト</span><span class="p">)</span> <span class="p">{ </span> <span class="n">タイトル</span> <span class="o">:= </span> <span class="n">R </span><span class="o">。</span><span class="n">URL </span><span class="o">。</span><span class="n">Path </span><span class="p">[ </span><span class="nb">len </span><span class="p">(</span><span class="s">"/ edit /" </span><span class="p">)</span><span class="o">:</span><span class="p">] </span> <span class="n">p </span><span class="p">、</span> <span class="n">err </span> <span class="o">:= </span> <span class="n">loadPage </span><span class="p">(</span><span class="n">title </span><span class="p">)</span> <span class="k">if </span> <span class="n">err </span> <span class="o">!= </span> <span class="no">nil </span> <span class="p">{ </span> <span class="n">p </span> <span class="o">= </span> <span class="o">&</span><span class="n">Page </span><span class="p">{ </span><span class="n">Title </span><span class="o">:</span> <span class="n">title </span><span class="p">} </span> <span class="p">} </span> <span class="n">renderTemplate </span><span class="p">(</span><span class="n">w </span><span class="p">、</span> <span class="s">「編集」</span><span class="p">、</span> <span class="n">p </span><span class="p">)</span> <span class="p">}</span> <span class="k">FUNC </span> <span class="n">saveHandler </span><span class="p">(</span><span class="n">W </span> <span class="n">HTTP </span><span class="o">。</span><span class="n">ResponseWriter </span><span class="p">、</span> <span class="n">R </span> <span class="o">* </span><span class="n">HTTP </span><span class="o">。</span><span class="n">リクエスト</span><span class="p">)</span> <span class="p">{ </span> <span class="n">タイトル</span> <span class="o">:= </span> <span class="n">R </span><span class="o">。</span><span class="n">URL </span><span class="o">。</span><span class="n">パス</span><span class="p">[ </span><span class="nb">len </span><span class="p">(</span><span class="s">"/ save /" </span><span class="p">)</span><span class="o">:</span><span class="p">] </span> <span class="n">body </span> <span class="o">:= </span> <span class="n">r </span><span class="o">。</span><span class="n">FormValue </span><span class="p">(</span><span class="s">"body" </span><span class="p">)</span> <span class="n">p </span> <span class="o">:= </span> <span class="o">&</span><span class="n">Page </span><span class="p">{ </span><span class="n">Title </span><span class="o">:</span> <span class="n">title </span><span class="p">、</span> <span class="n">Body </span><span class="o">:</span> <span class="p">[] </span><span class="kt">byte </span><span class="p">(</span><span class="n">body </span><span class="p">)} </span> <span class="n">err</span> <span class="o">:= </span> <span class="n">p </span><span class="o">。</span><span class="n">save </span><span class="p">()</span> <span class="c">// saveに失敗したら、500 </span> <span class="n">エラー</span><span class="k">if </span> <span class="n">err </span> <span class="o">!= </span> <span class="no">nil </span> <span class="p">{ </span> <span class="n">http </span><span class="o">。</span><span class="n">エラー</span><span class="p">(</span><span class="n">W </span><span class="p">、</span> <span class="n">ERR </span><span class="o">。</span><span class="n">エラー</span><span class="p">()、</span> <span class="n">HTTP </span><span class="o">。</span><span class="n">StatusInternalServerError </span><span class="p">)</span> <span class="k">リターン</span> <span class="p">} </span> <span class="n">HTTP </span><span class="o">。</span><span class="n">リダイレクト</span><span class="p">(</span><span class="n">W </span><span class="p">、</span> <span class="n">R </span><span class="p">、</span> <span class="s">"/ビュー/" </span><span class="o">+ </span><span class="n">タイトル</span><span class="p">、</span> <span class="n">HTTP </span><span class="o">。</span><span class="n">StatusFound </span><span class="p">)</span> <span class="p">}</span> <span class="k">func </span> <span class="n">main </span><span class="p">()</span> <span class="p">{ </span> <span class="n">http </span><span class="o">。</span><span class="n">HandleFunc </span><span class="p">(</span><span class="s">"/ view /" </span><span class="p">、</span> <span class="n">viewHandler </span><span class="p">)</span> <span class="n">http </span><span class="o">。</span><span class="n">HandleFunc </span><span class="p">(</span><span class="s">"/ edit /" </span><span class="p">、</span> <span class="n">editHandler </span><span class="p">)</span> <span class="n">http </span><span class="o">。</span><span class="n">HandleFunc </span><span class="p">(</span><span class="s">"/ save /" </span><span class="p">、</span> <span class="n">saveHandler </span><span class="p">)</span> <span class="c">// /に</span> <span class="n">アクセスしたり</span><span class="c">/ view以外にアクセスすると404NOTFOUND </span><span class="n">log </span><span class="o">。</span><span class="n">致命的</span><span class="p">(</span><span class="n">HTTP </span><span class="o">。 </span><span class="n">ListenAndServe </span><span class="p">(</span><span class="s">":8080" </span><span class="p">、</span> <span class="no">nilの</span><span class="p">))</span> <span class="p">} </span> |
/ editとなるhtmlファイル
edit.html
1 2 3 4 5 6 7 8 9 10 11 |
<span class="nt"><h1></span> {{.Title}}を編集しています<span class="nt"></ h1></span> <span class="nt"><form </span> <span class="na">action = </span><span class="s">"/save/{{.Title}}" </span> <span class="na">method = </span><span class="s">"POST" </span><span class="nt">> </span> <span class="nt"><div> </span> <span class="nt"><textarea </span> <span class="na">name = </span><span class="s">"body" </span> <span class="na">rows = </span><span class="s">"20" </span> <span class="na">cols = </span><span class="s">"80" </span><span class="nt">></span> {{printf "%s"。本文}} <span class="nt"></ textarea> </span> <span class="nt"></ div> </span> <span class="nt"><div> </span> <span class="nt"><input </span> <span class="na">type = </span><span class="s">"submit" </span> <span class="na">value = </span><span class="s">"Save" </span><span class="nt">> </span> <span class="nt"></ div> </span> <span class="nt"></ form></span> |
/ viewとなるhmtlファイル
view.html
1 2 3 4 5 |
<span class="nt"><h1></span> {{.Title}} <span class="nt"></ h1></span> <span class="nt"><P></span> [ <span class="nt"><a </span> <span class="na">href= </span><span class="nt">"/edit/{{.Title}}"></span>編集<span class="nt">する</a></span> ] <span class="nt"></ P></span> <span class="nt"><div></span> {{printf "%s" .Body}} <span class="nt"></ div></span> |
動作確認
editページでhtmlファイル生成
/ viewが一覧ページ
/ view / test1などでアクセス
https://www.udemy.com/course/go-fintech/learn/lecture/12088980