@@ -6,8 +6,10 @@ import (
6
6
"crypto/sha1" //#nosec // Not used for cryptography.
7
7
_ "embed"
8
8
"encoding/hex"
9
+ "encoding/json"
9
10
"errors"
10
11
"fmt"
12
+ "html"
11
13
htmltemplate "html/template"
12
14
"io"
13
15
"io/fs"
@@ -28,6 +30,7 @@ import (
28
30
"golang.org/x/sync/singleflight"
29
31
"golang.org/x/xerrors"
30
32
33
+ "github.com/coder/coder/buildinfo"
31
34
"github.com/coder/coder/coderd/httpapi"
32
35
"github.com/coder/coder/codersdk"
33
36
)
@@ -102,10 +105,20 @@ func Handler(siteFS fs.FS, binFS http.FileSystem, binHashes map[string]string) h
102
105
})))
103
106
mux .Handle ("/" , http .FileServer (http .FS (siteFS ))) // All other non-html static files.
104
107
108
+ buildInfo := codersdk.BuildInfoResponse {
109
+ ExternalURL : buildinfo .ExternalURL (),
110
+ Version : buildinfo .Version (),
111
+ }
112
+ buildInfoResponse , err := json .Marshal (buildInfo )
113
+ if err != nil {
114
+ panic ("failed to marshal build info: " + err .Error ())
115
+ }
116
+
105
117
return secureHeaders (& handler {
106
- fs : siteFS ,
107
- htmlFiles : files ,
108
- h : mux ,
118
+ fs : siteFS ,
119
+ htmlFiles : files ,
120
+ h : mux ,
121
+ buildInfoJSON : html .EscapeString (string (buildInfoResponse )),
109
122
})
110
123
}
111
124
@@ -117,8 +130,9 @@ type handler struct {
117
130
// scripts, and that nonce is passed through a template.
118
131
// We only do this for html files to reduce the amount of in memory caching
119
132
// of duplicate files as `fs`.
120
- htmlFiles * htmlTemplates
121
- h http.Handler
133
+ htmlFiles * htmlTemplates
134
+ h http.Handler
135
+ buildInfoJSON string
122
136
}
123
137
124
138
// filePath returns the filepath of the requested file.
@@ -138,8 +152,9 @@ func (h *handler) exists(filePath string) bool {
138
152
}
139
153
140
154
type htmlState struct {
141
- CSP cspState
142
- CSRF csrfState
155
+ CSP cspState
156
+ CSRF csrfState
157
+ BuildInfo string
143
158
}
144
159
145
160
type cspState struct {
@@ -184,7 +199,8 @@ func (h *handler) ServeHTTP(resp http.ResponseWriter, req *http.Request) {
184
199
reqFile := filePath (req .URL .Path )
185
200
state := htmlState {
186
201
// Token is the CSRF token for the given request
187
- CSRF : csrfState {Token : nosurf .Token (req )},
202
+ CSRF : csrfState {Token : nosurf .Token (req )},
203
+ BuildInfo : h .buildInfoJSON ,
188
204
}
189
205
190
206
// First check if it's a file we have in our templates
0 commit comments