Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Hide profiles by default if they aren't new #10910

Merged
3 commits merged into from
Aug 16, 2021

Conversation

lhecker
Copy link
Member

@lhecker lhecker commented Aug 9, 2021

Let's say a user doesn't know that they need to write "hidden": true in
order to prevent a profile from showing up (and a settings UI doesn't exist).
Naturally they would open settings.json and try to remove the profile object.
This section of code recognizes if a profile was seen before and marks it as
"hidden": true by default and thus ensures the behavior the user expects:
Profiles won't show up again after they've been removed from settings.json.

References

#8324 - Application State

PR Checklist

Validation Steps Performed

  • settings.json/state.json are created if they don't exist ✔️
  • Removing any profile from settings.json doesn't cause it to appear again ✔️
  • Hitting save in SUI creates profiles with "hidden": true ✔️
  • Removing a default profile and hitting save in SUI works ❌
    An empty object is added instead.

@ghost ghost added Area-Settings Issues related to settings and customizability, for console or terminal Issue-Task It's a feature request, but it doesn't really need a major design. Product-Terminal The new Windows Terminal. labels Aug 9, 2021
Copy link
Member

@carlos-zamora carlos-zamora left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok! It took me a while to understand it but I think I get it now. So it'll work something like this:

  1. settings.json has profiles A, B, C, D (D = dynamic profile)
    • GeneratedProfiles: A,B,C,D
  2. user removes D and saves
    • GeneratedProfiles: A,B,C
    • D is loaded, but it's marked as hidden
  3. _AppendDynamicProfilesToUserSettings
    • D is hidden, so we don't append it to the JSON
      Right?

Either way, you showed me that it works earlier, and it looks great!

@@ -746,7 +785,7 @@ bool CascadiaSettings::_AppendDynamicProfilesToUserSettings()
for (const auto& profile : _allProfiles)
{
// Skip profiles that are in the user settings or the default settings.
if (isInJsonObj(profile, _userSettings) || isInJsonObj(profile, _defaultSettings))
if (profile.Hidden() || isInJsonObj(profile, _userSettings) || isInJsonObj(profile, _defaultSettings))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So technically this is the same as if (profile.Hidden() || profile.Origin() == OriginTag::User) right? Just doesn't make sense to change it because it'll probably have some kind of unintended consequence.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah this is just there, because it would be confusing otherwise, if the profile you deleted suddenly shows up again. It felt weird, when I tested it. 😅

@WSLUser
Copy link
Contributor

WSLUser commented Aug 10, 2021

Naturally they would open settings.json and try to remove the profile object

If someone is trying to delete that profile, wouldn't using "disabledProfileSources": be a better solution? For example, not everyone uses the Azure profile, a user can disable sourcing it but they first have to know about it. If they don't, then they'll simply try removing it by hand and of course it's regenerated. Marking something like that as "hidden" isn't the right solution, that just hides what the user will consider "bloatware". It should be removed altogether in this case.

@zadjii-msft
Copy link
Member

If someone is trying to delete that profile, wouldn't using "disabledProfileSources": be a better solution?

After the literally 100 issues that have been filed on us for "i deleted the thing why does it come back", I'm gonna say no. Most folks don't know how dynamic profiles work, and they honsetly don't care. They just want to delete the thing and have it go away.

@DHowett
Copy link
Member

DHowett commented Aug 10, 2021

Naturally they would open settings.json and try to remove the profile object

If someone is trying to delete that profile, wouldn't using "disabledProfileSources": be a better solution? For example, not everyone uses the Azure profile, a user can disable sourcing it but they first have to know about it. If they don't, then they'll simply try removing it by hand and of course it's regenerated. Marking something like that as "hidden" isn't the right solution, that just hides what the user will consider "bloatware". It should be removed altogether in this case.

Allowing users to delete individual profiles from a generator solves the case where they only want to delete one WSL profile--not all of them--because they've made a custom version of one that they want to detach from it. Disabling an entire generator is "the nuclear option." 😄

However, I tend to agree with the rest of this statement. I'm more in favor of making the profile object not exist (so it never gets re-serialized on save, and doesn't show up in the settings UI) when the user deletes it. That will improve uniformity with user-origin profiles and allow us to simplify the logic behind [Delete] in the Settings UI.

Reading the code review, it looks like one of the intermediate nodes is marked as hidden... so we will never write a new entry for a deleted-then-hidden profile to the JSON. This is awesome.

@DHowett
Copy link
Member

DHowett commented Aug 10, 2021

Due to GitHub being somewhat down, I cannot review using the web UI. However:

+            for (auto profile : resultPtr->_allProfiles)
+            {
+                if (generatedProfiles.emplace(profile.Guid()).second)
+                {
+                    generatedProfilesChanged = true;

This is going to add user-origin profiles to the list, is is not? We'll eventually have a list of all profiles ever seen, rather than a list of profiles that were generated by a profile generator. Is this a worthwhile concern?

+            // In case that a user removed all of their profiles, we want to default to pretend as if
+            // the user asked for a "reset" of the profile list and readd all profiles as visible.
+            if (hiddenProfiles == resultPtr->_allProfiles.Size())
+            {
+                for (auto profile : resultPtr->_allProfiles)
+                {
+                    profile.Hidden(false);

We can remove the validation step in _Validate... that checks that at least one profile is visible if we're going to do this 😄

         // Skip profiles that are in the user settings or the default settings.
-        if (isInJsonObj(profile, _userSettings) || isInJsonObj(profile, _defaultSettings))
+        if (profile.Hidden() || isInJsonObj(profile, _userSettings) || isInJsonObj(profile, _defaultSettings))

This comment could use some updating!

@lhecker
Copy link
Member Author

lhecker commented Aug 10, 2021

@DHowett Regarding your diffs in the order you wrote them:

  1. Even generated profiles will be tagged as User, if they're in the settings.json during load. If we ignore User profiles, we'd end up in a situation where no profile is added to the set, if someone removes state.json, but not settings.json.
  2. I've removed that code
  3. Comment added 👍

@DHowett
Copy link
Member

DHowett commented Aug 11, 2021

@msftbot make sure @zadjii-msft signs off

@ghost ghost added the AutoMerge Marked for automatic merge by the bot when requirements are met label Aug 11, 2021
@ghost
Copy link

ghost commented Aug 11, 2021

Hello @DHowett!

Because you've given me some instructions on how to help merge this pull request, I'll be modifying my merge approach. Here's how I understand your requirements for merging this pull request:

  • I'll only merge this pull request if it's approved by @zadjii-msft

If this doesn't seem right to you, you can tell me to cancel these instructions and use the auto-merge policy that has been configured for this repository. Try telling me "forget everything I just told you".

@DHowett
Copy link
Member

DHowett commented Aug 11, 2021

Okay, so confirming the settings UI experience:

  1. We will want to let users delete these profiles, right?
  2. When they do, should we set hidden or delete the profile?
    • If we delete it, it will show back up as hidden when they save. Maybe that makes sense?
    • If we set it hidden, it will not disappear from the list.
      • We need a visual treatment for hidden profiles so that we don't get complaints that "delete does nothing, but it goes away from the menu"

We should file a followup (does somebody want to own it for the 1.11 cycle?) for making the settings UI do the "right" thing here.

@lhecker
Copy link
Member Author

lhecker commented Aug 12, 2021

We will want to let users delete these profiles, right?

What are "these" profiles? Custom or generated ones? Because I believe the former is unaffected by this change. The hidden attribute is only set on non-User profiles after all...

I've tried this PR and deleting profiles in the SUI works as expected I believe.

@DHowett
Copy link
Member

DHowett commented Aug 12, 2021

We will want to let users delete these profiles, right?

What are "these" profiles? Custom or generated ones? Because I believe the former is unaffected by this change. The hidden attribute is only set on non-User profiles after all...

I've tried this PR and deleting profiles in the SUI works as expected I believe.

Ah I mean Generated ones :)

@carlos-zamora
Copy link
Member

Okay, so confirming the settings UI experience:

  1. We will want to let users delete these profiles, right?

  2. When they do, should we set hidden or delete the profile?

    • If we delete it, it will show back up as hidden when they save. Maybe that makes sense?

    • If we set it hidden, it will not disappear from the list.

      • We need a visual treatment for hidden profiles so that we don't get complaints that "delete does nothing, but it goes away from the menu"

We should file a followup (does somebody want to own it for the 1.11 cycle?) for making the settings UI do the "right" thing here.

I think half of the problem here is we need an extensions page. I feel like the proper design should be something like this:

  • Scenario 1: If you remove the profile from the JSON --> the profile won't appear in the dropdown or SUI
    • this is done using AppState::GeneratedProfiles
  • Scenario 2: If you delete the profile from SUI (now, all profiles should be delete-able) --> do the same as Scenario 1
    • handled the same way as Scenario 1
  • Scenario 3: The user wants a deleted auto-generated profile to come back --> go to the Extensions page and re-enable it

For now, I think this implementation is fine because it helps JSON-only users not see the profile. Thoughts?

@DHowett
Copy link
Member

DHowett commented Aug 12, 2021

Yes, that's the proper design. However: what's going to happen today and how much do we need to fix for 1.11?

@Alacritous

This comment has been minimized.

@DHowett

This comment has been minimized.

@microsoft microsoft deleted a comment from Alacritous Aug 13, 2021
Copy link
Member

@zadjii-msft zadjii-msft left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yea I'm cool with this. We obviously have more stuff to work out in post, but we always did. This doesn't really make it that much worse.

The only real caution here is the scenario where WSL just fails to load entirely (cause it does that sometimes), then we fail to find the profile source, then we don't include it in the settings.json when we reserialize. But actually, that was a problem before too. Yea this is better than before and we'll work out the kinks.

@ghost ghost merged commit 5d36e5d into main Aug 16, 2021
@ghost ghost deleted the dev/lhecker/app-state-generated-profiles branch August 16, 2021 13:32
DHowett pushed a commit that referenced this pull request Aug 25, 2021
Let's say a user doesn't know that they need to write `"hidden": true` in
order to prevent a profile from showing up (and a settings UI doesn't exist).
Naturally they would open settings.json and try to remove the profile object.
This section of code recognizes if a profile was seen before and marks it as
`"hidden": true` by default and thus ensures the behavior the user expects:
Profiles won't show up again after they've been removed from settings.json.

## References

#8324 - Application State

## PR Checklist
* [x] Closes #8270
* [x] I work here
* [x] Tests added/passed

## Validation Steps Performed

* settings.json/state.json are created if they don't exist ✔️
* Removing any profile from settings.json doesn't cause it to appear again ✔️
* Hitting save in SUI creates profiles with `"hidden": true` ✔️
* Removing a default profile and hitting save in SUI works ❌
  An empty object is added instead.
@ghost
Copy link

ghost commented Aug 31, 2021

🎉Windows Terminal Preview v1.10.2383.0 has been released which incorporates this pull request.:tada:

Handy links:

This pull request was closed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Area-Settings Issues related to settings and customizability, for console or terminal AutoMerge Marked for automatic merge by the bot when requirements are met Issue-Task It's a feature request, but it doesn't really need a major design. Product-Terminal The new Windows Terminal.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Default profiles appear even if removed from the config.json
6 participants