<p dir="auto"><strong>Proposal</strong></p>
<p dir="auto">Include a default <code class="notranslate">profiles.json</code> in the package, allow the user to override it and merge their settings into it.</p>
<p dir="auto"><strong>Questions</strong></p>
<ul dir="auto">
<li>What if you want to delete a stock profile?</li>
<li>Optional features?</li>
<li>Turn off defaults? Perhaps <code class="notranslate">{... "thing": null, }</code>?</li>
</ul>
<h3 dir="auto">Child Work Items</h3>
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> <a class="issue-link js-issue-link" data-error-text="Failed to load title" data-id="465442249" data-permission-text="Title is private" data-url="https://github.com/microsoft/terminal/issues/1880" data-hovercard-type="issue" data-hovercard-url="/microsoft/terminal/issues/1880/hovercard" href="https://github.com/microsoft/terminal/issues/1880">#1880</a> Keep the original json blob around, and when we make edits to it, only append them or replace the existing values</li>
</ul>
<hr> 
<h2 dir="auto">Things that need to be done to accomplish Cascading Settings</h2>
<p dir="auto">Each <code class="notranslate">&lt;h3&gt;</code> here is a single PR into master, broken into either sub-PRs or work for me to do as a part of that PR</p>
<h3 dir="auto">[x] Don't re-serialize settings on load (PR: <a class="issue-link js-issue-link" data-error-text="Failed to load title" data-id="482436885" data-permission-text="Title is private" data-url="https://github.com/microsoft/terminal/issues/2475" data-hovercard-type="pull_request" data-hovercard-url="/microsoft/terminal/pull/2475/hovercard" href="https://github.com/microsoft/terminal/pull/2475">#2475</a>)</h3>
<p dir="auto">This should be done first and foremost. This is not really helping anyone. Old settings all migrate nicely, so whatever. Let's just pull it.</p>
<h3 dir="auto">[_] Combine a defaults.json with a profiles.json (PR: <a class="issue-link js-issue-link" data-error-text="Failed to load title" data-id="484247000" data-permission-text="Title is private" data-url="https://github.com/microsoft/terminal/issues/2515" data-hovercard-type="pull_request" data-hovercard-url="/microsoft/terminal/pull/2515/hovercard" href="https://github.com/microsoft/terminal/pull/2515">#2515</a>)</h3>
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add a defaults.json to the package</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Create a function for layering a <code class="notranslate">Json::Value</code> on top of an existing object</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add tests for layering a profile json blob on top of a profile</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add functions to search a list of <code class="notranslate">Profile</code>s for a duplicate, and layer on that dupe or create a new <code class="notranslate">Profile</code> if no such dupe exists.</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Ensure we can layer each of the following: (WITH TESTS)
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> layer profiles</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> layer color schemes</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> layer keybindings (for a matching key, the user action should override the default action) <strong>(NEEDS TESTS)</strong></li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> layer globals <strong>(NEEDS TESTS)</strong></li>
</ul>
</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> When loading settings, load defaults, then layer user settings on top of default profiles</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Maintain user settings ordering, not defaults+user ordering</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add support for unbinding default keys
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> unbind with <code class="notranslate">"unbound"</code></li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> unbind with <code class="notranslate">null</code></li>
</ul>
</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add support for hiding profiles</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Ensure that we can reset optional default settings with <code class="notranslate">null</code> (e.g. <code class="notranslate">"iconPath": null</code>)</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Create the User Settings file if it doesn't exist</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Stamp the "defaults.json" file into the code, so we can't possibly fail loading it</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add support for Alt clicking on "settings" to launch the defaults.json file</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> default construct profiles with scheme "Campbell" to make "scheme" and unnecessary setting in the partial diff</li>
</ul>
<h3 dir="auto">[_] Add Dynamic Profile Generators</h3>
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add Dynamic Profile Generator for WSL
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Create Dynamic Profile Generator interface</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> <del>Provide DPG's with <code class="notranslate">GetNamespaceGuid</code> and <code class="notranslate">GetGuidForName</code> functions from <code class="notranslate">App</code> somehow</del> We're not doing this anymore. We'll create the GUID for the profile when it's returned, if it has a GUID of {0}
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add a test for generateing a guid based on namespace if GUID is {0}</li>
</ul>
</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add layering for dynamic profiles based on <code class="notranslate">guid</code> and <code class="notranslate">source</code>, not <em>just</em> <code class="notranslate">guid</code></li>
</ul>
</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add Dynamic Profile Generator for Powershell Core</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add Dynamic Profile Generator for Azure Cloud Shell</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Ensure that existing WSL, Powershell Core, and Azure profiles gracefully migrate to dynamic profiles</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Add <code class="notranslate">disabledProfileSources</code> in user settings to hide dynamic profiles by namespace</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> On first launch of the terminal, if Powershell Core exists, make it the default profile</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> When adding this profiles, insert them into our JSON parse tree to save them
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Only add the delta between the default profile and the dynamic profile's default state to the json. Don't include any user customizations (though at this point there won't be any)</li>
</ul>
</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> Ensure adding a dynamic entry doesn't reformat settings</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> For profiles that were created from a dynamic profile source, they'll have both a <code class="notranslate">guid</code> and <code class="notranslate">source</code> guid that must <em>both</em> match. If a user profile with a <code class="notranslate">source</code> set does not find a matching profile at load time, the profile <strong>should be ignored</strong>.</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> profile diffs should probably not include <code class="notranslate">"table"</code>. Probably don't need to include in the diff keys that are <code class="notranslate">std::nullopt</code> in both the base and derived.</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> Make sure to re-order profiles so they're { user profiles, dynamics not in user profiles, defaults not in user profiles }</li>
</ul>
<h3 dir="auto">[_] Smart Serializing</h3>
<p dir="auto">This would be needed for a Settings UI, so we don't necessarily need it for 1.0</p>
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> Keep the original JSON parse tree around in memory</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> Only serialize things different from defaults
<ul class="contains-task-list">
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox" checked=""> profiles</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> schemes</li>
<li class="task-list-item"><input type="checkbox" id="" disabled="" class="task-list-item-checkbox"> keybindings</li>
</ul>
</li>
</ul>
<h1 dir="auto">Summary of the new feature/enhancement</h1>
<p dir="auto">I think it could be useful to have Cascadia re-scan the WSL distros every time it launches, so that installing a new WSL distro will reflect on the profiles menu.</p>
<h1 dir="auto">Proposed technical implementation details (optional)</h1>
<p dir="auto">It would just run <code class="notranslate">CascadiaSettings::_AppendWslProfiles</code> every time the app loads up, so it gets them all and adds any <em>new</em> profiles necessary,</p>