Conversation
| } | ||
|
|
||
| // Adapted from 'https://golang.org/src/crypto/tls/generate_cert.go' | ||
| func generateSelfSignedCert() (string, string, error) { |
There was a problem hiding this comment.
Please simplify this method to only use what you're giving in the var-part.
websocket_test.go
Outdated
|
|
||
| // Adapted from 'https://golang.org/src/crypto/tls/generate_cert.go' | ||
| func generateSelfSignedCert() (string, string, error) { | ||
| var ( |
There was a problem hiding this comment.
var is very useful outside of methods, but not needed inside. You can directly write:
host := "127.0.0.1"
websocket_test.go
Outdated
|
|
||
| var priv *ecdsa.PrivateKey | ||
| var err error | ||
| switch ecdsaCurve { |
websocket_test.go
Outdated
| var notBefore time.Time | ||
| if len(validFrom) == 0 { | ||
| notBefore = time.Now() | ||
| } else { |
websocket_test.go
Outdated
| } | ||
|
|
||
| hosts := strings.Split(host, ",") | ||
| for _, h := range hosts { |
There was a problem hiding this comment.
remove for - there is only one host.
websocket_test.go
Outdated
|
|
||
| hosts := strings.Split(host, ",") | ||
| for _, h := range hosts { | ||
| if ip := net.ParseIP(h); ip != nil { |
websocket_test.go
Outdated
| Val: 10, | ||
| } | ||
| sr := &SimpleResponse{} | ||
| assert.Equal(t, uint64(0), client.Rx()) |
There was a problem hiding this comment.
I think you need require here, else the test will continue, even if this fails.
|
I found a way to download the patch: https://patch-diff.githubusercontent.com/raw/dedis/onet/pull/405.patch See: |
f97b92f to
0c26f50
Compare
local.go
Outdated
|
|
||
| // newTCPServerWithWebSocketTLS creates a new server with a tcpRouter with | ||
| // "localhost:"+port as an address and configure TLS for its websocket. | ||
| func newTCPServerWithWebSocketTLS(s network.Suite, port int, path string, |
There was a problem hiding this comment.
This is repeated code with respect to newTCPServer, right? Better would be to move the h.Start() and listening check out, and then call newTCPServer in both the TLS and non-TLS case. In the TLS case, add a call to SetWebsocketTLS.
Private methods are private for a reason: you are free to hack on them as much as necessary in order to make your new feature fit in without massive copy/paste. Becaues those copy/pastes become a huge anchor around our neck later.
server.go
Outdated
| } | ||
|
|
||
| // SetWebsocketTLS sets the TLS configuration for its websocket. | ||
| func (c *Server) SetWebsocketTLS(tlsCertificate []byte, tlsCertificateKey []byte) error { |
There was a problem hiding this comment.
The type is WebSocket (capital S) so all methods that talk about it should use the same capitalization.
websocket.go
Outdated
| if err != nil { | ||
| return err | ||
| } | ||
| w.server.Server.TLSConfig = &tls.Config{Certificates: []tls.Certificate{cert}} |
There was a problem hiding this comment.
With this API, you make it impossible for the caller to customize the tls.Config if they need to (and we will need to, in order to support LetsEncrypt via the golang.org/x/crypto/acme/autocert package) Another way to do this would be for type WebSocket to have a field called TLSConfig, with a comment saying, "can only be modified before Start is called". Then in app/config.go, instead of calling server.SetWebsockerTLS, you'd set server.WebSocket.TLSConfig as needed. the private field websocket in type onet.Server would need to be exported, but I see no problem with that.
Go prefers correct defaults, and empowering the caller to override them by sending in custom configs. And on balance, a reasonable new variable export (onet.Server.websocket) is better than two new exported APIs.
websocket.go
Outdated
| tls bool | ||
| // Pool of certificates we trust, can be used for self-signed certificates; | ||
| // only useful if tls is set to true. | ||
| trustedCertificates *x509.CertPool |
There was a problem hiding this comment.
Same as the server side:
This makes it impossible for callers to change the tls.Config if they want to. Instead, give them a TLSClientConfig field they can set, and then in Send(), do d := &websocket.Dialer{ TLSClientConfig: c.TLSClientConfig }
websocket.go
Outdated
| } | ||
|
|
||
| var wsProtocol string | ||
| if c.tls { |
There was a problem hiding this comment.
I do not see how the caller makes c.tls == true.
websocket.go
Outdated
| wsProtocol = "ws" | ||
| } | ||
| serverURL := fmt.Sprintf("%s://%s/%s/%s", wsProtocol, url, c.service, path) | ||
| headers := http.Header{"Origin": []string{"http://" + url}} |
There was a problem hiding this comment.
Should this http be https if wsProtocol is wss?
|
|
||
| const ( | ||
| // String is a CertificateURL type containing a certificate. | ||
| String CertificateURLType = "string" |
There was a problem hiding this comment.
Another proposal: the type should default to file, so that WebSocketTLSCertificate = "/etc/conode.crt" will do what any reasonable person would expect.
But since it is already here, WebSocketTLSCertificate = "string:XXX" should work too. (Although it is unclear that YAML can accept the embedded newlines that you typically find in PEM-encoded cert files.)
I do like the type:blob format, because it will help with LetsEncrypt. We can add LetsEncrypt support here like this: WebSocketTLSCertificate = "le:hostname.example.com" (LE requires that the server know what it's public FQDN is at the moment it requests the certificate.)
There was a problem hiding this comment.
I see! Yes I can do that. Also, are you saying we should change the delimiter from "://" to ":", or is "://" still fine?
There was a problem hiding this comment.
No, that's a mistake. I propose that the following work:
- "filename.pem"
- "file://filename.pem"
- "string://certificate-goes-here"
- "letsencrypt://FQDN-goes-here" (later, in another commit)
| Address network.Address | ||
| ListenAddress string | ||
| Description string | ||
| WebSocketTLSCertificate CertificateURL |
There was a problem hiding this comment.
There needs to be some new code in config_test.go proving that YAML can handle string:foo\nbar\nbaz correctly, because PEM-encoded certs have newlines in them.
There was a problem hiding this comment.
I guess you mean TOML, not YAML. But that's a fair concern. By checking the doc (https://github.com/toml-lang/toml) it seems it should not be an issue, right? I can still write a test for that (ParseCothority), since there isn't a test for loading and parsing the private.toml file in config_test.go anyway.
|
We also chatted on Slack about the fact that "go test -v" fails while "go test" succeeds. |
0c26f50 to
7907072
Compare
…mments on generating self-signed certificate.
…bSocket TLS certificate type set to 'file' + added test for ParseCothority.
| certFile.WriteString(wsTLSCert) | ||
| certFile.Close() | ||
|
|
||
| keyFile, err := ioutil.TempFile("", "temp_key.pem") |
There was a problem hiding this comment.
from godoc for TempFile: "It is the caller's responsibility to remove the file when no longer needed" See: https://godoc.org/io/ioutil#example-TempFile
There was a problem hiding this comment.
Ohh right! I was in fact looking at examples in our codebase and didn't see those removed, thus I assumed it was automatically done. For example, if you look in platform_test.go and search for ioutil.TempFile, are any of those removed in any way? Or should we add an issue to fix those?
There was a problem hiding this comment.
Yes, you can add an issue, thanks.
private.tomlfor setting the WebSocket TLS certificate and key, if wanted.WebSocketis now usingListenAndServeTLSusing the TLS configuration found in theprivate.tomlif given.Client(inwebsocket.go) can now communicate in TLS, if asked.In the
private.tomlfile, we can set the 2 WebSocket TLS fields using 2 different ways:string://{THE CONTENT OF THE CERTIFICATE}file://{THE PATH OF THE FILE CONTAINING THE CERTIFICATE}Fixes #383