NTR: migrate admin to TypeScript — services, tests, ESLint flat config & SW6.6/6.7 Vite fixes - #1293
Open
diw-dhagen wants to merge 46 commits into
Open
NTR: migrate admin to TypeScript — services, tests, ESLint flat config & SW6.6/6.7 Vite fixes#1293diw-dhagen wants to merge 46 commits into
diw-dhagen wants to merge 46 commits into
Conversation
diw-dhagen
force-pushed
the
users/dh/WIP-Refactor
branch
from
June 24, 2026 10:58
3403375 to
6d51884
Compare
…lit into sub-components) - extract refund logic into tested TS services (Calculator, PayloadBuilder, CompositionFormatter); migrate RefundItemService + grids to TS - add Vitest specs (102 tests total) - split monolithic template into mollie-refund-manager-cart/-refunds/-instructions/-summary sub-components (props in, events out; Vue 2/3 compatible) - add tsconfig.json + global.d.ts for Shopware/twig/scss ambient types - fix template bugs (:ghost bindings, composition :key, position-identifier typo) and the isRefunding loading state on full refund Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…button styling & tutorial UX
- move cart/refunds/instructions/summary sub-components into mollie-refund-manager/components and register them from the parent (main.js back to a single import)
- prettier-format the twig templates (html parser via .prettierrc override); keep the summary {% block %} structure via prettier-ignore
- introduce SCSS color variables and restyle the SW6.6 Meteor ghost buttons (.mt-button--ghost-ghost / --ghost-danger-ghost)
- add hover + clearly muted disabled styling for the refund (.warning) and full-refund (.danger) buttons; refund button text -> #1e1e24; spacing between verify checkbox and refund button
- tutorial buttons: state-aware "Show/Hide Tutorial" label (new btnShowTutorial/btnHideTutorial snippets in all 23 locales) and scroll to the highlighted element on activate
- decouple "Full Refund" and "Rounding difference" tutorials (separate tutorialRoundingDiffVisible flag)
- make the tutorial highlight an outline+offset so it stays visible on the red full-refund button
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate the component to index.ts (ThisType pattern, conventional option order) - extract a tested CancelItemService (buildCancelRequest, isCancelSuccess, getFailureSnippetKey) - remove dead cancelableQuantity data and redundant :value binding in the template - keep the dual v-model bindings for Vue 2/3 compatibility Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…sService, tests)
- migrate the extended component to index.ts (ThisType pattern); keep Component.extend + Component.override and the Vue 2/3 EventBus branches
- extract a tested LineItemStatusService (shipping/cancel status lookups, applyCancelResponse, buildCancelData)
- modernize: bind(this) -> arrow functions, async/await for the status load, spread instead of Object.assign
- buildCancelData no longer mutates the stored status entries
- hand-format the top-level {% block %} override template and exclude it from Prettier via .prettierignore (no wrapping element for an inline prettier-ignore)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- rename index.js -> index.ts (no logic to extract; just the criteria default prop) - drop the no-longer-needed eslint no-undef disables (Shopware is typed via global.d.ts) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…Service, tests) - migrate the component to index.ts (ThisType pattern) - extract a tested ApiKeyTestService (isValid, buildResultMessage with injected labels) - modernize: drop "const me = this", arrow callbacks, type-safe DOM access (querySelector<HTMLInputElement>, optional chaining) - prettier-format the template Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…g list redesign, greeting fix)
- migrate the component to index.ts (ThisType pattern); inline the trivial userName logic, drop junk JSDoc / eslint-disables
- make getCurrentUser robust across versions (Pinia Store first, Vuex State fallback, null-safe) so the greeting name resolves on Shopware 6.6/6.7
- fix the greeting interpolation: use $t(key, { userName }) instead of $tc(key, 0, { userName }) which did not interpolate named values in Vue 3 vue-i18n
- restyle the onboarding list as numbered step badges (CSS counter) instead of the markerless, oddly-indented list
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Use $t(key, { plugin }) instead of $tc(key, 0, { plugin }) for the pluginLogs and
pluginConfiguration labels — the $tc named interpolation does not substitute named
values in Vue 3 vue-i18n, so the plugin name was missing. Both snippets are single-form.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…eScript) - migrate component + OrderLifeTimeLimitsDetector service to TypeScript (ThisType pattern, class fields, typed) - convert the existing service spec to .spec.ts (normalized import path) - DRY the warning update into updateWarnings(); type-safe DOM access (querySelector<HTMLInputElement>, parseInt radix) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…eResultService, tests) - migrate the component to index.ts (ThisType pattern) - extract a tested UpdateResultService (isSuccess, buildErrorMessage with injected label) - drop "const me = this" and the trivial loading-toggle helpers; reset the loading flag via .finally() - prettier-format the template Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…, OrderNumberFormatService, tests)
- migrate the component to index.ts (ThisType pattern)
- extract a tested OrderNumberFormatService (replaces {ordernumber}/{customernumber} via StringUtils)
- rename the local template variable to formatTemplate (it shadowed the imported template), drop junk JSDoc
- prettier-format the template
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- rename index.js -> index.ts; drop empty data/computed/methods blocks and the eslint no-undef disable (no logic, just an info alert) - remove the unused ~scss/variables import from the stylesheet Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…es for SW 6.7 - migrate the component to index.ts (ThisType pattern, string -> stringUtils, drop eslint-disables/junk JSDoc) - fix contactName getter: it checked window.name instead of this.name, so a typed name was ignored on submit - fix button icons for 6.7: default-documentation-file -> regular-file, default-communication-speech-bubbles -> regular-comments - vertically center the value in the recipient single-select - align the email field with the name field: the new grid-based mt-email-field has a taller label row; match its label row/line-height so both inputs line up (kept as sw-email-field, CSS only) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…ests) + fix misaligned quantity input - migrate index.js/MollieShippingEvents.js to TypeScript - extract pure ShippableItemsService (buildShippableLineItems, collectSelectedItems) with Vitest tests - remove dead MollieShipping.js (imported nowhere) - annotate this.* array callbacks to avoid implicit-any (TS7044) - fix quantity input vertical alignment: drop default mt-field bottom margin in table-cell Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Annotate this.orderItems.forEach / this.mollieRefunds.map callbacks so the implicitly-any parameters no longer trigger TS7044 in strict editors. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
… cy-selector typo - migrate index.js to TypeScript (ThisType, typed params, drop eslint-disable) - hand-format template, add it to .prettierignore (top-level block override) - remove default mt-field/sw-field bottom margin so tracking fields are evenly spaced - fix cy-trackiing-carrier -> cy-tracking-carrier in template and Cypress repository Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
… helper - migrate sw-order-detail, sw-order-list, sw-order-user-card and mollie-order-tab overrides to TS - migrate the sw-order barrel and the empty sw-order-line-items-grid stub to TS - extract shared getLatestTransaction() helper (was duplicated in detail + tab) with Vitest tests - modernize loops/callbacks (arrow fns, drop .bind(this)), type params, make Shopware.State access 6.7-safe Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate the sw-system-config override and the sw-settings/sw-plugin barrels to TS
- mark sw-system-config as a module (export {}) to avoid a global-scope Component collision (TS2451)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…ignore
The extension override templates extend Shopware core via top-level {% block %} / {% parent %},
which Prettier's HTML parser would flatten, so they are hand-formatted and added to .prettierignore.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
vitest is a devDependency in dev/node_modules and is not reachable from the admin tsconfig's default node resolution (administration/node_modules is empty), so every spec's 'import ... from vitest' raised TS2307 in the editor/tsc. Add baseUrl + a paths mapping for vitest. Build-safe: the Shopware webpack build ignores tsconfig, this only affects editor/tsc resolution. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate OrderAttributes, CreditcardAttributes, ProductAttributes to TS (typed fields/returns, drop redundant JSDoc) - make constructor-only fields readonly, simplify ProductAttributes.hasData(), drop dead return in CreditcardAttributes ctor - logic unchanged; existing ProductAttributes spec still green Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate StringUtils, ArrayUtilsService, VersionCompare to TS with typed signatures - modernize loops (some/findIndex), add parseInt radix, simplify isNullOrEmpty - logic unchanged; existing utils specs still green Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate ProductService and SubscriptionService to TS with typed signatures - import ProductAttributes type, make SubscriptionService._app readonly - logic unchanged; existing service specs still green Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate all 9 Mollie ApiService subclasses to TS with typed signatures and Promise<any> returns - drop eslint-disable, mark __post/__get private, drop redundant JSDoc, typed then/catch callbacks - logic and endpoints unchanged Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate acl, default-search-configuration, module index and the action constant to TS
- type the async Module.register callbacks, drop eslint-disable, mark acl as a module (export {})
- logic unchanged
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
… actions - migrate mollie-subscriptions-list, MollieSubscriptionGrid and mollie-subscriptions-detail to TS (ThisType, typed callbacks) - fix history.sort Date subtraction via getTime(), simplify getFormattedDate, drop eslint-disable/redundant JSDoc - collapse the 4 duplicated btnConfirm*_Click handlers into a shared _runSubscriptionAction helper (303 -> 274 lines, template unchanged) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate sw-customer barrel/module, sw-customer-detail override and the mollie-subscriptions view to TS - dedupe: delegate the view's statusColor to the shared SubscriptionService (was an exact copy) - drop eslint-disable; logic and templates unchanged Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate sw-product barrel/module, sw-product-detail override and the mollie product view to TS - dedupe + 6.7-safe store access: wrap repeated Shopware.State.get fallback in _resolveStore() with optional chaining (State -> Store) - dedupe initFields voucher-type normalization into _normalizeVoucherType() - drop eslint-disable; logic and templates unchanged Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- the cart and line-item subscription rules were byte-identical except name and template - extract a shared createSubscriptionRuleConfig(template) factory; each rule is now a thin extend call - drop eslint-disable; logic and templates unchanged Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…cript - migrate the ship/refund flow-action modals, sw-flow-sequence-action override and sw-search-bar-item override to TS - extract shared createFlowActionModalConfig() factory to remove the duplicated modal config (ship overrides data/created for warnings) - drop eslint-disable/redundant JSDoc; logic and templates unchanged Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- migrate api-service.init to TS; collapse the 8 identical ApiService providers into a registerHttpService() helper - migrate main.js -> main.ts; replace 22 Shopware.Locale.extend calls with a locales map + loop (drops 22 eslint-disable comments) - completes the admin TypeScript migration (no remaining .js in administration/src) Note: run bin/console bundle:dump so var/plugins.json points at main.ts. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The vertical-centering flex on .sw-select__selection turned it into a flex row; the single-select wrapper did not grow, so the selected value was clipped when the dropdown was open (e.g. "International Support (inf"). Let .sw-single-select__selection grow and its input fill the full width. Verified live in the built admin. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
TypeScript does not append .json for extensionless imports (even with resolveJsonModule), so the snippet imports raised TS2307 after the main.js -> main.ts migration. Reference the .json files explicitly; resolveJsonModule resolves them and the Vite build is unaffected. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- add a 'make typecheck' target (tsc --noEmit) and wire it into 'make pr' - upgrade lint stack: ESLint 10 (flat config in config/eslint.config.cjs, .cjs so require honours NODE_PATH=dev/node_modules), typescript-eslint 8, TypeScript 6.0, eslint-config-prettier 10; drop eslint 7 / babel-eslint / unused plugins - eslint lints the administration TypeScript (.tmp vite cache ignored), no-explicit-any off for the intentional Shopware any-typing - tsconfig: ignoreDeprecations 6.0, drop baseUrl (paths stay relative), exclude dead sw-plugin subtree - global.d.ts: declare untyped polyfill side-effect imports (regenerator-runtime, core-js) Verified: make typecheck=0, make eslint=0, make vitest=147/147. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Rename the remaining 6 Vitest spec files under administration/tests from .js to .ts (pure renames). Now covered by make typecheck and make eslint; vitest 147/147 unchanged. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…hip modal Closing the per-item ship modal ran the legacy /ship/status reload, whose response uses a different shape (quantityShippable + metadata-keyed) than the order-details status passed via initialShippingStatus (shippableQuantity + sw-item-keyed). This blanked the shippable column (option disabled) and the shipped column (~) until reload. - drop reloadData() from onCloseShipItemModal (cancel changes nothing; a successful ship triggers a parent re-fetch via EventShippedOrder) - watch initialShippingStatus so the parent's correctly-shaped status drives the grid - LineItemStatusService: read shippableQuantity or the legacy quantityShippable Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The greeting used $t(key, { userName }); $t is not reliably available on Vue 2
(Shopware 6.5) components, so the call threw during render and the whole section
stayed blank. Resolve the title in a computed using $tc (available everywhere) and
interpolate {userName} manually, which works on vue-i18n 8 (SW<6.6) and 9 (SW>=6.6).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Closing the refund manager calls loadData(), which set isDetailsLoading=true and hid the whole tab behind the skeleton until a remount (tab switch) restored it. Only show the skeleton on the initial load (isDetailsLoading && !details) so reloads keep the existing content visible. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Broaden the .gitignore from the .vite/assets subfolders to the whole src/Resources/public/administration/ build output. The static/*.png assets stay tracked — they are source images referenced by the PayPal Express and POS templates. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> � Conflicts: � .gitignore
Drop the title computed/$tc workaround and interpolate the greeting with
$t(key, { userName }) directly in the template — the version confirmed working on
Shopware 6.7. Cross-version handling will be centralised separately.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…rsion store access) - .shopware-extension.yml: enable_es_build_for_admin: false so shopware-cli runs the real Shopware build and emits .vite/entrypoints.json. The Vite-based admin (6.6.10+/6.7) loads plugins only via that manifest; the esbuild flat bundle never loaded. - main.ts: drop core-js/stable + regenerator-runtime/runtime imports. They break the real Vite/webpack build (unresolvable) and are unnecessary on SW6.5+ (core ships polyfills). - add getStore() cross-version helper (core/service/utils/store.utils.ts): on 6.6 the session lives in Vuex (Shopware.State, undefined-safe), on 6.7 in Pinia (Shopware.Store, whose get() THROWS for unknown ids). Check State first, then guard the Store throw. Migrate mollie-pluginconfig-section-info, mollie-order-tab and sw-product-detail-mollie (fixes "Store with id \"session\" not found" on 6.6). - .gitignore: ignore generated src/Resources/public/static/css output. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- .shopware-extension.yml: pin shopwareVersionConstraint to ~6.6.0 so the release/zip
build is deterministic and emits the broadly compatible layout (flat js/ plus a .vite
manifest pointing to it), which both the webpack admin (6.5/early 6.6) and the Vite
admin (6.6.10+/6.7) load. A 6.7 target would emit hashed assets/ with no flat js.
- makefile: clean public/administration + static/{css,js} before `extension zip` so stale
local build output does not leak into the distribution ZIP; clarify the storefront-only
flat-copy comment.
- .gitignore: ignore generated public/static/js build output.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…mit-output strategy (mollie#1291) master mollie#1291 commits the compiled admin output (.vite manifest + flat css/js) and ignores only the hashed assets/ dir, so a fresh clone runs without an admin build. This branch had ignored the whole public/administration/ — the opposite. Align with master: - .gitignore: ignore only public/administration/assets/ (keep .vite/css/js tracked). - Rebuild the admin from the migrated TypeScript source (shopware-cli ~6.6.0) and commit the fresh .vite/entrypoints.json, .vite/manifest.json, css and js so the committed artifact reflects the TS admin instead of master's stale .js build. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
diw-dhagen
force-pushed
the
users/dh/WIP-Refactor
branch
from
June 24, 2026 11:05
6d51884 to
085de71
Compare
After the admin TypeScript migration, wire `make typecheck` (tsc --noEmit) into step_review.yml as its own job (mirrors the ESLint job, reuses the dev-dependency cache) so type regressions fail CI on every PR. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
diw-dhagen
marked this pull request as ready for review
June 24, 2026 11:12
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.
No description provided.