godoc: add GoogleCN property to pages

Use that property to determine whether to show share functionality
or link to sites that are blocked in mainland China.

This change requires https://go-review.googlesource.com/c/52872

Change-Id: I47327f9dbd2624206564fa99eb1cc6a10b4f46db
Reviewed-on: https://go-review.googlesource.com/52873
Reviewed-by: Chris Broadfoot <cbro@golang.org>
This commit is contained in:
Andrew Bonventre 2017-08-02 16:37:59 -04:00
parent fcc44a6330
commit 4e70a1b26a
8 changed files with 40 additions and 26 deletions

View File

@ -10,7 +10,7 @@ binary. It can be tedious to recompile assets every time, but you can pass a
flag to load CSS/JS/templates from disk every time a page loads: flag to load CSS/JS/templates from disk every time a page loads:
``` ```
godoc --templates=$GOPATH/src/golang.org/x/tools/godoc/static --http=:6060 godoc -templates=$GOPATH/src/golang.org/x/tools/godoc/static -http=:6060
``` ```
## Recompiling static assets ## Recompiling static assets

View File

@ -423,7 +423,7 @@ func sanitizeFunc(src string) string {
type PageInfo struct { type PageInfo struct {
Dirname string // directory containing the package Dirname string // directory containing the package
Err error // error or nil Err error // error or nil
Share bool // show share button on examples GoogleCN bool // page is being served from golang.google.cn
Mode PageInfoMode // display metadata from query string Mode PageInfoMode // display metadata from query string
@ -683,8 +683,8 @@ func (p *Presentation) example_htmlFunc(info *PageInfo, funcName string) string
err := p.ExampleHTML.Execute(&buf, struct { err := p.ExampleHTML.Execute(&buf, struct {
Name, Doc, Code, Play, Output string Name, Doc, Code, Play, Output string
Share bool GoogleCN bool
}{eg.Name, eg.Doc, code, play, out, info.Share}) }{eg.Name, eg.Doc, code, play, out, info.GoogleCN})
if err != nil { if err != nil {
log.Print(err) log.Print(err)
} }

View File

@ -9,6 +9,7 @@ import (
"os" "os"
"path/filepath" "path/filepath"
"runtime" "runtime"
"strings"
) )
// Page describes the contents of the top-level godoc webpage. // Page describes the contents of the top-level godoc webpage.
@ -19,7 +20,7 @@ type Page struct {
SrcPath string SrcPath string
Query string Query string
Body []byte Body []byte
Share bool GoogleCN bool // page is being served from golang.google.cn
// filled in by servePage // filled in by servePage
SearchBox bool SearchBox bool
@ -51,19 +52,25 @@ func (p *Presentation) ServeError(w http.ResponseWriter, r *http.Request, relpat
Title: "File " + relpath, Title: "File " + relpath,
Subtitle: relpath, Subtitle: relpath,
Body: applyTemplate(p.ErrorHTML, "errorHTML", err), Body: applyTemplate(p.ErrorHTML, "errorHTML", err),
Share: allowShare(r), GoogleCN: googleCN(r),
}) })
} }
var onAppengine = false // overriden in appengine.go when on app engine var onAppengine = false // overridden in appengine.go when on app engine
func allowShare(r *http.Request) bool { func googleCN(r *http.Request) bool {
if r.FormValue("googlecn") != "" {
return true
}
if !onAppengine { if !onAppengine {
return false
}
if strings.HasSuffix(r.Host, ".cn") {
return true return true
} }
switch r.Header.Get("X-AppEngine-Country") { switch r.Header.Get("X-AppEngine-Country") {
case "", "ZZ", "CN": case "", "ZZ", "CN":
return false
}
return true return true
} }
return false
}

View File

@ -19,6 +19,7 @@ import (
"net/http" "net/http"
"net/http/httputil" "net/http/httputil"
"net/url" "net/url"
"strings"
"time" "time"
"golang.org/x/net/context" "golang.org/x/net/context"
@ -147,8 +148,8 @@ func cacheKey(body string) string {
} }
func share(w http.ResponseWriter, r *http.Request) { func share(w http.ResponseWriter, r *http.Request) {
if !allowShare(r) { if googleCN(r) {
http.Error(w, "Forbidden", http.StatusForbidden) http.Error(w, http.StatusText(http.StatusForbidden), http.StatusForbidden)
return return
} }
target, _ := url.Parse(playgroundURL) target, _ := url.Parse(playgroundURL)
@ -157,13 +158,19 @@ func share(w http.ResponseWriter, r *http.Request) {
p.ServeHTTP(w, r) p.ServeHTTP(w, r)
} }
func allowShare(r *http.Request) bool { func googleCN(r *http.Request) bool {
if r.FormValue("googlecn") != "" {
return true
}
if appengine.IsDevAppServer() { if appengine.IsDevAppServer() {
return false
}
if strings.HasSuffix(r.Host, ".cn") {
return true return true
} }
switch r.Header.Get("X-AppEngine-Country") { switch r.Header.Get("X-AppEngine-Country") {
case "", "ZZ", "CN": case "", "ZZ", "CN":
return false
}
return true return true
} }
return false
}

View File

@ -126,7 +126,7 @@ func (p *Presentation) HandleSearch(w http.ResponseWriter, r *http.Request) {
Tabtitle: query, Tabtitle: query,
Query: query, Query: query,
Body: body.Bytes(), Body: body.Bytes(),
Share: allowShare(r), GoogleCN: googleCN(r),
}) })
} }

View File

@ -312,13 +312,13 @@ func (h *handlerServer) ServeHTTP(w http.ResponseWriter, r *http.Request) {
info.TypeInfoIndex[ti.Name] = i info.TypeInfoIndex[ti.Name] = i
} }
info.Share = allowShare(r) info.GoogleCN = googleCN(r)
h.p.ServePage(w, Page{ h.p.ServePage(w, Page{
Title: title, Title: title,
Tabtitle: tabtitle, Tabtitle: tabtitle,
Subtitle: subtitle, Subtitle: subtitle,
Body: applyTemplate(h.p.PackageHTML, "packageHTML", info), Body: applyTemplate(h.p.PackageHTML, "packageHTML", info),
Share: info.Share, GoogleCN: info.GoogleCN,
}) })
} }
@ -583,7 +583,7 @@ func (p *Presentation) serveTextFile(w http.ResponseWriter, r *http.Request, abs
SrcPath: relpath, SrcPath: relpath,
Tabtitle: relpath, Tabtitle: relpath,
Body: buf.Bytes(), Body: buf.Bytes(),
Share: allowShare(r), GoogleCN: googleCN(r),
}) })
} }
@ -654,7 +654,7 @@ func (p *Presentation) serveDirectory(w http.ResponseWriter, r *http.Request, ab
SrcPath: relpath, SrcPath: relpath,
Tabtitle: relpath, Tabtitle: relpath,
Body: applyTemplate(p.DirlistHTML, "dirlistHTML", list), Body: applyTemplate(p.DirlistHTML, "dirlistHTML", list),
Share: allowShare(r), GoogleCN: googleCN(r),
}) })
} }
@ -683,7 +683,7 @@ func (p *Presentation) ServeHTMLDoc(w http.ResponseWriter, r *http.Request, absp
page := Page{ page := Page{
Title: meta.Title, Title: meta.Title,
Subtitle: meta.Subtitle, Subtitle: meta.Subtitle,
Share: allowShare(r), GoogleCN: googleCN(r),
} }
// evaluate as template if indicated // evaluate as template if indicated

View File

@ -13,7 +13,7 @@
<div class="buttons"> <div class="buttons">
<a class="run" title="Run this code [shift-enter]">Run</a> <a class="run" title="Run this code [shift-enter]">Run</a>
<a class="fmt" title="Format this code">Format</a> <a class="fmt" title="Format this code">Format</a>
{{if $.Share}} {{if not $.GoogleCN}}
<a class="share" title="Share this code">Share</a> <a class="share" title="Share this code">Share</a>
{{end}} {{end}}
</div> </div>

View File

@ -55,7 +55,7 @@ func main() {
<div class="buttons"> <div class="buttons">
<a class="run" title="Run this code [shift-enter]">Run</a> <a class="run" title="Run this code [shift-enter]">Run</a>
<a class="fmt" title="Format this code">Format</a> <a class="fmt" title="Format this code">Format</a>
{{if $.Share}} {{if not $.GoogleCN}}
<a class="share" title="Share this code">Share</a> <a class="share" title="Share this code">Share</a>
{{end}} {{end}}
</div> </div>