cmd/golangorg: take on serving of go.dev

This CL merges go.dev/cmd/frontend into cmd/golangorg,
now that they share the same serving framework (internal/web).

Change-Id: I367d5c79b993f25ce411544b00f6db6d820290e0
Reviewed-on: https://go-review.googlesource.com/c/website/+/339404
Trust: Russ Cox <rsc@golang.org>
Run-TryBot: Russ Cox <rsc@golang.org>
Website-Publish: Russ Cox <rsc@golang.org>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Jamal Carvalho <jamal@golang.org>
diff --git a/cmd/golangorg/cloudbuild.yaml b/cmd/golangorg/cloudbuild.yaml
index b1e8860..f392763 100644
--- a/cmd/golangorg/cloudbuild.yaml
+++ b/cmd/golangorg/cloudbuild.yaml
@@ -17,15 +17,25 @@
     args: ["rm", "-rf", "_gotmp"]
   - name: golang
     args: ["go", "test", "./..."]
+  - name: golang
+    entrypoint: bash
+    args: ["-c", "go run ./go.dev/cmd/events/ > ./go.dev/_content/events.yaml"]
   - name: gcr.io/cloud-builders/gcloud
     entrypoint: bash
     args: ["./go-app-deploy.sh", "cmd/golangorg/app.yaml"]
+  - name: gcr.io/cloud-builders/gcloud
+    entrypoint: bash
+    args: ["./go-app-deploy.sh", "--project=go-discovery", "cmd/golangorg/godevapp.yaml"]
   - name: golang
     args: [
-      "go", "run", "./cmd/versionprune", "--dry_run=false",
+      "go", "run", "./go.dev/cmd/versionprune", "--dry_run=false",
       "--project=$PROJECT_ID", "--service=default",
     ]
-    dir: go.dev
+  - name: golang
+    args: [
+      "go", "run", "./go.dev/cmd/versionprune", "--dry_run=false",
+      "--project=go-discovery", "--service=go-dev",
+    ]
 
 options:
   machineType: N1_HIGHCPU_8
diff --git a/go.dev/cmd/frontend/csp.go b/cmd/golangorg/csp.go
similarity index 100%
rename from go.dev/cmd/frontend/csp.go
rename to cmd/golangorg/csp.go
diff --git a/go.dev/cmd/frontend/main.go b/cmd/golangorg/godev.go
similarity index 73%
rename from go.dev/cmd/frontend/main.go
rename to cmd/golangorg/godev.go
index effd257..ca280d2 100644
--- a/go.dev/cmd/frontend/main.go
+++ b/cmd/golangorg/godev.go
@@ -5,12 +5,8 @@
 package main
 
 import (
-	"log"
-	"net"
 	"net/http"
 	"net/url"
-	"os"
-	"path/filepath"
 	"sort"
 	"strings"
 	"time"
@@ -18,7 +14,6 @@
 	"golang.org/x/website/internal/backport/html/template"
 	"golang.org/x/website/internal/backport/osfs"
 	"golang.org/x/website/internal/web"
-	"golang.org/x/website/internal/webtest"
 )
 
 var discoveryHosts = map[string]string{
@@ -27,35 +22,7 @@
 	"staging.go.dev": "staging-pkg.go.dev",
 }
 
-func main() {
-	dir := "../../_content"
-	if _, err := os.Stat("go.dev/_content/events.yaml"); err == nil {
-		// Running in repo root.
-		dir = "go.dev/_content"
-	}
-
-	h, err := NewHandler(dir)
-	if err != nil {
-		log.Fatal(err)
-	}
-
-	h = webtest.HandlerWithCheck(h, "/_readycheck",
-		filepath.Join(dir, "cmd/frontend/testdata/*.txt"))
-
-	addr := ":" + listenPort()
-	if addr == ":0" {
-		addr = "localhost:0"
-	}
-	l, err := net.Listen("tcp", addr)
-	if err != nil {
-		log.Fatalf("net.Listen(%q, %q) = _, %v", "tcp", addr, err)
-	}
-	defer l.Close()
-	log.Printf("Listening on http://%v/\n", l.Addr().String())
-	log.Print(http.Serve(l, h))
-}
-
-func NewHandler(dir string) (http.Handler, error) {
+func godevHandler(dir string) (http.Handler, error) {
 	godev := web.NewSite(osfs.DirFS(dir))
 	godev.Funcs(template.FuncMap{
 		"newest":  newest,
@@ -117,13 +84,6 @@
 	http.Redirect(w, r, "https://go.dev/learn/"+strings.TrimPrefix(r.URL.Path, "/"), http.StatusMovedPermanently)
 }
 
-func listenPort() string {
-	if p := os.Getenv("PORT"); p != "" {
-		return p
-	}
-	return "0"
-}
-
 type redirectHosts map[string]string
 
 func (rh redirectHosts) ServeHTTP(w http.ResponseWriter, r *http.Request) {
diff --git a/go.dev/cmd/frontend/main_test.go b/cmd/golangorg/godev_test.go
similarity index 97%
rename from go.dev/cmd/frontend/main_test.go
rename to cmd/golangorg/godev_test.go
index 05a60d8..962c1af 100644
--- a/go.dev/cmd/frontend/main_test.go
+++ b/cmd/golangorg/godev_test.go
@@ -81,7 +81,7 @@
 }
 
 func TestSite(t *testing.T) {
-	h, err := NewHandler("../../_content")
+	h, err := godevHandler("../../go.dev/_content")
 	if err != nil {
 		t.Fatal(err)
 	}
diff --git a/cmd/golangorg/godevapp.yaml b/cmd/golangorg/godevapp.yaml
new file mode 100644
index 0000000..a93e566
--- /dev/null
+++ b/cmd/golangorg/godevapp.yaml
@@ -0,0 +1,8 @@
+runtime: go115
+service: go-dev
+main: ./cmd/golangorg
+
+handlers:
+  - url: /.*
+    secure: always
+    script: auto
diff --git a/go.dev/cmd/frontend/golden_test.go b/cmd/golangorg/golden_test.go
similarity index 96%
rename from go.dev/cmd/frontend/golden_test.go
rename to cmd/golangorg/golden_test.go
index 04b6435..567174e 100644
--- a/go.dev/cmd/frontend/golden_test.go
+++ b/cmd/golangorg/golden_test.go
@@ -20,14 +20,14 @@
 
 func TestGolden(t *testing.T) {
 	start := time.Now()
-	h, err := NewHandler("../../_content")
+	h, err := godevHandler("../../go.dev/_content")
 	if err != nil {
 		t.Fatal(err)
 	}
 	total := time.Since(start)
 	t.Logf("Load %v\n", total)
 
-	root := "../../testdata/golden"
+	root := "../../go.dev/testdata/golden"
 	err = filepath.Walk(root, func(name string, info os.FileInfo, err error) error {
 		if err != nil {
 			return err
diff --git a/cmd/golangorg/server.go b/cmd/golangorg/server.go
index a707371..54f3c86 100644
--- a/cmd/golangorg/server.go
+++ b/cmd/golangorg/server.go
@@ -193,6 +193,13 @@
 		mux.Handle("/dl/", http.RedirectHandler("https://golang.org/dl/", http.StatusFound))
 	}
 
+	godev, err := godevHandler(filepath.Join(contentDir, "../go.dev/_content"))
+	if err != nil {
+		log.Fatalf("godevHandler: %v", err)
+	}
+	mux.Handle("go.dev/", godev)
+	mux.Handle("learn.go.dev/", godev)
+
 	var h http.Handler = mux
 	if env.EnforceHosts() {
 		h = hostEnforcerHandler(h)
@@ -317,10 +324,6 @@
 	log.Println("AppEngine initialization complete")
 }
 
-func blogHandler(w http.ResponseWriter, r *http.Request) {
-	http.Redirect(w, r, "https://blog.golang.org"+strings.TrimPrefix(r.URL.Path, "/blog"), http.StatusFound)
-}
-
 type fmtResponse struct {
 	Body  string
 	Error string
@@ -341,6 +344,8 @@
 }
 
 var validHosts = map[string]bool{
+	"go.dev":           true,
+	"learn.go.dev":     true,
 	"golang.org":       true,
 	"golang.google.cn": true,
 	"m.golang.org":     true,
@@ -442,9 +447,11 @@
 func (r *linkRewriter) Flush() {
 	repl := []string{
 		`href="/`, `href="/` + r.host + `/`,
+		`src="/`, `src="/` + r.host + `/`,
 	}
 	for host := range validHosts {
 		repl = append(repl, `href="https://`+host, `href="/`+host)
+		repl = append(repl, `src="https://`+host, `src="/`+host)
 	}
 	strings.NewReplacer(repl...).WriteString(r.ResponseWriter, string(r.buf))
 	r.buf = nil
diff --git a/cmd/golangorg/server_test.go b/cmd/golangorg/server_test.go
index 04c7664..d7b8c01 100644
--- a/cmd/golangorg/server_test.go
+++ b/cmd/golangorg/server_test.go
@@ -18,6 +18,7 @@
 
 func TestWeb(t *testing.T) {
 	h := NewHandler("../../_content", runtime.GOROOT())
+
 	files, err := filepath.Glob("testdata/*.txt")
 	if err != nil {
 		t.Fatal(err)
diff --git a/go.dev/cmd/frontend/testdata/godev.txt b/cmd/golangorg/testdata/godev.txt
similarity index 67%
rename from go.dev/cmd/frontend/testdata/godev.txt
rename to cmd/golangorg/testdata/godev.txt
index 3785608..d220c2c 100644
--- a/go.dev/cmd/frontend/testdata/godev.txt
+++ b/cmd/golangorg/testdata/godev.txt
@@ -4,18 +4,18 @@
 GET https://go.dev/solutions/google/
 body ~ it\s+has\s+powered\s+many\s+projects\s+at\s+Google.
 
-GET /solutions/chrome
+GET https://go.dev/solutions/chrome
 redirect == /solutions/google/chrome
 
-GET /solutions/coredata
+GET https://go.dev/solutions/coredata
 redirect == /solutions/google/coredata
 
-GET /solutions/firebase
+GET https://go.dev/solutions/firebase
 redirect == /solutions/google/firebase
 
-GET /solutions/sitereliability
+GET https://go.dev/solutions/sitereliability
 redirect == /solutions/google/sitereliability
 
-GET /solutions/americanexpress
+GET https://go.dev/solutions/americanexpress
 body contains <div class="Article-date">19 December 2019</div>
 
diff --git a/go.dev/LICENSE b/go.dev/LICENSE
deleted file mode 100644
index 6a66aea..0000000
--- a/go.dev/LICENSE
+++ /dev/null
@@ -1,27 +0,0 @@
-Copyright (c) 2009 The Go Authors. All rights reserved.
-
-Redistribution and use in source and binary forms, with or without
-modification, are permitted provided that the following conditions are
-met:
-
-   * Redistributions of source code must retain the above copyright
-notice, this list of conditions and the following disclaimer.
-   * Redistributions in binary form must reproduce the above
-copyright notice, this list of conditions and the following disclaimer
-in the documentation and/or other materials provided with the
-distribution.
-   * Neither the name of Google Inc. nor the names of its
-contributors may be used to endorse or promote products derived from
-this software without specific prior written permission.
-
-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/go.dev/app.staging.yaml b/go.dev/app.staging.yaml
deleted file mode 100644
index 65c2d31..0000000
--- a/go.dev/app.staging.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-# This app is deployed via Cloud Build as directed by cloudbuild.staging.yaml.
-# Do not deploy directly.
-
-runtime: go115
-service: staging-go-dev
-main: ./cmd/frontend
-
-handlers:
-  - url: /.*
-    secure: always
-    script: auto
diff --git a/go.dev/app.yaml b/go.dev/app.yaml
deleted file mode 100644
index b9e5b4f..0000000
--- a/go.dev/app.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-# This app is deployed via Cloud Build as directed by cloudbuild.yaml.
-# Do not deploy directly.
-
-runtime: go115
-service: go-dev
-main: ./go.dev/cmd/frontend
-
-handlers:
-  - url: /.*
-    secure: always
-    script: auto
diff --git a/go.dev/cloudbuild.staging.yaml b/go.dev/cloudbuild.staging.yaml
deleted file mode 100644
index 7eabb32..0000000
--- a/go.dev/cloudbuild.staging.yaml
+++ /dev/null
@@ -1,24 +0,0 @@
-steps:
-  - name: 'golang'
-    entrypoint: bash
-    args:
-      - -c
-      - go run ./cmd/events/ > ./_content/events.yaml
-    dir: go.dev
-  - name: 'golang'
-    args:
-      - test
-      - ./...
-    dir: go.dev
-  - name: "gcr.io/cloud-builders/gcloud"
-    args: ["app", "deploy", "app.staging.yaml"]
-    dir: go.dev
-  - name: "gcr.io/cloud-builders/gcloud"
-    args: ["app", "deploy", "app.staging.learn.yaml"]
-    dir: go.dev
-  - name: 'golang'
-    args: ["go", "run", "./cmd/versionprune", "--project=$PROJECT_ID", "--service=staging-go-dev", "--dry_run=false"]
-    dir: go.dev
-  - name: 'golang'
-    args: ["go", "run", "./cmd/versionprune", "--project=$PROJECT_ID", "--service=staging-learn-go-dev", "--dry_run=false"]
-    dir: go.dev
diff --git a/go.dev/cloudbuild.yaml b/go.dev/cloudbuild.yaml
deleted file mode 100644
index 48ac8aa..0000000
--- a/go.dev/cloudbuild.yaml
+++ /dev/null
@@ -1,24 +0,0 @@
-# This Cloud Build file is run automatically when commits land in the website repo.
-# See https://console.cloud.google.com/cloud-build/triggers?project=golang-org.
-# Do not run directly.
-
-steps:
-  - name: 'golang'
-    args: ["go", "test", "./..."]
-    dir: go.dev
-  - name: 'golang'
-    entrypoint: bash
-    args: ["-c", "go run ./cmd/events/ > ./_content/events.yaml"]
-    dir: go.dev
-  - name: "gcr.io/cloud-builders/gcloud"
-    entrypoint: bash
-    args: ["./go-app-deploy.sh", "--project=go-discovery", "go.dev/app.yaml"]
-  - name: 'golang'
-    args: [
-      "go", "run", "./cmd/versionprune", "--dry_run=false",
-      "--project=go-discovery", "--service=go-dev",
-    ]
-    dir: go.dev
-
-options:
-  machineType: E2_HIGHCPU_8
diff --git a/go.dev/cmd/frontend/server_test.go b/go.dev/cmd/frontend/server_test.go
deleted file mode 100644
index 4b0d4ec..0000000
--- a/go.dev/cmd/frontend/server_test.go
+++ /dev/null
@@ -1,19 +0,0 @@
-// Copyright 2021 The Go Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style
-// license that can be found in the LICENSE file.
-
-package main
-
-import (
-	"testing"
-
-	"golang.org/x/website/internal/webtest"
-)
-
-func TestWeb(t *testing.T) {
-	h, err := NewHandler("../../_content")
-	if err != nil {
-		t.Fatal(err)
-	}
-	webtest.TestHandler(t, "testdata/*.txt", h)
-}