From eb8fd0be73940518e5050c6658503c56570a3143 Mon Sep 17 00:00:00 2001 From: reinkrul Date: Fri, 1 Dec 2023 10:35:37 +0100 Subject: [PATCH] Root URL server config property to replace auth.publicurl (#2633) --- README.rst | 6 +-- auth/auth.go | 9 ++-- auth/auth_test.go | 52 +------------------ auth/cmd/cmd.go | 4 -- auth/cmd/cmd_test.go | 1 - auth/config.go | 1 - auth/test.go | 1 - auth/test/testconfig.yaml | 3 -- charts/nuts-node/values.yaml | 2 +- core/server_config.go | 20 ++++++- core/server_config_test.go | 25 +++++++++ docs/pages/deployment/cli-reference.rst | 4 +- docs/pages/deployment/configuration.rst | 2 +- docs/pages/deployment/server_options.rst | 4 +- .../getting-started/1-running-docker.rst | 3 +- .../getting-started/5-authentication.rst | 3 +- .../auth/selfsigned/config/node/nuts.yaml | 2 +- e2e-tests/denylist/defaults/nuts.yaml | 2 +- e2e-tests/denylist/github/nuts.yaml | 2 +- .../nuts-network/direct-wan/node-A/nuts.yaml | 2 +- .../nuts-network/direct-wan/node-B/nuts.yaml | 2 +- .../gossip-overflow/node-A/nuts.yaml | 2 +- .../gossip-overflow/node-B/nuts.yaml | 2 +- .../nuts-network/gossip/node-A/nuts.yaml | 2 +- .../nuts-network/gossip/node-B/nuts.yaml | 2 +- .../nuts-network/gossip/node-C/nuts.yaml | 2 +- .../nuts-network/gossip/node-D/nuts.yaml | 2 +- .../private-transactions/node-A/nuts.yaml | 2 +- .../private-transactions/node-B/nuts.yaml | 2 +- .../ssl-offloading/haproxy/node-A/nuts.yaml | 2 +- .../ssl-offloading/haproxy/node-B/nuts.yaml | 2 +- .../ssl-offloading/nginx/node-A/nuts.yaml | 2 +- .../ssl-offloading/nginx/node-B/nuts.yaml | 2 +- .../ssl-pass-through/node-A/nuts.yaml | 2 +- .../ssl-pass-through/node-B/nuts.yaml | 2 +- e2e-tests/oauth-flow/rfc002/node-A/nuts.yaml | 2 +- e2e-tests/oauth-flow/rfc002/node-B/nuts.yaml | 2 +- e2e-tests/oauth-flow/rfc021/node-A/nuts.yaml | 2 +- e2e-tests/oauth-flow/rfc021/node-B/nuts.yaml | 2 +- .../issuer-initiated/node-A/nuts.yaml | 2 +- .../issuer-initiated/node-B/nuts.yaml | 2 +- .../network-issuance/node-A/nuts.yaml | 2 +- .../network-issuance/node-B/nuts.yaml | 2 +- e2e-tests/ops/key-rotation/node-A/nuts.yaml | 2 +- e2e-tests/ops/key-rotation/node-B/nuts.yaml | 2 +- .../storage/backup-restore/node-A/nuts.yaml | 2 +- e2e-tests/storage/redis/node-A/nuts.yaml | 2 +- e2e-tests/storage/redis/node-B/nuts.yaml | 2 +- e2e-tests/storage/vault/nuts.yaml | 2 +- main_test.go | 2 +- test/node/server.go | 2 +- 51 files changed, 95 insertions(+), 115 deletions(-) delete mode 100644 auth/test/testconfig.yaml diff --git a/README.rst b/README.rst index 350f0ccb54..f11f43e231 100644 --- a/README.rst +++ b/README.rst @@ -185,6 +185,7 @@ The following options can be configured on the server: internalratelimiter true When set, expensive internal calls are rate-limited to protect the network. Always enabled in strict mode. loggerformat text Log format (text, json) strictmode true When set, insecure settings are forbidden. + url Public facing URL of the server (required). Must be HTTPS when strictmode is set. verbosity info Log level (trace, debug, info, warn, error) tls.certfile PEM file containing the certificate for the server (also used as client certificate). tls.certheader Name of the HTTP header that will contain the client certificate when TLS is offloaded. @@ -195,7 +196,6 @@ The following options can be configured on the server: auth.accesstokenlifespan 60 defines how long (in seconds) an access token is valid. Uses default in strict mode. auth.clockskew 5000 allowed JWT Clock skew in milliseconds auth.contractvalidators [irma,uzi,dummy,employeeid] sets the different contract validators to use - auth.publicurl public URL which can be reached by a users IRMA client, this should include the scheme and domain: https://example.com. Additional paths should only be added if some sort of url-rewriting is done in a reverse-proxy. auth.http.timeout 30 HTTP timeout (in seconds) used by the Auth API HTTP client auth.irma.autoupdateschemas true set if you want automatically update the IRMA schemas every 60 minutes. auth.irma.schememanager pbdf IRMA schemeManager to use for attributes. Can be either 'pbdf' or 'irma-demo'. @@ -227,7 +227,7 @@ The following options can be configured on the server: http.default.auth.type Whether to enable authentication for the default interface, specify 'token_v2' for bearer token mode or 'token' for legacy bearer token mode. http.default.cors.origin [] When set, enables CORS from the specified origins on the default HTTP interface. **JSONLD** - jsonld.contexts.localmapping [https://nuts.nl/credentials/v1=assets/contexts/nuts.ldjson,https://www.w3.org/2018/credentials/v1=assets/contexts/w3c-credentials-v1.ldjson,https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json=assets/contexts/lds-jws2020-v1.ldjson,https://schema.org=assets/contexts/schema-org-v13.ldjson] This setting allows mapping external URLs to local files for e.g. preventing external dependencies. These mappings have precedence over those in remoteallowlist. + jsonld.contexts.localmapping [https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json=assets/contexts/lds-jws2020-v1.ldjson,https://schema.org=assets/contexts/schema-org-v13.ldjson,https://nuts.nl/credentials/v1=assets/contexts/nuts.ldjson,https://www.w3.org/2018/credentials/v1=assets/contexts/w3c-credentials-v1.ldjson] This setting allows mapping external URLs to local files for e.g. preventing external dependencies. These mappings have precedence over those in remoteallowlist. jsonld.contexts.remoteallowlist [https://schema.org,https://www.w3.org/2018/credentials/v1,https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json] In strict mode, fetching external JSON-LD contexts is not allowed except for context-URLs listed here. **Network** network.bootstrapnodes [] List of bootstrap nodes (':') which the node initially connect to. @@ -291,7 +291,7 @@ See :ref:`getting started ` on how to set this up correctly. The incorporated `IRMA server `_ is automatically changed to production mode. In fact, running in strict mode is the only way to enable IRMA's production mode. -In addition, it requires ``auth.irma.schememanager=pbdf`` and the ``auth.publicurl`` where the IRMA client can reach the server must be set. +In addition, it requires ``auth.irma.schememanager=pbdf``. As a general safety precaution ``auth.contractvalidators`` ignores the ``dummy`` option if configured, requesting an access token from another node on ``/n2n/auth/v1/accesstoken`` does not return any error details, diff --git a/auth/auth.go b/auth/auth.go index f77a801d31..c7dbeefd8d 100644 --- a/auth/auth.go +++ b/auth/auth.go @@ -124,17 +124,14 @@ func (auth *Auth) Configure(config core.ServerConfig) error { return errors.New("in strictmode the only valid irma-scheme-manager is 'pbdf'") } - if auth.config.PublicURL == "" { - return errors.New("invalid auth.publicurl: must provide url") - } var err error - auth.publicURL, err = core.ParsePublicURL(auth.config.PublicURL, config.Strictmode) + auth.publicURL, err = config.ServerURL() if err != nil { - return fmt.Errorf("invalid auth.publicurl: %w", err) + return err } auth.contractNotary = notary.NewNotary(notary.Config{ - PublicURL: auth.config.PublicURL, + PublicURL: auth.publicURL.String(), IrmaConfigPath: path.Join(config.Datadir, "irma"), IrmaSchemeManager: auth.config.Irma.SchemeManager, AutoUpdateIrmaSchemas: auth.config.Irma.AutoUpdateSchemas, diff --git a/auth/auth_test.go b/auth/auth_test.go index 21f1d9a9ae..ddc777f4a5 100644 --- a/auth/auth_test.go +++ b/auth/auth_test.go @@ -33,6 +33,7 @@ import ( func TestAuth_Configure(t *testing.T) { tlsServerConfig := *core.NewServerConfig() + tlsServerConfig.URL = "https://nuts.nl" tlsServerConfig.LegacyTLS.TrustStoreFile = "test/certs/ca.pem" tlsServerConfig.LegacyTLS.CertKeyFile = "test/certs/example.com.key" tlsServerConfig.LegacyTLS.CertFile = "test/certs/example.com.pem" @@ -40,7 +41,6 @@ func TestAuth_Configure(t *testing.T) { t.Run("ok", func(t *testing.T) { config := DefaultConfig() config.ContractValidators = []string{"uzi"} - config.PublicURL = "https://nuts.nl" ctrl := gomock.NewController(t) pkiMock := pki.NewMockProvider(ctrl) pkiMock.EXPECT().AddTruststore(gomock.Any()) // uzi @@ -53,28 +53,6 @@ func TestAuth_Configure(t *testing.T) { require.NoError(t, i.Configure(tlsServerConfig)) }) - t.Run("publicUrl", func(t *testing.T) { - t.Run("error - missing", func(t *testing.T) { - authCfg := TestConfig() - authCfg.PublicURL = "" - authCfg.Irma.SchemeManager = "pbdf" - i := testInstance(t, authCfg) - cfg := core.NewServerConfig() - cfg.Strictmode = true - cfg.TLS.CertFile = "certificate.pem" - assert.EqualError(t, i.Configure(*cfg), "invalid auth.publicurl: must provide url") - }) - t.Run("error - invalid URL (must be hostname, not IP)", func(t *testing.T) { - authCfg := TestConfig() - authCfg.Irma.SchemeManager = "pbdf" - authCfg.PublicURL = "https://127.0.0.1" - i := testInstance(t, authCfg) - cfg := core.NewServerConfig() - cfg.Strictmode = true - assert.EqualError(t, i.Configure(*cfg), "invalid auth.publicurl: hostname is IP") - }) - }) - t.Run("error - IRMA config failure", func(t *testing.T) { authCfg := TestConfig() authCfg.Irma.SchemeManager = "non-existing" @@ -106,6 +84,7 @@ func TestAuth_Configure(t *testing.T) { i := testInstance(t, authCfg) serverConfig := core.NewServerConfig() serverConfig.Strictmode = true + serverConfig.URL = "https://nuts.nl" err := i.Configure(*serverConfig) assert.EqualError(t, err, "in strictmode TLS must be enabled") }) @@ -118,33 +97,6 @@ func TestAuth_Configure(t *testing.T) { err := i.Configure(tlsServerConfig) assert.ErrorIs(t, err, assert.AnError) }) - t.Run("public url", func(t *testing.T) { - type test struct { - strict bool - pURL string - errStr string - } - tt := []test{ - {true, "", "invalid auth.publicurl: must provide url"}, - {true, ":invalid", "invalid auth.publicurl: parse \":invalid\": missing protocol scheme"}, - {true, "https://127.0.0.1", "invalid auth.publicurl: hostname is IP"}, - {true, "https://example.com", "invalid auth.publicurl: hostname is RFC2606 reserved"}, - {true, "https://localhost", "invalid auth.publicurl: hostname is RFC2606 reserved"}, - {true, "http://nuts.nl", "invalid auth.publicurl: scheme must be https"}, - - {false, "", "invalid auth.publicurl: must provide url"}, - {false, ":invalid", "invalid auth.publicurl: parse \":invalid\": missing protocol scheme"}, - {false, "something://nuts.nl", "invalid auth.publicurl: scheme must be http or https"}, - } - authCfg := TestConfig() - cfg := core.NewServerConfig() - for _, test := range tt { - authCfg.PublicURL = test.pURL - i := testInstance(t, authCfg) - cfg.Strictmode = test.strict - assert.EqualError(t, i.Configure(*cfg), test.errStr, "test config: url=%s; strict=%s", test.pURL, test.strict) - } - }) } func TestAuth_Name(t *testing.T) { diff --git a/auth/cmd/cmd.go b/auth/cmd/cmd.go index 13a1680b73..d9c8f8cdd3 100644 --- a/auth/cmd/cmd.go +++ b/auth/cmd/cmd.go @@ -23,9 +23,6 @@ import ( "github.com/spf13/pflag" ) -// ConfPublicURL is the config key for the public URL the http/irma server can be discovered -const ConfPublicURL = "auth.publicurl" - // ConfClockSkew is the config key for allowed JWT clockskew (deviance of iat, exp) in milliseconds const ConfClockSkew = "auth.clockskew" @@ -55,7 +52,6 @@ func FlagSet() *pflag.FlagSet { defs := auth.DefaultConfig() flags.String(ConfIrmaSchemeManager, defs.Irma.SchemeManager, "IRMA schemeManager to use for attributes. Can be either 'pbdf' or 'irma-demo'.") - flags.String(ConfPublicURL, defs.PublicURL, "public URL which can be reached by a users IRMA client, this should include the scheme and domain: https://example.com. Additional paths should only be added if some sort of url-rewriting is done in a reverse-proxy.") flags.Bool(ConfAutoUpdateIrmaSchemas, defs.Irma.AutoUpdateSchemas, "set if you want automatically update the IRMA schemas every 60 minutes.") flags.Int(ConfHTTPTimeout, defs.HTTPTimeout, "HTTP timeout (in seconds) used by the Auth API HTTP client") flags.Int(ConfClockSkew, defs.ClockSkew, "allowed JWT Clock skew in milliseconds") diff --git a/auth/cmd/cmd_test.go b/auth/cmd/cmd_test.go index 70b246442c..6df25bb351 100644 --- a/auth/cmd/cmd_test.go +++ b/auth/cmd/cmd_test.go @@ -49,7 +49,6 @@ func TestFlagSet(t *testing.T) { ConfAutoUpdateIrmaSchemas, ConfIrmaSchemeManager, ConfPresentationExchangeMappingFile, - ConfPublicURL, ConfV2APIEnabled, }, keys) } diff --git a/auth/config.go b/auth/config.go index 1b1bf1acd8..3f64eba2da 100644 --- a/auth/config.go +++ b/auth/config.go @@ -29,7 +29,6 @@ import ( type Config struct { Irma IrmaConfig `koanf:"irma"` HTTPTimeout int `koanf:"http.timeout"` - PublicURL string `koanf:"publicurl"` ClockSkew int `koanf:"clockskew"` ContractValidators []string `koanf:"contractvalidators"` AccessTokenLifeSpan int `koanf:"accesstokenlifespan"` diff --git a/auth/test.go b/auth/test.go index bfe96fb526..76c1f8afe1 100644 --- a/auth/test.go +++ b/auth/test.go @@ -31,7 +31,6 @@ import ( func TestConfig() Config { config := DefaultConfig() config.ContractValidators = []string{"dummy"} - config.PublicURL = "https://nuts.nl" return config } diff --git a/auth/test/testconfig.yaml b/auth/test/testconfig.yaml deleted file mode 100644 index 6092c3b5f5..0000000000 --- a/auth/test/testconfig.yaml +++ /dev/null @@ -1,3 +0,0 @@ -publicUrl: https://example.org -irma: - directory: ../../development/irma \ No newline at end of file diff --git a/charts/nuts-node/values.yaml b/charts/nuts-node/values.yaml index e03afdf4f8..742864ddb5 100644 --- a/charts/nuts-node/values.yaml +++ b/charts/nuts-node/values.yaml @@ -109,8 +109,8 @@ nuts: network: enabletls: true grpcaddr: :5555 + url: https://chart-example.local auth: - publicurl: https://chart-example.local contractvalidators: - irma - uzi diff --git a/core/server_config.go b/core/server_config.go index 80a45fe7f9..ed6b59ccd9 100644 --- a/core/server_config.go +++ b/core/server_config.go @@ -23,12 +23,14 @@ import ( "bytes" "crypto/tls" "crypto/x509" + "errors" "fmt" "github.com/knadh/koanf" "github.com/knadh/koanf/providers/env" "github.com/knadh/koanf/providers/posflag" "github.com/sirupsen/logrus" "github.com/spf13/pflag" + "net/url" "reflect" "strings" ) @@ -58,7 +60,9 @@ type ServerConfig struct { Datadir string `koanf:"datadir"` TLS TLSConfig `koanf:"tls"` LegacyTLS *NetworkTLSConfig `koanf:"network"` - configMap *koanf.Koanf + // URL contains the base URL for public-facing HTTP services. + URL string `koanf:"url"` + configMap *koanf.Koanf } // TLSConfig specifies how TLS should be configured for connections. @@ -261,6 +265,7 @@ func FlagSet() *pflag.FlagSet { flagSet.Bool("strictmode", true, "When set, insecure settings are forbidden.") flagSet.Bool("internalratelimiter", true, "When set, expensive internal calls are rate-limited to protect the network. Always enabled in strict mode.") flagSet.String("datadir", "./data", "Directory where the node stores its files.") + flagSet.String("url", "", "Public facing URL of the server (required). Must be HTTPS when strictmode is set.") flagSet.String("tls.certfile", "", "PEM file containing the certificate for the server (also used as client certificate).") flagSet.String("tls.certkeyfile", "", "PEM file containing the private key of the server certificate.") flagSet.String("tls.truststorefile", "truststore.pem", "PEM file containing the trusted CA certificates for authenticating remote servers.") @@ -315,6 +320,19 @@ func (ngc *ServerConfig) InjectIntoEngine(e Injectable) error { return unmarshalRecursive([]string{strings.ToLower(e.Name())}, e.Config(), ngc.configMap) } +// ServerURL returns the parsed URL of the server +func (ngc *ServerConfig) ServerURL() (*url.URL, error) { + // Validate server URL + if ngc.URL == "" { + return nil, errors.New("'url' must be configured") + } + result, err := ParsePublicURL(ngc.URL, ngc.Strictmode) + if err != nil { + return nil, fmt.Errorf("invalid 'url': %w", err) + } + return result, nil +} + func elemType(ty reflect.Type) (reflect.Type, bool) { isPtr := ty.Kind() == reflect.Ptr diff --git a/core/server_config_test.go b/core/server_config_test.go index 67430aa380..aa6c311965 100644 --- a/core/server_config_test.go +++ b/core/server_config_test.go @@ -294,3 +294,28 @@ func TestTLSConfig_LoadTrustStore(t *testing.T) { assert.EqualError(t, err, "unable to read trust store (file=test/non-existent.pem): open test/non-existent.pem: no such file or directory") }) } + +func TestServerConfig_ServerURL(t *testing.T) { + t.Run("url", func(t *testing.T) { + cfg := ServerConfig{URL: "https://example.com"} + actual, err := cfg.ServerURL() + assert.NoError(t, err) + assert.Equal(t, "https://example.com", actual.String()) + }) + t.Run("public URL can be http when not in strict mode", func(t *testing.T) { + cfg := ServerConfig{URL: "http://nuts.nl"} + actual, err := cfg.ServerURL() + assert.NoError(t, err) + assert.Equal(t, "http://nuts.nl", actual.String()) + }) + t.Run("url is required", func(t *testing.T) { + cfg := ServerConfig{} + _, err := cfg.ServerURL() + assert.EqualError(t, err, "'url' must be configured") + }) + t.Run("url is invalid", func(t *testing.T) { + cfg := ServerConfig{URL: "nuts.nl"} + _, err := cfg.ServerURL() + assert.EqualError(t, err, "invalid 'url': url must contain scheme and host") + }) +} diff --git a/docs/pages/deployment/cli-reference.rst b/docs/pages/deployment/cli-reference.rst index fea8bf69eb..ac8c33f2fb 100755 --- a/docs/pages/deployment/cli-reference.rst +++ b/docs/pages/deployment/cli-reference.rst @@ -19,7 +19,6 @@ The following options apply to the server commands below: --auth.http.timeout int HTTP timeout (in seconds) used by the Auth API HTTP client (default 30) --auth.irma.autoupdateschemas set if you want automatically update the IRMA schemas every 60 minutes. (default true) --auth.irma.schememanager string IRMA schemeManager to use for attributes. Can be either 'pbdf' or 'irma-demo'. (default "pbdf") - --auth.publicurl string public URL which can be reached by a users IRMA client, this should include the scheme and domain: https://example.com. Additional paths should only be added if some sort of url-rewriting is done in a reverse-proxy. --configfile string Nuts config file (default "nuts.yaml") --cpuprofile string When set, a CPU profile is written to the given path. Ignored when strictmode is set. --crypto.external.address string Address of the external storage service. @@ -46,7 +45,7 @@ The following options apply to the server commands below: --http.default.log string What to log about HTTP requests. Options are 'nothing', 'metadata' (log request method, URI, IP and response code), and 'metadata-and-body' (log the request and response body, in addition to the metadata). (default "metadata") --http.default.tls string Whether to enable TLS for the default interface, options are 'disabled', 'server', 'server-client'. Leaving it empty is synonymous to 'disabled', --internalratelimiter When set, expensive internal calls are rate-limited to protect the network. Always enabled in strict mode. (default true) - --jsonld.contexts.localmapping stringToString This setting allows mapping external URLs to local files for e.g. preventing external dependencies. These mappings have precedence over those in remoteallowlist. (default [https://www.w3.org/2018/credentials/v1=assets/contexts/w3c-credentials-v1.ldjson,https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json=assets/contexts/lds-jws2020-v1.ldjson,https://schema.org=assets/contexts/schema-org-v13.ldjson,https://nuts.nl/credentials/v1=assets/contexts/nuts.ldjson]) + --jsonld.contexts.localmapping stringToString This setting allows mapping external URLs to local files for e.g. preventing external dependencies. These mappings have precedence over those in remoteallowlist. (default [https://nuts.nl/credentials/v1=assets/contexts/nuts.ldjson,https://www.w3.org/2018/credentials/v1=assets/contexts/w3c-credentials-v1.ldjson,https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json=assets/contexts/lds-jws2020-v1.ldjson,https://schema.org=assets/contexts/schema-org-v13.ldjson]) --jsonld.contexts.remoteallowlist strings In strict mode, fetching external JSON-LD contexts is not allowed except for context-URLs listed here. (default [https://schema.org,https://www.w3.org/2018/credentials/v1,https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json]) --loggerformat string Log format (text, json) (default "text") --network.bootstrapnodes strings List of bootstrap nodes (':') which the node initially connect to. @@ -79,6 +78,7 @@ The following options apply to the server commands below: --tls.certkeyfile string PEM file containing the private key of the server certificate. --tls.offload string Whether to enable TLS offloading for incoming connections. Enable by setting it to 'incoming'. If enabled 'tls.certheader' must be configured as well. --tls.truststorefile string PEM file containing the trusted CA certificates for authenticating remote servers. (default "truststore.pem") + --url string Public facing URL of the server (required). Must be HTTPS when strictmode is set. --vcr.openid4vci.definitionsdir string Directory with the additional credential definitions the node could issue (experimental, may change without notice). --vcr.openid4vci.enabled Enable issuing and receiving credentials over OpenID4VCI. (default true) --vcr.openid4vci.timeout duration Time-out for OpenID4VCI HTTP client operations. (default 30s) diff --git a/docs/pages/deployment/configuration.rst b/docs/pages/deployment/configuration.rst index 98aba45603..54bfc32897 100644 --- a/docs/pages/deployment/configuration.rst +++ b/docs/pages/deployment/configuration.rst @@ -79,7 +79,7 @@ See :ref:`getting started ` on how to set this up correctly. The incorporated `IRMA server `_ is automatically changed to production mode. In fact, running in strict mode is the only way to enable IRMA's production mode. -In addition, it requires ``auth.irma.schememanager=pbdf`` and the ``auth.publicurl`` where the IRMA client can reach the server must be set. +In addition, it requires ``auth.irma.schememanager=pbdf``. As a general safety precaution ``auth.contractvalidators`` ignores the ``dummy`` option if configured, requesting an access token from another node on ``/n2n/auth/v1/accesstoken`` does not return any error details, diff --git a/docs/pages/deployment/server_options.rst b/docs/pages/deployment/server_options.rst index cb1e7afef7..85076e29c5 100755 --- a/docs/pages/deployment/server_options.rst +++ b/docs/pages/deployment/server_options.rst @@ -11,6 +11,7 @@ internalratelimiter true When set, expensive internal calls are rate-limited to protect the network. Always enabled in strict mode. loggerformat text Log format (text, json) strictmode true When set, insecure settings are forbidden. + url Public facing URL of the server (required). Must be HTTPS when strictmode is set. verbosity info Log level (trace, debug, info, warn, error) tls.certfile PEM file containing the certificate for the server (also used as client certificate). tls.certheader Name of the HTTP header that will contain the client certificate when TLS is offloaded. @@ -21,7 +22,6 @@ auth.accesstokenlifespan 60 defines how long (in seconds) an access token is valid. Uses default in strict mode. auth.clockskew 5000 allowed JWT Clock skew in milliseconds auth.contractvalidators [irma,uzi,dummy,employeeid] sets the different contract validators to use - auth.publicurl public URL which can be reached by a users IRMA client, this should include the scheme and domain: https://example.com. Additional paths should only be added if some sort of url-rewriting is done in a reverse-proxy. auth.http.timeout 30 HTTP timeout (in seconds) used by the Auth API HTTP client auth.irma.autoupdateschemas true set if you want automatically update the IRMA schemas every 60 minutes. auth.irma.schememanager pbdf IRMA schemeManager to use for attributes. Can be either 'pbdf' or 'irma-demo'. @@ -53,7 +53,7 @@ http.default.auth.type Whether to enable authentication for the default interface, specify 'token_v2' for bearer token mode or 'token' for legacy bearer token mode. http.default.cors.origin [] When set, enables CORS from the specified origins on the default HTTP interface. **JSONLD** - jsonld.contexts.localmapping [https://nuts.nl/credentials/v1=assets/contexts/nuts.ldjson,https://www.w3.org/2018/credentials/v1=assets/contexts/w3c-credentials-v1.ldjson,https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json=assets/contexts/lds-jws2020-v1.ldjson,https://schema.org=assets/contexts/schema-org-v13.ldjson] This setting allows mapping external URLs to local files for e.g. preventing external dependencies. These mappings have precedence over those in remoteallowlist. + jsonld.contexts.localmapping [https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json=assets/contexts/lds-jws2020-v1.ldjson,https://schema.org=assets/contexts/schema-org-v13.ldjson,https://nuts.nl/credentials/v1=assets/contexts/nuts.ldjson,https://www.w3.org/2018/credentials/v1=assets/contexts/w3c-credentials-v1.ldjson] This setting allows mapping external URLs to local files for e.g. preventing external dependencies. These mappings have precedence over those in remoteallowlist. jsonld.contexts.remoteallowlist [https://schema.org,https://www.w3.org/2018/credentials/v1,https://w3c-ccg.github.io/lds-jws2020/contexts/lds-jws2020-v1.json] In strict mode, fetching external JSON-LD contexts is not allowed except for context-URLs listed here. **Network** network.bootstrapnodes [] List of bootstrap nodes (':') which the node initially connect to. diff --git a/docs/pages/getting-started/1-running-docker.rst b/docs/pages/getting-started/1-running-docker.rst index 33cbab1d0f..9e1d7c8d48 100644 --- a/docs/pages/getting-started/1-running-docker.rst +++ b/docs/pages/getting-started/1-running-docker.rst @@ -48,8 +48,7 @@ This setup uses the following ``nuts.yaml`` configuration file: network: bootstrapnodes: - example.com:5555 - auth: - publicurl: https://example.com + url: https://example.com .. note:: diff --git a/docs/pages/getting-started/5-authentication.rst b/docs/pages/getting-started/5-authentication.rst index 602069e882..b5bd9b630f 100644 --- a/docs/pages/getting-started/5-authentication.rst +++ b/docs/pages/getting-started/5-authentication.rst @@ -20,8 +20,7 @@ The domain must be configured on the Nuts node: .. code-block:: yaml - auth: - publicurl: https://example.com + url: https://example.com Getting a valid contract ************************ diff --git a/e2e-tests/auth/selfsigned/config/node/nuts.yaml b/e2e-tests/auth/selfsigned/config/node/nuts.yaml index 4697085b84..425acee0f0 100644 --- a/e2e-tests/auth/selfsigned/config/node/nuts.yaml +++ b/e2e-tests/auth/selfsigned/config/node/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node:1323 datadir: /opt/nuts/data strictmode: false http: @@ -7,7 +8,6 @@ http: origin: "*" verbosity: debug auth: - publicurl: http://node:1323 contractvalidators: - selfsigned network: diff --git a/e2e-tests/denylist/defaults/nuts.yaml b/e2e-tests/denylist/defaults/nuts.yaml index 5636650b57..611864b045 100644 --- a/e2e-tests/denylist/defaults/nuts.yaml +++ b/e2e-tests/denylist/defaults/nuts.yaml @@ -1,3 +1,4 @@ +url: http://nuts-node verbosity: trace strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://nuts-node contractvalidators: - dummy irma: diff --git a/e2e-tests/denylist/github/nuts.yaml b/e2e-tests/denylist/github/nuts.yaml index 794ed11345..dba5e5b107 100644 --- a/e2e-tests/denylist/github/nuts.yaml +++ b/e2e-tests/denylist/github/nuts.yaml @@ -1,3 +1,4 @@ +url: http://nuts-node verbosity: trace strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://nuts-node contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/direct-wan/node-A/nuts.yaml b/e2e-tests/nuts-network/direct-wan/node-A/nuts.yaml index aa5876837d..5cae48ba51 100644 --- a/e2e-tests/nuts-network/direct-wan/node-A/nuts.yaml +++ b/e2e-tests/nuts-network/direct-wan/node-A/nuts.yaml @@ -1,10 +1,10 @@ +url: https://node-A verbosity: debug internalratelimiter: false http: default: address: :1323 auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/direct-wan/node-B/nuts.yaml b/e2e-tests/nuts-network/direct-wan/node-B/nuts.yaml index d8fe3aa960..e6f2b370dd 100644 --- a/e2e-tests/nuts-network/direct-wan/node-B/nuts.yaml +++ b/e2e-tests/nuts-network/direct-wan/node-B/nuts.yaml @@ -1,10 +1,10 @@ +url: https://node-B verbosity: debug internalratelimiter: false http: default: address: :1323 auth: - publicurl: https://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/gossip-overflow/node-A/nuts.yaml b/e2e-tests/nuts-network/gossip-overflow/node-A/nuts.yaml index 3168ee03dd..c51926cff7 100644 --- a/e2e-tests/nuts-network/gossip-overflow/node-A/nuts.yaml +++ b/e2e-tests/nuts-network/gossip-overflow/node-A/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-A verbosity: debug strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/gossip-overflow/node-B/nuts.yaml b/e2e-tests/nuts-network/gossip-overflow/node-B/nuts.yaml index aa53375990..bff8eb9aec 100644 --- a/e2e-tests/nuts-network/gossip-overflow/node-B/nuts.yaml +++ b/e2e-tests/nuts-network/gossip-overflow/node-B/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-B verbosity: debug strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/gossip/node-A/nuts.yaml b/e2e-tests/nuts-network/gossip/node-A/nuts.yaml index f71e2b7324..8a9289d422 100644 --- a/e2e-tests/nuts-network/gossip/node-A/nuts.yaml +++ b/e2e-tests/nuts-network/gossip/node-A/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-A verbosity: debug strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/gossip/node-B/nuts.yaml b/e2e-tests/nuts-network/gossip/node-B/nuts.yaml index c3e57b9bae..d52819919d 100644 --- a/e2e-tests/nuts-network/gossip/node-B/nuts.yaml +++ b/e2e-tests/nuts-network/gossip/node-B/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-B verbosity: debug strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/gossip/node-C/nuts.yaml b/e2e-tests/nuts-network/gossip/node-C/nuts.yaml index 9922480ed3..0fc7658f5b 100644 --- a/e2e-tests/nuts-network/gossip/node-C/nuts.yaml +++ b/e2e-tests/nuts-network/gossip/node-C/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-C verbosity: debug strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://node-C contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/gossip/node-D/nuts.yaml b/e2e-tests/nuts-network/gossip/node-D/nuts.yaml index 0ac26ceca2..f4310da488 100644 --- a/e2e-tests/nuts-network/gossip/node-D/nuts.yaml +++ b/e2e-tests/nuts-network/gossip/node-D/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-D verbosity: debug strictmode: false internalratelimiter: false @@ -5,7 +6,6 @@ http: default: address: :1323 auth: - publicurl: http://node-D contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/private-transactions/node-A/nuts.yaml b/e2e-tests/nuts-network/private-transactions/node-A/nuts.yaml index 31be29b5c7..7b5269d5e9 100644 --- a/e2e-tests/nuts-network/private-transactions/node-A/nuts.yaml +++ b/e2e-tests/nuts-network/private-transactions/node-A/nuts.yaml @@ -1,3 +1,4 @@ +url: https://node-A verbosity: debug strictmode: true internalratelimiter: false @@ -6,7 +7,6 @@ http: default: address: :1323 auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/private-transactions/node-B/nuts.yaml b/e2e-tests/nuts-network/private-transactions/node-B/nuts.yaml index def0f22cf4..4fdb49f879 100644 --- a/e2e-tests/nuts-network/private-transactions/node-B/nuts.yaml +++ b/e2e-tests/nuts-network/private-transactions/node-B/nuts.yaml @@ -1,3 +1,4 @@ +url: https://node-B verbosity: debug strictmode: true internalratelimiter: false @@ -6,7 +7,6 @@ http: default: address: :1323 auth: - publicurl: https://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/ssl-offloading/haproxy/node-A/nuts.yaml b/e2e-tests/nuts-network/ssl-offloading/haproxy/node-A/nuts.yaml index 461c443748..068baf10ba 100644 --- a/e2e-tests/nuts-network/ssl-offloading/haproxy/node-A/nuts.yaml +++ b/e2e-tests/nuts-network/ssl-offloading/haproxy/node-A/nuts.yaml @@ -1,7 +1,7 @@ +url: https://node-A verbosity: debug internalratelimiter: false auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/ssl-offloading/haproxy/node-B/nuts.yaml b/e2e-tests/nuts-network/ssl-offloading/haproxy/node-B/nuts.yaml index 148eb802d9..a74546a6dd 100644 --- a/e2e-tests/nuts-network/ssl-offloading/haproxy/node-B/nuts.yaml +++ b/e2e-tests/nuts-network/ssl-offloading/haproxy/node-B/nuts.yaml @@ -1,7 +1,7 @@ +url: https://node-B verbosity: debug internalratelimiter: false auth: - publicurl: https://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/ssl-offloading/nginx/node-A/nuts.yaml b/e2e-tests/nuts-network/ssl-offloading/nginx/node-A/nuts.yaml index 461c443748..068baf10ba 100644 --- a/e2e-tests/nuts-network/ssl-offloading/nginx/node-A/nuts.yaml +++ b/e2e-tests/nuts-network/ssl-offloading/nginx/node-A/nuts.yaml @@ -1,7 +1,7 @@ +url: https://node-A verbosity: debug internalratelimiter: false auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/ssl-offloading/nginx/node-B/nuts.yaml b/e2e-tests/nuts-network/ssl-offloading/nginx/node-B/nuts.yaml index 148eb802d9..a74546a6dd 100644 --- a/e2e-tests/nuts-network/ssl-offloading/nginx/node-B/nuts.yaml +++ b/e2e-tests/nuts-network/ssl-offloading/nginx/node-B/nuts.yaml @@ -1,7 +1,7 @@ +url: https://node-B verbosity: debug internalratelimiter: false auth: - publicurl: https://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/ssl-pass-through/node-A/nuts.yaml b/e2e-tests/nuts-network/ssl-pass-through/node-A/nuts.yaml index 4390a17b04..ac684d748b 100644 --- a/e2e-tests/nuts-network/ssl-pass-through/node-A/nuts.yaml +++ b/e2e-tests/nuts-network/ssl-pass-through/node-A/nuts.yaml @@ -1,6 +1,6 @@ +url: https://node-A verbosity: debug auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/nuts-network/ssl-pass-through/node-B/nuts.yaml b/e2e-tests/nuts-network/ssl-pass-through/node-B/nuts.yaml index 7a7fec6a83..2919b2e496 100644 --- a/e2e-tests/nuts-network/ssl-pass-through/node-B/nuts.yaml +++ b/e2e-tests/nuts-network/ssl-pass-through/node-B/nuts.yaml @@ -1,6 +1,6 @@ +url: https://node-B verbosity: debug auth: - publicurl: https://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/oauth-flow/rfc002/node-A/nuts.yaml b/e2e-tests/oauth-flow/rfc002/node-A/nuts.yaml index 3a5389a516..b2e5b8785e 100644 --- a/e2e-tests/oauth-flow/rfc002/node-A/nuts.yaml +++ b/e2e-tests/oauth-flow/rfc002/node-A/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-A verbosity: debug strictmode: false internalratelimiter: false @@ -6,7 +7,6 @@ http: default: address: :1323 auth: - publicurl: http://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/oauth-flow/rfc002/node-B/nuts.yaml b/e2e-tests/oauth-flow/rfc002/node-B/nuts.yaml index 658d7cc936..e0c75f0ee6 100644 --- a/e2e-tests/oauth-flow/rfc002/node-B/nuts.yaml +++ b/e2e-tests/oauth-flow/rfc002/node-B/nuts.yaml @@ -1,3 +1,4 @@ +url: http://node-b verbosity: debug strictmode: false internalratelimiter: false @@ -7,7 +8,6 @@ http: address: :1323 auth: tlsenabled: true - publicurl: http://node-b contractvalidators: - dummy irma: diff --git a/e2e-tests/oauth-flow/rfc021/node-A/nuts.yaml b/e2e-tests/oauth-flow/rfc021/node-A/nuts.yaml index bf51193545..d256ee0ae4 100644 --- a/e2e-tests/oauth-flow/rfc021/node-A/nuts.yaml +++ b/e2e-tests/oauth-flow/rfc021/node-A/nuts.yaml @@ -1,3 +1,4 @@ +url: https://nodeA verbosity: debug strictmode: false internalratelimiter: false @@ -6,7 +7,6 @@ http: default: address: :1323 auth: - publicurl: https://nodeA v2apienabled: true presentationexchangemappingfile: /opt/nuts/presentationexchangemapping.json contractvalidators: diff --git a/e2e-tests/oauth-flow/rfc021/node-B/nuts.yaml b/e2e-tests/oauth-flow/rfc021/node-B/nuts.yaml index 3691731054..48297172e5 100644 --- a/e2e-tests/oauth-flow/rfc021/node-B/nuts.yaml +++ b/e2e-tests/oauth-flow/rfc021/node-B/nuts.yaml @@ -1,3 +1,4 @@ +url: https://nodeB verbosity: debug strictmode: false internalratelimiter: false @@ -8,7 +9,6 @@ http: auth: tlsenabled: true v2apienabled: true - publicurl: https://nodeB contractvalidators: - dummy irma: diff --git a/e2e-tests/openid4vci/issuer-initiated/node-A/nuts.yaml b/e2e-tests/openid4vci/issuer-initiated/node-A/nuts.yaml index 55b00577d1..3a8b4650aa 100644 --- a/e2e-tests/openid4vci/issuer-initiated/node-A/nuts.yaml +++ b/e2e-tests/openid4vci/issuer-initiated/node-A/nuts.yaml @@ -1,3 +1,4 @@ +url: https://nodeA:1323 verbosity: debug strictmode: true internalratelimiter: false @@ -10,7 +11,6 @@ http: address: :443 tls: server-client auth: - publicurl: https://nodeA:1323 contractvalidators: - dummy irma: diff --git a/e2e-tests/openid4vci/issuer-initiated/node-B/nuts.yaml b/e2e-tests/openid4vci/issuer-initiated/node-B/nuts.yaml index 1c41aa2828..42fe45dbbf 100644 --- a/e2e-tests/openid4vci/issuer-initiated/node-B/nuts.yaml +++ b/e2e-tests/openid4vci/issuer-initiated/node-B/nuts.yaml @@ -1,3 +1,4 @@ +url: https://nodeB:1323 verbosity: debug strictmode: true internalratelimiter: false @@ -10,7 +11,6 @@ http: address: :443 tls: server-client auth: - publicurl: https://nodeB:1323 contractvalidators: - dummy irma: diff --git a/e2e-tests/openid4vci/network-issuance/node-A/nuts.yaml b/e2e-tests/openid4vci/network-issuance/node-A/nuts.yaml index e3d7926948..7d3ad6c8b9 100644 --- a/e2e-tests/openid4vci/network-issuance/node-A/nuts.yaml +++ b/e2e-tests/openid4vci/network-issuance/node-A/nuts.yaml @@ -1,3 +1,4 @@ +url: https://nodeA:1323 verbosity: debug strictmode: true internalratelimiter: false @@ -10,7 +11,6 @@ http: address: :443 tls: server-client auth: - publicurl: https://nodeA:1323 contractvalidators: - dummy irma: diff --git a/e2e-tests/openid4vci/network-issuance/node-B/nuts.yaml b/e2e-tests/openid4vci/network-issuance/node-B/nuts.yaml index ce73fe5010..a10682b075 100644 --- a/e2e-tests/openid4vci/network-issuance/node-B/nuts.yaml +++ b/e2e-tests/openid4vci/network-issuance/node-B/nuts.yaml @@ -1,3 +1,4 @@ +url: https://nodeB:1323 verbosity: debug strictmode: true internalratelimiter: false @@ -10,7 +11,6 @@ http: address: :443 tls: server-client auth: - publicurl: https://nodeB:1323 contractvalidators: - dummy irma: diff --git a/e2e-tests/ops/key-rotation/node-A/nuts.yaml b/e2e-tests/ops/key-rotation/node-A/nuts.yaml index f6cae490b3..ff296702ab 100644 --- a/e2e-tests/ops/key-rotation/node-A/nuts.yaml +++ b/e2e-tests/ops/key-rotation/node-A/nuts.yaml @@ -1,10 +1,10 @@ +url: https://node-A verbosity: debug internalratelimiter: false http: default: address: :1323 auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/ops/key-rotation/node-B/nuts.yaml b/e2e-tests/ops/key-rotation/node-B/nuts.yaml index b7545fd654..c30b6a4bf3 100644 --- a/e2e-tests/ops/key-rotation/node-B/nuts.yaml +++ b/e2e-tests/ops/key-rotation/node-B/nuts.yaml @@ -1,10 +1,10 @@ +url: https://node-B verbosity: debug internalratelimiter: false http: default: address: :1323 auth: - publicurl: https://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/storage/backup-restore/node-A/nuts.yaml b/e2e-tests/storage/backup-restore/node-A/nuts.yaml index 3a70a73fb1..63cc7348c8 100644 --- a/e2e-tests/storage/backup-restore/node-A/nuts.yaml +++ b/e2e-tests/storage/backup-restore/node-A/nuts.yaml @@ -1,8 +1,8 @@ +url: "http://nodeA" verbosity: debug strictmode: false internalratelimiter: false auth: - publicurl: "http://nodeA" contractvalidators: - dummy irma: diff --git a/e2e-tests/storage/redis/node-A/nuts.yaml b/e2e-tests/storage/redis/node-A/nuts.yaml index d850f441d0..2760a031fe 100644 --- a/e2e-tests/storage/redis/node-A/nuts.yaml +++ b/e2e-tests/storage/redis/node-A/nuts.yaml @@ -1,10 +1,10 @@ +url: https://node-A verbosity: debug internalratelimiter: false http: default: address: :1323 auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/e2e-tests/storage/redis/node-B/nuts.yaml b/e2e-tests/storage/redis/node-B/nuts.yaml index e4da37fde3..f7697f251d 100644 --- a/e2e-tests/storage/redis/node-B/nuts.yaml +++ b/e2e-tests/storage/redis/node-B/nuts.yaml @@ -1,10 +1,10 @@ +url: https://node-B verbosity: debug internalratelimiter: false http: default: address: :1323 auth: - publicurl: https://node-B contractvalidators: - dummy irma: diff --git a/e2e-tests/storage/vault/nuts.yaml b/e2e-tests/storage/vault/nuts.yaml index 9574b1f38a..dcf3446e9e 100644 --- a/e2e-tests/storage/vault/nuts.yaml +++ b/e2e-tests/storage/vault/nuts.yaml @@ -1,10 +1,10 @@ +url: https://node-A verbosity: debug internalratelimiter: false http: default: address: :1323 auth: - publicurl: https://node-A contractvalidators: - dummy irma: diff --git a/main_test.go b/main_test.go index 3a15984e56..3621bbd280 100644 --- a/main_test.go +++ b/main_test.go @@ -206,6 +206,7 @@ func getIntegrationTestConfig(t *testing.T, testDirectory string) (core.ServerCo } config := *system.Config + config.URL = "https://nuts.nl" config.LegacyTLS.Enabled = true config.TLS.CertFile = pki.CertificateFile(t) config.TLS.CertKeyFile = config.TLS.CertFile @@ -218,7 +219,6 @@ func getIntegrationTestConfig(t *testing.T, testDirectory string) (core.ServerCo authConfig := auth.DefaultConfig() authConfig.ContractValidators = []string{"dummy"} // disables IRMA - authConfig.PublicURL = "https://nuts.nl" cryptoConfig := crypto.Config{Storage: "fs"} diff --git a/test/node/server.go b/test/node/server.go index dde6da4377..0066aac439 100644 --- a/test/node/server.go +++ b/test/node/server.go @@ -72,7 +72,7 @@ func StartServer(t *testing.T, configFunc ...func(httpServerURL string)) (string t.Setenv("NUTS_NETWORK_GRPCADDR", grpcPort) t.Setenv("NUTS_EVENTS_NATS_PORT", natsPort) t.Setenv("NUTS_EVENTS_NATS_HOSTNAME", "localhost") - t.Setenv("NUTS_AUTH_PUBLICURL", httpServerURL) + t.Setenv("NUTS_URL", httpServerURL) certFile := pki.CertificateFile(t) t.Setenv("NUTS_TLS_CERTFILE", certFile) t.Setenv("NUTS_TLS_CERTKEYFILE", certFile)