From 9ac46046cb1bfd320ffa7b1a2c049a1dfa4ebf83 Mon Sep 17 00:00:00 2001 From: sneak Date: Tue, 24 Mar 2020 13:32:35 -0700 Subject: [PATCH] initial, broken --- .drone.yml | 17 ++++++++++ .gitignore | 1 + Dockerfile | 24 ++++++++++++++ Makefile | 80 ++++++++++++++++++++++++++++++++++++++++++++++ _layouts/base.html | 74 ++++++++++++++++++++++++++++++++++++++++++ _pages/index.html | 1 + cmd/server/main.go | 14 ++++++++ go.mod | 14 ++++++++ go.sum | 80 ++++++++++++++++++++++++++++++++++++++++++++++ hn/handlers.go | 11 +++++++ hn/server.go | 65 +++++++++++++++++++++++++++++++++++++ hn/templates.go | 40 +++++++++++++++++++++++ 12 files changed, 421 insertions(+) create mode 100644 .drone.yml create mode 100644 Dockerfile create mode 100644 Makefile create mode 100644 _layouts/base.html create mode 100644 _pages/index.html create mode 100644 cmd/server/main.go create mode 100644 go.mod create mode 100644 go.sum create mode 100644 hn/handlers.go create mode 100644 hn/server.go create mode 100644 hn/templates.go diff --git a/.drone.yml b/.drone.yml new file mode 100644 index 0000000..a33bc95 --- /dev/null +++ b/.drone.yml @@ -0,0 +1,17 @@ +kind: pipeline +name: default + +steps: +- name: docker + image: plugins/docker + settings: + repo: sneak/hntransparency + dry_run: true + username: + from_secret: docker_username + password: + from_secret: docker_password + auto_tag: true + tags: + - ${DRONE_COMMIT_SHA} + - ${DRONE_BRANCH} diff --git a/.gitignore b/.gitignore index 9a3a8d8..5ad385c 100644 --- a/.gitignore +++ b/.gitignore @@ -12,3 +12,4 @@ # Output of the go coverage tool, specifically when used with LiteIDE *.out +server diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..d095398 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,24 @@ +FROM golang:1.13 as builder + +WORKDIR /go/src/git.eeqj.de/sneak/hntransparencylog +COPY . . + +#RUN make lint && make build +RUN make build + +WORKDIR /go +RUN tar cvfz go-src.tgz src && du -sh * + +# this container doesn't do anything except hold the build artifact +# and make sure it compiles. + +FROM alpine + +COPY --from=builder /go/src/git.eeqj.de/sneak/hntransparencylog/server /bin/server + +# put the source in there too for safekeeping +COPY --from=builder /go/go-src.tgz /usr/local/src/go-src.tgz + +CMD /bin/server + +# FIXME add testing diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..8c72eeb --- /dev/null +++ b/Makefile @@ -0,0 +1,80 @@ +VERSION := $(shell git rev-parse --short HEAD) +BUILDTIME := $(shell date -u '+%Y-%m-%dT%H:%M:%SZ') +BUILDTIMEFILENAME := $(shell date -u '+%Y%m%d-%H%M%SZ') +BUILDTIMETAG := $(shell date -u '+%Y%m%d%H%M%S') +BUILDUSER := $(shell whoami) +BUILDHOST := $(shell hostname -s) +BUILDARCH := $(shell uname -m) + +FN := server +IMAGENAME := sneak/hntransparencylog + +UNAME_S := $(shell uname -s) + +GOLDFLAGS += -X main.Version=$(VERSION) +GOLDFLAGS += -X main.Buildarch=$(BUILDARCH) + +# osx can't statically link apparently?! +ifeq ($(UNAME_S),Darwin) + GOFLAGS := -ldflags "$(GOLDFLAGS)" +endif + +ifneq ($(UNAME_S),Darwin) + GOFLAGS = -ldflags "-linkmode external -extldflags -static $(GOLDFLAGS)" +endif + +default: run + +debug: build + GOTRACEBACK=all DEBUG=1 ./$(FN) + +run: build + ./$(FN) + +clean: + -rm ./$(FN) + +build: ./$(FN) + +.lintsetup: + go get -v -u golang.org/x/lint/golint + go get -u github.com/GeertJohan/fgt + touch .lintsetup + +lint: fmt .lintsetup + fgt golint ./... + +go-get: + cd cmd/$(FN) && go get -v + +#./$(FN): */*.go cmd/*/*.go go-get +./$(FN): cmd/*/*.go go-get + cd cmd/$(FN) && go build -o ../../$(FN) $(GOFLAGS) . + +fmt: + gofmt -s -w . + +test: lint build-docker-image + +is_uncommitted: + git diff --exit-code >/dev/null 2>&1 + +build-docker-image: clean + docker build -t $(IMAGENAME) . + +build-docker-image-dist: is_uncommitted clean + docker build -t $(IMAGENAME):$(VERSION) -t $(IMAGENAME):latest -t $(IMAGENAME):$(BUILDTIMETAG) . + +dist: lint build-docker-image + -mkdir -p ./output + docker run --rm --entrypoint cat $(IMAGENAME) /bin/$(FN) > output/$(FN) + docker save $(IMAGENAME) | bzip2 > output/$(BUILDTIMEFILENAME).$(FN).tbz2 + +hub: upload-docker-image + +upload-docker-image: build-docker-image + docker push $(IMAGENAME):$(VERSION) + docker push $(IMAGENAME):$(BUILDTIMETAG) + docker push $(IMAGENAME):latest + +.PHONY: build fmt test is_uncommitted build-docker-image dist hub upload-docker-image clean run rundebug default build-docker-image-dist diff --git a/_layouts/base.html b/_layouts/base.html new file mode 100644 index 0000000..2b6825e --- /dev/null +++ b/_layouts/base.html @@ -0,0 +1,74 @@ + + + + + + + + + + + {{block "title" .}} + default title + {{end}} + + + + + + + + {{block "body" .}} + + + + +
+
+
+

A Bootstrap 4 Starter Template

+

Complete with pre-defined file paths and responsive navigation!

+
    +
  • Bootstrap 4.3.1
  • +
  • jQuery 3.4.1
  • +
+
+
+
+ {{end}} + + + + + + + + diff --git a/_pages/index.html b/_pages/index.html new file mode 100644 index 0000000..d61de61 --- /dev/null +++ b/_pages/index.html @@ -0,0 +1 @@ +indexpage diff --git a/cmd/server/main.go b/cmd/server/main.go new file mode 100644 index 0000000..2ebbfb4 --- /dev/null +++ b/cmd/server/main.go @@ -0,0 +1,14 @@ +package main + +import ( + "os" + + "git.eeqj.de/sneak/hntransparencylog/hn" +) + +var Version string +var Buildarch string + +func main() { + os.Exit(hn.RunServer(Version, Buildarch)) +} diff --git a/go.mod b/go.mod new file mode 100644 index 0000000..cb21b04 --- /dev/null +++ b/go.mod @@ -0,0 +1,14 @@ +module git.eeqj.de/sneak/hntransparencylog + +go 1.14 + +require ( + github.com/dgrijalva/jwt-go v3.2.0+incompatible // indirect + github.com/jinzhu/gorm v1.9.12 + github.com/labstack/echo v3.3.10+incompatible + github.com/labstack/echo/v4 v4.1.15 + github.com/labstack/gommon v0.3.0 + github.com/mattn/go-isatty v0.0.12 + github.com/rs/zerolog v1.18.0 + github.com/ziflex/lecho/v2 v2.0.0 +) diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..7d55488 --- /dev/null +++ b/go.sum @@ -0,0 +1,80 @@ +github.com/coreos/go-systemd v0.0.0-20190321100706-95778dfbb74e/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= +github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/denisenkom/go-mssqldb v0.0.0-20191124224453-732737034ffd/go.mod h1:xbL0rPBG9cCiLr28tMa8zpbdarY27NDyej4t/EjAShU= +github.com/dgrijalva/jwt-go v1.0.2 h1:KPldsxuKGsS2FPWsNeg9ZO18aCrGKujPoWXn2yo+KQM= +github.com/dgrijalva/jwt-go v3.2.0+incompatible h1:7qlOGliEKZXTDg6OTjfoBKDXWrumCAMpl/TFQ4/5kLM= +github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ= +github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0= +github.com/go-sql-driver/mysql v1.4.1/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= +github.com/golang-sql/civil v0.0.0-20190719163853-cb61b32ac6fe/go.mod h1:8vg3r2VgvsThLBIFL93Qb5yWzgyZWhEmBwUJWevAkK0= +github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= +github.com/jinzhu/gorm v1.9.12 h1:Drgk1clyWT9t9ERbzHza6Mj/8FY/CqMyVzOiHviMo6Q= +github.com/jinzhu/gorm v1.9.12/go.mod h1:vhTjlKSJUTWNtcbQtrMBFCxy7eXTzeCAzfL5fBZT/Qs= +github.com/jinzhu/inflection v1.0.0 h1:K317FqzuhWc8YvSVlFMCCUb36O/S9MCKRDI7QkRKD/E= +github.com/jinzhu/inflection v1.0.0/go.mod h1:h+uFLlag+Qp1Va5pdKtLDYj+kHp5pxUVkryuEj+Srlc= +github.com/jinzhu/now v1.0.1/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8= +github.com/labstack/echo v1.4.4 h1:1bEiBNeGSUKxcPDGfZ/7IgdhJJZx8wV/pICJh4W2NJI= +github.com/labstack/echo v3.3.10+incompatible h1:pGRcYk231ExFAyoAjAfD85kQzRJCRI8bbnE7CX5OEgg= +github.com/labstack/echo v3.3.10+incompatible/go.mod h1:0INS7j/VjnFxD4E2wkz67b8cVwCLbBmJyDaka6Cmk1s= +github.com/labstack/echo/v4 v4.1.10/go.mod h1:i541M3Fj6f76NZtHSj7TXnyM8n2gaodfvfxNnFqi74g= +github.com/labstack/echo/v4 v4.1.15 h1:4aE6KfJC+wCnMjODwcpeEGWGsRfszxZMwB3QVTECj2I= +github.com/labstack/echo/v4 v4.1.15/go.mod h1:GWO5IBVzI371K8XJe50CSvHjQCafK6cw8R/moLhEU6o= +github.com/labstack/gommon v0.3.0 h1:JEeO0bvc78PKdyHxloTKiF8BD5iGrH8T6MSeGvSgob0= +github.com/labstack/gommon v0.3.0/go.mod h1:MULnywXg0yavhxWKc+lOruYdAhDwPK9wf0OL7NoOu+k= +github.com/lib/pq v1.1.1/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= +github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= +github.com/mattn/go-colorable v0.1.6 h1:6Su7aK7lXmJ/U79bYtBjLNaha4Fs1Rg9plHpcH+vvnE= +github.com/mattn/go-colorable v0.1.6/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= +github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= +github.com/mattn/go-isatty v0.0.9/go.mod h1:YNRxwqDuOph6SZLI9vUUz6OYw3QyUt7WiY2yME+cCiQ= +github.com/mattn/go-isatty v0.0.12 h1:wuysRhFDzyxgEmMf5xjvJ2M9dZoWAXNNr5LSBS7uHXY= +github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= +github.com/mattn/go-sqlite3 v2.0.1+incompatible h1:xQ15muvnzGBHpIpdrNi1DA5x0+TcBZzsIDwmw9uTHzw= +github.com/mattn/go-sqlite3 v2.0.1+incompatible/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc= +github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/rs/xid v1.2.1/go.mod h1:+uKXf+4Djp6Md1KODXJxgGQPKngRmWyn10oCKFzNHOQ= +github.com/rs/zerolog v1.15.0/go.mod h1:xYTKnLHcpfU2225ny5qZjxnj9NvkumZYjJHlAThCjNc= +github.com/rs/zerolog v1.18.0 h1:CbAm3kP2Tptby1i9sYy2MGRg0uxIN9cyDb59Ys7W8z8= +github.com/rs/zerolog v1.18.0/go.mod h1:9nvC1axdVrAHcu/s9taAVfBuIdTZLVQmKQyvrUjF5+I= +github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= +github.com/valyala/bytebufferpool v1.0.0 h1:GqA5TC/0021Y/b9FG4Oi9Mr3q7XYx6KllzawFIhcdPw= +github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc= +github.com/valyala/fasttemplate v1.0.1/go.mod h1:UQGH1tvbgY+Nz5t2n7tXsz52dQxojPUpymEIMZ47gx8= +github.com/valyala/fasttemplate v1.1.0 h1:RZqt0yGBsps8NGvLSGW804QQqCUYYLsaOjTVHy1Ocw4= +github.com/valyala/fasttemplate v1.1.0/go.mod h1:UQGH1tvbgY+Nz5t2n7tXsz52dQxojPUpymEIMZ47gx8= +github.com/zenazn/goji v0.9.0/go.mod h1:7S9M489iMyHBNxwZnk9/EHS098H4/F6TATF2mIxtB1Q= +github.com/ziflex/lecho v1.2.0 h1:/ykfd7V/aTsWUYNFimgbdhUiEMnWzvNaCxtbM/LX5F8= +github.com/ziflex/lecho/v2 v2.0.0 h1:ggrWF5LaGAC+Y+WX71jFK7uYR7cUFbHjIgGqCyrYC5Q= +github.com/ziflex/lecho/v2 v2.0.0/go.mod h1:s7dy9Fynjx6z+/7xE2BsK13vXIS3oQoo4ZaKXYG5xUs= +golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20190701094942-4def268fd1a4/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20191205180655-e7c4368fe9dd/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200221231518-2aa609cf4a9d h1:1ZiEyfaQIg3Qh0EoqpwAakHVhecoE5wlSg5GjnafJGw= +golang.org/x/crypto v0.0.0-20200221231518-2aa609cf4a9d/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200226121028-0de0cce0169b h1:0mm1VjtFUOIlE1SbDlwjYaDxZVDP2S5ou6y0gSgXHu8= +golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190813064441-fde4db37ae7a/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200116001909-b77594299b42/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae h1:/WDfKMnPU+m5M4xB+6x4kaepxRw6jWvR5iDRdvjHgy8= +golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/text v0.3.2 h1:tW2bmiBqwgJj/UpqtC8EpXEZVYOwU0yG4iWbprSVAcs= +golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= +golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20190425163242-31fd60d6bfdc/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= +golang.org/x/tools v0.0.0-20190828213141-aed303cbaa74/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= diff --git a/hn/handlers.go b/hn/handlers.go new file mode 100644 index 0000000..42be59f --- /dev/null +++ b/hn/handlers.go @@ -0,0 +1,11 @@ +package hn + +import ( + "net/http" + + "github.com/labstack/echo" +) + +func indexHandler(c echo.Context) error { + return c.Render(http.StatusOK, "index", nil) +} diff --git a/hn/server.go b/hn/server.go new file mode 100644 index 0000000..eb47cff --- /dev/null +++ b/hn/server.go @@ -0,0 +1,65 @@ +package hn + +import ( + "os" + "time" + + "github.com/jinzhu/gorm" + _ "github.com/jinzhu/gorm/dialects/sqlite" + "github.com/labstack/echo" + "github.com/labstack/echo/middleware" + "github.com/labstack/gommon/log" + "github.com/ziflex/lecho/v2" +) + +// required for orm + +type App struct { + version string + buildarch string + e *echo.Echo + logger *string + db *gorm.DB + startup time.Time +} + +func RunServer(version string, buildarch string) int { + a := new(App) + a.version = version + a.buildarch = buildarch + a.startup = time.Now() + a.runForever() + return 0 +} + +func (a *App) runForever() { + + // Echo instance + a.e = echo.New() + + lev := log.INFO + if os.Getenv("DEBUG") != "" { + lev = log.DEBUG + } + + logger := lecho.New( + os.Stdout, + lecho.WithLevel(lev), + lecho.WithTimestamp(), + lecho.WithCaller(), + ) + a.e.Logger = logger + a.e.Use(middleware.RequestID()) + + // Middleware + a.e.Use(middleware.Logger()) + a.e.Use(middleware.Recover()) + + a.e.Renderer = NewTemplate("./view/") + + // Routes + a.e.GET("/", indexHandler) + + // Start server + a.e.Logger.Fatal(a.e.Start(":8080")) +} diff --git a/hn/templates.go b/hn/templates.go new file mode 100644 index 0000000..f4a304a --- /dev/null +++ b/hn/templates.go @@ -0,0 +1,40 @@ +package hn + +import ( + "errors" + "html/template" + "io" + + "github.com/labstack/echo" +) + +// Define the template registry struct +type TemplateRegistry struct { + templates map[string]*template.Template +} + +// Implement e.Renderer interface +func (t *TemplateRegistry) Render(w io.Writer, name string, data interface{}, c echo.Context) error { + tmpl, ok := t.templates[name] + if !ok { + err := errors.New("Template not found -> " + name) + return err + } + return tmpl.ExecuteTemplate(w, "base.html", data) +} + +func NewTemplate(templatesDir string) *TemplateRegistry { + //ext := ".html" + + ins := TemplateRegistry{ + templates: map[string]*template.Template{}, + } + + //layout := templatesDir + "base" + ext + + templates := make(map[string]*template.Template) + templates["index"] = template.Must(template.ParseFiles("_pages/index.html", "_layouts/base.html")) + //templates["about.html"] = template.Must(template.ParseFiles("view/about.html", "view/base.html")) + + return &ins +}