Skip to content

Add comprehensive metrics display to fertilizer application page#306

Merged
SvenVw merged 36 commits into
developmentfrom
FDM291
Oct 31, 2025
Merged

Add comprehensive metrics display to fertilizer application page#306
SvenVw merged 36 commits into
developmentfrom
FDM291

Conversation

@SvenVw
Copy link
Copy Markdown
Collaborator

@SvenVw SvenVw commented Oct 24, 2025

Summary by CodeRabbit

  • New Features

    • Added fertilizer applications dashboard displaying norms, nitrogen balance, and nutrient advice metrics
    • Fertilizer types now display with visual icons in the applications list
    • Progress bars added for nutrient guidance visualization
  • Improvements

    • Enhanced precision for dose values between 0–1 kg/ha (displays with 2 decimal places)
    • Improved spacing and alignment in fertilizer applications list
    • Progress bar now displays for nutrients with zero advice values

Closes #291

@SvenVw SvenVw self-assigned this Oct 24, 2025
@changeset-bot
Copy link
Copy Markdown

changeset-bot Bot commented Oct 24, 2025

🦋 Changeset detected

Latest commit: 45c86cd

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 1 package
Name Type
@svenvw/fdm-app Minor

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Oct 24, 2025

Warning

Rate limit exceeded

@SvenVw has exceeded the limit for the number of commits or files that can be reviewed per hour. Please wait 18 minutes and 29 seconds before requesting another review.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

📥 Commits

Reviewing files that changed from the base of the PR and between a0b58e0 and 45c86cd.

📒 Files selected for processing (4)
  • fdm-app/app/components/blocks/fertilizer-applications/metrics.tsx (1 hunks)
  • fdm-app/app/integrations/calculator.ts (1 hunks)
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx (8 hunks)
  • fdm-calculator/src/norms/nl/2025/value/input.ts (2 hunks)

Walkthrough

This PR refactors the fertilizer applications page UI, introducing a new metrics dashboard component that displays norms, nitrogen balance, and nutrient advice data. It includes new calculator integration functions, updates the fertilizer applications list and card components, modifies nutrient advice card precision formatting, and adds related changesets for minor and patch version releases.

Changes

Cohort / File(s) Summary
Changeset entries
.changeset/clear-phones-flash.md, .changeset/common-ears-make.md, .changeset/eight-lizards-listen.md, .changeset/slow-ears-stand.md
Four changeset files for minor and patch version releases noting UI design improvements for fertilizer icon and spacing, progress bar display at zero advice, dose precision formatting for 0–1 kg/ha values, and new metrics display for norms, nitrogen balance, and nutrient advice.
Fertilizer application components refactoring
fdm-app/app/components/blocks/fertilizer-applications/card.tsx, fdm-app/app/components/blocks/fertilizer-applications/list.tsx, fdm-app/app/components/blocks/fertilizer-applications/cards.tsx
Refactored card component to accept fertilizers prop and use FertilizerApplicationsList component; updated list component with new item-based UI, delete/edit handlers, and fertilizer type icons; deleted cards.tsx which previously constructed detail cards from dose data.
New metrics dashboard component
fdm-app/app/components/blocks/fertilizer-applications/metrics.tsx
New FertilizerApplicationMetricsCard component rendering three expandable sections (Gebruiksnormen, Stikstofbalans, Bemestingsadvies) with async data loading, skeleton states, progress bars, and tooltip-enhanced labels.
Calculator integrations
fdm-app/app/integrations/calculator.ts
New module exporting three async helper functions: getNitrogenBalanceforField, getNutrientAdviceForField, and getNorms for fetching and computing field-specific metrics data.
Fertilizer route updates
fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx, fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
Enhanced loader to fetch norms, nitrogen balance, and nutrient advice metrics; added responsive grid layout for FertilizerApplicationMetricsCard; threaded fertilizers data through to FertilizerApplicationCard.
Nutrient advice formatting updates
fdm-app/app/components/blocks/nutrient-advice/cards.tsx
Updated dose and advice value rendering with toPrecision(2) for values between 0 and 1 kg/ha; changed percentage default from 0 to 100; restructured UI layout to always render Bemestingsniveau block with conditional value display; updated colorBar logic for progress indicators.
Calculator type refinements
fdm-calculator/src/norms/nl/2025/filling/input.ts, fdm-calculator/src/norms/nl/2025/value/input.ts
Updated principal_id parameter type from string to PrincipalId in collectInputForFertilizerApplicationFilling and collectNL2025InputForNorms functions.
Dependencies
fdm-app/package.json
Added @radix-ui/react-progress@^1.1.7 dependency for progress bar component.

Sequence Diagram

sequenceDiagram
    participant Route as Fertilizer Route
    participant Loader as Loader
    participant Calc as Calculator<br/>Integrations
    participant FDM as FDM Tooling
    participant UI as Metrics Card
    participant User as User

    User->>Route: Navigate to fertilizer page
    Route->>Loader: Execute loader
    Loader->>Calc: getNorms(fdm, principal_id, b_id)
    Calc->>FDM: collectNormsInput + computeNorms
    FDM-->>Calc: norms data
    Calc-->>Loader: {value, filling}
    
    Loader->>Calc: getNitrogenBalanceforField(...)
    Calc->>FDM: collectInputForNitrogenBalance + compute
    FDM-->>Calc: N balance data
    Calc-->>Loader: NitrogenBalanceNumeric
    
    Loader->>Calc: getNutrientAdviceForField(...)
    Calc->>FDM: Fetch soil, cultivations + compute
    FDM-->>Calc: nutrient advice
    Calc-->>Loader: advice data
    
    Loader-->>Route: {norms, nitrogenBalance,<br/>nutrientAdvice, ...}
    Route->>UI: Render with metrics data
    UI->>UI: Load with Suspense/Await
    UI->>UI: Render skeleton states
    UI-->>User: Display 3 sections:<br/>Norms, Balance, Advice

    rect rgb(200, 220, 255)
        Note over UI: Each section shows<br/>progress bar + values<br/>with color logic
    end
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Areas requiring extra attention:

  • Async data fetching in route loader: Verify that getNorms, getNitrogenBalanceforField, and getNutrientAdviceForField handle errors gracefully and that the Suspense/Await integration in the metrics component works as expected with the new data structure.
  • Calculator integration module: Review the logic in getNorms, getNitrogenBalanceforField, and getNutrientAdviceForField to ensure correct data assembly, proper API calls to FDM tooling, and handling of edge cases (e.g., missing cultivations, null b_lu_catalogue).
  • Component refactoring (card/list): Validate that the refactored FertilizerApplicationCard and FertilizerApplicationsList components maintain functional parity with the deleted cards.tsx component and that the new ItemGroup/Item-based UI renders correctly across breakpoints.
  • Precision formatting and progress bar color logic: Double-check the toPrecision(2) formatting for doses/advice values between 0 and 1, the percentage calculation changes, and the colorBar conditions (green for EOC/0 advice, orange for >100%, default otherwise).
  • Type changes in calculator: Verify that the principal_id type changes from string to PrincipalId propagate correctly through all call sites and do not introduce runtime issues.

Possibly related PRs

Suggested reviewers

  • BoraIneviNMI
  • gerardhros

Poem

🐰 Metrics bloom where norms once stood,
Progress bars in every hue so good,
Nitrogen, phosphate, advice so true—
A dashboard refined, for farmland's due! 🌾✨

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 42.86% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed The pull request title "Add comprehensive metrics display to fertilizer application page" directly summarizes the primary change in the changeset. The new FertilizerApplicationMetricsCard component is the main feature being introduced, which renders a dashboard displaying key metrics including legal norms (nitrogen, phosphate, manure), nitrogen balance, and nutrient advice. The title is clear, concise, and specific enough for a reviewer scanning the history to understand the core contribution without being vague or overly broad.
Linked Issues Check ✅ Passed The pull request successfully addresses all major objectives from issue #291. The new FertilizerApplicationMetricsCard component displays the required metrics in three expandable sections (Gebruiksnormen, Stikstofbalans, Bemestingsadvies) with current values, limit/advice comparisons, and visual status indicators via progress bars with dynamic color logic [#291]. The loader was augmented to fetch norms, nitrogen balance, and nutrient advice data through new calculator integration functions (getNorms, getNitrogenBalanceforField, getNutrientAdviceForField) [#291]. The UI components were refactored to support list-based rendering instead of cards, and the FertilizerApplicationsList component now uses proper item-based layout with appropriate handlers [#291]. Supporting changes to nutrient advice display (precision formatting, percentage calculations) ensure the metrics are rendered accurately and clearly [#291].
Out of Scope Changes Check ✅ Passed All code changes in this pull request are directly related to implementing the comprehensive metrics display feature described in issue #291. The new FertilizerApplicationMetricsCard component, refactored FertilizerApplicationCard and FertilizerApplicationsList components, calculator integration functions, route loader updates, and nutrient advice display refinements are all integral to the metrics display implementation. Supporting changes such as the PrincipalId type refinements in fdm-calculator and the addition of @radix-ui/react-progress dependency are necessary supporting modifications for the core functionality. The changeset files document the UI/design improvements and display precision enhancements related to the feature.

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

@SvenVw SvenVw changed the base branch from development to FDM297 October 24, 2025 13:14
@codecov
Copy link
Copy Markdown

codecov Bot commented Oct 24, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 93.31%. Comparing base (a7381bd) to head (45c86cd).
⚠️ Report is 37 commits behind head on development.

Additional details and impacted files
@@             Coverage Diff              @@
##           development     #306   +/-   ##
============================================
  Coverage        93.31%   93.31%           
============================================
  Files               96       96           
  Lines            15325    15325           
  Branches          1557     1557           
============================================
  Hits             14301    14301           
  Misses            1022     1022           
  Partials             2        2           
Flag Coverage Δ
fdm-calculator 95.48% <100.00%> (ø)
fdm-core 91.66% <ø> (ø)
fdm-data 94.04% <ø> (ø)

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Signed-off-by: Sven Verweij <37927107+SvenVw@users.noreply.github.com>
@SvenVw SvenVw changed the base branch from FDM297 to development October 31, 2025 14:41
@coderabbitai coderabbitai Bot changed the title @coderabbitai Add comprehensive metrics display to fertilizer application page Oct 31, 2025
@coderabbitai coderabbitai Bot added branch:development Issue only affecting development, not the main branch (yet) enhancement New feature or request fdm-app fdm-core fdm-calculator labels Oct 31, 2025
@SvenVw SvenVw requested a review from gerardhros October 31, 2025 15:43
@SvenVw SvenVw requested a review from BoraIneviNMI October 31, 2025 15:46
@SvenVw
Copy link
Copy Markdown
Collaborator Author

SvenVw commented Oct 31, 2025

@coderabbitai review

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Oct 31, 2025

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

Copy link
Copy Markdown
Collaborator

@gerardhros gerardhros left a comment

Choose a reason for hiding this comment

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

nice. might be good to add later for a specific selection of fields or farm level.

Copy link
Copy Markdown
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: 2

🧹 Nitpick comments (5)
fdm-calculator/src/norms/nl/2025/value/input.ts (1)

54-54: Remove redundant type cast.

The cast as PrincipalId is unnecessary since principal_id is already declared as PrincipalId at line 27.

Apply this diff:

-        principal_id as PrincipalId,
+        principal_id,
fdm-app/app/components/blocks/fertilizer-applications/metrics.tsx (2)

461-478: Use local task variable consistently.

The conditional label logic at lines 462-467 and 472-477 references resolvedNitrogenBalance.balance.task, but a local task variable is already calculated at lines 326-330. Using the local variable is clearer and avoids redundant property access.

Apply this diff:

                                                                <TooltipTrigger
                                                                    asChild
                                                                >
                                                                    <p className="text-xl font-bold whitespace-nowrap px-2">
-                                                                       {resolvedNitrogenBalance
-                                                                           .balance
-                                                                           .task <
-                                                                       0
+                                                                       {task < 0
                                                                            ? "Opgave"
                                                                            : "Ruimte"}
                                                                    </p>
                                                                </TooltipTrigger>
                                                                <TooltipContent>
                                                                    <p>
-                                                                       {resolvedNitrogenBalance
-                                                                           .balance
-                                                                           .task <
-                                                                       0
+                                                                       {task < 0
                                                                            ? "Hoeveelheid totaal stikstof die verminderd moet worden om het doel te halen"
                                                                            : "Hoeveelheid totaal stikstof die nog over waarbij het doel gehaald kan worden"}
                                                                    </p>
                                                                </TooltipContent>

721-747: Minor formatting inconsistency in skeleton components.

Line 725 has inconsistent spacing (text-right px-2 with double space) compared to lines 732 and 740.

Apply this diff for consistency:

         <div className="grid grid-cols-[1fr_auto] items-center">
             <p className="whitespace-nowrap px-2">Stikstof</p>
-            <span className="text-right  px-2">
+            <span className="text-right px-2">
                 {<Spinner className="h-3" />} kg N
             </span>
         </div>
fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx (1)

119-131: Improve type safety for fertilizer parameter metadata.

Lines 120, 126-128 use any type annotations for parameter metadata. Consider adding proper types or using type assertions to improve type safety.

If getFertilizerParametersDescription() returns a well-defined type, use it instead of any:

         const applicationMethods = fertilizerParameterDescription.find(
-            (x: any) => x.parameter === "p_app_method_options",
+            (x) => x.parameter === "p_app_method_options",
         )
         if (!applicationMethods) throw new Error("Parameter metadata missing")
         // Map fertilizers to options for the combobox
         const fertilizerOptions = fertilizers.map((fertilizer) => {
             const applicationMethodOptions = fertilizer.p_app_method_options
-                .map((opt: any) => {
+                .map((opt) => {
                     const meta = applicationMethods.options.find(
-                        (x: any) => x.value === opt,
+                        (x) => x.value === opt,
                     )
                     return meta ? { value: opt, label: meta.label } : undefined
                 })
                 .filter(Boolean)
fdm-app/app/components/blocks/fertilizer-applications/list.tsx (1)

131-143: Simplify delete handler invocation.

The code wraps a single p_app_id in an array at line 139-141, but the handleDelete signature at line 44 accepts string | string[]. This makes the wrapping unnecessary.

Apply this diff to simplify:

                                                        onClick={() => {
                                                            if (
                                                                application.p_app_ids
                                                            ) {
                                                                handleDelete(
                                                                    application.p_app_ids,
                                                                )
                                                            } else {
                                                                handleDelete(
-                                                                   [
-                                                                       application.p_app_id,
-                                                                   ]
+                                                                   application.p_app_id
                                                                )
                                                            }
                                                        }}
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between a7381bd and a0b58e0.

⛔ Files ignored due to path filters (3)
  • fdm-app/app/components/ui/progress.tsx is excluded by !fdm-app/app/components/ui/**
  • fdm-app/app/components/ui/spinner.tsx is excluded by !fdm-app/app/components/ui/**
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (15)
  • .changeset/clear-phones-flash.md (1 hunks)
  • .changeset/common-ears-make.md (1 hunks)
  • .changeset/eight-lizards-listen.md (1 hunks)
  • .changeset/slow-ears-stand.md (1 hunks)
  • fdm-app/app/components/blocks/fertilizer-applications/card.tsx (3 hunks)
  • fdm-app/app/components/blocks/fertilizer-applications/cards.tsx (0 hunks)
  • fdm-app/app/components/blocks/fertilizer-applications/list.tsx (1 hunks)
  • fdm-app/app/components/blocks/fertilizer-applications/metrics.tsx (1 hunks)
  • fdm-app/app/components/blocks/nutrient-advice/cards.tsx (3 hunks)
  • fdm-app/app/integrations/calculator.ts (1 hunks)
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx (8 hunks)
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx (2 hunks)
  • fdm-app/package.json (1 hunks)
  • fdm-calculator/src/norms/nl/2025/filling/input.ts (2 hunks)
  • fdm-calculator/src/norms/nl/2025/value/input.ts (1 hunks)
💤 Files with no reviewable changes (1)
  • fdm-app/app/components/blocks/fertilizer-applications/cards.tsx
🧰 Additional context used
🧠 Learnings (36)
📓 Common learnings
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 274
File: fdm-app/app/routes/farm.$b_id_farm._index.tsx:160-163
Timestamp: 2025-09-23T12:29:34.184Z
Learning: In the FDM application, the fertilizer application route intentionally uses `${calendar}/field/fertilizer` instead of the originally planned `/farm/{farmId}/add/fertilizer` structure. This design decision prioritizes starting from the field list view to provide better field selection workflow before applying fertilizer, rather than direct dashboard-to-action navigation.
📚 Learning: 2025-03-04T09:03:04.358Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 87
File: fdm-core/src/farm.ts:22-25
Timestamp: 2025-03-04T09:03:04.358Z
Learning: In the FDM codebase, functions that insert/create data (like `addFarm`) intentionally use `principal_id: string` instead of `PrincipalId` to enforce that only a single principal ID can be used for creation operations, while read operations use the more flexible `PrincipalId` type which supports both single IDs and arrays of IDs.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/value/input.ts
  • fdm-calculator/src/norms/nl/2025/filling/input.ts
📚 Learning: 2025-07-21T12:06:07.070Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 156
File: fdm-calculator/src/norms/nl/2025/stikstofgebruiksnorm.ts:295-303
Timestamp: 2025-07-21T12:06:07.070Z
Learning: Functions in the fdm-calculator with "NL2025" in their names are specifically designed for Netherlands 2025 agricultural norms calculation and hardcoded 2025 dates are appropriate in this context, as different years would have separate calculation modules.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/value/input.ts
  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/integrations/calculator.ts
📚 Learning: 2025-08-11T11:55:26.053Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 233
File: fdm-app/app/integrations/nmi.ts:54-0
Timestamp: 2025-08-11T11:55:26.053Z
Learning: The NMI API Estimates endpoint (`https://api.nmi-agro.nl/estimates`) always returns the fields `b_gwl_ghg`, `b_gwl_glg`, and `cultivations` according to its specification. These fields should be kept as required (not optional) in the TypeScript return type and Zod validation schema in `fdm-app/app/integrations/nmi.ts`.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/value/input.ts
  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/integrations/calculator.ts
📚 Learning: 2025-01-31T15:05:14.310Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 67
File: fdm-app/app/routes/farm.create.$b_id_farm.fields.$b_id.tsx:601-610
Timestamp: 2025-01-31T15:05:14.310Z
Learning: The `updateField` function in fdm-core has optional parameters after `fdm` and `b_id`. The TypeScript definitions might show 8 required parameters due to a potential version mismatch.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/value/input.ts
  • fdm-calculator/src/norms/nl/2025/filling/input.ts
📚 Learning: 2025-09-23T12:29:34.184Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 274
File: fdm-app/app/routes/farm.$b_id_farm._index.tsx:160-163
Timestamp: 2025-09-23T12:29:34.184Z
Learning: In the FDM application, the fertilizer application route intentionally uses `${calendar}/field/fertilizer` instead of the originally planned `/farm/{farmId}/add/fertilizer` structure. This design decision prioritizes starting from the field list view to provide better field selection workflow before applying fertilizer, rather than direct dashboard-to-action navigation.

Applied to files:

  • .changeset/clear-phones-flash.md
  • .changeset/slow-ears-stand.md
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
  • fdm-app/app/components/blocks/fertilizer-applications/card.tsx
  • fdm-app/app/components/blocks/fertilizer-applications/list.tsx
📚 Learning: 2025-09-26T08:34:50.413Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 279
File: fdm-app/app/routes/farm.$b_id_farm.$calendar.norms.tsx:277-283
Timestamp: 2025-09-26T08:34:50.413Z
Learning: In the fdm project, fdm-core and fdm-app are updated together as part of a monorepo structure, which eliminates legacy data concerns when new fields like b_isproductive are introduced. Both packages are synchronized, so there's no need for defensive coding against undefined values for newly introduced database fields.

Applied to files:

  • fdm-app/package.json
  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2024-12-11T12:09:35.540Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 20
File: fdm-app/tsconfig.json:8-9
Timestamp: 2024-12-11T12:09:35.540Z
Learning: In the `fdm-app/tsconfig.json` file, the include path `.react-router/types/**/*` refers to a build-time generated directory which is intentionally not included in the repository.

Applied to files:

  • fdm-app/package.json
📚 Learning: 2024-11-25T12:42:32.783Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 6
File: fdm-app/vite.config.ts:5-9
Timestamp: 2024-11-25T12:42:32.783Z
Learning: In the `fdm-app` project, SvenVw is preparing for migration to Remix v3 and may include type declarations or configurations for v3 features in advance, such as in `vite.config.ts`.

Applied to files:

  • fdm-app/package.json
📚 Learning: 2025-03-04T10:56:35.540Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 88
File: fdm-calculator/src/doses/calculate-dose.ts:18-18
Timestamp: 2025-03-04T10:56:35.540Z
Learning: In the FDM calculator, fertilizer nutrient rates (p_n_rt, p_p_rt, p_k_rt) are measured in g/kg, and are converted to fractions by dividing by 10 during dose calculations.

Applied to files:

  • .changeset/eight-lizards-listen.md
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-02-14T09:56:37.606Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 75
File: fdm-app/app/routes/farm.$b_id_farm.field.$b_id.fertilizer.tsx:68-71
Timestamp: 2025-02-14T09:56:37.606Z
Learning: The `calculateDose` function in `svenvw/fdm-calculator` is a synchronous function that includes built-in validation for negative application amounts and nutrient rates.

Applied to files:

  • .changeset/eight-lizards-listen.md
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/integrations/calculator.ts
  • fdm-app/app/components/blocks/fertilizer-applications/card.tsx
📚 Learning: 2025-09-23T12:27:07.391Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 274
File: fdm-app/app/routes/farm.$b_id_farm._index.tsx:151-204
Timestamp: 2025-09-23T12:27:07.391Z
Learning: In the FDM application, field overview functionality is implemented as a dedicated page accessible via `farm/{farmId}/{calendar}/field` rather than as a direct listing on the dashboard. The dashboard includes a "Perceelsoverzicht" quick action card that provides navigation to this comprehensive field management interface.

Applied to files:

  • .changeset/slow-ears-stand.md
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
📚 Learning: 2025-09-23T12:37:58.711Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 274
File: fdm-app/app/routes/farm.$b_id_farm.$calendar.field._index.tsx:113-148
Timestamp: 2025-09-23T12:37:58.711Z
Learning: In the FDM application, the current field data fetching implementation using Promise.all with individual API calls (getCultivations, getFertilizerApplications, getCurrentSoilData) performs acceptably even with farms containing 90+ fields. No performance issues have been observed in practice with this approach.

Applied to files:

  • .changeset/slow-ears-stand.md
  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
  • fdm-app/app/integrations/calculator.ts
📚 Learning: 2025-08-13T10:33:05.313Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 0
File: :0-0
Timestamp: 2025-08-13T10:33:05.313Z
Learning: In the fdm project, fdm-calculator integration for new features like b_lu_variety is handled in separate updates from the core data model changes. When fdm-core functions are updated to support new fields, fdm-calculator can consume these enhanced APIs without requiring changes in the same PR that introduces the core functionality.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
  • fdm-app/app/integrations/calculator.ts
📚 Learning: 2025-09-24T14:02:48.574Z
Learnt from: BoraIneviNMI
Repo: SvenVw/fdm PR: 272
File: fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer.manage.new.$p_id.tsx:85-101
Timestamp: 2025-09-24T14:02:48.574Z
Learning: Both getFertilizer and getFertilizers functions in svenvw/fdm-core perform authorization checks using the user's principal_id to verify farm access before returning fertilizer data.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
  • fdm-app/app/integrations/calculator.ts
📚 Learning: 2025-02-13T08:35:59.306Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 71
File: fdm-app/app/routes/farm.$b_id_farm.field.$b_id.cultivation.$b_lu.harvest.$b_id_harvesting.tsx:114-124
Timestamp: 2025-02-13T08:35:59.306Z
Learning: The HarvestForm component in fdm-app expects undefined (not 0) for b_lu_yield when no yield information is available, as 0 would incorrectly imply that yield data exists.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
📚 Learning: 2025-09-23T10:02:32.123Z
Learnt from: BoraIneviNMI
Repo: SvenVw/fdm PR: 272
File: fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue.manage.$p_id.tsx:151-164
Timestamp: 2025-09-23T10:02:32.123Z
Learning: The getFertilizer function from svenvw/fdm-core throws an exception if the fertilizer doesn't exist, rather than returning null or undefined.

Applied to files:

  • fdm-calculator/src/norms/nl/2025/filling/input.ts
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
  • fdm-app/app/integrations/calculator.ts
📚 Learning: 2025-04-18T13:49:17.029Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 124
File: fdm-app/app/components/custom/farm/farm-title.tsx:3-3
Timestamp: 2025-04-18T13:49:17.029Z
Learning: In the fdm project, NavLink and other routing components can be imported from either "react-router" or "react-router-dom" as react-router-dom is included in react-router.

Applied to files:

  • fdm-app/app/components/blocks/nutrient-advice/cards.tsx
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-01-09T16:03:37.764Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 42
File: fdm-app/app/routes/farm/_b_id_farm/layout.tsx:46-95
Timestamp: 2025-01-09T16:03:37.764Z
Learning: A shared layout component `FarmLayoutBase` has been created in `components/custom/farm-layout-base.tsx` to maintain consistency across farm-related pages. The component handles farm selection dropdown, breadcrumb navigation, and provides a common layout structure.

Applied to files:

  • fdm-app/app/components/blocks/fertilizer-applications/metrics.tsx
  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
  • fdm-app/app/components/blocks/fertilizer-applications/card.tsx
  • fdm-app/app/components/blocks/fertilizer-applications/list.tsx
📚 Learning: 2025-01-09T16:03:37.764Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 42
File: fdm-app/app/routes/farm/_b_id_farm/layout.tsx:46-95
Timestamp: 2025-01-09T16:03:37.764Z
Learning: The `FarmLayout` component in `components/custom/farm-layout.tsx` provides a reusable layout structure for farm-related pages, with support for farm selection dropdown, customizable breadcrumb titles, and flexible content rendering through either children or Outlet components.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/components/blocks/fertilizer-applications/list.tsx
📚 Learning: 2025-08-11T12:24:32.200Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 233
File: fdm-app/app/components/blocks/atlas-fields/cultivation-history.tsx:53-53
Timestamp: 2025-08-11T12:24:32.200Z
Learning: In `fdm-app/app/components/blocks/atlas-fields/cultivation-history.tsx`, the NMI API for cultivations guarantees that each year will be unique in the cultivation history data, so using `cultivation.year` as a React list key is safe and won't cause duplicate key warnings.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-09-24T14:02:48.574Z
Learnt from: BoraIneviNMI
Repo: SvenVw/fdm PR: 272
File: fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer.manage.new.$p_id.tsx:85-101
Timestamp: 2025-09-24T14:02:48.574Z
Learning: The getFertilizer function in svenvw/fdm-core does not perform authorization checks, unlike getFertilizers which includes a checkPermission call to verify farm access. This means getFertilizer(fdm, p_id) can potentially return fertilizer details for any fertilizer ID without validating user permissions.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
  • fdm-app/app/integrations/calculator.ts
📚 Learning: 2024-12-16T10:56:07.561Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 16
File: fdm-app/app/routes/app.addfarm.$b_id_farm.cultivations.$b_lu_catalogue.fertilizers.tsx:1-1
Timestamp: 2024-12-16T10:56:07.561Z
Learning: The project uses `react-router` v7, and the `data` function is exported and used for error handling in loaders and actions.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-04-29T11:28:44.181Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 132
File: fdm-app/app/routes/farm.create.$b_id_farm.$calendar.access.tsx:54-68
Timestamp: 2025-04-29T11:28:44.181Z
Learning: In React Router v7, the `json()` function has been replaced with `data()` for creating responses in loaders and actions.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-04-29T11:28:44.181Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 132
File: fdm-app/app/routes/farm.create.$b_id_farm.$calendar.access.tsx:54-68
Timestamp: 2025-04-29T11:28:44.181Z
Learning: In React Router v7, the `json()` function has been deprecated and removed. Instead, either return plain JavaScript objects directly from loaders/actions, or use the `data()` function for responses with custom status codes and headers.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-05-09T14:41:43.484Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 138
File: fdm-app/app/components/custom/fertilizer-applications/form.tsx:6-6
Timestamp: 2025-05-09T14:41:43.484Z
Learning: The project uses React Router v7 which exports a Form component directly from the "react-router" package, not from "remix-run/react".

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-07-24T08:29:44.044Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 198
File: fdm-app/app/routes/farm.$b_id_farm.$calendar.balance.nitrogen.$b_id.tsx:146-148
Timestamp: 2025-07-24T08:29:44.044Z
Learning: In React Router v7, the defer() function has been removed. Instead, loaders can return promises directly in the response object, and components use Suspense and Await to handle them without needing defer().

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-05-09T14:41:43.484Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 138
File: fdm-app/app/components/custom/fertilizer-applications/form.tsx:6-6
Timestamp: 2025-05-09T14:41:43.484Z
Learning: The project uses React Router v7 which exports a Form component directly from the "react-router" package, making importing from "remix-run/react" unnecessary.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-07-24T08:29:44.044Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 198
File: fdm-app/app/routes/farm.$b_id_farm.$calendar.balance.nitrogen.$b_id.tsx:146-148
Timestamp: 2025-07-24T08:29:44.044Z
Learning: React Router v7 supports Suspense patterns by returning promises directly from loaders. The pattern is: return { data: somePromise } from loader, then use <Suspense><Await resolve={loaderData.data}>{resolvedData => ...}</Await></Suspense> in components.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-05-09T14:53:44.578Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 138
File: fdm-app/app/components/custom/combobox.tsx:34-37
Timestamp: 2025-05-09T14:53:44.578Z
Learning: In the context of this React Router v7 project, it's important to follow the pattern of importing only the types (like UseFormReturn) from "react-hook-form" while importing the Form component from "react-router" to avoid naming conflicts.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
  • fdm-app/app/components/blocks/fertilizer-applications/card.tsx
📚 Learning: 2025-01-14T16:06:24.294Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 45
File: fdm-app/app/routes/farm.$b_id_farm._index.tsx:1-1
Timestamp: 2025-01-14T16:06:24.294Z
Learning: In the fdm-app codebase, the `redirect` function should be imported from `react-router`, not `react-router-dom`.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-01-31T15:05:14.310Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 67
File: fdm-app/app/routes/farm.create.$b_id_farm.fields.$b_id.tsx:601-610
Timestamp: 2025-01-31T15:05:14.310Z
Learning: When using `updateField` from fdm-core, all 8 parameters must be provided in order: fdm, b_id, b_name, b_geometry, b_area, b_id_source, b_id_farm, and b_id_farm_source.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-01-09T16:03:37.764Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 42
File: fdm-app/app/routes/farm/_b_id_farm/layout.tsx:46-95
Timestamp: 2025-01-09T16:03:37.764Z
Learning: A comprehensive farm layout system has been created in `components/custom/farm-layouts/` with `BaseFarmLayout` and `FarmSidebarLayout` components. The system supports both simple and sidebar-based layouts while maintaining consistent header and farm selection functionality across all farm routes.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-01-09T16:03:37.764Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 42
File: fdm-app/app/routes/farm/_b_id_farm/layout.tsx:46-95
Timestamp: 2025-01-09T16:03:37.764Z
Learning: The farm layout system has been reorganized into separate components (`FarmHeader`, `ContentLayout`, `PaginationLayout`) to support different navigation patterns (sidebar, pagination) while maintaining consistent styling. Each layout component is designed to be used independently or combined as needed.

Applied to files:

  • fdm-app/app/routes/farm.$b_id_farm.$calendar.field.$b_id.fertilizer._index.tsx
📚 Learning: 2025-04-04T14:27:39.518Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 116
File: fdm-app/app/routes/farm.$b_id_farm.$calendar.field.new.tsx:111-154
Timestamp: 2025-04-04T14:27:39.518Z
Learning: In the FDM application, cultivation retrieval logic should be centralized in utility functions rather than duplicated across loader and action functions to improve maintainability and ensure consistent behavior.

Applied to files:

  • fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx
📚 Learning: 2025-05-09T14:58:10.465Z
Learnt from: SvenVw
Repo: SvenVw/fdm PR: 138
File: fdm-app/app/components/custom/combobox.tsx:34-37
Timestamp: 2025-05-09T14:58:10.465Z
Learning: When updating React components that use both react-hook-form and React Router v7, it's important to only import types (like UseFormReturn, FieldValues) from react-hook-form to avoid naming conflicts with React Router's Form component. Use `import type { ... } from 'react-hook-form'` syntax to ensure only types are imported.

Applied to files:

  • fdm-app/app/components/blocks/fertilizer-applications/card.tsx
🔇 Additional comments (7)
fdm-calculator/src/norms/nl/2025/value/input.ts (1)

27-27: LGTM: Type alignment with PrincipalId.

The parameter type update from string to PrincipalId correctly aligns with the core type system and matches the related change in filling/input.ts.

fdm-app/package.json (1)

25-25: LGTM: Progress UI dependency added.

The @radix-ui/react-progress dependency supports the new metrics visualization features introduced in this PR.

fdm-calculator/src/norms/nl/2025/filling/input.ts (2)

28-28: LGTM: Type alignment with PrincipalId.

The parameter type update from string to PrincipalId correctly aligns with the core type system and matches the related change in value/input.ts.


36-36: Verify downstream date range handling in database queries—this requires testing with actual data.

The endOfYear precision change from 00:00:00.000 to 23:59:59.999 on December 31st is intentional and correctly documented. The timeframe2025 object is passed directly to external @svenvw/fdm-core functions (getCultivations and getFertilizerApplications), which handle the actual date filtering.

Since these functions are from an external package, their internal comparison logic (e.g., <= vs <) cannot be verified within this repository. The change is localized and aligns with the documented intent, but its impact on records retrieved from database queries depends on how the external package implements the timeframe filtering.

Verify that records on December 31st are correctly included/excluded as intended when calling the norms calculator with actual field and fertilizer application data.

fdm-app/app/routes/farm.create.$b_id_farm.$calendar.fertilizers.$b_lu_catalogue._index.tsx (2)

167-167: LGTM: Fertilizers data exposed in loader.

The fertilizers data is correctly added to the loader return, enabling the component to access fertilizer metadata.


183-183: LGTM: Fertilizers prop passed to component.

The fertilizers array is correctly passed to FertilizerApplicationCard, supporting the enhanced metrics display functionality.

fdm-app/app/components/blocks/nutrient-advice/cards.tsx (1)

61-61: Verify percentage default for zero advice.

When advice is 0 or negative, the percentage defaults to 100. This might be misleading in the UI, as it suggests the target is fully met when there's actually no target defined.

Please verify this is the intended behavior. If advice === 0 represents "no limit" or "not applicable," consider:

  • Hiding the progress bar entirely
  • Using a distinct visual indicator
  • Showing "N/A" instead of a percentage

Also, consider the special case handling at lines 104-105 where advice === 0 and symbol === "EOC" gets a green bar, which suggests this may be intentional for specific nutrients.

Comment thread fdm-app/app/components/blocks/fertilizer-applications/metrics.tsx
Comment thread fdm-app/app/integrations/calculator.ts
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

branch:development Issue only affecting development, not the main branch (yet) enhancement New feature or request fdm-app fdm-calculator fdm-core

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Upgrade Fertilizer Application Page with Detailed Metrics List

2 participants