Repository navigation
Tags
Tags
Stop swallowing a failed leaderboard fetch silently When the leaderboard fetch fails it was turned into an empty leaderboard with no log line. That leaves ALL SEVEN boards without a sample, frozen on their last standings, while the rest of the cycle succeeds: the feed pass still writes, the sample still counts as taken, and nothing says why the standings stopped moving. Same rule as the road cache: a network error is not a finding. Both fetches now log the failure and what it costs. This mostly bites self-hosters, who otherwise have no trace at all.
The jump landed on the map, zoomed out past all recognition Two things that grate in use and are invisible while building. The map link from Exposed has always carried lat and lng — the map simply never read them. fitInitial() fitted the whole turf, which is precisely the view in which a single cell cannot be seen. A target from the link now wins over the default fit: zoom 14, measured against the tile the browser actually requests (8508/5531 at zoom 14 is arithmetically exactly the target cell). A broken or half-filled link is not an error but simply no target — the map loads normally. The board chips threw the reader back to the top on every switch. They reload the page, and with no anchor you land at the top of a page you had scrolled to the bottom of. They now carry their own anchor, the section has a mark, and scroll-margin keeps its heading clear of the sticky rail. The smooth scrolling that comes with it applies to document pages only. Set globally it would drag the map and the panels along, which gain nothing from it.
Rank 75 of 1473, but 1463 were compared The rank counted players present in BOTH snapshots who did better — the field behind it counted the newer snapshot alone. Players who only turned up inside the window sat in the denominator while they could never appear in the numerator: a rank out of more players than were ever compared. Ten too many over 24 hours, thirty-two over 48. Both now count the same population, in one query instead of two.
The member lists named every player and were being discarded — search… … by name, get the gang The ask was a targeted lookup: which gang does this player belong to. The mapping had been in player_snap all along, only the way in by name was missing — and names were known for 326 of 1476 players, barely a quarter. api team me returns members with 376 entries, each carrying user_id AND username. The poller already fetches it once per gang and read only the totals from it. Across the 22 gangs our users belong to that is 937 players — about three times what the leaderboards yield, for zero extra requests. Names are learnt on a real fetch rather than from the cache, and written only when one actually changed. Plus api players with q=: matches anywhere in the name, case-insensitively, and returns gang, cells and APs from the latest sample. Someone known by name but absent from the snapshots still comes back — without figures rather than not at all. Percent and underscore are escaped, or a search for _ would match every name. id= additionally returns a current block with the present state, so the gang need not be dug out of the history. The README states the limit plainly: an empty result means "not known here", not "does not exist".
The tour snap stayed on car — hitting the attack targets of all things Asked why occupied cells were left out, the answer turned out to be that they should not be: enemy cells with the smallest AP deficit are the core of the game and the planner sorts by exactly that. The earlier reasoning was simply wrong. Nothing was disappearing — cell_roads only filters virgin ground, occupied cells are listed in full in every mode. The gap sat one level down: api snap knew only DRIVABLE. Anyone on foot putting an occupied cell in a tour got the car road point, and where no car can go, none at all — at which point the tour falls back to the cell centre. Precisely the routing-to-nowhere we had just removed, reintroduced through the back door. snap_cells now takes the mode. Cells with a road are untouched, those work on foot too. The rest get their path point, looked up on the spot where none has been checked yet rather than waiting for the background drip — that takes hours, the tour is being built now. In car mode no path query is made at all. Right now this affects 72 occupied cells without a car road, but that is a snapshot: of 72141 occupied cells only 10312 have ever been snapped, the rest follow as soon as someone puts them in a tour.
Not everyone drives — targets and routes for bikes and on foot Two war-bikers and a war-walker asked whether the road classification could serve hikeable and rideable routes too. Both halves turned out to be hard-wired to cars. Routing first, because that is the real pain: /route/v1/driving sat in the code twice. FOSSGIS runs routed-bike and routed-foot beside routed-car, separate engines each. On one test leg 3628 m by car against 2539 m on foot — a walker was being sent around the block instead of down the path that goes straight there. Instance and profile name belong together and now travel as a pair through MODES; an unknown mode falls back to car rather than failing. Target selection was the second problem. found=0 means "no road for a CAR", and that erased the cell from every list — while a walker reaches a cell on a footpath perfectly well. Of 22064 cells dismissed that way, 19288 are virgin ground. A sample of 60 against Overpass found a path in 15 % of them (path, bridleway, footway), so roughly 2900 targets never made it into the list at all. Hence path_lat/path_lng/path_kind on cell_roads, filled by a second drip that checks only the found=0 cells — a few thousand rather than the whole cache, and it runs on whatever budget the road drip leaves. It stores the OSM way type instead of a yes/no: what counts as usable depends on the mode, and a changed rule then needs no new Overpass run. NULL means unchecked, '' checked and nothing there — keeping those apart stops every pass from re-querying the empty ones. On foot every way counts; by bike the subset you may legally ride: no steps, and footway stays out rather than promising a ride that is not allowed. Unclassified cells stay visible in every mode — unknown is not a finding. In the interface the switch sits in the planner, because it changes that very list; users.travel_mode remembers the choice, api virgin takes it as the default and accepts mode= to override per call.
Using the API meant putting your login in a script — read-only tokens… … that may only read There was exactly one way into the API: the session cookie. That is full access — it can set your position, edit your crew, wipe your coverage trail — and it lives 60 days. In a cron file or a committed config it hands over the whole account. Which is precisely where we would have sent people, having just documented the API. New are read-only tokens: info tab, give it a name, done. They may reach the six read endpoints and nothing else — the writing routes and api live stay deliberately cookie-only, as does the interface. Verification is by effect rather than status code: with a token the account still exists, the watcher scope is unchanged, no position was stored, and a token cannot mint another token. Only a SHA-256 hash is stored, not bcrypt: the value carries 256 bits of entropy rather than being a guessable password, and it is checked on every request. The plaintext exists exactly once, on screen. That page is rendered directly instead of redirecting — a redirect would have to carry it in the URL and therefore into the access log, the Referer header and the browser history. Two subtleties: a present-but-invalid token does NOT fall back to the cookie, otherwise a revoked script would keep working in a browser context and nobody would notice the revocation achieved nothing. And a token never sets last_seen — that figure means a human had the app in front of them, and a per-minute cron job must not look like one.
Virgin ground lived in the database only — an endpoint for it, carryi… …ng the road point instead of the cell centre FusedStamen plans his wardrives with his own script which, for lack of an alternative, reaches straight into the SQLite: virgin_cells JOIN cell_roads, a bbox, nearest-neighbor, GPX for OsmAnd. His README tells readers to go hunting with .schema users for the right column name — precisely the coupling we wanted to avoid, and his example command already fails on users.name. api virgin serves the same over HTTP: virgin ground in your own turf, bbox as lat_min,lat_max,lng_min,lng_max, roads_only by default. Swapped bounds get sorted rather than silently returning an empty answer that reads as "nothing here". The field matters more than the endpoint: it returns rlat/rlng, the drivable point INSIDE the cell. His script navigates to vc.lat/vc.lng, the centre, and joins cell_roads only for found=1 — while the snapped point sits right there. That is the routing-to-nowhere problem we solved internally long ago. Both coordinates go out so the difference stays visible instead of hidden, and navigate_with names the right one in every response.
PreviousNext