ARCH-001 Phase 28: consolidate Admin/Store/Vendor HomeController infra actions - #829
Merged
Merged
Conversation
…a actions
First infra-action (not domain-entity) consolidation in this initiative:
GetStatesByCountryId, Logout, and SetLanguage were duplicated across
HomeController in 2 or 3 of the 3 hosts, differing only in a small
parameterizable string each.
Findings from reading all 3 hosts' full HomeController before designing:
- SetLanguage is Admin+Store only - Vendor never had this action. Confirmed
by reading Vendor's HomeController.cs directly (no grep-based assumption).
Putting it on a base Vendor also inherits from would have silently added a
new route to Vendor, since MVC discovers every public action across the
whole inheritance chain - so it lives on a second-level base,
BaseHomeControllerWithSetLanguage : BaseHomeController, used only by
Admin/Store. Vendor extends BaseHomeController directly. Same two-level
split BaseOrderController/BaseOrderManagementController already
established for Order's Vendor-is-a-subset shape.
- GetStatesByCountryId's SelectState resource key: Admin and Store use the
IDENTICAL literal "Admin.Address.SelectState" (not "Store.Address.SelectState"
as might be assumed from the naming pattern seen elsewhere in this
initiative) - verified by reading Admin's own method, not just the
earlier Store-vs-Vendor diff. Only Vendor differs
("Vendor.Address.SelectState"). Parameterized via an abstract
SelectStateResourceKey property.
- The empty-countryId branch's key ("Address.SelectState", no host prefix)
is byte-identical across all 3 hosts - not parameterized, left as a shared
literal in the base.
- The addSelectStateItem/result.Any() check-order difference between
Admin/Store (nested if) and Vendor (combined &&) is confirmed COSMETIC,
not behavioral - both forms are logically equivalent for every input.
- Logout's route name ("AdminLogin"/"StoreLogin"/"VendorLogin") is the one
genuinely 3-way difference, parameterized via LogoutRouteName.
DashboardActivity/ChangeStore (Admin-only) and Index/Statistics/AccessDenied
(real per-host views) stay untouched on each concrete host controller.
Admin/Store/Vendor's HomeController restate their host's attribute set
explicitly (BaseHomeController extends the generic BaseController, not any
host's own base, same as BaseProductController/BasePictureController).
Found but explicitly out of scope: AccessDenied() is also byte-identical
across all 3 hosts - missed by the earlier repo-wide survey because its
method-name search only matched async Task<IActionResult> signatures and
AccessDenied is synchronous. Flagged for a future micro-phase, not folded in
here to keep this phase's diff to its assigned scope.
No prior test coverage existed for any of the 3 originals' HomeController.
Added BaseHomeControllerTests (parameterization proven via two differently-
configured test subclasses, not just one), HomeControllerAttributeTests for
Admin/Store, and HomeControllerSurfaceTests for Vendor (asserting Vendor's
HomeController does NOT declare SetLanguage, the regression this whole
two-level-base design exists to prevent).
No behavior change. Verified: dotnet build GrandNode.sln 0 errors. Per-project
test runs (parallel full-solution runs are known-flaky): Admin 1440/1440,
Store 142/142, Vendor 27/27.
No live smoke test run this phase - deferred, disclosed in the PR body (pure
infra plumbing, no cross-tenant/access-control surface).
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_013y3MqvZq7y1Uc5p4JZad2i
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
ARCH-001 Phase 28: HomeController infra actions
First infra-action consolidation in this initiative (not a domain entity):
GetStatesByCountryId,Logout, andSetLanguagewere duplicated acrossHomeControllerin 2 or 3 of the 3 hosts, each differing only in one smallparameterizable string.
What was actually duplicated (read all 3 originals first, not assumed)
SetLanguage: Admin+Store only — Vendor never had this action (confirmedby reading
Grand.Web.Vendor/Controllers/HomeController.csdirectly, not bytrusting an earlier grep). Putting it on a base Vendor also extends would have
silently added a brand-new route to Vendor (MVC discovers every public action
across the whole inheritance chain) — so it lives on a second-level base,
BaseHomeControllerWithSetLanguage : BaseHomeController, used only byAdmin/Store. Vendor extends the plain
BaseHomeControllerdirectly. Sametwo-level split
BaseOrderController/BaseOrderManagementControlleralreadyestablished for Order's Vendor-is-a-subset shape.
GetStatesByCountryId'sSelectStateresource key: Admin and Store use theidentical literal
"Admin.Address.SelectState"— not"Store.Address.SelectState",which would be the naming-pattern guess from elsewhere in this initiative.
Verified by reading Admin's own method (the earlier survey only diffed
Store vs. Vendor). Only Vendor differs (
"Vendor.Address.SelectState").Parameterized via an abstract
SelectStateResourceKeyproperty.countryId-branch key ("Address.SelectState", no host prefix) isbyte-identical across all 3 hosts — left as a shared literal, not parameterized.
addSelectStateItem/result.Any()check-order difference betweenAdmin/Store (nested
if) and Vendor (combined&&) is confirmed cosmetic,not behavioral — logically equivalent for every input.
Logout's route name ("AdminLogin"/"StoreLogin"/"VendorLogin") is theone genuinely 3-way difference, parameterized via
LogoutRouteName.DashboardActivity/ChangeStore(Admin-only) andIndex/Statistics/AccessDenied(real per-host views) stay untouched on each concrete controller.Found, explicitly out of scope
AccessDenied()is also byte-identical across all 3 hosts — missed by theearlier repo-wide survey because its method-name search only matched async
Task<IActionResult>signatures, andAccessDeniedis synchronous(
IActionResult). Flagged for a future micro-phase rather than folded into thisone's diff.
Tests
No prior coverage existed for any of the 3 originals. Added:
BaseHomeControllerTests— parameterization proven via two differently-configuredtest subclasses (not just one), covering
GetStatesByCountryId's 4 branches,Logout, andSetLanguage's both redirect paths.HomeControllerAttributeTests(Admin + Store).HomeControllerSurfaceTests(Vendor) — asserts Vendor'sHomeControllerdoesnot declare
SetLanguage, the exact regression the two-level-base designexists to prevent.
Verification
dotnet build GrandNode.sln— 0 errors. Per-project test runs (parallelfull-solution runs are known-flaky):
Grand.Web.Admin.Tests: 1440/1440Grand.Web.Store.Tests: 142/142Grand.Web.Vendor.Tests: 27/27No live smoke test run this phase — deferred, disclosed here rather than silently
skipped: pure infra plumbing (language switch, logout, states dropdown), no
cross-tenant/access-control surface, same justification class as Phase 24/25.