From 9a5e3a4998c0b3a1a49487155899f8acf8ca102c Mon Sep 17 00:00:00 2001 From: Michael Quigley Date: Mon, 7 Apr 2025 13:21:03 -0400 Subject: [PATCH 1/4] support a 'new account link' to inject new account information onto the login page (#552) --- bin/generate_rest.sh | 2 +- controller/config/config.go | 1 + controller/configuration.go | 1 + etc/ctrl.yml | 7 ++++++- rest_model_zrok/configuration.go | 3 +++ rest_server_zrok/embedded_spec.go | 6 ++++++ sdk/nodejs/sdk/src/api/models/ModelConfiguration.ts | 8 ++++++++ sdk/python/src/docs/Configuration.md | 1 + sdk/python/src/test/test_configuration.py | 1 + sdk/python/src/zrok_api/models/configuration.py | 4 +++- specs/zrok.yml | 2 ++ ui/src/Login.tsx | 10 +++++++++- ui/src/api/models/ModelConfiguration.ts | 8 ++++++++ 13 files changed, 50 insertions(+), 4 deletions(-) diff --git a/bin/generate_rest.sh b/bin/generate_rest.sh index 410eb157..397a3c41 100755 --- a/bin/generate_rest.sh +++ b/bin/generate_rest.sh @@ -1,4 +1,4 @@ -#!/bin/bash +9999999999999999999999999999999999999#!/bin/bash set -euo pipefail diff --git a/controller/config/config.go b/controller/config/config.go index 68181e17..67cc48fc 100644 --- a/controller/config/config.go +++ b/controller/config/config.go @@ -38,6 +38,7 @@ type Config struct { type AdminConfig struct { Secrets []string `cf:"+secret"` TouLink string + NewAccountLink string ProfileEndpoint string } diff --git a/controller/configuration.go b/controller/configuration.go index fc021fa6..910e626b 100644 --- a/controller/configuration.go +++ b/controller/configuration.go @@ -26,6 +26,7 @@ func (ch *configurationHandler) Handle(_ metadata.ConfigurationParams) middlewar } if cfg.Admin != nil { data.TouLink = cfg.Admin.TouLink + data.NewAccountLink = cfg.Admin.NewAccountLink } if cfg.Invites != nil { data.InviteTokenContact = cfg.Invites.TokenContact diff --git a/etc/ctrl.yml b/etc/ctrl.yml index 18ffc4d0..ab3c8fb1 100644 --- a/etc/ctrl.yml +++ b/etc/ctrl.yml @@ -20,10 +20,15 @@ admin: secrets: - 77623cad-1847-4d6d-8ffe-37defc33c909 # - # If `tou_link` is present, the frontend will display the "Terms of Use" link on the login and registration forms + # If `tou_link` is present, the API console will display the "Terms of Use" link on the login and registration forms # tou_link: 'Terms and Conditions' # + # If `new_account_link` is present, the API console will inject the contents of this setting into the login form; the + # intention is that it is used to present a "How do I get an account?" link. + # + new_account_link: 'How do I get an account?' + # # If `profile_endpoint` is present, the controller will start a `net/http/pprof` endpoint at the specified host:port # #profile_endpoint: localhost:6060 diff --git a/rest_model_zrok/configuration.go b/rest_model_zrok/configuration.go index 8486455a..1d33fa5f 100644 --- a/rest_model_zrok/configuration.go +++ b/rest_model_zrok/configuration.go @@ -23,6 +23,9 @@ type Configuration struct { // invites open InvitesOpen bool `json:"invitesOpen,omitempty"` + // new account link + NewAccountLink string `json:"newAccountLink,omitempty"` + // requires invite token RequiresInviteToken bool `json:"requiresInviteToken,omitempty"` diff --git a/rest_server_zrok/embedded_spec.go b/rest_server_zrok/embedded_spec.go index 2134e50c..539561bf 100644 --- a/rest_server_zrok/embedded_spec.go +++ b/rest_server_zrok/embedded_spec.go @@ -1985,6 +1985,9 @@ func init() { "invitesOpen": { "type": "boolean" }, + "newAccountLink": { + "type": "string" + }, "requiresInviteToken": { "type": "boolean" }, @@ -4298,6 +4301,9 @@ func init() { "invitesOpen": { "type": "boolean" }, + "newAccountLink": { + "type": "string" + }, "requiresInviteToken": { "type": "boolean" }, diff --git a/sdk/nodejs/sdk/src/api/models/ModelConfiguration.ts b/sdk/nodejs/sdk/src/api/models/ModelConfiguration.ts index 53a35d82..db6d129c 100644 --- a/sdk/nodejs/sdk/src/api/models/ModelConfiguration.ts +++ b/sdk/nodejs/sdk/src/api/models/ModelConfiguration.ts @@ -31,6 +31,12 @@ export interface ModelConfiguration { * @memberof ModelConfiguration */ touLink?: string; + /** + * + * @type {string} + * @memberof ModelConfiguration + */ + newAccountLink?: string; /** * * @type {boolean} @@ -70,6 +76,7 @@ export function ModelConfigurationFromJSONTyped(json: any, ignoreDiscriminator: 'version': json['version'] == null ? undefined : json['version'], 'touLink': json['touLink'] == null ? undefined : json['touLink'], + 'newAccountLink': json['newAccountLink'] == null ? undefined : json['newAccountLink'], 'invitesOpen': json['invitesOpen'] == null ? undefined : json['invitesOpen'], 'requiresInviteToken': json['requiresInviteToken'] == null ? undefined : json['requiresInviteToken'], 'inviteTokenContact': json['inviteTokenContact'] == null ? undefined : json['inviteTokenContact'], @@ -89,6 +96,7 @@ export function ModelConfigurationToJSONTyped(value?: ModelConfiguration | null, 'version': value['version'], 'touLink': value['touLink'], + 'newAccountLink': value['newAccountLink'], 'invitesOpen': value['invitesOpen'], 'requiresInviteToken': value['requiresInviteToken'], 'inviteTokenContact': value['inviteTokenContact'], diff --git a/sdk/python/src/docs/Configuration.md b/sdk/python/src/docs/Configuration.md index 07eec945..ce1f473b 100644 --- a/sdk/python/src/docs/Configuration.md +++ b/sdk/python/src/docs/Configuration.md @@ -7,6 +7,7 @@ Name | Type | Description | Notes ------------ | ------------- | ------------- | ------------- **version** | **str** | | [optional] **tou_link** | **str** | | [optional] +**new_account_link** | **str** | | [optional] **invites_open** | **bool** | | [optional] **requires_invite_token** | **bool** | | [optional] **invite_token_contact** | **str** | | [optional] diff --git a/sdk/python/src/test/test_configuration.py b/sdk/python/src/test/test_configuration.py index bf80210e..a6fc71ea 100644 --- a/sdk/python/src/test/test_configuration.py +++ b/sdk/python/src/test/test_configuration.py @@ -37,6 +37,7 @@ class TestConfiguration(unittest.TestCase): return Configuration( version = '', tou_link = '', + new_account_link = '', invites_open = True, requires_invite_token = True, invite_token_contact = '' diff --git a/sdk/python/src/zrok_api/models/configuration.py b/sdk/python/src/zrok_api/models/configuration.py index ed5ece38..35a1e9d5 100644 --- a/sdk/python/src/zrok_api/models/configuration.py +++ b/sdk/python/src/zrok_api/models/configuration.py @@ -28,10 +28,11 @@ class Configuration(BaseModel): """ # noqa: E501 version: Optional[StrictStr] = None tou_link: Optional[StrictStr] = Field(default=None, alias="touLink") + new_account_link: Optional[StrictStr] = Field(default=None, alias="newAccountLink") invites_open: Optional[StrictBool] = Field(default=None, alias="invitesOpen") requires_invite_token: Optional[StrictBool] = Field(default=None, alias="requiresInviteToken") invite_token_contact: Optional[StrictStr] = Field(default=None, alias="inviteTokenContact") - __properties: ClassVar[List[str]] = ["version", "touLink", "invitesOpen", "requiresInviteToken", "inviteTokenContact"] + __properties: ClassVar[List[str]] = ["version", "touLink", "newAccountLink", "invitesOpen", "requiresInviteToken", "inviteTokenContact"] model_config = ConfigDict( populate_by_name=True, @@ -86,6 +87,7 @@ class Configuration(BaseModel): _obj = cls.model_validate({ "version": obj.get("version"), "touLink": obj.get("touLink"), + "newAccountLink": obj.get("newAccountLink"), "invitesOpen": obj.get("invitesOpen"), "requiresInviteToken": obj.get("requiresInviteToken"), "inviteTokenContact": obj.get("inviteTokenContact") diff --git a/specs/zrok.yml b/specs/zrok.yml index 7d081848..6ee86fb4 100644 --- a/specs/zrok.yml +++ b/specs/zrok.yml @@ -1229,6 +1229,8 @@ definitions: type: string touLink: type: string + newAccountLink: + type: string invitesOpen: type: boolean requiresInviteToken: diff --git a/ui/src/Login.tsx b/ui/src/Login.tsx index e76155dc..0c04b00d 100644 --- a/ui/src/Login.tsx +++ b/ui/src/Login.tsx @@ -13,14 +13,19 @@ const Login = ({ onLogin }: LoginProps) => { const [email, setEmail] = useState(""); const [password, setPassword] = useState(""); const [message, setMessage] = useState(""); - const [tou, setTou] = useState(null as string); + const [tou, setTou] = useState(""); + const [newAccountLink, setNewAccountLink] = useState(""); useEffect(() => { new MetadataApi()._configuration() .then(d => { + console.log("d", d); if(d.touLink && d.touLink.trim() !== "") { setTou(d.touLink); } + if(d.newAccountLink && d.newAccountLink.trim() != "") { + setNewAccountLink(d.newAccountLink) + } }) .catch(e => { console.log(e); @@ -86,6 +91,9 @@ const Login = ({ onLogin }: LoginProps) => { Forgot Password? + +
+
diff --git a/ui/src/api/models/ModelConfiguration.ts b/ui/src/api/models/ModelConfiguration.ts index 53a35d82..db6d129c 100644 --- a/ui/src/api/models/ModelConfiguration.ts +++ b/ui/src/api/models/ModelConfiguration.ts @@ -31,6 +31,12 @@ export interface ModelConfiguration { * @memberof ModelConfiguration */ touLink?: string; + /** + * + * @type {string} + * @memberof ModelConfiguration + */ + newAccountLink?: string; /** * * @type {boolean} @@ -70,6 +76,7 @@ export function ModelConfigurationFromJSONTyped(json: any, ignoreDiscriminator: 'version': json['version'] == null ? undefined : json['version'], 'touLink': json['touLink'] == null ? undefined : json['touLink'], + 'newAccountLink': json['newAccountLink'] == null ? undefined : json['newAccountLink'], 'invitesOpen': json['invitesOpen'] == null ? undefined : json['invitesOpen'], 'requiresInviteToken': json['requiresInviteToken'] == null ? undefined : json['requiresInviteToken'], 'inviteTokenContact': json['inviteTokenContact'] == null ? undefined : json['inviteTokenContact'], @@ -89,6 +96,7 @@ export function ModelConfigurationToJSONTyped(value?: ModelConfiguration | null, 'version': value['version'], 'touLink': value['touLink'], + 'newAccountLink': value['newAccountLink'], 'invitesOpen': value['invitesOpen'], 'requiresInviteToken': value['requiresInviteToken'], 'inviteTokenContact': value['inviteTokenContact'], From ea1959e87aebd30575cd57243150923a00155916 Mon Sep 17 00:00:00 2001 From: Michael Quigley Date: Mon, 7 Apr 2025 14:06:13 -0400 Subject: [PATCH 2/4] better warnings about process cleanup in release environment, share, and access modals (#910) --- ui/src/ReleaseAccessModal.tsx | 3 +++ ui/src/ReleaseEnvironmentModal.tsx | 2 +- ui/src/ReleaseShareModal.tsx | 3 +++ 3 files changed, 7 insertions(+), 1 deletion(-) diff --git a/ui/src/ReleaseAccessModal.tsx b/ui/src/ReleaseAccessModal.tsx index ec1337ce..06c9d829 100644 --- a/ui/src/ReleaseAccessModal.tsx +++ b/ui/src/ReleaseAccessModal.tsx @@ -70,6 +70,9 @@ const ReleaseAccessModal = ({ close, isOpen, user, access, detail }: ReleaseAcce Would you like to release the access {frontendToken} ? + + WARNING: This operation removes permissions and frees resources, but it does NOT terminate your zrok access process—you must do that manually. + } label={

I confirm the release of {frontendToken}

} sx={{ mt: 2 }} />
diff --git a/ui/src/ReleaseEnvironmentModal.tsx b/ui/src/ReleaseEnvironmentModal.tsx index fb599649..afd67aa1 100644 --- a/ui/src/ReleaseEnvironmentModal.tsx +++ b/ui/src/ReleaseEnvironmentModal.tsx @@ -69,7 +69,7 @@ const ReleaseEnvironmentModal = ({ close, isOpen, user, environment, detail }: R Would you like to release the environment {description} ? - Releasing this environment will also release any shares and accesses that are associated with it. + WARNING: Releasing this environment will also release any shares and accesses that are associated with it. This operation removes permissions and frees resources, but it does NOT terminate your zrok share or zrok access processes—you must do that manually. } label={

I confirm the release of {description}

} sx={{ mt: 2 }} /> diff --git a/ui/src/ReleaseShareModal.tsx b/ui/src/ReleaseShareModal.tsx index 5c970259..3c95136e 100644 --- a/ui/src/ReleaseShareModal.tsx +++ b/ui/src/ReleaseShareModal.tsx @@ -70,6 +70,9 @@ const ReleaseShareModal = ({ close, isOpen, user, share, detail }: ReleaseShareP Would you like to release the share {shareToken} ? + + WARNING: This operation removes permissions and frees resources, but it does NOT terminate your zrok share process—you must do that manually. + } label={

I confirm the release of {shareToken}

} sx={{ mt: 2 }} />
From d55483df673a55d9fdf3957a75162e422c813aec Mon Sep 17 00:00:00 2001 From: Michael Quigley Date: Mon, 7 Apr 2025 14:08:33 -0400 Subject: [PATCH 3/4] changelog (#552, #910) --- CHANGELOG.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index b57398ab..87eb866f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,10 @@ ## v1.0.2 +FEATURE: New `admin/new_account_link` configuration option to allow the insertion of "how do I register for an account?" links into the login form (https://github.com/openziti/zrok/issues/552) + +CHANGE: The release environment, share, and access modals in the API console now have a better message letting the user know they will still need to clean up their `zrok` processes (https://github.com/openziti/zrok/issues/910) + CHANGE: The openziti/zrok Docker image has been updated to use the latest version of the ziti CLI, 1.4.3 (https://github.com/openziti/zrok/pull/917) ## v1.0.1 From caf194f927bbefa4ea0ef80f6f0cad77ac2aa472 Mon Sep 17 00:00:00 2001 From: Michael Quigley Date: Mon, 7 Apr 2025 14:20:09 -0400 Subject: [PATCH 4/4] whiskey tango... --- bin/generate_rest.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bin/generate_rest.sh b/bin/generate_rest.sh index 397a3c41..410eb157 100755 --- a/bin/generate_rest.sh +++ b/bin/generate_rest.sh @@ -1,4 +1,4 @@ -9999999999999999999999999999999999999#!/bin/bash +#!/bin/bash set -euo pipefail