Skip to content

feat(deployment): adds weekly deployment cost display for auto-topped-up deployments#2359

Merged
ygrishajev merged 2 commits intomainfrom
feature/auto-reload
Dec 16, 2025
Merged

feat(deployment): adds weekly deployment cost display for auto-topped-up deployments#2359
ygrishajev merged 2 commits intomainfrom
feature/auto-reload

Conversation

@ygrishajev
Copy link
Contributor

@ygrishajev ygrishajev commented Dec 16, 2025

  • Adds GET /v1/weekly-cost API endpoint returning USD cost
  • Calculates weekly cost using DrainingDeploymentService with BalancesService conversion
  • Displays weekly cost in AccountOverview UI with formal description
  • Adds ManagedDeploymentHttpService for console API endpoints
  • Adds comprehensive unit tests with BalancesService mocking
  • Updates documentation for auto top-up immediate check scenario

refs #1779

image image image

Summary by CodeRabbit

  • New Features
    • Weekly deployment cost shown in the billing/account overview.
  • Bug Fixes / UX
    • Confirmation dialog added when toggling Auto Reload (requires user confirmation).
  • Documentation
    • Wallet reload check docs updated to include the new auto top-up trigger scenario.

✏️ Tip: You can customize this high-level summary in your review settings.

@ygrishajev ygrishajev requested a review from a team as a code owner December 16, 2025 11:15
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Dec 16, 2025

Walkthrough

Adds a weekly deployment cost feature end-to-end: new backend service method and controller endpoint, API schema and route, HTTP SDK client, frontend query and UI display, DI wiring, tests, and docs update for wallet reload triggers.

Changes

Cohort / File(s) Change Summary
Documentation
apps/api/src/billing/services/wallet-balance-reload-check/README.md
Added "When deployment auto top-up is enabled" scenario, reordered trigger scenarios, updated sequence diagram to include deployment auto top‑up immediate-check path.
API Schema & Routing
apps/api/src/deployment/http-schemas/deployment.schema.ts, apps/api/src/deployment/routes/deployments/deployments.router.ts
Added GetWeeklyDeploymentCostResponseSchema and new GET /v1/weekly-cost route returning { weeklyCost }.
Backend Controller
apps/api/src/deployment/controllers/deployment/deployment.controller.ts
Injected DrainingDeploymentService and added protected endpoint getWeeklyDeploymentCost() delegating to service with user/ability context.
Backend Service & Tests
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts, apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
Added BalancesService dependency; new public calculateWeeklyDeploymentCost(userId, ability); refactored cost logic into private helpers (#findAutoTopUpDeploymentSettings, #findDrainingDeployments, #accumulateDeploymentCost); tests updated/wired to mock BalancesService and exercise weekly-cost scenarios.
HTTP SDK
packages/http-sdk/src/deployment/managed-deployment-http.service.ts, packages/http-sdk/src/index.ts
New ManagedDeploymentHttpService with getWeeklyDeploymentCost() and WeeklyDeploymentCostResponse interface; exported from SDK index.
Frontend DI Container
apps/deploy-web/src/services/app-di-container/app-di-container.ts
Added managedDeployment container entry creating a dedicated Axios client with withUserToken and returning ManagedDeploymentHttpService.
Frontend Query Infrastructure
apps/deploy-web/src/queries/useDeploymentQueries.ts, apps/deploy-web/src/queries/queryKeys.ts, apps/deploy-web/src/queries/index.ts
New useWeeklyDeploymentCostQuery hook; added QueryKeys.getWeeklyDeploymentCostKey(); re-exported deployment queries (duplicate export/method present).
Frontend UI
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
Integrated weekly cost query and conditional display; added confirmation popup flow for toggling Auto Reload and adjusted layout.

Sequence Diagram(s)

sequenceDiagram
    participant Frontend as Frontend UI
    participant Query as useWeeklyDeploymentCostQuery
    participant HttpSdk as ManagedDeploymentHttpService
    participant Api as DeploymentController
    participant Service as DrainingDeploymentService
    participant Db as Database/RPC
    participant Balances as BalancesService

    Frontend->>Query: request weekly cost
    Query->>HttpSdk: getWeeklyDeploymentCost()
    HttpSdk->>Api: GET /v1/weekly-cost
    Api->>Service: calculateWeeklyDeploymentCost(userId, ability)
    Service->>Service: authorize (AnyAbility)
    Service->>Db: find auto-top-up settings & draining deployments
    Db-->>Service: deployments & settings
    Service->>Balances: toFiatAmount(per-deployment cost)
    Balances-->>Service: fiat amounts
    Service-->>Api: weeklyCost (number)
    Api-->>HttpSdk: { data: { weeklyCost } }
    HttpSdk-->>Query: weeklyCost
    Query-->>Frontend: render weeklyCost
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

  • Review focus:
    • Duplicate getWeeklyDeploymentCostKey() and duplicate export in queries/index.ts.
    • Correctness of #accumulateDeploymentCost() and fiat conversions via BalancesService.toFiatAmount().
    • Proper injection of BalancesService into all DrainingDeploymentService instantiation sites.
    • Authorization checks using AnyAbility in calculateWeeklyDeploymentCost().

Possibly related PRs

Suggested reviewers

  • baktun14
  • stalniy

"I nibble code in the midnight light,
Weekly costs counted, neat and bright,
Services, routes, and queries hum—so tight,
A carrot clue for every deployer's night,
Hop, compile, and ship — hooray, delight!" 🐇✨

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The PR title accurately describes the main feature: adding weekly deployment cost display for auto-topped-up deployments, which is reflected throughout the changeset.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feature/auto-reload

Comment @coderabbitai help to get the list of available commands and usage tips.

@codecov
Copy link

codecov bot commented Dec 16, 2025

Codecov Report

❌ Patch coverage is 70.88608% with 23 lines in your changes missing coverage. Please review.
✅ Project coverage is 51.36%. Comparing base (795a5c8) to head (84c54c6).
⚠️ Report is 2 commits behind head on main.
✅ All tests successful. No failed tests found.

Files with missing lines Patch % Lines
.../billing-usage/AccountOverview/AccountOverview.tsx 0.00% 14 Missing ⚠️
...pps/deploy-web/src/queries/useDeploymentQueries.ts 50.00% 4 Missing ⚠️
...nt/controllers/deployment/deployment.controller.ts 66.66% 2 Missing ⚠️
...eployment/routes/deployments/deployments.router.ts 50.00% 2 Missing ⚠️
.../src/services/app-di-container/app-di-container.ts 83.33% 1 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main    #2359      +/-   ##
==========================================
+ Coverage   51.32%   51.36%   +0.03%     
==========================================
  Files        1060     1061       +1     
  Lines       28952    29016      +64     
  Branches     6372     6383      +11     
==========================================
+ Hits        14860    14903      +43     
- Misses      13696    13819     +123     
+ Partials      396      294     -102     
Flag Coverage Δ *Carryforward flag
api 81.01% <91.83%> (+0.03%) ⬆️
deploy-web 31.07% <36.66%> (+0.02%) ⬆️
log-collector 75.35% <ø> (ø)
notifications 87.94% <ø> (ø)
provider-console 81.48% <ø> (ø) Carriedforward from 2ff2a3e
provider-proxy 84.35% <ø> (ø) Carriedforward from 2ff2a3e

*This pull request uses carry forward flags. Click here to find out more.

Files with missing lines Coverage Δ
...i/src/deployment/http-schemas/deployment.schema.ts 100.00% <100.00%> (ø)
...draining-deployment/draining-deployment.service.ts 98.05% <100.00%> (+1.71%) ⬆️
apps/deploy-web/src/queries/index.ts 100.00% <100.00%> (ø)
apps/deploy-web/src/queries/queryKeys.ts 100.00% <100.00%> (ø)
.../src/services/app-di-container/app-di-container.ts 79.16% <83.33%> (+0.34%) ⬆️
...nt/controllers/deployment/deployment.controller.ts 95.00% <66.66%> (-5.00%) ⬇️
...eployment/routes/deployments/deployments.router.ts 94.52% <50.00%> (-2.59%) ⬇️
...pps/deploy-web/src/queries/useDeploymentQueries.ts 50.00% <50.00%> (ø)
.../billing-usage/AccountOverview/AccountOverview.tsx 0.00% <0.00%> (ø)

... and 36 files with indirect coverage changes

🚀 New features to boost your workflow:
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (4)
apps/api/src/billing/services/wallet-balance-reload-check/README.md (1)

50-50: Consider rewording for readability.

Three consecutive sentences begin with "When", which can make the text slightly repetitive. Consider varying the sentence structure for improved readability, e.g., starting one sentence with "For deployment auto top-up enablement, an immediate check..." or similar.

apps/api/src/deployment/http-schemas/deployment.schema.ts (1)

268-272: Schema follows existing patterns.

The new schema is well-structured and consistent with other response schemas in this file. The description clearly documents the field's purpose.

Consider adding .min(0) validation for weeklyCost to ensure the API always returns non-negative values, though this is optional for a response schema.

 export const GetWeeklyDeploymentCostResponseSchema = z.object({
   data: z.object({
-    weeklyCost: z.number().describe("Total weekly cost in USD for all deployments with auto top-up enabled")
+    weeklyCost: z.number().min(0).describe("Total weekly cost in USD for all deployments with auto top-up enabled")
   })
 });
apps/deploy-web/src/queries/useDeploymentQueries.ts (1)

7-16: LGTM with minor optimization opportunity.

The hook implementation follows React Query patterns correctly. The query key is properly centralized, and type safety is maintained.

Minor optimization: The return await on line 13 is redundant since managedDeployment.getWeeklyDeploymentCost() already returns a Promise and the queryFn will handle the async resolution.

Apply this diff to simplify:

     queryFn: async () => {
-      return await managedDeployment.getWeeklyDeploymentCost();
+      return managedDeployment.getWeeklyDeploymentCost();
     }
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (1)

135-143: LGTM!

The weekly cost display is well-implemented with proper loading state handling and conditional rendering. The formatted currency presentation and descriptive text provide clear information to users about their ongoing deployment costs.

Minor note: The condition weeklyCost !== undefined && weeklyCost > 0 could be simplified to just weeklyCost > 0 since the comparison already handles undefined (undefined > 0 is false). However, the explicit undefined check improves readability and intent, so this is purely a style preference.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 795a5c8 and fbac70f.

📒 Files selected for processing (14)
  • apps/api/src/billing/services/wallet-balance-reload-check/README.md (3 hunks)
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts (3 hunks)
  • apps/api/src/deployment/http-schemas/deployment.schema.ts (2 hunks)
  • apps/api/src/deployment/routes/deployments/deployments.router.ts (2 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (5 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3 hunks)
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (6 hunks)
  • apps/deploy-web/src/hooks/useFlag.tsx (1 hunks)
  • apps/deploy-web/src/queries/index.ts (1 hunks)
  • apps/deploy-web/src/queries/queryKeys.ts (1 hunks)
  • apps/deploy-web/src/queries/useDeploymentQueries.ts (1 hunks)
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts (2 hunks)
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1 hunks)
  • packages/http-sdk/src/index.ts (1 hunks)
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{ts,tsx,js}

📄 CodeRabbit inference engine (.cursor/rules/general.mdc)

**/*.{ts,tsx,js}: Never use type any or cast to type any. Always define the proper TypeScript types.
Never use deprecated methods from libraries.
Don't add unnecessary comments to the code.

Files:

  • apps/api/src/deployment/http-schemas/deployment.schema.ts
  • apps/deploy-web/src/queries/index.ts
  • apps/deploy-web/src/queries/useDeploymentQueries.ts
  • packages/http-sdk/src/index.ts
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
  • apps/deploy-web/src/hooks/useFlag.tsx
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts
  • apps/api/src/deployment/routes/deployments/deployments.router.ts
  • apps/deploy-web/src/queries/queryKeys.ts
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts
**/*.spec.{ts,tsx}

📄 CodeRabbit inference engine (.cursor/rules/no-jest-mock.mdc)

Don't use jest.mock() in test files. Instead, use jest-mock-extended to create mocks and pass mocks as dependencies to the service under test

Use setup function instead of beforeEach in test files. The setup function must be at the bottom of the root describe block, should create an object under test and return it, accept a single parameter with inline type definition, avoid shared state, and not have a specified return type.

**/*.spec.{ts,tsx}: Use <Subject>.name in the root describe suite description instead of hardcoded class/service name strings to enable automated refactoring tools to find all references
Use either a method name or a condition starting with 'when' for nested suite descriptions in tests
Use present simple, 3rd person singular for test descriptions without prepending 'should'

Files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
🧠 Learnings (8)
📚 Learning: 2025-11-25T17:45:49.180Z
Learnt from: CR
Repo: akash-network/console PR: 0
File: .cursor/rules/query-by-in-tests.mdc:0-0
Timestamp: 2025-11-25T17:45:49.180Z
Learning: Applies to {apps/deploy-web,apps/provider-console}/**/*.spec.tsx : Use `queryBy` methods instead of `getBy` methods in test expectations

Applied to files:

  • apps/deploy-web/src/queries/index.ts
  • apps/deploy-web/src/queries/useDeploymentQueries.ts
📚 Learning: 2025-06-03T15:06:34.211Z
Learnt from: baktun14
Repo: akash-network/console PR: 1428
File: apps/api/src/deployment/controllers/deployment/deployment.controller.ts:0-0
Timestamp: 2025-06-03T15:06:34.211Z
Learning: The `getByOwnerAndDseq` method in `apps/api/src/deployment/controllers/deployment/deployment.controller.ts` is intentionally public without the `Protected` decorator because it serves public blockchain data from an indexer, following the pattern of public blockchain APIs.

Applied to files:

  • apps/deploy-web/src/queries/index.ts
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts
📚 Learning: 2025-11-19T16:13:43.249Z
Learnt from: stalniy
Repo: akash-network/console PR: 2255
File: apps/api/src/middlewares/privateMiddleware.ts:5-9
Timestamp: 2025-11-19T16:13:43.249Z
Learning: In the Akash Console API (apps/api), avoid resolving DI container dependencies at module scope (module initialization time) to prevent side effects. Instead, resolve dependencies inside functions/methods where they are actually used, even if this means resolving on every invocation, to maintain explicit control over when side effects occur and improve testability.

Applied to files:

  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
📚 Learning: 2025-11-25T17:45:44.790Z
Learnt from: CR
Repo: akash-network/console PR: 0
File: .cursor/rules/no-jest-mock.mdc:0-0
Timestamp: 2025-11-25T17:45:44.790Z
Learning: Applies to **/*.spec.{ts,tsx} : Don't use `jest.mock()` in test files. Instead, use `jest-mock-extended` to create mocks and pass mocks as dependencies to the service under test

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-11-19T15:15:07.283Z
Learnt from: ygrishajev
Repo: akash-network/console PR: 2254
File: apps/api/test/functional/sign-and-broadcast-tx.spec.ts:4-4
Timestamp: 2025-11-19T15:15:07.283Z
Learning: In the Akash Network Console project, when tests use native Node.js fetch (available in Node 18+), fetch-mock should be used for HTTP mocking instead of nock, as nock does not support intercepting native fetch calls. This applies to apps/api/test/functional/sign-and-broadcast-tx.spec.ts and any other tests using native fetch.

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-10-15T16:39:55.348Z
Learnt from: jzsfkzm
Repo: akash-network/console PR: 2039
File: apps/deploy-web/tests/ui/change-wallets.spec.ts:4-10
Timestamp: 2025-10-15T16:39:55.348Z
Learning: In the Akash Console E2E tests using the context-with-extension fixture, the first wallet is automatically created during fixture setup via `importWalletToLeap` in `apps/deploy-web/tests/ui/fixture/wallet-setup.ts`, so tests that call `frontPage.createWallet()` are creating a second wallet to test wallet switching functionality.

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-06-05T21:07:51.985Z
Learnt from: baktun14
Repo: akash-network/console PR: 1432
File: apps/deploy-web/src/components/deployments/DeploymentAlerts/DeploymentCloseAlert.tsx:38-38
Timestamp: 2025-06-05T21:07:51.985Z
Learning: The ContactPointSelect component in apps/deploy-web/src/components/alerts/ContactPointSelectForm/ContactPointSelect.tsx uses the useFormContext hook internally to connect to React Hook Form, so it doesn't need to be wrapped in a FormField component.

Applied to files:

  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
📚 Learning: 2025-07-28T10:40:13.595Z
Learnt from: stalniy
Repo: akash-network/console PR: 1480
File: apps/deploy-web/src/hooks/useFlag.tsx:0-0
Timestamp: 2025-07-28T10:40:13.595Z
Learning: In the Akash Network Console project, backend-specific feature flags are intentional and acceptable. The frontend FeatureFlag union type should only include flags that are actually used by the frontend, not all flags defined in the backend. Backend can have internal feature flags for backend-only functionality without requiring frontend synchronization.

Applied to files:

  • apps/deploy-web/src/hooks/useFlag.tsx
🧬 Code graph analysis (5)
apps/deploy-web/src/queries/useDeploymentQueries.ts (1)
apps/deploy-web/src/context/ServicesProvider/ServicesProvider.tsx (1)
  • useServices (35-37)
apps/deploy-web/src/services/app-di-container/app-di-container.ts (3)
packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)
  • ManagedDeploymentHttpService (9-22)
apps/deploy-web/src/services/auth/auth/auth.service.ts (1)
  • withUserToken (69-79)
apps/deploy-web/src/services/auth/auth/interceptors.ts (1)
  • withUserToken (15-25)
packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)
packages/http-sdk/src/api-http/api-http.service.ts (1)
  • ApiHttpService (9-29)
apps/api/src/deployment/routes/deployments/deployments.router.ts (3)
apps/api/src/core/lib/create-route/create-route.ts (1)
  • createRoute (5-11)
apps/api/src/core/services/openapi-docs/openapi-security.ts (1)
  • SECURITY_BEARER_OR_API_KEY (5-5)
apps/api/src/deployment/http-schemas/deployment.schema.ts (1)
  • GetWeeklyDeploymentCostResponseSchema (268-272)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3)
apps/api/src/utils/constants.ts (1)
  • averageBlockCountInAnHour (8-8)
apps/api/src/deployment/repositories/deployment-setting/deployment-setting.repository.ts (1)
  • AutoTopUpDeployment (18-24)
apps/api/src/deployment/repositories/lease/lease.repository.ts (1)
  • DrainingDeploymentOutput (7-14)
🪛 LanguageTool
apps/api/src/billing/services/wallet-balance-reload-check/README.md

[style] ~50-~50: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...bled, the first check runs immediately. When deployment auto top-up is enabled, an i...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (8)
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: Validate local packages
  • GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (19)
apps/deploy-web/src/hooks/useFlag.tsx (1)

6-8: LGTM!

The dummy flag implementation correctly returns false specifically for "console_embedded_login" while enabling all other flags when NEXT_PUBLIC_UNLEASH_ENABLE_ALL is set. This prevents embedded login in development/testing scenarios where all flags are enabled.

apps/api/src/billing/services/wallet-balance-reload-check/README.md (1)

59-80: Documentation update looks good.

The sequence diagram clearly illustrates the new deployment auto top-up flow with DeploymentSettingService.scheduleImmediate() and WalletReloadJobService.scheduleImmediate(). The branching logic is well-represented.

apps/deploy-web/src/queries/index.ts (1)

9-9: LGTM!

The new export follows the established pattern for re-exporting query modules.

packages/http-sdk/src/index.ts (1)

17-17: LGTM!

The new export follows the established pattern and is logically grouped with the existing deployment HTTP service export.

apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (3)

345-390: Test helper follows the pattern, minor improvement possible.

The setupCalculateWeeklyCost helper is well-structured and follows the project patterns. One observation:

The "userWallet" in input check on line 352 will always be true when userWallet is explicitly passed (even as undefined), which is the intended behavior here. The tests correctly use this to differentiate between "not specified" (use default) and "explicitly undefined" (test missing wallet).


236-254: Comprehensive test coverage for calculateWeeklyDeploymentCost.

The tests cover the main scenarios including:

  • Standard calculation with multiple deployments
  • Deployments closing after the 7-day window
  • Missing user wallet
  • Missing wallet address
  • No deployments
  • Null predictedClosedHeight
  • Deployments closing at/before currentHeight
  • Invalid blockRate values

518-561: Setup function correctly updated with BalancesService dependency.

The setup function properly instantiates the BalancesService mock and passes it to the DrainingDeploymentService constructor, following the jest-mock-extended pattern required by the coding guidelines.

apps/deploy-web/src/queries/queryKeys.ts (1)

78-79: LGTM!

The new query key generator follows the established pattern and is appropriately placed with other related keys.

packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)

5-7: LGTM!

The interface definition is clean and follows proper TypeScript conventions.

apps/api/src/deployment/routes/deployments/deployments.router.ts (1)

368-388: LGTM!

The route definition and handler implementation follow established patterns in the codebase. The security requirement (SECURITY_BEARER_OR_API_KEY) is appropriate for a user-specific cost calculation endpoint.

apps/deploy-web/src/services/app-di-container/app-di-container.ts (1)

95-98: LGTM!

The service wiring follows the established DI container pattern and is consistent with other HTTP service registrations in the container. The use of withUserToken interceptor is appropriate for authenticated endpoints.

apps/api/src/deployment/controllers/deployment/deployment.controller.ts (1)

104-108: LGTM!

The controller method correctly applies authorization via the @Protected decorator with "read" access, delegates to the service layer with proper user context and ability, and returns a correctly shaped response.

apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (2)

33-70: LGTM!

The addition of a confirmation dialog before enabling/disabling auto-reload is a good UX improvement. The implementation correctly:

  • Prompts with clear, context-specific messages
  • Returns early if not confirmed, preventing unnecessary API calls
  • Maintains proper error handling
  • Includes confirm in the dependency array

125-128: LGTM!

The updated card header provides clear information about the auto-reload feature with an appropriate description of its behavior.

apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (5)

133-153: LGTM!

The refactoring of calculateAllDeploymentCostUntilDate to use private helper methods (#findAutoTopUpDeploymentSettings, #findDrainingDeployments, #accumulateDeploymentCost) improves code organization and maintainability while preserving the original calculation logic.


163-192: LGTM!

The calculateWeeklyDeploymentCost method is well-implemented with:

  • Proper authorization using ability-based access control on both wallet and deployment settings
  • Correct weekly cost calculation (7 days × 24 hours × blocks per hour × block rate)
  • Appropriate filtering for active deployments (predictedClosedHeight > currentHeight)
  • Proper conversion to USD via BalancesService
  • Safe handling of edge cases (no wallet, no settings, zero cost)

201-209: LGTM!

The #findAutoTopUpDeploymentSettings helper properly validates wallet existence before querying deployment settings and returns a consistent empty array when validation fails.


220-223: LGTM!

The #findDrainingDeployments helper cleanly extracts a common pattern and delegates to the existing findLeases method.


233-242: LGTM!

The #accumulateDeploymentCost helper provides a clean abstraction for cost accumulation with a callback pattern that allows flexible per-deployment cost calculations.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (3)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (2)

201-209: Redundant wallet lookup in #findAutoTopUpDeploymentSettings.

The method queries userWalletRepository.findOneBy({ address }) and then checks userWallet?.address, but the address parameter is already known. The check seems unnecessary since you're querying by address—if a record is found, it will have that address.

This lookup may be intended to verify wallet existence, but the pattern differs from calculateWeeklyDeploymentCost which uses accessibleBy. Consider aligning the authorization approach or simplifying if the wallet existence check is redundant.

 async #findAutoTopUpDeploymentSettings(address: string): Promise<AutoTopUpDeployment[]> {
   const userWallet = await this.userWalletRepository.findOneBy({ address });

-  if (!userWallet?.address) {
+  if (!userWallet) {
     return [];
   }

   return this.deploymentSettingRepository.findAutoTopUpDeploymentsByOwner(address);
 }

233-242: Consider using reduce or Promise.all for accumulation.

The sequential for...of loop with await is correct but processes deployments one-at-a-time. Since the callback in current usages performs only synchronous calculations (no I/O), this could be simplified. If callbacks remain sync-only, consider making the callback synchronous to clarify intent.

 async #accumulateDeploymentCost(
   drainingDeployments: DrainingDeploymentOutput[],
-  callback: (deployment: DrainingDeploymentOutput) => Promise<number>
+  callback: (deployment: DrainingDeploymentOutput) => number
 ): Promise<number> {
-  let totalAmount = 0;
-  for (const deployment of drainingDeployments) {
-    totalAmount += await callback(deployment);
-  }
-  return totalAmount;
+  return drainingDeployments.reduce((total, deployment) => total + callback(deployment), 0);
 }
apps/api/src/billing/services/wallet-balance-reload-check/README.md (1)

43-51: Documentation update accurately reflects the new trigger scenario.

The addition of the deployment auto top-up scenario is well-documented. The sequence diagram clearly shows the new flow path.

Minor style note: Lines 45-50 have repetitive sentence starters ("When..."). Consider varying the structure for readability, e.g., "Immediately upon enabling deployment auto top-up..." or "After a user enables...".

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between fbac70f and 320cbb0.

⛔ Files ignored due to path filters (1)
  • apps/api/test/functional/__snapshots__/docs.spec.ts.snap is excluded by !**/*.snap
📒 Files selected for processing (14)
  • apps/api/src/billing/services/wallet-balance-reload-check/README.md (3 hunks)
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts (3 hunks)
  • apps/api/src/deployment/http-schemas/deployment.schema.ts (2 hunks)
  • apps/api/src/deployment/routes/deployments/deployments.router.ts (2 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (5 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3 hunks)
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (6 hunks)
  • apps/deploy-web/src/hooks/useFlag.tsx (1 hunks)
  • apps/deploy-web/src/queries/index.ts (1 hunks)
  • apps/deploy-web/src/queries/queryKeys.ts (1 hunks)
  • apps/deploy-web/src/queries/useDeploymentQueries.ts (1 hunks)
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts (2 hunks)
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1 hunks)
  • packages/http-sdk/src/index.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (8)
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
  • apps/deploy-web/src/queries/index.ts
  • apps/api/src/deployment/http-schemas/deployment.schema.ts
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
  • packages/http-sdk/src/index.ts
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx,js}

📄 CodeRabbit inference engine (.cursor/rules/general.mdc)

**/*.{ts,tsx,js}: Never use type any or cast to type any. Always define the proper TypeScript types.
Never use deprecated methods from libraries.
Don't add unnecessary comments to the code.

Files:

  • apps/api/src/deployment/routes/deployments/deployments.router.ts
  • apps/deploy-web/src/hooks/useFlag.tsx
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts
  • apps/deploy-web/src/queries/queryKeys.ts
  • apps/deploy-web/src/queries/useDeploymentQueries.ts
🧠 Learnings (2)
📚 Learning: 2025-07-28T10:40:13.595Z
Learnt from: stalniy
Repo: akash-network/console PR: 1480
File: apps/deploy-web/src/hooks/useFlag.tsx:0-0
Timestamp: 2025-07-28T10:40:13.595Z
Learning: In the Akash Network Console project, backend-specific feature flags are intentional and acceptable. The frontend FeatureFlag union type should only include flags that are actually used by the frontend, not all flags defined in the backend. Backend can have internal feature flags for backend-only functionality without requiring frontend synchronization.

Applied to files:

  • apps/deploy-web/src/hooks/useFlag.tsx
📚 Learning: 2025-11-25T17:45:49.180Z
Learnt from: CR
Repo: akash-network/console PR: 0
File: .cursor/rules/query-by-in-tests.mdc:0-0
Timestamp: 2025-11-25T17:45:49.180Z
Learning: Applies to {apps/deploy-web,apps/provider-console}/**/*.spec.tsx : Use `queryBy` methods instead of `getBy` methods in test expectations

Applied to files:

  • apps/deploy-web/src/queries/useDeploymentQueries.ts
🧬 Code graph analysis (3)
apps/api/src/deployment/routes/deployments/deployments.router.ts (3)
apps/api/src/core/lib/create-route/create-route.ts (1)
  • createRoute (5-11)
apps/api/src/core/services/openapi-docs/openapi-security.ts (1)
  • SECURITY_BEARER_OR_API_KEY (5-5)
apps/api/src/deployment/http-schemas/deployment.schema.ts (1)
  • GetWeeklyDeploymentCostResponseSchema (268-272)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3)
apps/api/src/utils/constants.ts (1)
  • averageBlockCountInAnHour (8-8)
apps/api/src/deployment/repositories/deployment-setting/deployment-setting.repository.ts (1)
  • AutoTopUpDeployment (18-24)
apps/api/src/deployment/repositories/lease/lease.repository.ts (1)
  • DrainingDeploymentOutput (7-14)
apps/deploy-web/src/queries/useDeploymentQueries.ts (1)
apps/deploy-web/src/context/ServicesProvider/ServicesProvider.tsx (1)
  • useServices (35-37)
🪛 LanguageTool
apps/api/src/billing/services/wallet-balance-reload-check/README.md

[style] ~50-~50: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...bled, the first check runs immediately. When deployment auto top-up is enabled, an i...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
  • GitHub Check: validate / validate-app
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: test-build
🔇 Additional comments (7)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3)

1-31: LGTM on constructor and import changes.

The new BalancesService dependency and AnyAbility import are properly integrated. The constructor maintains the existing pattern of dependency injection via tsyringe.


133-153: Refactored cost calculation logic is cleaner.

The delegation to #findAutoTopUpDeploymentSettings and #findDrainingDeployments improves readability. The #accumulateDeploymentCost helper with callback pattern allows for flexible cost calculation strategies.


163-192: Verify the cost calculation logic for deployments that close before the week ends.

The current logic at line 181 calculates cost for all deployments where predictedClosedHeight > currentHeight, multiplying by blocksInAWeek. However, if a deployment is predicted to close mid-week, the user would be charged for a full week even though the deployment won't run that long.

Consider whether this is intentional (charging for potential cost if auto top-up keeps it running) or if it should calculate only until predictedClosedHeight for deployments closing within the week.

apps/deploy-web/src/queries/queryKeys.ts (1)

78-79: LGTM!

The new getWeeklyDeploymentCostKey follows the established pattern for static query key generators in this file. The simple array structure is appropriate for a user-scoped resource that doesn't require additional parameters.

apps/deploy-web/src/queries/useDeploymentQueries.ts (1)

7-16: LGTM! Well-structured React Query hook.

The hook correctly integrates with the services context and follows React Query v5 patterns. The Omit type properly excludes queryKey and queryFn from options.

Minor note: The async/await in the queryFn is redundant since getWeeklyDeploymentCost() already returns a Promise, but this is stylistic and harmless.

apps/api/src/deployment/routes/deployments/deployments.router.ts (1)

368-388: LGTM! Well-structured route definition.

The new /v1/weekly-cost endpoint follows the established patterns in this router:

  • Proper use of createRoute with security configuration
  • Consistent response schema integration
  • Controller resolution via tsyringe container
  • Appropriate HTTP method (GET) for a read operation

The route is properly secured with SECURITY_BEARER_OR_API_KEY, consistent with other authenticated deployment endpoints.

apps/deploy-web/src/hooks/useFlag.tsx (1)

6-8: Add inline comment explaining why console_embedded_login is excluded from all-flags-enabled mode.

The useDummyFlag function intentionally disables "console_embedded_login" even when NEXT_PUBLIC_UNLEASH_ENABLE_ALL is active. While the README documents that the useFlag hook is "patched" for consistent behavior during local development, the code lacks an inline explanation for why this specific flag is excluded. Add a brief comment (e.g., "embedded login is security-sensitive and must remain disabled in all-flags-enabled dev mode") to clarify the intentional behavior for future maintainers.

⛔ Skipped due to learnings
Learnt from: stalniy
Repo: akash-network/console PR: 1480
File: apps/deploy-web/src/hooks/useFlag.tsx:0-0
Timestamp: 2025-07-28T10:40:13.595Z
Learning: In the Akash Network Console project, backend-specific feature flags are intentional and acceptable. The frontend FeatureFlag union type should only include flags that are actually used by the frontend, not all flags defined in the backend. Backend can have internal feature flags for backend-only functionality without requiring frontend synchronization.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (3)
apps/api/src/billing/services/wallet-balance-reload-check/README.md (1)

50-50: Reword consecutive "When" sentences for better flow.

The static analysis tool flagged three successive sentences beginning with "When." Consider restructuring line 50 to vary sentence openers and improve readability.

-When auto-reload is enabled, the first check runs immediately. When deployment auto top-up is enabled, an immediate check is scheduled to ensure the wallet balance can cover the new deployment costs. Subsequent checks run on a daily schedule. Immediate triggers (deployments/deposits) ensure the balance is checked right after spending or depositing funds, rather than waiting for the next scheduled check.
+When auto-reload is enabled, the first check runs immediately. If deployment auto top-up is enabled, an immediate check is scheduled to ensure the wallet balance can cover the new deployment costs. Subsequent checks run on a daily schedule. Immediate triggers (deployments/deposits) ensure the balance is checked right after spending or depositing funds, rather than waiting for the next scheduled check.
apps/deploy-web/src/hooks/useFlag.tsx (1)

6-8: Consider renaming parameter for consistency.

The implementation correctly enables all flags except console_embedded_login when the enable-all environment variable is set. However, the parameter name name is inconsistent with the type definition on line 11, which uses flag.

Apply this diff for consistency:

-const useDummyFlag: FeatureFlagHook = name => {
-  return name !== "console_embedded_login";
+const useDummyFlag: FeatureFlagHook = flag => {
+  return flag !== "console_embedded_login";
 };
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (1)

378-383: Consider more realistic mock behavior for fiat conversion.

The mock returns the same expectedFiatAmount for any non-zero uakt amount. While this works for single-deployment scenarios, the test at lines 237-254 sums costs from multiple deployments (blockRate 50 and 75) but receives the same flat fiat amount. This doesn't reflect real aggregation behavior.

Consider a proportional mock implementation:

-baseSetup.balancesService.toFiatAmount.mockImplementation(async (uaktAmount: number) => {
-  if (uaktAmount === 0) {
-    return 0;
-  }
-  return input.expectedFiatAmount ?? 0;
-});
+baseSetup.balancesService.toFiatAmount.mockImplementation(async (uaktAmount: number) => {
+  // Use a simple conversion rate for testing, e.g., 1 uakt = 0.0001 USD
+  return uaktAmount * 0.0001;
+});

Then update test assertions to calculate expected values based on actual block rates.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 320cbb0 and 4caede8.

⛔ Files ignored due to path filters (1)
  • apps/api/test/functional/__snapshots__/docs.spec.ts.snap is excluded by !**/*.snap
📒 Files selected for processing (14)
  • apps/api/src/billing/services/wallet-balance-reload-check/README.md (3 hunks)
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts (3 hunks)
  • apps/api/src/deployment/http-schemas/deployment.schema.ts (2 hunks)
  • apps/api/src/deployment/routes/deployments/deployments.router.ts (2 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (5 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3 hunks)
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (6 hunks)
  • apps/deploy-web/src/hooks/useFlag.tsx (1 hunks)
  • apps/deploy-web/src/queries/index.ts (1 hunks)
  • apps/deploy-web/src/queries/queryKeys.ts (1 hunks)
  • apps/deploy-web/src/queries/useDeploymentQueries.ts (1 hunks)
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts (2 hunks)
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1 hunks)
  • packages/http-sdk/src/index.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (3)
  • apps/deploy-web/src/queries/index.ts
  • apps/deploy-web/src/queries/useDeploymentQueries.ts
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{ts,tsx,js}

📄 CodeRabbit inference engine (.cursor/rules/general.mdc)

**/*.{ts,tsx,js}: Never use type any or cast to type any. Always define the proper TypeScript types.
Never use deprecated methods from libraries.
Don't add unnecessary comments to the code.

Files:

  • packages/http-sdk/src/index.ts
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
  • apps/api/src/deployment/routes/deployments/deployments.router.ts
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts
  • apps/deploy-web/src/hooks/useFlag.tsx
  • apps/api/src/deployment/http-schemas/deployment.schema.ts
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts
  • apps/deploy-web/src/queries/queryKeys.ts
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
**/*.spec.{ts,tsx}

📄 CodeRabbit inference engine (.cursor/rules/no-jest-mock.mdc)

Don't use jest.mock() in test files. Instead, use jest-mock-extended to create mocks and pass mocks as dependencies to the service under test

Use setup function instead of beforeEach in test files. The setup function must be at the bottom of the root describe block, should create an object under test and return it, accept a single parameter with inline type definition, avoid shared state, and not have a specified return type.

**/*.spec.{ts,tsx}: Use <Subject>.name in the root describe suite description instead of hardcoded class/service name strings to enable automated refactoring tools to find all references
Use either a method name or a condition starting with 'when' for nested suite descriptions in tests
Use present simple, 3rd person singular for test descriptions without prepending 'should'

Files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
🧠 Learnings (6)
📚 Learning: 2025-06-05T21:07:51.985Z
Learnt from: baktun14
Repo: akash-network/console PR: 1432
File: apps/deploy-web/src/components/deployments/DeploymentAlerts/DeploymentCloseAlert.tsx:38-38
Timestamp: 2025-06-05T21:07:51.985Z
Learning: The ContactPointSelect component in apps/deploy-web/src/components/alerts/ContactPointSelectForm/ContactPointSelect.tsx uses the useFormContext hook internally to connect to React Hook Form, so it doesn't need to be wrapped in a FormField component.

Applied to files:

  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
📚 Learning: 2025-06-03T15:06:34.211Z
Learnt from: baktun14
Repo: akash-network/console PR: 1428
File: apps/api/src/deployment/controllers/deployment/deployment.controller.ts:0-0
Timestamp: 2025-06-03T15:06:34.211Z
Learning: The `getByOwnerAndDseq` method in `apps/api/src/deployment/controllers/deployment/deployment.controller.ts` is intentionally public without the `Protected` decorator because it serves public blockchain data from an indexer, following the pattern of public blockchain APIs.

Applied to files:

  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts
📚 Learning: 2025-07-28T10:40:13.595Z
Learnt from: stalniy
Repo: akash-network/console PR: 1480
File: apps/deploy-web/src/hooks/useFlag.tsx:0-0
Timestamp: 2025-07-28T10:40:13.595Z
Learning: In the Akash Network Console project, backend-specific feature flags are intentional and acceptable. The frontend FeatureFlag union type should only include flags that are actually used by the frontend, not all flags defined in the backend. Backend can have internal feature flags for backend-only functionality without requiring frontend synchronization.

Applied to files:

  • apps/deploy-web/src/hooks/useFlag.tsx
📚 Learning: 2025-11-25T17:45:44.790Z
Learnt from: CR
Repo: akash-network/console PR: 0
File: .cursor/rules/no-jest-mock.mdc:0-0
Timestamp: 2025-11-25T17:45:44.790Z
Learning: Applies to **/*.spec.{ts,tsx} : Don't use `jest.mock()` in test files. Instead, use `jest-mock-extended` to create mocks and pass mocks as dependencies to the service under test

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-11-19T15:15:07.283Z
Learnt from: ygrishajev
Repo: akash-network/console PR: 2254
File: apps/api/test/functional/sign-and-broadcast-tx.spec.ts:4-4
Timestamp: 2025-11-19T15:15:07.283Z
Learning: In the Akash Network Console project, when tests use native Node.js fetch (available in Node 18+), fetch-mock should be used for HTTP mocking instead of nock, as nock does not support intercepting native fetch calls. This applies to apps/api/test/functional/sign-and-broadcast-tx.spec.ts and any other tests using native fetch.

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-10-15T16:39:55.348Z
Learnt from: jzsfkzm
Repo: akash-network/console PR: 2039
File: apps/deploy-web/tests/ui/change-wallets.spec.ts:4-10
Timestamp: 2025-10-15T16:39:55.348Z
Learning: In the Akash Console E2E tests using the context-with-extension fixture, the first wallet is automatically created during fixture setup via `importWalletToLeap` in `apps/deploy-web/tests/ui/fixture/wallet-setup.ts`, so tests that call `frontPage.createWallet()` are creating a second wallet to test wallet switching functionality.

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
🧬 Code graph analysis (5)
packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)
packages/http-sdk/src/api-http/api-http.service.ts (1)
  • ApiHttpService (9-29)
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (3)
apps/deploy-web/src/queries/useDeploymentQueries.ts (1)
  • useWeeklyDeploymentCostQuery (7-16)
apps/deploy-web/src/queries/useWalletSettingsQueries.tsx (1)
  • useWalletSettingsMutations (20-56)
packages/ui/context/PopupProvider/PopupProvider.tsx (1)
  • usePopup (140-146)
apps/api/src/deployment/routes/deployments/deployments.router.ts (3)
apps/api/src/core/lib/create-route/create-route.ts (1)
  • createRoute (5-11)
apps/api/src/core/services/openapi-docs/openapi-security.ts (1)
  • SECURITY_BEARER_OR_API_KEY (5-5)
apps/api/src/deployment/http-schemas/deployment.schema.ts (1)
  • GetWeeklyDeploymentCostResponseSchema (268-272)
apps/api/src/deployment/controllers/deployment/deployment.controller.ts (1)
apps/api/src/deployment/http-schemas/deployment.schema.ts (1)
  • GetWeeklyDeploymentCostResponse (286-286)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (1)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3)
  • address (201-209)
  • deploymentSettings (220-223)
  • drainingDeployments (233-242)
🪛 LanguageTool
apps/api/src/billing/services/wallet-balance-reload-check/README.md

[style] ~50-~50: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...bled, the first check runs immediately. When deployment auto top-up is enabled, an i...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (8)
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: Validate local packages
  • GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (17)
apps/api/src/billing/services/wallet-balance-reload-check/README.md (1)

43-80: Documentation of new deployment auto top-up scenario is clear and well-integrated.

The new trigger scenario is properly documented across the list, narrative, and sequence diagram. The logic is easy to follow: immediate check when auto top-up is enabled ensures wallet balance covers new deployment costs before proceeding. The placement as scenario #2 and the [OR] branching in the diagram accurately represent the control flow.

apps/deploy-web/src/queries/queryKeys.ts (1)

78-79: LGTM!

The new query key follows the established pattern in the class and is appropriately placed near other deployment-related keys.

apps/api/src/deployment/http-schemas/deployment.schema.ts (2)

268-272: LGTM!

The schema follows the established pattern of wrapping response data in a data object and includes a clear description for the OpenAPI documentation.


286-286: LGTM!

Type export is properly inferred from the schema.

packages/http-sdk/src/deployment/managed-deployment-http.service.ts (2)

5-7: LGTM!

The interface properly types the extracted API data structure with weeklyCost as a number.


9-21: LGTM!

The service class correctly extends ApiHttpService, uses extractApiData to unwrap the response, and returns the weeklyCost value. The JSDoc accurately documents that the return value is in USD.

packages/http-sdk/src/index.ts (1)

17-17: LGTM!

The new service is properly exported from the SDK's public API, following the established pattern and positioned logically next to the related deployment service.

apps/api/src/deployment/routes/deployments/deployments.router.ts (2)

18-18: LGTM!

Import correctly added to the schema imports block.


368-388: LGTM!

The route definition follows the established patterns in the file:

  • Uses createRoute helper consistently
  • Properly applies SECURITY_BEARER_OR_API_KEY for authentication
  • Handler uses the container.resolve pattern for dependency injection
  • Response schema is correctly referenced
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (1)

529-529: LGTM! Proper mock setup and dependency injection.

The BalancesService is correctly mocked using jest-mock-extended and properly wired into the service constructor and test fixtures.

Also applies to: 545-546, 557-557

apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (3)

33-70: Excellent UX improvement with confirmation dialog.

The confirmation flow ensures users understand the implications of enabling/disabling auto-reload before making changes. The implementation correctly uses usePopup and properly updates the dependency array to include confirm.


135-143: LGTM! Clean conditional rendering of weekly cost.

The weekly cost is displayed only when loaded and greater than zero, which correctly handles both loading states and cases where no auto-topped-up deployments exist. The currency formatting using FormattedNumber is appropriate.


125-134: LGTM! Layout adjustments accommodate new content.

The header layout changes properly accommodate the CardDescription and vertical arrangement of the Switch with the weekly cost display below it.

apps/api/src/deployment/controllers/deployment/deployment.controller.ts (1)

104-108: LGTM! Clean controller implementation.

The new method follows the established patterns in this controller:

  • Appropriate authorization decorator (@Protected with read on UserWallet)
  • Delegates business logic to the service layer
  • Properly passes user context (userId and ability)
  • Returns response in the expected schema format
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3)

163-192: LGTM! Comprehensive weekly cost calculation with proper authorization.

The implementation demonstrates several good practices:

  • Ability-based access control for wallet and deployment settings (lines 164, 170)
  • Clever use of Number.MAX_SAFE_INTEGER to include all deployments regardless of predicted closure (line 178)
  • Robust validation: null checks, currentHeight comparison, and blockRate > 0 (line 181)
  • Performance optimization: early return when cost is zero avoids unnecessary fiat conversion (lines 187-189)
  • Clear documentation explaining the 7-day calculation window

133-153: LGTM! Clean refactoring with reusable helpers.

The refactoring extracts common patterns into private helpers (#findAutoTopUpDeploymentSettings, #findDrainingDeployments, #accumulateDeploymentCost) that are now shared between calculateAllDeploymentCostUntilDate and the new calculateWeeklyDeploymentCost method. This improves maintainability while preserving the original behavior.


194-242: LGTM! Well-designed private helper methods.

The three new private helpers are well-structured:

  • #findAutoTopUpDeploymentSettings: Validates wallet existence before querying (defensive programming)
  • #findDrainingDeployments: Simple extraction and delegation to existing findLeases method
  • #accumulateDeploymentCost: Generic accumulator accepting a callback for flexible cost calculation

All helpers are properly documented with JSDoc and follow single-responsibility principle.

…-up deployments

- Adds GET /v1/weekly-cost API endpoint returning USD cost
- Calculates weekly cost using DrainingDeploymentService with BalancesService conversion
- Displays weekly cost in AccountOverview UI with formal description
- Adds ManagedDeploymentHttpService for console API endpoints
- Adds comprehensive unit tests with BalancesService mocking
- Updates documentation for auto top-up immediate check scenario

refs #1779
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (3)
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (1)

125-143: Consider extracting the weekly cost display into a separate component.

The conditional rendering logic for the weekly cost section is clear and handles loading/empty states well. However, wrapping the Switch in an extra flex items-center justify-between div (line 132-134) leaves the Switch isolated without any visible label or adjacent element to justify the justify-between.

-                  <div className="flex items-center justify-between">
-                    <Switch checked={walletSettings?.autoReloadEnabled ?? false} onCheckedChange={toggleAutoReload} disabled={isReloadChangeDisabled} />
-                  </div>
+                  <Switch checked={walletSettings?.autoReloadEnabled ?? false} onCheckedChange={toggleAutoReload} disabled={isReloadChangeDisabled} />
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (1)

233-242: Consider using reduce or Promise.all for accumulation.

The sequential for...of loop with await works correctly but processes deployments one at a time. If the callback doesn't have ordering dependencies, parallel execution could improve performance for large deployment lists.

  async #accumulateDeploymentCost(
    drainingDeployments: DrainingDeploymentOutput[],
    callback: (deployment: DrainingDeploymentOutput) => Promise<number>
  ): Promise<number> {
-   let totalAmount = 0;
-   for (const deployment of drainingDeployments) {
-     totalAmount += await callback(deployment);
-   }
-   return totalAmount;
+   const costs = await Promise.all(drainingDeployments.map(callback));
+   return costs.reduce((sum, cost) => sum + cost, 0);
  }
apps/api/src/billing/services/wallet-balance-reload-check/README.md (1)

50-50: Consider rephrasing to avoid repetitive sentence structure.

Three consecutive sentences begin with "When", which impacts readability. Consider combining or restructuring.

Apply this diff to improve the flow:

-When auto-reload is enabled, the first check runs immediately. When deployment auto top-up is enabled, an immediate check is scheduled to ensure the wallet balance can cover the new deployment costs. Subsequent checks run on a daily schedule. Immediate triggers (deployments/deposits) ensure the balance is checked right after spending or depositing funds, rather than waiting for the next scheduled check.
+The first check runs immediately when auto-reload is enabled. Enabling deployment auto top-up schedules an immediate check to ensure the wallet balance can cover the new deployment costs. Subsequent checks run on a daily schedule, with immediate triggers (deployments/deposits) ensuring the balance is checked right after spending or depositing funds rather than waiting for the next scheduled check.
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 4caede8 and 2ff2a3e.

⛔ Files ignored due to path filters (1)
  • apps/api/test/functional/__snapshots__/docs.spec.ts.snap is excluded by !**/*.snap
📒 Files selected for processing (13)
  • apps/api/src/billing/services/wallet-balance-reload-check/README.md (3 hunks)
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts (3 hunks)
  • apps/api/src/deployment/http-schemas/deployment.schema.ts (2 hunks)
  • apps/api/src/deployment/routes/deployments/deployments.router.ts (2 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (5 hunks)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3 hunks)
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (6 hunks)
  • apps/deploy-web/src/queries/index.ts (1 hunks)
  • apps/deploy-web/src/queries/queryKeys.ts (1 hunks)
  • apps/deploy-web/src/queries/useDeploymentQueries.ts (1 hunks)
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts (2 hunks)
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1 hunks)
  • packages/http-sdk/src/index.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (4)
  • packages/http-sdk/src/index.ts
  • apps/deploy-web/src/queries/queryKeys.ts
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts
  • apps/api/src/deployment/controllers/deployment/deployment.controller.ts
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{ts,tsx,js}

📄 CodeRabbit inference engine (.cursor/rules/general.mdc)

**/*.{ts,tsx,js}: Never use type any or cast to type any. Always define the proper TypeScript types.
Never use deprecated methods from libraries.
Don't add unnecessary comments to the code.

Files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
  • apps/deploy-web/src/queries/index.ts
  • apps/api/src/deployment/http-schemas/deployment.schema.ts
  • apps/api/src/deployment/routes/deployments/deployments.router.ts
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts
  • apps/deploy-web/src/queries/useDeploymentQueries.ts
**/*.spec.{ts,tsx}

📄 CodeRabbit inference engine (.cursor/rules/no-jest-mock.mdc)

Don't use jest.mock() in test files. Instead, use jest-mock-extended to create mocks and pass mocks as dependencies to the service under test

Use setup function instead of beforeEach in test files. The setup function must be at the bottom of the root describe block, should create an object under test and return it, accept a single parameter with inline type definition, avoid shared state, and not have a specified return type.

**/*.spec.{ts,tsx}: Use <Subject>.name in the root describe suite description instead of hardcoded class/service name strings to enable automated refactoring tools to find all references
Use either a method name or a condition starting with 'when' for nested suite descriptions in tests
Use present simple, 3rd person singular for test descriptions without prepending 'should'

Files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
🧠 Learnings (7)
📚 Learning: 2025-11-25T17:45:44.790Z
Learnt from: CR
Repo: akash-network/console PR: 0
File: .cursor/rules/no-jest-mock.mdc:0-0
Timestamp: 2025-11-25T17:45:44.790Z
Learning: Applies to **/*.spec.{ts,tsx} : Don't use `jest.mock()` in test files. Instead, use `jest-mock-extended` to create mocks and pass mocks as dependencies to the service under test

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-11-19T15:15:07.283Z
Learnt from: ygrishajev
Repo: akash-network/console PR: 2254
File: apps/api/test/functional/sign-and-broadcast-tx.spec.ts:4-4
Timestamp: 2025-11-19T15:15:07.283Z
Learning: In the Akash Network Console project, when tests use native Node.js fetch (available in Node 18+), fetch-mock should be used for HTTP mocking instead of nock, as nock does not support intercepting native fetch calls. This applies to apps/api/test/functional/sign-and-broadcast-tx.spec.ts and any other tests using native fetch.

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-10-15T16:39:55.348Z
Learnt from: jzsfkzm
Repo: akash-network/console PR: 2039
File: apps/deploy-web/tests/ui/change-wallets.spec.ts:4-10
Timestamp: 2025-10-15T16:39:55.348Z
Learning: In the Akash Console E2E tests using the context-with-extension fixture, the first wallet is automatically created during fixture setup via `importWalletToLeap` in `apps/deploy-web/tests/ui/fixture/wallet-setup.ts`, so tests that call `frontPage.createWallet()` are creating a second wallet to test wallet switching functionality.

Applied to files:

  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts
📚 Learning: 2025-11-25T17:45:49.180Z
Learnt from: CR
Repo: akash-network/console PR: 0
File: .cursor/rules/query-by-in-tests.mdc:0-0
Timestamp: 2025-11-25T17:45:49.180Z
Learning: Applies to {apps/deploy-web,apps/provider-console}/**/*.spec.tsx : Use `queryBy` methods instead of `getBy` methods in test expectations

Applied to files:

  • apps/deploy-web/src/queries/index.ts
  • apps/deploy-web/src/queries/useDeploymentQueries.ts
📚 Learning: 2025-06-03T15:06:34.211Z
Learnt from: baktun14
Repo: akash-network/console PR: 1428
File: apps/api/src/deployment/controllers/deployment/deployment.controller.ts:0-0
Timestamp: 2025-06-03T15:06:34.211Z
Learning: The `getByOwnerAndDseq` method in `apps/api/src/deployment/controllers/deployment/deployment.controller.ts` is intentionally public without the `Protected` decorator because it serves public blockchain data from an indexer, following the pattern of public blockchain APIs.

Applied to files:

  • apps/deploy-web/src/queries/index.ts
📚 Learning: 2025-06-05T21:07:51.985Z
Learnt from: baktun14
Repo: akash-network/console PR: 1432
File: apps/deploy-web/src/components/deployments/DeploymentAlerts/DeploymentCloseAlert.tsx:38-38
Timestamp: 2025-06-05T21:07:51.985Z
Learning: The ContactPointSelect component in apps/deploy-web/src/components/alerts/ContactPointSelectForm/ContactPointSelect.tsx uses the useFormContext hook internally to connect to React Hook Form, so it doesn't need to be wrapped in a FormField component.

Applied to files:

  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
📚 Learning: 2025-11-19T16:13:43.249Z
Learnt from: stalniy
Repo: akash-network/console PR: 2255
File: apps/api/src/middlewares/privateMiddleware.ts:5-9
Timestamp: 2025-11-19T16:13:43.249Z
Learning: In the Akash Console API (apps/api), avoid resolving DI container dependencies at module scope (module initialization time) to prevent side effects. Instead, resolve dependencies inside functions/methods where they are actually used, even if this means resolving on every invocation, to maintain explicit control over when side effects occur and improve testability.

Applied to files:

  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
🧬 Code graph analysis (4)
apps/api/src/deployment/routes/deployments/deployments.router.ts (3)
apps/api/src/core/lib/create-route/create-route.ts (1)
  • createRoute (5-11)
apps/api/src/core/services/openapi-docs/openapi-security.ts (1)
  • SECURITY_BEARER_OR_API_KEY (5-5)
apps/api/src/deployment/http-schemas/deployment.schema.ts (1)
  • GetWeeklyDeploymentCostResponseSchema (268-272)
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (4)
apps/deploy-web/src/queries/useDeploymentQueries.ts (1)
  • useWeeklyDeploymentCostQuery (7-16)
apps/deploy-web/src/queries/useWalletSettingsQueries.tsx (1)
  • useWalletSettingsMutations (20-56)
packages/ui/context/PopupProvider/PopupProvider.tsx (1)
  • usePopup (140-146)
packages/ui/components/switch.tsx (1)
  • Switch (52-52)
apps/deploy-web/src/services/app-di-container/app-di-container.ts (3)
packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)
  • ManagedDeploymentHttpService (9-22)
apps/deploy-web/src/services/auth/auth/auth.service.ts (1)
  • withUserToken (69-79)
apps/deploy-web/src/services/auth/auth/interceptors.ts (1)
  • withUserToken (15-25)
apps/deploy-web/src/queries/useDeploymentQueries.ts (2)
apps/deploy-web/src/context/ServicesProvider/ServicesProvider.tsx (1)
  • useServices (35-37)
apps/deploy-web/src/queries/queryKeys.ts (1)
  • QueryKeys (1-127)
🪛 LanguageTool
apps/api/src/billing/services/wallet-balance-reload-check/README.md

[style] ~50-~50: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...bled, the first check runs immediately. When deployment auto top-up is enabled, an i...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (8)
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: Validate local packages
  • GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (21)
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (3)

3-4: LGTM!

Imports are correctly added for the new UI components and confirmation popup hook.


23-25: LGTM!

Query hook and popup confirmation are properly destructured and used.


33-69: LGTM!

The confirmation flow is well implemented:

  • Clear user-facing messages for enable/disable scenarios
  • Early return on cancel prevents unintended state changes
  • Dependency array correctly includes confirm
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (4)

1-14: LGTM!

Imports are correctly organized with new dependencies for authorization and balance conversion.


27-31: LGTM!

Constructor properly extended to include the new BalancesService dependency for fiat conversion.


163-192: Well-structured weekly cost calculation.

The method correctly:

  • Applies authorization via ability parameter
  • Returns early with 0 for missing wallet/deployments
  • Uses Number.MAX_SAFE_INTEGER for closureHeight to include all active deployments regardless of when they would close
  • Converts the final uAKT amount to fiat

201-209: Potential redundant wallet lookup.

#findAutoTopUpDeploymentSettings looks up the user wallet by address (line 202), but the caller (calculateAllDeploymentCostUntilDate) already receives an address parameter. The wallet existence check could fail silently if the wallet doesn't exist, which may hide issues.

Consider whether this validation is intentional or if the caller should be responsible for ensuring the wallet exists.

apps/deploy-web/src/queries/index.ts (1)

9-9: LGTM!

Re-export follows the established pattern for query module exports.

apps/deploy-web/src/queries/useDeploymentQueries.ts (1)

7-16: LGTM!

Well-structured React Query hook that:

  • Properly types the query result as number
  • Uses Omit to prevent overriding queryKey/queryFn
  • Follows the established pattern from other query hooks in the codebase
apps/deploy-web/src/services/app-di-container/app-di-container.ts (2)

7-7: LGTM!

Import correctly added alongside other HTTP service imports.


95-98: LGTM!

The managedDeployment service follows the established pattern:

  • Lazily instantiated via factory function (aligned with retrieved learning about avoiding module-scope resolution)
  • Uses withUserToken interceptor for authenticated requests
  • Mirrors the deploymentSetting service configuration
apps/api/src/deployment/http-schemas/deployment.schema.ts (2)

268-272: LGTM!

The schema is well-defined with a clear description and follows the established patterns in the file.


286-286: LGTM!

The type export follows the correct pattern used for other response types in this file.

apps/api/src/deployment/routes/deployments/deployments.router.ts (2)

18-18: LGTM!

Import is correctly placed with other schema imports.


368-388: LGTM!

The route implementation follows the established patterns in this file with appropriate security, proper OpenAPI documentation, and correct controller method invocation.

apps/api/src/deployment/services/draining-deployment/draining-deployment.service.spec.ts (6)

3-3: LGTM!

Type import for AnyAbility is correctly used in the test setup at line 353.


10-10: LGTM!

Type import for BalancesService is correctly used for mocking at line 529.


236-391: LGTM! Comprehensive test coverage.

The test suite follows all coding guidelines and provides excellent coverage:

  • Uses jest-mock-extended for mocking (no jest.mock())
  • Helper function setupCalculateWeeklyCost with inline types
  • Present simple, 3rd person singular test descriptions
  • Covers all edge cases: valid calculations, late closures, missing wallet/address, empty deployments, null heights, invalid block rates

The balancesService.toFiatAmount mock implementation is appropriately simplified for unit testing.


529-529: LGTM!

BalancesService is properly mocked using jest-mock-extended as per coding guidelines.


545-546: LGTM!

The balancesService dependency is correctly passed to the DrainingDeploymentService constructor.


557-557: LGTM!

The balancesService is correctly included in the setup return object for test access.

stalniy
stalniy previously approved these changes Dec 16, 2025
baktun14
baktun14 previously approved these changes Dec 16, 2025
@ygrishajev ygrishajev dismissed stale reviews from baktun14 and stalniy via 84c54c6 December 16, 2025 14:48
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (2)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (2)

233-242: Consider removing unnecessary async keyword.

Since the callback now returns number synchronously, this method doesn't need to be async. The previous review suggesting Promise.all was for when the callback was async.

-  async #accumulateDeploymentCost(
+  #accumulateDeploymentCost(
     drainingDeployments: DrainingDeploymentOutput[],
     callback: (deployment: DrainingDeploymentOutput) => number
-  ): Promise<number> {
+  ): number {
     let totalAmount = 0;
     for (const deployment of drainingDeployments) {
       totalAmount += callback(deployment);
     }
     return totalAmount;
   }

You would also need to remove the await on lines 146 and 180 when calling this method.


201-209: Minor redundancy in validation.

The method queries userWalletRepository.findOneBy({ address }) and then checks !userWallet?.address. Since you're already querying by the address, if a wallet is found, it will have that address. The check effectively validates wallet existence only.

   async #findAutoTopUpDeploymentSettings(address: string): Promise<AutoTopUpDeployment[]> {
     const userWallet = await this.userWalletRepository.findOneBy({ address });
 
-    if (!userWallet?.address) {
+    if (!userWallet) {
       return [];
     }
 
     return this.deploymentSettingRepository.findAutoTopUpDeploymentsByOwner(address);
   }
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 2ff2a3e and 84c54c6.

📒 Files selected for processing (5)
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3 hunks)
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (6 hunks)
  • apps/deploy-web/src/queries/index.ts (1 hunks)
  • apps/deploy-web/src/services/app-di-container/app-di-container.ts (2 hunks)
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • apps/deploy-web/src/queries/index.ts
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx,js}

📄 CodeRabbit inference engine (.cursor/rules/general.mdc)

**/*.{ts,tsx,js}: Never use type any or cast to type any. Always define the proper TypeScript types.
Never use deprecated methods from libraries.
Don't add unnecessary comments to the code.

Files:

  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
  • apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts
  • packages/http-sdk/src/deployment/managed-deployment-http.service.ts
🧠 Learnings (2)
📚 Learning: 2025-11-19T16:13:43.249Z
Learnt from: stalniy
Repo: akash-network/console PR: 2255
File: apps/api/src/middlewares/privateMiddleware.ts:5-9
Timestamp: 2025-11-19T16:13:43.249Z
Learning: In the Akash Console API (apps/api), avoid resolving DI container dependencies at module scope (module initialization time) to prevent side effects. Instead, resolve dependencies inside functions/methods where they are actually used, even if this means resolving on every invocation, to maintain explicit control over when side effects occur and improve testability.

Applied to files:

  • apps/deploy-web/src/services/app-di-container/app-di-container.ts
📚 Learning: 2025-06-05T21:07:51.985Z
Learnt from: baktun14
Repo: akash-network/console PR: 1432
File: apps/deploy-web/src/components/deployments/DeploymentAlerts/DeploymentCloseAlert.tsx:38-38
Timestamp: 2025-06-05T21:07:51.985Z
Learning: The ContactPointSelect component in apps/deploy-web/src/components/alerts/ContactPointSelectForm/ContactPointSelect.tsx uses the useFormContext hook internally to connect to React Hook Form, so it doesn't need to be wrapped in a FormField component.

Applied to files:

  • apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx
🧬 Code graph analysis (4)
apps/deploy-web/src/services/app-di-container/app-di-container.ts (4)
packages/http-sdk/src/index.ts (1)
  • createHttpClient (28-28)
apps/deploy-web/src/services/auth/auth/auth.service.ts (1)
  • withUserToken (69-79)
apps/deploy-web/src/services/auth/auth/interceptors.ts (1)
  • withUserToken (15-25)
packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)
  • ManagedDeploymentHttpService (10-21)
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (4)
apps/deploy-web/src/queries/useDeploymentQueries.ts (1)
  • useWeeklyDeploymentCostQuery (7-16)
apps/deploy-web/src/queries/useWalletSettingsQueries.tsx (1)
  • useWalletSettingsMutations (20-56)
packages/ui/context/PopupProvider/PopupProvider.tsx (1)
  • usePopup (140-146)
packages/http-sdk/src/wallet-settings/wallet-settings-http.service.ts (2)
  • createWalletSettings (15-17)
  • updateWalletSettings (19-21)
apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (3)
apps/api/src/utils/constants.ts (1)
  • averageBlockCountInAnHour (8-8)
apps/api/src/deployment/repositories/deployment-setting/deployment-setting.repository.ts (1)
  • AutoTopUpDeployment (18-24)
apps/api/src/deployment/repositories/lease/lease.repository.ts (1)
  • DrainingDeploymentOutput (7-14)
packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)
packages/http-sdk/src/index.ts (1)
  • HttpClient (28-28)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (8)
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: validate / validate-app
  • GitHub Check: test-build
  • GitHub Check: Validate local packages
  • GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (5)
packages/http-sdk/src/deployment/managed-deployment-http.service.ts (1)

1-21: LGTM!

The implementation correctly uses constructor injection with HttpClient (as suggested in previous review), and the JSDoc now accurately reflects that the method returns the weekly cost in USD. The response structure handling with extractData is appropriate.

apps/api/src/deployment/services/draining-deployment/draining-deployment.service.ts (1)

163-192: LGTM! Weekly cost calculation logic is correct.

The method properly:

  1. Applies authorization via accessibleBy on both wallet and deployment settings
  2. Uses Number.MAX_SAFE_INTEGER to capture all deployments regardless of predicted close height
  3. Filters to only active deployments with positive block rates
  4. Converts the accumulated credit cost to fiat at the end
apps/deploy-web/src/components/billing-usage/AccountOverview/AccountOverview.tsx (2)

33-70: Good addition of confirmation dialog.

The confirmation flow properly:

  1. Presents context-appropriate messages for enable vs. disable actions
  2. Prevents state changes if user cancels
  3. Correctly includes confirm in the dependency array

135-143: LGTM!

The conditional rendering correctly distinguishes between loading state and zero cost (both valid scenarios where weeklyCost !== undefined is essential). The currency formatting using FormattedNumber is appropriate.

apps/deploy-web/src/services/app-di-container/app-di-container.ts (1)

95-100: LGTM!

The managedDeployment factory correctly:

  1. Uses the pattern requested in previous reviews (passing HttpClient to constructor rather than extending ApiHttpService)
  2. Follows the lazy resolution pattern via factory function (per learnings about avoiding module-scope DI resolution)
  3. Applies the withUserToken interceptor for authenticated requests

@ygrishajev ygrishajev merged commit ec84b32 into main Dec 16, 2025
65 of 66 checks passed
@ygrishajev ygrishajev deleted the feature/auto-reload branch December 16, 2025 15:05
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants

Comments