Slightly against the grain: I'd keep the 2011 combi until it actually dies. It's fifteen years old, not thirty. Doing the floor and the airtightness work now, with the boiler still in place, means the heat pump quote in three years will be smaller and better designed. Grants change, but so do install prices and so does the kit.
Marta
@mulch_marta
Four raised beds, heavy clay underneath, and a compost pile she is proud of.
68 credit Contributor
- From answers
- 0
- From questions
- 69
- Lifetime
- 69
Two separate things are happening and you are treating them as one.
The burst: focus refetching only touches queries that are active and stale. Your staleTime is the default 0, so every active query is stale the instant it resolves, so all of them refetch. Six panels with three or four queries each, plus dependents that fire once their parent resolves, gets you to 60-odd without anything being wrong. Set a real staleTime and most of it evaporates:
defaultOptions: { queries: { staleTime: 30_000, gcTime: 5 * 60_000 } }
A dashboard where data one refresh old is unacceptable is a dashboard that wants a socket, not polling on focus.
The 21 entries: inactive ones (0 observers) are leftovers held for gcTime, and they do not refetch on focus. They are not sending requests. They are just evidence that something in your key changes more often than it should - which is worth chasing, but separately from the burst.
Yes, set the global default high and override per query. staleTime: 0 on the two that matter, or refetchOnWindowFocus: 'always' if you want them to refetch even when fresh. The default is the wrong place to be aggressive because it applies to the 25 queries you were not thinking about.
Not quite - query keys are compared by a deterministic hash, not by reference. hashKey stringifies with sorted object keys, so a fresh literal with the same contents produces the same hash and the same cache entry. Memoising the object changes nothing here. The reason there are 21 entries is that the contents genuinely differ, which is why the hash dump above is the right diagnostic.
Check the cable is detachable and standard before buying. The one thing that has killed cheap mics for me is a captive cable failing at the strain point, which turns an eighty-dollar mic into a bin item over a two-dollar fault.
I lost two plants and nearly a cat to the assumption that hanging things up counts as out of reach. She got on the bookcase, then onto the curtain rail, and the trailing pothos was effectively a rope with snacks on it. Vertical does not work with a determined cat - a door does.
Practical version, from a couple of hundred diffusers made for a market stall. You need a carrier, not just the oil. Neat fragrance barely climbs the reeds and what does climb evaporates unevenly. Most people use a diffuser base sold for the purpose, and the usual working range lands somewhere around a quarter to a third fragrance by weight with the rest base. Fibre reeds move liquid noticeably faster than natural rattan, so with rattan expect a slower, quieter throw and tell people to flip the reeds weekly. A 100ml bottle with eight fibre reeds lasted me about two months in a normal sized room.
If the cache does turn out to hold the stale value, look at your optimistic update. The classic shape is:
onMutate: async () => { const prev = qc.getQueryData(key); ...; return { prev } }
onError: (e, v, ctx) => qc.setQueryData(key, ctx.prev)
onSettled: () => qc.invalidateQueries({ queryKey: key })
If anything in that chain runs after the refetch resolves - a rollback firing on a request that actually succeeded but returned a non-2xx body, a second in-flight mutation settling late - you get exactly this: fresh data on the wire, stale data in the cache, and no error anywhere. Log dataUpdatedAt on every write and the ordering becomes obvious.
Went full swap with no furnace in a similar climate and I'd do it again, but I did air sealing and an attic top-up first, and I'm on a low overnight rate. Without both of those I would have kept the furnace and I'd have been right to.
Parent of two, learned bar models under protest, now use them myself for anything with mixtures or percentages. Draw the total as a strip, cut it into the number of parts in the ratio, label one part, done. The genuinely useful thing is that when the question changes shape - one part is 12 more than another, find the total - the drawing still works and cross multiplication needs rearranging first.
This is just what the curve looks like. Mine peak in their first full laying year, drop noticeably in year three, and by five they are ornamental with occasional bonuses. The birds themselves usually have years left in them, I have had hens reach eight and one hybrid make ten, though hybrids bred hard for output tend to have shorter, rougher retirements than heritage breeds. I run a rolling flock: two new pullets every second year, so I always have someone laying and nobody has to make a decision on a specific bird.
Worth adding that some rescue and rehoming groups will take healthy ex layers, which is a middle road people forget exists.
Also test a scrap with a wet brush first. Some coloured papers are dyed in a way that bleeds onto the board or the text block, and you only find out at the worst possible moment.
Key by the resource and its parameters, not by the place it is displayed. ['orders', { status, page }] and ['customer', id].
The reason is that screens are not unique owners of data. The moment two screens both show the customer, screen keys give you two copies that go stale independently, and updating one leaves the other wrong. Resource keys give you one entry that both screens observe, so a single invalidation fixes both, and the second screen renders instantly from cache instead of refetching.
Invalidation stays just as easy because matching is by prefix: invalidateQueries({ queryKey: ['orders'] }) hits every orders query regardless of the filters after it. That prefix behaviour is the whole design and it is what screen keys throw away.
Exactly that, and it is why the resource goes first in the key and the specifics after. Once you internalise "keys are paths, invalidation matches prefixes", most of the design questions answer themselves.
Noise is a compressor hum plus a fan, roughly like a dehumidifier running. Through a stud wall it's noticeable at night if a bedroom is right there. Through a garage wall it's nothing.
Roof age. If the roof has ten years left in it you're paying to remove and reinstall an array halfway through its life. Do the roof first, or do both together and negotiate as one job.
Small correction to the idea that English borrowed it once and kept it. It is better described as several borrowings from a living professional Latin, because legal Latin stayed in active use in English courts long after Latin stopped being a general written language here. That is also why the word never went through the usual sound changes you would expect from a fifteenth century loan, and why it still looks like an undigested Latin word today: it never really stopped being one.
Second-hand corporate stock. Companies dump chairs when they downsize offices and the mid-tier commercial ones go for a fraction of new. Sit in it, hold your weight on it for a minute, and check the cylinder doesn't sink before you hand over money.
Also make sure the card is actually being streamed rather than blocking. If a parent server component awaits something before rendering the client card, nothing downstream can flush early no matter how many boundaries you place. The clue is that the whole page appears at once after 700ms rather than in two stages, which is what you described.
Client-owned until submit, and then it becomes a mutation with its own identity - not a mutated copy of the server record. Keep the draft in Zustand keyed by job id, and on submit hand it to a mutation and clear the draft on success. The ugliness usually comes from trying to make one object be both at once.
The framing that made this stop being an argument on my team: state is either owned by the server or owned by the client, and the question is never which library, it is which of those two a piece of data is. A job record is server-owned even when you are editing it offline - you are holding a pending intent, not the truth. Drafts, filters and UI state are client-owned.
Once you say it that way, your current split is already correct and the proposal is to break it. Keep the three Zustand stores small and stop worrying that they are small.
If you have programmed at all, the closest feeling is your first strongly typed language after a loose one. The rules are not clever, there are just more places where you are not allowed to hand-wave, and the compiler is a human with a red pen. Same as programming, the fix is volume of small exercises rather than staring at one big one.
This is the bit I had not thought through. If the ducks are going to churn the one dry patch I have left, that changes the maths a lot.
I order a lot and my first hour routine is fixed: unbox immediately, check for pests before it goes near anything else, water thoroughly into the sink and let it drain properly, then a bright spot away from radiators and direct sun, and a bag or a clear box over it for a week if it is a humidity fussy species. Nothing else for at least a month. Most plants that look dead on arrival are dehydrated rather than dead, and the ones that do not recover usually declare themselves within ten days.