Skip to content

Feature: Stock spending report - #996

Open
tbrkkup wants to merge 5 commits into
patzly:masterfrom
tbrkkup:stock-spending-report
Open

Feature: Stock spending report#996
tbrkkup wants to merge 5 commits into
patzly:masterfrom
tbrkkup:stock-spending-report

Conversation

@tbrkkup

@tbrkkup tbrkkup commented Aug 6, 2026

Copy link
Copy Markdown

Closes #995

Implements the report discussed in the issue.

Commits

Split by layer, so the build change, the query and the UI can be read apart from one another.

Commit Layer
Add AndroidChart dependency build
Query purchase transactions from the stock log API
Add spending aggregation view model logic
Add spending report screen UI
Add spending report entry to the stock overview menu entry point

Query and arithmetic

Built on the stock_log source proposed in the issue:

/objects/stock_log?query[]=transaction_type=purchase
                  &query[]=undone=0
                  &query[]=purchased_date>=<start>
                  &query[]=purchased_date<=<end>

Per row the spend is |amount| × price. Two details worth confirming against how the web report behaves:

  • Rows with a null price contribute zero rather than being dropped, so a row's absence from the total never silently changes the row count.
  • amount is taken as an absolute value, so a correction row recorded with a negative amount still registers as spend rather than subtracting
    from the period.

Loading

Products, product groups and stores are updated, then read back in one Single.zip() before the purchase log is fetched. The update matters because those three resolve the grouping labels: without it, whichever entity no other screen had synced yet would leave raw ids on screen. It is not forced, so it is a cheap no-op once the data is current.

Switching the grouping afterwards re-aggregates in memory with no second round trip; only a period change or pull-to-refresh hits the network.

Chart decisions

The top eight slices are shown individually and the remainder is collapsed into a single Others slice; past that the legend stops being readable at phone width. The list below is not truncated, so the full breakdown stays available.

Labels on narrow slices are drawn smaller so they still fit their segment. The library supports only one value text size per data set, so rather than reimplementing the slice geometry, the renderer draws the values in two passes — wide slices at the regular size, narrow ones reduced — with the formatter blanking out whichever group is not part of the current pass. That is the one piece of custom drawing code here and the part I would look at first in review.

Slice colours are a fixed twelve-colour palette rather than theme colours, because adjacent slices have to stay distinguishable from one another. The chart hole, legend text and surrounding chrome do follow the active theme in both light and dark.

For an empty period the chart is hidden and an inline label takes its place. Deliberately not InfoFullscreenHelper: that helper injects into a container sitting behind the scroll view, which on this screen draws the illustration underneath the filter chips.

Dependency

com.github.AppDevNext.AndroidChart:chartLib:5.2.4, which also required adding the JitPack repository to settings.gradle — Maven Central holds only snapshots of it. This is the only addition to the dependency set.

It is Apache 2.0 and needs minSdk 23, both matching this project, and the Kotlin standard library it brings was already on the runtime classpath, so it adds no new runtime.

Formatting

Amounts use the configured PREF.CURRENCY with the device locale's decimal separators. English and German strings are included.

Testing

Ran on device Pixel 9 Pro running LineageOS 24 against a production server across all three periods and all three groupings, with the resulting figures reconciled line by line against the same report in the web UI. Also covered: a period with no purchases, a dataset with more than eight groups to confirm the Others collapse, and purchases with a missing price and with a null shopping location.

tbrkkup added 5 commits August 6, 2026 17:06
Used by the spending report to render the breakdown as a pie chart.
AppDevNext/AndroidChart is the actively maintained fork of MPAndroidChart,
whose last release is v3.1.0 from 2019. It is Apache 2.0 and requires
minSdk 23, matching this project, and its Kotlin standard library is
already on the runtime classpath. It has to come from JitPack, since
Maven Central carries only snapshots of it.
Grocy exposes no dedicated price history object, so spending is derived
from stock_log filtered to transaction_type=purchase and undone=0 within
the selected date range.
Updates products, product groups and stores, reads them back in a single
Single.zip(), then fetches the purchase log for the range and sums
amount x price per group key. The update keeps group labels from falling
back to raw ids when an entity has not been synced by another screen yet;
it is not forced, so it stays a cheap no-op once the data is current.

Amounts are taken as absolute values so a correction recorded with a
negative amount still counts as spend, and entries without a price
contribute zero rather than being dropped.
Pie chart over the breakdown plus a sorted list of the same figures.
Date range and grouping are picked with filter chips; changing the
grouping re-aggregates in memory without another request.

The top eight slices are shown individually and the remainder is
collapsed into one "Others" slice. Because the library supports only one
value text size per data set, the renderer draws the values in two passes
so that labels on narrow slices can be smaller and still fit; the
formatter blanks out whichever group is not part of the current pass, and
the slice geometry stays entirely in the library.
Reachable from the stock overview overflow menu, next to stock journal
and stock entries, mirroring where the web UI keeps its stock reports.
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.

Feature request: Stock spending report

1 participant