...

Source file src/html/template/doc.go

Documentation: html/template

		 1  // Copyright 2011 The Go Authors. All rights reserved.
		 2  // Use of this source code is governed by a BSD-style
		 3  // license that can be found in the LICENSE file.
		 4  
		 5  /*
		 6  Package template (html/template) implements data-driven templates for
		 7  generating HTML output safe against code injection. It provides the
		 8  same interface as package text/template and should be used instead of
		 9  text/template whenever the output is HTML.
		10  
		11  The documentation here focuses on the security features of the package.
		12  For information about how to program the templates themselves, see the
		13  documentation for text/template.
		14  
		15  Introduction
		16  
		17  This package wraps package text/template so you can share its template API
		18  to parse and execute HTML templates safely.
		19  
		20  	tmpl, err := template.New("name").Parse(...)
		21  	// Error checking elided
		22  	err = tmpl.Execute(out, data)
		23  
		24  If successful, tmpl will now be injection-safe. Otherwise, err is an error
		25  defined in the docs for ErrorCode.
		26  
		27  HTML templates treat data values as plain text which should be encoded so they
		28  can be safely embedded in an HTML document. The escaping is contextual, so
		29  actions can appear within JavaScript, CSS, and URI contexts.
		30  
		31  The security model used by this package assumes that template authors are
		32  trusted, while Execute's data parameter is not. More details are
		33  provided below.
		34  
		35  Example
		36  
		37  	import "text/template"
		38  	...
		39  	t, err := template.New("foo").Parse(`{{define "T"}}Hello, {{.}}!{{end}}`)
		40  	err = t.ExecuteTemplate(out, "T", "<script>alert('you have been pwned')</script>")
		41  
		42  produces
		43  
		44  	Hello, <script>alert('you have been pwned')</script>!
		45  
		46  but the contextual autoescaping in html/template
		47  
		48  	import "html/template"
		49  	...
		50  	t, err := template.New("foo").Parse(`{{define "T"}}Hello, {{.}}!{{end}}`)
		51  	err = t.ExecuteTemplate(out, "T", "<script>alert('you have been pwned')</script>")
		52  
		53  produces safe, escaped HTML output
		54  
		55  	Hello, &lt;script&gt;alert(&#39;you have been pwned&#39;)&lt;/script&gt;!
		56  
		57  
		58  Contexts
		59  
		60  This package understands HTML, CSS, JavaScript, and URIs. It adds sanitizing
		61  functions to each simple action pipeline, so given the excerpt
		62  
		63  	<a href="/search?q={{.}}">{{.}}</a>
		64  
		65  At parse time each {{.}} is overwritten to add escaping functions as necessary.
		66  In this case it becomes
		67  
		68  	<a href="/search?q={{. | urlescaper | attrescaper}}">{{. | htmlescaper}}</a>
		69  
		70  where urlescaper, attrescaper, and htmlescaper are aliases for internal escaping
		71  functions.
		72  
		73  For these internal escaping functions, if an action pipeline evaluates to
		74  a nil interface value, it is treated as though it were an empty string.
		75  
		76  Namespaced and data- attributes
		77  
		78  Attributes with a namespace are treated as if they had no namespace.
		79  Given the excerpt
		80  
		81  	<a my:href="{{.}}"></a>
		82  
		83  At parse time the attribute will be treated as if it were just "href".
		84  So at parse time the template becomes:
		85  
		86  	<a my:href="{{. | urlescaper | attrescaper}}"></a>
		87  
		88  Similarly to attributes with namespaces, attributes with a "data-" prefix are
		89  treated as if they had no "data-" prefix. So given
		90  
		91  	<a data-href="{{.}}"></a>
		92  
		93  At parse time this becomes
		94  
		95  	<a data-href="{{. | urlescaper | attrescaper}}"></a>
		96  
		97  If an attribute has both a namespace and a "data-" prefix, only the namespace
		98  will be removed when determining the context. For example
		99  
	 100  	<a my:data-href="{{.}}"></a>
	 101  
	 102  This is handled as if "my:data-href" was just "data-href" and not "href" as
	 103  it would be if the "data-" prefix were to be ignored too. Thus at parse
	 104  time this becomes just
	 105  
	 106  	<a my:data-href="{{. | attrescaper}}"></a>
	 107  
	 108  As a special case, attributes with the namespace "xmlns" are always treated
	 109  as containing URLs. Given the excerpts
	 110  
	 111  	<a xmlns:title="{{.}}"></a>
	 112  	<a xmlns:href="{{.}}"></a>
	 113  	<a xmlns:onclick="{{.}}"></a>
	 114  
	 115  At parse time they become:
	 116  
	 117  	<a xmlns:title="{{. | urlescaper | attrescaper}}"></a>
	 118  	<a xmlns:href="{{. | urlescaper | attrescaper}}"></a>
	 119  	<a xmlns:onclick="{{. | urlescaper | attrescaper}}"></a>
	 120  
	 121  Errors
	 122  
	 123  See the documentation of ErrorCode for details.
	 124  
	 125  
	 126  A fuller picture
	 127  
	 128  The rest of this package comment may be skipped on first reading; it includes
	 129  details necessary to understand escaping contexts and error messages. Most users
	 130  will not need to understand these details.
	 131  
	 132  
	 133  Contexts
	 134  
	 135  Assuming {{.}} is `O'Reilly: How are <i>you</i>?`, the table below shows
	 136  how {{.}} appears when used in the context to the left.
	 137  
	 138  	Context													{{.}} After
	 139  	{{.}}														O'Reilly: How are &lt;i&gt;you&lt;/i&gt;?
	 140  	<a title='{{.}}'>								O&#39;Reilly: How are you?
	 141  	<a href="/{{.}}">								O&#39;Reilly: How are %3ci%3eyou%3c/i%3e?
	 142  	<a href="?q={{.}}">							O&#39;Reilly%3a%20How%20are%3ci%3e...%3f
	 143  	<a onx='f("{{.}}")'>						 O\x27Reilly: How are \x3ci\x3eyou...?
	 144  	<a onx='f({{.}})'>							 "O\x27Reilly: How are \x3ci\x3eyou...?"
	 145  	<a onx='pattern = /{{.}}/;'>		 O\x27Reilly: How are \x3ci\x3eyou...\x3f
	 146  
	 147  If used in an unsafe context, then the value might be filtered out:
	 148  
	 149  	Context													{{.}} After
	 150  	<a href="{{.}}">								 #ZgotmplZ
	 151  
	 152  since "O'Reilly:" is not an allowed protocol like "http:".
	 153  
	 154  
	 155  If {{.}} is the innocuous word, `left`, then it can appear more widely,
	 156  
	 157  	Context															{{.}} After
	 158  	{{.}}																left
	 159  	<a title='{{.}}'>										left
	 160  	<a href='{{.}}'>										 left
	 161  	<a href='/{{.}}'>										left
	 162  	<a href='?dir={{.}}'>								left
	 163  	<a style="border-{{.}}: 4px">				left
	 164  	<a style="align: {{.}}">						 left
	 165  	<a style="background: '{{.}}'>			 left
	 166  	<a style="background: url('{{.}}')>	left
	 167  	<style>p.{{.}} {color:red}</style>	 left
	 168  
	 169  Non-string values can be used in JavaScript contexts.
	 170  If {{.}} is
	 171  
	 172  	struct{A,B string}{ "foo", "bar" }
	 173  
	 174  in the escaped template
	 175  
	 176  	<script>var pair = {{.}};</script>
	 177  
	 178  then the template output is
	 179  
	 180  	<script>var pair = {"A": "foo", "B": "bar"};</script>
	 181  
	 182  See package json to understand how non-string content is marshaled for
	 183  embedding in JavaScript contexts.
	 184  
	 185  
	 186  Typed Strings
	 187  
	 188  By default, this package assumes that all pipelines produce a plain text string.
	 189  It adds escaping pipeline stages necessary to correctly and safely embed that
	 190  plain text string in the appropriate context.
	 191  
	 192  When a data value is not plain text, you can make sure it is not over-escaped
	 193  by marking it with its type.
	 194  
	 195  Types HTML, JS, URL, and others from content.go can carry safe content that is
	 196  exempted from escaping.
	 197  
	 198  The template
	 199  
	 200  	Hello, {{.}}!
	 201  
	 202  can be invoked with
	 203  
	 204  	tmpl.Execute(out, template.HTML(`<b>World</b>`))
	 205  
	 206  to produce
	 207  
	 208  	Hello, <b>World</b>!
	 209  
	 210  instead of the
	 211  
	 212  	Hello, &lt;b&gt;World&lt;b&gt;!
	 213  
	 214  that would have been produced if {{.}} was a regular string.
	 215  
	 216  
	 217  Security Model
	 218  
	 219  https://rawgit.com/mikesamuel/sanitized-jquery-templates/trunk/safetemplate.html#problem_definition defines "safe" as used by this package.
	 220  
	 221  This package assumes that template authors are trusted, that Execute's data
	 222  parameter is not, and seeks to preserve the properties below in the face
	 223  of untrusted data:
	 224  
	 225  Structure Preservation Property:
	 226  "... when a template author writes an HTML tag in a safe templating language,
	 227  the browser will interpret the corresponding portion of the output as a tag
	 228  regardless of the values of untrusted data, and similarly for other structures
	 229  such as attribute boundaries and JS and CSS string boundaries."
	 230  
	 231  Code Effect Property:
	 232  "... only code specified by the template author should run as a result of
	 233  injecting the template output into a page and all code specified by the
	 234  template author should run as a result of the same."
	 235  
	 236  Least Surprise Property:
	 237  "A developer (or code reviewer) familiar with HTML, CSS, and JavaScript, who
	 238  knows that contextual autoescaping happens should be able to look at a {{.}}
	 239  and correctly infer what sanitization happens."
	 240  */
	 241  package template
	 242  

View as plain text