Генератор готов. Начал писать поиск.
parent
88ac87b090
commit
42989eb601
|
@ -10,6 +10,7 @@ import (
|
|||
"github.com/tiburon-777/OTUS_HighLoad/internal/application"
|
||||
"github.com/tiburon-777/OTUS_HighLoad/internal/auth"
|
||||
"github.com/tiburon-777/OTUS_HighLoad/internal/handlers"
|
||||
"github.com/tiburon-777/OTUS_HighLoad/pkg/dataset"
|
||||
"log"
|
||||
"net"
|
||||
"net/http"
|
||||
|
@ -28,6 +29,7 @@ func main() {
|
|||
if err != nil {
|
||||
log.Fatal(fmt.Errorf("can't build app: %w", err).Error())
|
||||
}
|
||||
go dataset.FillDB(app.DB, 1000000)
|
||||
|
||||
m.Map(log.New(os.Stdout, "[app]", log.Lshortfile))
|
||||
m.Map(app)
|
||||
|
@ -66,6 +68,9 @@ func main() {
|
|||
|
||||
m.Get("/list", auth.LoginRequired, handlers.GetUserList)
|
||||
|
||||
m.Get("/search", auth.LoginRequired, handlers.GetSearch)
|
||||
m.Post("/search", auth.LoginRequired, handlers.PostSearch)
|
||||
|
||||
m.NotFound(func(r render.Render) {
|
||||
r.HTML(404, "404", nil)
|
||||
})
|
||||
|
|
2
go.mod
2
go.mod
|
@ -9,6 +9,8 @@ require (
|
|||
github.com/go-sql-driver/mysql v1.5.0
|
||||
github.com/gorilla/context v1.1.1 // indirect
|
||||
github.com/gorilla/sessions v1.2.1 // indirect
|
||||
github.com/mdigger/translit v0.0.0-20190913173519-84222363843c
|
||||
github.com/tiburon-777/modules v0.0.0-20201210103219-a0362a8da783
|
||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9
|
||||
golang.org/x/exp v0.0.0-20201229011636-eab1b5eb1a03 // indirect
|
||||
)
|
||||
|
|
28
go.sum
28
go.sum
|
@ -1,5 +1,7 @@
|
|||
dmitri.shuralyov.com/gpu/mtl v0.0.0-20201218220906-28db891af037/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU=
|
||||
github.com/BurntSushi/toml v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
|
||||
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
|
||||
github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo=
|
||||
github.com/DATA-DOG/go-sqlmock v1.5.0 h1:Shsta01QNfFxHCfpW6YH2STWB0MudeXXEWMr20OEh60=
|
||||
github.com/DATA-DOG/go-sqlmock v1.5.0/go.mod h1:f/Ixk793poVmq4qj/V1dPUg2JEAKC73Q5eFN3EC/SaM=
|
||||
github.com/amitrai48/logger v0.0.0-20190214092904-448001c055ec/go.mod h1:RZEHP3cxXvQlMuMjkpdh6qXA4b0CpjxnUBNxOpR0r30=
|
||||
|
@ -12,6 +14,7 @@ github.com/codegangsta/martini-contrib v0.0.0-20140208234550-8ce6181c2609/go.mod
|
|||
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
|
||||
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8=
|
||||
github.com/go-sql-driver/mysql v1.5.0 h1:ozyZYNQW3x3HtqT1jira07DN2PArx2v7/mN66gGcHOs=
|
||||
github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
|
||||
github.com/gorilla/context v1.1.1 h1:AWwleXJkX/nhcU9bZSnZoi3h/qGYqQAGhq6zZe/aQW8=
|
||||
|
@ -23,6 +26,8 @@ github.com/gorilla/sessions v1.2.1/go.mod h1:dk2InVEVJ0sfLlnXv9EAgkf6ecYs/i80K/z
|
|||
github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
|
||||
github.com/lib/pq v1.9.0 h1:L8nSXQQzAYByakOFMTwpjRoHsMJklur4Gi59b6VivR8=
|
||||
github.com/lib/pq v1.9.0/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o=
|
||||
github.com/mdigger/translit v0.0.0-20190913173519-84222363843c h1:Bj5jKnXdlMMV4r1Dt1ivUhNoO1KoIAszisMGn3WaOBQ=
|
||||
github.com/mdigger/translit v0.0.0-20190913173519-84222363843c/go.mod h1:HlwkSjmUw4wUp9tJkwrQFI9EDmGdEUOLlwymW1OQErM=
|
||||
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
||||
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
|
||||
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||
|
@ -39,14 +44,37 @@ go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/
|
|||
go.uber.org/zap v1.9.1/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q=
|
||||
golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
||||
golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9 h1:psW17arqaxU48Z5kZ0CQnkZWQJsqcURM6tKiBApRjXI=
|
||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||
golang.org/x/exp v0.0.0-20190731235908-ec7cb31e5a56/go.mod h1:JhuoJpWY28nO4Vef9tZUw9qufEGTyX1+7lmHxV5q5G4=
|
||||
golang.org/x/exp v0.0.0-20201229011636-eab1b5eb1a03 h1:XlAInxBYX5nBofPaY51uv/x9xmRgZGr/lDOsePd2AcE=
|
||||
golang.org/x/exp v0.0.0-20201229011636-eab1b5eb1a03/go.mod h1:I6l2HNBLBZEcrOoCpyKLdY2lHoRZ8lI4x60KMCQDft4=
|
||||
golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js=
|
||||
golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
|
||||
golang.org/x/mobile v0.0.0-20190312151609-d3739f865fa6/go.mod h1:z+o9i4GpDbdi3rU15maQ/Ox0txvL9dWGYEHz965HBQE=
|
||||
golang.org/x/mobile v0.0.0-20201217150744-e6ae53a27f4f/go.mod h1:skQtrUTUwhdJvXM/2KKJzY8pDgNr9I/FOMqDVRPBUS4=
|
||||
golang.org/x/mod v0.1.0/go.mod h1:0QHyrYULN0/3qlju5TqG8bIK38QM8yzMo5ekMj3DlcY=
|
||||
golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg=
|
||||
golang.org/x/mod v0.1.1-0.20191209134235-331c550502dd/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/mod v0.3.1-0.20200828183125-ce943fd02449/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
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/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/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-20191001151750-bb3f8db39f24/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||
golang.org/x/tools v0.0.0-20190312151545-0bb0c0a6e846/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
|
||||
golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
|
||||
golang.org/x/tools v0.0.0-20200117012304-6edc0a871e69/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28=
|
||||
golang.org/x/tools v0.0.0-20200207183749-b753a1ba74fa/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28=
|
||||
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
|
||||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/natefinch/lumberjack.v2 v2.0.0 h1:1Lc07Kr7qY4U2YPouBjpCLxpiyxIVoxqXgkXLknAOE8=
|
||||
|
|
|
@ -26,9 +26,6 @@ func New(configFile, envPrefix string) (App, error) {
|
|||
if err = dbInit(db); err != nil {
|
||||
return App{}, err
|
||||
}
|
||||
if err = dbFill(db); err != nil {
|
||||
return App{}, err
|
||||
}
|
||||
return App{Config: conf, DB: db}, nil
|
||||
}
|
||||
|
||||
|
@ -75,10 +72,3 @@ func dbInit(db *sql.DB) error {
|
|||
log.Println("All tables exists")
|
||||
return nil
|
||||
}
|
||||
|
||||
func dbFill(db *sql.DB) error {
|
||||
log.Println("Try to generate rows and fill the DB...")
|
||||
|
||||
log.Println("All tables exists")
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -200,6 +200,14 @@ func GetUnSubscribe(app application.App, r render.Render, user auth.User, req *h
|
|||
|
||||
}
|
||||
|
||||
func GetSearch(r render.Render) {
|
||||
r.HTML(200, "search", nil)
|
||||
}
|
||||
|
||||
func PostSearch() {
|
||||
|
||||
}
|
||||
|
||||
func str2Time(s string, r render.Render) time.Time {
|
||||
t, err := time.Parse("2006-01-02 15:04:05", s)
|
||||
if err != nil {
|
||||
|
|
|
@ -0,0 +1,69 @@
|
|||
package dataset
|
||||
|
||||
import (
|
||||
"database/sql"
|
||||
"github.com/mdigger/translit"
|
||||
"log"
|
||||
"math/rand"
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
type Person struct {
|
||||
FirstName string
|
||||
SecondName string
|
||||
Password string
|
||||
BirthDate time.Time
|
||||
Gender string
|
||||
City string
|
||||
Interests []string
|
||||
}
|
||||
|
||||
func NewPerson() (p Person) {
|
||||
rand.Seed(time.Now().UnixNano())
|
||||
p.Gender=genders[rand.Intn(len(genders))]
|
||||
if p.Gender=="male" {
|
||||
p.FirstName=manNames[rand.Intn(len(manNames))]
|
||||
p.SecondName=secondNames[rand.Intn(len(secondNames))]
|
||||
} else {
|
||||
p.FirstName=womanNames[rand.Intn(len(womanNames))]
|
||||
p.SecondName=secondNames[rand.Intn(len(secondNames))]+"а"
|
||||
}
|
||||
t := make([]byte,16); rand.Read(t)
|
||||
p.Password=string(t)
|
||||
p.City=cities[rand.Intn(len(cities))]
|
||||
for i:=0;i<(rand.Intn(4)+3);i++ {
|
||||
p.Interests=append(p.Interests,interests[rand.Intn(len(interests))])
|
||||
}
|
||||
s,_ := time.ParseDuration(strconv.Itoa(rand.Intn(700000))+"h")
|
||||
p.BirthDate = time.Now().Add(-s)
|
||||
return
|
||||
}
|
||||
|
||||
func FillDB(db *sql.DB, lim int) {
|
||||
log.Println("Try to drop table USERS...")
|
||||
if _, err := db.Exec(`DELETE FROM users`); err != nil {
|
||||
log.Fatalf("can't exec query: %s", err.Error())
|
||||
}
|
||||
log.Printf("Try to generate %d rows and fill the DB...", lim)
|
||||
for i:=1;i<lim;i++{
|
||||
if i%100==0 {
|
||||
log.Printf("Successfully inserted %d rows", i)
|
||||
}
|
||||
p := NewPerson()
|
||||
if _, err := db.Exec(`INSERT INTO users ( Username, Password, Name, Surname, BirthDate, Gender, City, Interests ) values (?, ?, ?, ?, ?, ?, ?, ?)`,
|
||||
translit.Ru(p.FirstName)+strconv.Itoa(i),
|
||||
p.Password,
|
||||
p.FirstName,
|
||||
p.SecondName,
|
||||
p.BirthDate.Format("2006-01-02 15:04:05"),
|
||||
p.Gender,
|
||||
p.City,
|
||||
strings.Join(p.Interests, ","),
|
||||
); err != nil {
|
||||
log.Fatalf("can't insert row in DB. Inserted %d rows of %d", i, lim)
|
||||
}
|
||||
}
|
||||
log.Println("Table USERS filled successfully")
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package application
|
||||
package dataset
|
||||
|
||||
var genders = []string{"male", "female"}
|
||||
var manNames = []string{"Борей", "Будимир", "Бронислав", "Бажен", "Бонифаций", "Богдан", "Бенедикт", "Борислав", "Болеслав", "Боголюб", "Бартоломей", "Боеслав", "Берек", "Борис", "Боримир", "Бернар", "Боян", "Виталий", "Валентин", "Влас", "Варлаам", "Вениамин", "Владислав", "Владилен", "Всеволод", "Владимир", "Викторин", "Викентий", "Вадим", "Всеслав", "Велимир", "Всемил", "Валерий", "Варфоломей", "Виктор", "Валерьян", "Виссарион", "Василий", "Вячеслав", "Вышеслав", "Варлам", "Венедикт", "Владлен", "Василиск", "Глеб", "Георгий", "Гавриил", "Гедеон", "Герасим", "Герман", "Геннадий", "Гремислав", "Гаврила", "Григорий", "Георгий", "Гостомысл", "Гурий", "Галактион", "Гордей", "Добромысл", "Денис", "Демьян", "Дементий", "Данила", "Дорофей", "Дмитрий", "Демид", "Давыд", "Давыд", "Доброслав", "Давид", "Даниил", "Даниил", "Евграф", "Елизар", "Евстигней", "Евлампий", "Евсей", "Емельян", "Елисей", "Ермолай", "Ефрем", "Ефим", "Евдоким", "Евгений", "Егор", "Ермил", "Еремей", "Ерофей", "Евстафий", "Епифан", "Исаакий", "Иннокентий", "Игорь", "Исаак", "Иван", "Ипполит", "Измаил", "Исай", "Илларион", "Исидор", "Илья", "Ираклий", "Игнат", "Иларион", "Изот", "Иосиф", "Ипат", "Изяслав", "Игнатий", "Ипатий", "Иосиф", "Карл", "Кузьма", "Кирилл", "Кеша", "Карим", "Кирсан", "Касьян", "Кастор", "Корнелий", "Каюм", "Клим", "Кондрат", "Касим", "Корней", "Камалл", "Кристиан", "Косьма", "Лонгин", "Лавр", "Лукьян", "Лев", "Лаврентий", "Леон", "Любомир", "Лазарь", "Леонтий", "Лучезар", "Ладимир", "Лука", "Любим", "Леонид", "Любомысл", "Мефодий", "Мирон", "Милий", "Мартин", "Мариан", "Моисей", "Митрофан", "Мирослав", "Милан", "Макар", "Модест", "Михаил", "Максимилиан", "Мартын", "Мануил", "Максимильян", "Матвей", "Мир", "Максим", "Мокей", "Мина", "Мартьян", "Марк", "Михей", "Мстислав", "Милен", "Мечислав", "Никандр", "Наркис", "Натан", "Никифор", "Назар", "Наум", "Никола", "Николай", "Нестер", "Нил", "Никита", "Никодим", "Нестор", "Никанор", "Нифонт Никон", "Олег", "Олимп", "Онисим", "Остромир Октавиан", "Оскар", "Одиссей", "Онуфрий", "Осип", "Остап", "Октябрь", "Панкратий", "Петр", "Панфил", "Прокл", "Пантелеймон", "Прохор", "Прокофий", "Порфирий", "Панкрат", "Павел", "Пров", "Парфен", "Пахом", "Поликарп", "Прокопий", "Парфений", "Прокоп", "Парамон", "Потап", "Платон", "Пантелей", "Пимен", "Рафаил", "Ратибор", "Радован", "Руслан", "Радим", "Ростислав", "Родион", "Роман", "Ратмир", "Рюрик", "Радислав", "Савва", "Сеня", "Слава", "Серафим", "Спартак", "Степан", "Савелий", "Сергей", "Свет", "Самсон", "Северин", "Светозар", "Север", "Стас", "Симон", "Творимир", "Трофим", "Тихон", "Тимур", "Тимофей", "Терентий", "Тарас", "Твердислав", "Трифон", "Тит", "Умар", "Устин", "Уврикий", "Ульян", "Урал", "Усман", "Федот", "Филипп", "Филип", "Федор", "Флор", "Феофан", "Феоктист", "Ферапонт", "Филимон", "Фотий", "Фёдор", "Феликс", "Фортунат", "Феодосий", "Фрол", "Фадей", "Фирс", "Флорентин", "Федосей", "Фома", "Фока", "Федосий", "Христофор", "Харитон", "Харлампий", "Юлиан", "Юлий", "Ювеналий", "Юрий"}
|
|
@ -0,0 +1,58 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<style>
|
||||
table {
|
||||
border-collapse: collapse;
|
||||
border: 1px solid black;
|
||||
width: 100%;
|
||||
background-color: azure;
|
||||
}
|
||||
table th {
|
||||
border: 1px solid black;
|
||||
background-color: aquamarine;
|
||||
}
|
||||
table td {
|
||||
border: 1px solid black;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<h2>Search users</h2>
|
||||
<form method="POST">
|
||||
<table>
|
||||
<tr>
|
||||
<td>Префиксу имени и(или) фамилии</td>
|
||||
<td><input type="text" name="pref" /></td>
|
||||
</tr>
|
||||
</table>
|
||||
<button>Search</button>
|
||||
</form>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Name</th>
|
||||
<th>Years Old</th>
|
||||
<th>Gender</th>
|
||||
<th>City</th>
|
||||
<th>Action</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{{ range $value:=.table }}
|
||||
<tr>
|
||||
<td><a>{{ $value.Name }} {{ $value.Surname }}</a></td>
|
||||
<td><a>{{ $value.YearsOld }}</a></td>
|
||||
<td><a>{{ $value.Gender }}</a></td>
|
||||
<td><a>{{ $value.City }}</a></td>
|
||||
<td><a href="/subscribe?id={{ $value.Id }}">Subscribe</a></td>
|
||||
</tr>
|
||||
{{ end }}
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<h2>Available actions:</h2>
|
||||
<input type="button" onclick="location.href='/';" value="Home" />
|
||||
</body>
|
||||
</html>
|
Loading…
Reference in New Issue