Html 使用gorilla/schema解压字段

Html 使用gorilla/schema解压字段,html,go,gorilla,Html,Go,Gorilla,我正在使用将r.PostForm解包到一个结构中 我的问题是,我试图找到一种合理的方法来获取元素的选定值,这种方法允许我轻松地使用html/模板来重新选择字段,即在从会话重新填充表单时,注意到没有一种简单的方法来测试是否相等,只需将结构实例传递给RenderTemplate即可 为了说明我所拥有的: type Listing struct { Id string `schema:"-"` Title string `s

我正在使用将r.PostForm解包到一个结构中

我的问题是,我试图找到一种合理的方法来获取元素的选定值,这种方法允许我轻松地使用html/模板来重新选择字段,即在从会话重新填充表单时,注意到没有一种简单的方法来测试是否相等,只需将结构实例传递给RenderTemplate即可

为了说明我所拥有的:

type Listing struct {
    Id           string        `schema:"-"`
    Title        string        `schema:"title"`
    Company      string        `schema:"company"`
    Location     string        `schema:"location"`
        ...
    Term         string        `schema:"term"`
}
显然这行不通。我已经考虑将template.FuncMap作为一种可能的解决方案,但我不确定在希望将整个列表实例传递给模板(即,而不是逐个字段)时如何使用它。如果可能的话,我还希望尽量减少结构中不必要的字段。我可以为每个值设置布尔字段,例如Fulltime bool,但是如果用户返回并编辑内容,我需要代码将其他字段更改为false


有没有一种方法可以很好地与模板/html的限制相匹配,从而实现这一点?

您可以编写一个视图来构建和表示一个select元素:

然后实例化它:

termSelect := SelectBlock{
    Name:     "term",
    Selected: "",
    Options:  map[string]string{
        "full-time": "Full Time",
        "part-time": "Part Time",
        "contract":  "Contract",
        "freelance": "Freelance",
    },
}
并设置所选字段:

并在表单视图中输出视图片段:

{{template "select" $termSelect}}

其中$termSelect将是SelectBlock的实例

对于将来使用Go v1.2或更高版本的其他人,text/template和html/template现在在其他新操作符中提供了一个相等操作符:


我建议尽可能使用JS重新填充表单。@tomwilde我不能跨视图重新填充表单,除非我将数据存储在带有JS的cookie中。这是不安全的,而且我的gobbed超过了4K cookie限制。您可以将值作为JSON输出到块中,或者在页面加载后通过AJAX异步加载。是的,但是如果有一个相对较大的多达2000字的文本字段,则不会很快,并且在加载时可能会导致空字段的闪烁。用户通常会点击表单>预览,然后在需要调整时返回表单。由于我将其全部存储在会话中,因此我可以在提交时将其删除,否则将由会话到期处理。还允许我在两个步骤之间验证表单。这个问题的JS解决方案看起来很脆弱,但如果你知道一个好的库,我还是会看一看。我的设计基于Django form impl,它非常可靠。多亏了go nuts中的cronos,我使用了go 1.2RC2,它包括一个相等运算符!:考虑到你的答案是Go 1.1.x中实现这一点的一个更好的方法,除了使用or之外,我将接受这个答案。谢谢你在这个@tomwilde上的帮助。
renderTemplate(w, "create_listing.tmpl", M{
        "listing":              listing,
    })
 <label for="term">Term</label>
          <select data-placeholder="Term...?" id="term" name="term" required>
            <option name="term" value="full-time" {{ if .term == "full-time" }}selected{{end}}>Full Time</option>
            <option name="term" value="part-time"{{ if .term == "part-time" }}selected{{end}}>Part Time</option>
            <option name="term" value="contract" {{ if .term == "contract" }}selected{{end}}>Contract</option>
            <option name="term" value="freelance" {{ if .term == "freelance" }}selected{{end}}>Freelance</option>
          </select>
{{define "select"}}
    <select name="{{.Name}}>
        {{range $a, $b := .Options}}
             <option value="{{print $a}}" {{if $a == .Selected}}>{{print $b}}</option>
        {{end}}
    </select>
{{end}}
type SelectBlock struct {
    Name     string
    Selected string
    Options  map[string]string
}
termSelect := SelectBlock{
    Name:     "term",
    Selected: "",
    Options:  map[string]string{
        "full-time": "Full Time",
        "part-time": "Part Time",
        "contract":  "Contract",
        "freelance": "Freelance",
    },
}
termSelect.Selected = "full-time"
{{template "select" $termSelect}}
{{if eq .Term "full-time" }}selected{{end}}
...
{{if eq .Term "freelance" }}selected{{end}}