Skip to content

Fix growing-leaf-category-tracker: show the number the ranking is built on, and stop the floor moving between runs - #36

Draft
fiharet34 wants to merge 1 commit into
joomcode:mainfrom
fiharet34:fix/growing-leaf-display-ranking-metric
Draft

Fix growing-leaf-category-tracker: show the number the ranking is built on, and stop the floor moving between runs#36
fiharet34 wants to merge 1 commit into
joomcode:mainfrom
fiharet34:fix/growing-leaf-display-ranking-metric

Conversation

@fiharet34

Copy link
Copy Markdown
Contributor

Fix growing-leaf-category-tracker: show the number the ranking is built on, and stop the floor moving between runs

Summary

Nine defects. The skill ranks niches by month-over-month growth and is explicitly
forbidden from displaying that growth; it applies a size floor that it invents fresh
on each run, so the same category returns a different leader; and it promises a
per-category link that the platform does not support.

Rebased onto 421426d. 13,666 → 19,475 bytes, 4 hunks, description 982 characters
(inside the 1024 limit). That size is 44% above the largest file in the library and
needs a decision — see "On the file size" below.

The defects

1. The ranking metric is forbidden from appearing. Output says:

"Exactly these five columns on both marketplaces — fast growth is the filter that
selects the niches, not a displayed column."

Meanwhile Presentation rules prescribe a header for that very column ("Variação" / "Crescimento"), and the panel requires "the single fastest-growing niche (name +
growth %)"
on a card and plots growth on the bubble chart's axis. So the file
mandates the figure in three places and forbids it in the table.

On a text-only surface — where no card renders — it appeared nowhere at all. A live
run produced fifteen rows with the leader described as "o maior salto" and no
percentage anywhere
; nine of the fifteen rows carried no growth figure of any kind.
The seller could not tell 300% from 5% in a table sorted by exactly that.

The sibling high-demand-low-quality-finder already carries the right rule verbatim —
"never rank on a number the table does not show" — so this fix adopts the library's
own language rather than inventing any.

2. The size floor is invented per run, and it changes the answer. Growth explodes
off a near-zero base and nothing guarded against it. Two runs on the same category,
minutes apart, invented R$ 1.000.000 and R$ 300.000 — and run 2's leader,
Piscina de Fibra at R$ 468.400,35, sits below run 1's floor, so it could not have
appeared in run 1 at all. Same skill, same question, different top niche, for no
reason the seller can see.

3. Ranking on revenue growth alone recommends contracting niches. Four of twenty
rows had unit growth that inverted the reading:

niche revenue units
Carrinhos de limpeza +60,0% −12,2%
Geradores de Ozônio +48,6% −12,8%
Cortadores de Grama +52,9% +94,8%
Piscina de Fibra +331,1% +473,2%

The first two grew on a higher average ticket, not more demand. The last two are the
inverse — falling price, easier entry, thinner margin. Both readings matter and
neither was required.

4. The per-category link does not exist. Output promised "On Mercado Livre each
category links to its JoomPulse category dashboard page."
It does not: a JoomPulse
categories URL carrying a category identifier resolves to the same general categories
page, ignoring the identifier. The skill therefore emitted links that looked specific
and landed somewhere generic — worse for the seller than no link.

Worth noting that #31 added "There is no JoomPulse category dashboard link for Shopee
rows"
— carving out the marketplace where the absence was obvious, while leaving the
Mercado Livre claim that is equally untrue. The fix now covers both.

5. Wrong class of estimate disclaimer, and no lag. Category figures are a different
estimate class from product figures, and the monthly category data can lag by up to
about 31 days. The Mercado Livre variant carried neither. (The Shopee variant added by
#31 is already specific and good — untouched.)

6. The readings that decide entry were absent. Concentration, revenue per seller
and seasonality are what separate "growing" from "enterable". None were required. A
run volunteered all three unprompted and they inverted the recommendation: the two
fastest-growing niches turned out to have a single seller holding almost every order.
Whether a seller received that analysis depended on whether the model went looking.

7. Retry with no backoff. A transport failure returned an explicit 60-second retry
instruction. The guardrail said only "retry once quietly", so a run made three
attempts inside about 67 seconds and gave up while the correct action was to wait.

8. An empty result was indistinguishable from an outage. Nothing separated "the
service did not answer" from "the service answered with nothing", so a genuine empty
result reached the seller as "try again in a few minutes" — advice that can never come
true. The sibling category-opportunity-index already handles this split; its shape is
adopted here.

9. One page of the tree presented as the whole category. A query returns at most
100 rows and nothing said so. Casa, Móveis e Decoração has 536 deep sub-categories
above a R$ 300 mil floor
— verified independently: a query at offset 500 returns
exactly 36 further rows. The skill ranked a fraction and called it the category. After
the fix a run reported reading 919 leaf niches, of which 430 cleared the floor
and 187 were growing.

The size floor, and why it is relative

The floor is the greater of R$ 300 mil and 0,02% of the parent category's estimated
monthly revenue.
A fixed figure cannot serve both marketplaces, because they rank
different units — deep leaf niches on Mercado Livre against whole level-3 categories on
Shopee, which are far larger.

Calibrated against measured category revenue rather than chosen:

parent category monthly revenue 0,02% floor applied
Casa, Móveis e Decoração (MLB) R$ 3.165.271.044 R$ 633.054 R$ 633.054
Casa e Decoração (Shopee) R$ 2.297.316.578 R$ 459.463 R$ 459.463
Beleza e Cuidado Pessoal (MLB) R$ 1.139.153.808 R$ 227.831 R$ 300.000
Ferramentas (MLB) R$ 1.085.471.891 R$ 217.094 R$ 300.000
Instrumentos Musicais (MLB) R$ 198.516.396 R$ 39.703 R$ 300.000

The live runs reported R$ 633.054,21 and R$ 459 mil, matching the arithmetic.

Two consequences worth stating plainly. It preserves the behaviour validated on the
smaller categories, where the R$ 300 mil minimum binds. And it tightens Casa from
R$ 300 mil to R$ 633 mil, which changes a previously validated result: Piscina de Fibra (R$ 468 mil, concentration 0,946 — the high-concentration false leader the skill
spends a paragraph warning about), Luminárias de Lava (R$ 25,54 per seller) and
Afiadores de Facas (R$ 72,97) all drop out. The remaining list is better, but it is a
change, not a no-op.

What changed in the file

  • Two growth columns — revenue and units — and the table is now eight columns,
    adding concentration (tier plus raw value) and revenue per seller.
  • The relative size floor, stated in the output with the count it excluded.
  • Revenue and unit growth read together, with both divergence cases named.
  • Parent/child collapse before ranking, Mercado Livre only, keeping the row under
    the parent's identifier so the same niche does not appear under two identifiers
    across runs.
  • Enterability: concentration, revenue per seller, and seasonality — the last
    Mercado Livre only, because Shopee carries no seasonality data. Concentration is
    computed differently on each marketplace, so the rule forbids comparing it across
    them. The written read leads with the most enterable niche, not the fastest-growing.
  • Identifier-based navigation on both marketplaces, replacing a link that does not
    work with the route that does.
  • Full money precision on Mercado Livre; Shopee explicitly exempt, because its
    figures are rebuilt from the platform's own rounded sold counters and exact digits
    there would be false precision.
  • Coverage stated exactly — niches read against niches shown, never rounded or
    hedged — with ordering by growth accepted as sufficient for a top-N.
  • Category-specific disclaimer with the lag (Mercado Livre variant only).
  • Missing values, retry after a pause, empty-result-is-not-an-outage.

Validation

Chronology matters here, so it is stated rather than summarised.

The nine defects were found on the previous base (75f9070, 6,563 bytes) across six
live runs plus one transport failure. Their persistence in the current base was then
verified by inspection
— the quotes above are from 421426d, and none of the nine had
been addressed upstream. Two had become worse: the five-column rule now reads "on both
marketplaces"
, and the link claim survived while Shopee was carved out around it.

The fixes were validated against the current base in three runs:

run scope outcome
1 Casa, Móveis e Decoração (MLB) floor computed at R$ 633.054,21; eight columns; coverage 919 → 430 → 187 → 12; parent/child collapsed at both 100% and 58%; Piscina de Fibra correctly dropped by the floor
2 Casa e Decoração (Shopee) ranked at level 3 with folding disclosed; money rounded with the counter basis given; seasonality absence named rather than worked around; floor R$ 459 mil, correctly non-binding on larger level-3 units
3 Casa, Móveis e Decoração, repeat floor identical, leader identical, shape identical, recommendation identical; two wobbles found (below)

Run 2 also demonstrated the dual-metric and concentration rules working together on the
worst artifact either marketplace produced: Sementes e Mudas at +6.798% revenue on
−12,6% units
with concentration 0,981 — shown for transparency and explicitly
discarded as "distorção, não oportunidade".

Two tightenings came from the repeat run, and neither is visible in a single output:

  • The collapsed pair appeared under the parent's identifier in one run and the
    child's in the other. Since the identifier is the only way to find the niche and
    the table is meant to be saved and compared next period, the rule now pins it.
  • Coverage was reported exactly in one run ("919 … 430 … 187") and hedged in the other
    ("mais de 900 … cerca de 420"). The rule now requires exact counts, because a
    coverage claim nobody can audit is worth little more than none.

On the file size

19,475 bytes. The library's largest file is 13,552 and the median is 8,684, so this
is 44% over the maximum and 2,2× the median. The base was already 13,666 because #31
added a second marketplace; this change adds ~5,800.

Roughly a third of the addition is marketplace conditionals that exist only because one
skill now serves two marketplaces — "Mercado Livre only, since Shopee has nothing below
the level being ranked"
, "Shopee is exempt", "never compare that figure across
marketplaces"
. The rest is nine rules, each traceable to a run that produced a wrong
answer without it.

Three options, and this is a maintainer call:

  1. Accept it, on the grounds that the rules are load-bearing and the marketplace
    split is upstream's design rather than this change's.
  2. Extract the shared rules. Empty-result-is-not-an-outage, retry after a pause, and
    never presenting partial coverage as complete are not specific to this skill; they
    apply across the library and are being restated per file. A shared style document
    would carry them once. The repo does not currently have one.
  3. Split by marketplace. Cleanest on size, but it duplicates the growth logic and
    doubles the routing surface, and Make the focused skills marketplace-aware: add Shopee Brasil #31 deliberately went the other way.

I would take (2), and treat this file as the evidence for it rather than as an exception
to be waved through.

Known limitations

  • Shopee is validated on one run, in one category. Every marketplace-specific rule
    here — level-3 ranking, the precision exemption, the seasonality absence, the
    concentration incomparability — rests on that single run. It passed cleanly, but one
    run is one run.
  • The nine defects were not each individually re-reproduced on the current base.
    Their persistence is established by quoting the current file; their behaviour was
    observed on the previous one.
  • Determinism is measured across two runs, on one category, one marketplace. Enough
    to catch a moving answer; silent on how often.
  • The floor's 0,02% is calibrated, not derived. It reproduces the validated
    behaviour on three categories and tightens a fourth in a direction that looks right.
    A second opinion on that constant would be worth having.
  • Mercado Livre only for the parent/child collapse, by necessity — Shopee has no
    level below the one being ranked, so the rule cannot be exercised there at all.

Notes for maintainers

#33 means this skill now publishes an artifact on every run. Artifacts are private
by default, so this is not a disclosure problem, but it is a change in what the skill
does with the data and it arrived through a library-wide visualization change.

The panel path is newly exercised. Before #33 the visuals were optional and every
run we had was terminal-only, so the cards and charts had never rendered. They render
now, which is also what makes the growth figure reliably visible — the column fix and
the mandatory panel reinforce each other.

This PR does not touch CHANGELOG.md. The newest entry is 0.2.0 and the commits
after it are not recorded there, which reads like a release-time convention. Happy to
add an entry if that is wrong.

Checklist

  • Rebased onto current main (421426d)
  • Defect persistence verified against the current base
  • Both marketplaces exercised live
  • Repeat-run consistency measured, and two findings fixed from it
  • Floor calibration checkable from the table above
  • Description 982 characters, inside the 1024 limit
  • Canonical section order preserved; no new workflow steps
  • No prose line over 95 bytes
  • No cube, field, measure or query references introduced
  • File size — 44% over the library maximum, needs a decision
  • Shopee rules — validated on a single run

…lt on, and stop the floor moving between runs

The skill ranked niches by month-over-month growth and was forbidden from
displaying it - Output said "exactly these five columns ... not a displayed
column" while Presentation rules prescribed a header for that column and the
panel required the growth figure on a card. On a text surface it appeared
nowhere: one run showed fifteen rows with the leader called "o maior salto" and
no percentage anywhere. Both growth columns are now displayed.

The size floor was invented per run. Two runs on one category, minutes apart,
chose R$ 1.000.000 and R$ 300.000, and the second run's leader sat below the
first run's floor - so the same question returned a different top niche. The
floor is now the greater of R$ 300 mil and 0,02% of the parent category's
estimated monthly revenue, which is stated in the output. A fixed figure cannot
serve both marketplaces: Mercado Livre ranks deep leaf niches, Shopee ranks
whole level-3 categories.

Also: revenue and unit growth read together, since a niche can grow revenue
while selling fewer units; concentration and revenue per seller as columns, and
seasonality as a Mercado Livre reading only, because Shopee carries none;
identifier-based navigation on both marketplaces, replacing a per-category link
that does not resolve; full money precision on Mercado Livre with Shopee exempt,
its figures being rebuilt from rounded counters; exact coverage counts; a
category-specific disclaimer with the monthly lag; retry after a pause; and an
empty result separated from an outage.
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.

1 participant