Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

text/template: docs say "A template may be executed safely in parallel." which is misleading #19439

Closed
Dieterbe opened this issue Mar 7, 2017 · 2 comments

Comments

@Dieterbe
Copy link
Contributor

Dieterbe commented Mar 7, 2017

Hello,
first of, Go is awesome. I love it. thank you very much. But I recently ran into a snag that I think other people could run into as well, and I think extending the docs a bit would help. That's why I created https://go-review.googlesource.com/c/37444/ but I was asked to create an issue to justify the proposed change. so here we go.

What version of Go are you using (go version)?

1.8

What operating system and processor architecture are you using (go env)?

GOARCH="amd64"
GOBIN=""
GOEXE=""
GOHOSTARCH="amd64"
GOHOSTOS="linux"
GOOS="linux"
GOPATH="/home/dieter/go"
GORACE=""
GOROOT="/usr/lib/go"
GOTOOLDIR="/usr/lib/go/pkg/tool/linux_amd64"
GCCGO="gccgo"
CC="gcc"
GOGCCFLAGS="-fPIC -m64 -pthread -fmessage-length=0 -fdebug-prefix-map=/tmp/dieter/go-build064122595=/tmp/go-build -gno-record-gcc-switches"
CXX="g++"
CGO_ENABLED="1"
PKG_CONFIG="pkg-config"
CGO_CFLAGS="-g -O2"
CGO_CPPFLAGS=""
CGO_CXXFLAGS="-g -O2"
CGO_FFLAGS="-g -O2"
CGO_LDFLAGS="-g -O2"

What did you do?

I was recently working on a tool which consumes data from kafka and prints it to stdout via text/template, specifically Template.Execute() which was passed in os.Stdout as io.Writer.
The output was garbled (snippets of different execute calls intermingled). I tried various solutions, such as passing it a custom type implementing io.Writer, which protected os.Stdout with a lock; to no avail. output was still garbled.
We discussed it in the performance slack channel
(see https://gophers.slack.com/archives/performance/p1486655425001817)
, where a bunch of people tried to help (e.g. by looking into the atomicity of Write syscalls, http://man7.org/linux/man-pages/man2/write.2.html#BUGS, the go source code of how it calls syscall.Write, etc )

After a while I figured out template.Execute calls Write() multiple times as it walks the tree and prints individual pieces. Which was a bit confusing since
https://golang.org/pkg/text/template/#Template.Execute says "A template may be executed safely in parallel." my experience was by executing the template in parallel my output was getting corrupted. The docs didn't say anything about needing to execute into different writers, or needing to lock around the entire Template.Execute call if you want to use stdout.

So this is why I filed https://go-review.googlesource.com/c/37444/

cheers,
Dieter

@bradfitz bradfitz changed the title docs say "A template may be executed safely in parallel." which is misleading text/template: docs say "A template may be executed safely in parallel." which is misleading Mar 7, 2017
@bradfitz bradfitz added this to the Go1.9 milestone Mar 7, 2017
@robpike
Copy link
Contributor

robpike commented Mar 7, 2017

The meaning of "safely" in this context is, without corruption of the heap. That is, execution is data-race free.

Usually it's understood that I/O interleaves when there are multiple writers, but if it seems a surprise the documentation could say this. I don't want every concurrent-safe function in the library to need to describe the rules of concurrent execution though.

I will address the wording in the CL.

@robpike
Copy link
Contributor

robpike commented May 16, 2017

@robpike robpike closed this as completed May 16, 2017
@golang golang locked and limited conversation to collaborators May 16, 2018
@rsc rsc unassigned robpike Jun 23, 2022
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

4 participants