шаблоны предварительно кэширования Golang или более эффективный способ сделать это - PullRequest
0 голосов
/ 25 января 2019

У меня есть веб-приложение, и я пытаюсь предварительно кэшировать свои шаблоны, как показано ниже: https://golang.org/doc/articles/wiki/#tmp_10

В настоящее время это то, что я делаю.(Я включил пример вспомогательных функций шаблона, чтобы дать вам представление) (обратите внимание, что объект App - это остальная часть приложения, обрабатывающая фактическое веб-обслуживание и содержимое БД)

///a function that the template can pass a different arg
func functiontakingarguments(arg1 string, arg2 string) (firststring string) {
    return arg1

} * 1007Бьюсь об заклад, вы можете легко обнаружить первый набор проблем здесь.Шаблоны должны быть прочитаны с диска каждый раз для каждого запроса.

Поскольку у меня есть некоторые шаблонные функции, которые полагаются на то, что пользователь их просматривает, или переменные сеанса, я передаю r * http.Request в функцию рендеринга шаблона, чтобы при вызове моих вспомогательных функцийу них есть доступ к этим данным запроса.

Насколько я могу судить, это означает, что я не могу точно предварительно кэшировать эти шаблоны, как описано в той предыдущей ссылке (https://golang.org/doc/articles/wiki/#tmp_10)

Итак, во-первых, это плохоспособ сделать это в целом? (не для того, чтобы оправдать себя, но часть этого кода пришла от другого программиста)

Во-вторых, есть ли способ сделать это более эффективным? Например, кэширование некоторой части этого, новсе еще в состоянии использовать эти вспомогательные функции? Я почти уверен, что вся эта установка сильно снижает производительность моего приложения, но я могу ошибаться. Я пробовал несколько уродливых хаков, таких как попытка (someargs ... interface {}), а затемкастинг (да, я ужасный грешник)

1 Ответ

0 голосов
/ 25 января 2019

Передать все состояние каждого запроса в качестве аргумента для Execute. Определите тип, который инкапсулирует состояние для каждого запроса:

type data struct {
   r *http.Request
   Data map[string]interface{}
}

func (d *data) SessionFoo() bool {
    return hasUserSession(d.r)
}

Используйте этот тип в шаблонах:

<h1> Hello! </h1>
{{ functiontakingarguments "astring" "asecondstring" }}

{{ if $.SessionFoo }} Something to do with that session function {{else}} nevermind! {{end}}

templData["x"] is {{$.Data.x}}

С этими изменениями шаблон может быть проанализирован один раз при запуске программы. Предполагая, что указатель шаблона был сохранен в переменной уровня пакета myPageTemplate, вы можете выполнить его следующим образом:

err := myPageTemplate.Execute(w, data{Data:templData, r:r})
if err != nil {
   // handle error
}
...