Beschrijving
Turf is een selfhosted, cookieless analytics-plugin. Geen Google Analytics, geen Jetpack, geen externe netwerkverzoeken – alles wordt gemeten en opgeslagen in je eigen WordPress-database.
Waarom Turf
- Cookieless. Deduplicatie van bezoekers gebeurt met een eenrichtingshash van IP + user-agent, nooit met een cookie en nooit met het ruwe IP-adres.
- Zelfgehost. Alle data blijft in je eigen database; er wordt niets naar derden verzonden.
- Geen configuratie nodig. Elk openbaar berichttype en elke taxonomie wordt automatisch bijgehouden, ook types die je later toevoegt.
Wat het volgt
- Paginaweergaven (gededupliceerd én ruw), unieke bezoekers, weergaven per bezoeker en gemiddelde bezoekduur
- Apparaat, browser, besturingssysteem, taal en land (via Cloudflare’s header indien beschikbaar – geen GeoIP-opzoekingen)
- Referrers/verkeersbronnen, UTM-campagneparameters en het automatisch volgen van uitgaande links (volledige bestemmings-URL + de pagina waarvandaan geklikt is)
- Nieuwe versus terugkerende bezoekers, scrolldiepte en leestijd
- Zoektermen op de site, inclusief zoekopdrachten zonder resultaat
- Bezoekersroutes (overgangen van pagina naar pagina), landingspagina’s en een bounce-rate-indicatie – allemaal gereconstrueerd uit sessies
- Cache-offload: hoeveel verkeer wordt afgehandeld door een pagecache (SiteGround, Cloudflare, …) in plaats van WordPress te belasten
- 404-hits, reacties per periode, redactionele contentactiviteit, statistieken per auteur
- Bots & LLM-crawlers (Googlebot, GPTBot, ClaudeBot, …) – server-side bijgehouden en apart gehouden van menselijke bezoekersaantallen
- WooCommerce.funnel (weergaven, toevoegen aan winkelwagen, afrekenen) en formulierinzendingen (Contact Form 7, Gravity Forms) wanneer die plugins actief zijn
De beheerpagina’s gebruiken native WordPress postboxen: invouwbaar, verplaatsbaar, verbergbaar via Scherminstellingen, en vormgegeven volgens je beheerkleurenschema. De interface is Engels en wordt geleverd met een volledige Nederlandse (nl_NL) vertaling.
Schermafbeeldingen



Installatie
- Installeer en activeer de plugin.
- Dat is alles – weergaven worden direct geteld voor elk openbaar berichttype en elke taxonomie. Je vindt de rapportages onder het menu “Statistieken” in wp-admin.
Optionele extra’s (een zichtbare weergaventeller, het volgen van klikken op specifieke elementen, social-share-links, het importeren van historische weergaven uit Jetpack/entry-views via de beheerpagina “Statistieken > Importeren” of WP-CLI) staan beschreven in de README van de plugin op GitHub.
FAQ
-
Turf plaatst geen cookies en verstuurt geen data naar externe diensten. Deduplicatie gebeurt met een eenrichtingshash van IP + user-agent; het ruwe IP wordt nooit opgeslagen. De plugin is ontworpen om te passen binnen een grondslag van “gerechtvaardigd belang” voor first-party, geaggregeerde analytics – maar dit is geen juridisch advies: overleg met wie je privacybeleid beheert.
-
Welke data verzamelt Turf, en waar gaat die naartoe?
-
Per paginaweergave slaat Turf, uitsluitend in je eigen database, het volgende op: een eenrichtings-bezoekershash, een tijdstempel, de bekeken pagina, apparaattype/browser/OS-familie (afgeleid uit de User-Agent), taal, landcode (alleen als Cloudflare die levert), de hostnaam van de referrer, UTM-parameters, scrolldiepte en leestijd. Ruwe event-regels worden na 18 maanden automatisch opgeruimd (filterbaar); geaggregeerde totalen blijven bewaard. Er wordt nooit iets van je server verzonden.
-
Waarom zijn Turf’s cijfers lager dan die van Jetpack of een ruwe hitteller?
-
“Weergaven” is ontdubbeld: een herhaalde weergave van dezelfde pagina door dezelfde bezoeker binnen 30 minuten telt niet opnieuw mee (dezelfde standaard die Google Analytics en Matomo gebruiken). Het aparte getal “Ruwe weergaven” telt elke paginaweergave, voor een eerlijke vergelijking met tools die hits tellen.
-
Werkt het samen met pagecaching?
-
Ja. Het volgen wordt client-side uitgevoerd, dus gecachte pagina’s worden nog steeds geteld. Turf rapporteert zelfs hoeveel van je verkeer vanuit de cache wordt geserveerd.
-
Waar komt de landdata vandaan?
-
Uit de CF-IPCountry-header van de aanvraag, als je site achter Cloudflare draait. Turf roept bewust geen enkele geolocatie-API aan – dat zou betekenen dat IP-adressen van bezoekers naar een derde partij worden verzonden. Zonder Cloudflare blijft het land leeg, tenzij je via het filter turf_visitor_country je eigen lokale database koppelt.
-
Verwijdert het verwijderen van de plugin mijn statistieken?
-
Standaard niet – analyticsgeschiedenis is waardevol, dus de data blijft bewaard bij het verwijderen/opnieuw installeren. Om alles te verwijderen bij deïnstallatie, voeg define( ‘TURF_REMOVE_DATA_ON_UNINSTALL’, true ); toe aan wp-config.php (of zet de optie
turf_remove_data_on_uninstallop1) voordat je de plugin verwijdert. -
Waar kan ik een functie voorstellen of een bugrapport indienen?
-
Op de GitHub-repository van de plugin: https://github.com/fbloemhof/turf-stats/issues
Beoordelingen
Er zijn geen beoordelingen voor deze plugin.
Bijdragers & ontwikkelaars
“Turf Stats” is open source software. De volgende personen hebben bijgedragen aan deze plugin.
Bijdragers“Turf Stats” is vertaald in 1 locale. Dank voor de vertalers voor hun bijdragen.
Vertaal “Turf Stats” in je eigen taal.
Interesse in ontwikkeling?
Bekijk de code, haal de SVN repository op, of abonneer je op het ontwikkellog via RSS.
Changelog
1.27.0
- De schrijfwijze met en zonder www. van het eigen domein telt nu als dezelfde site: links daartussen worden niet meer als uitgaande klikken vastgelegd, en zulke referrers tellen als “Intern”. Bestaande regels met uitgaande links naar het eigen domein worden ook uit het rapport gefilterd.
- Weergaven van “overige” pagina’s (pagina’s die geen bericht of taxonomie-archief zijn, bijv. een agenda- of archiefpagina) leggen nu hun URL-pad vast, zichtbaar in het nieuwe vak “Overige pagina’s per URL”. Paginering wordt bij het archief zelf opgeteld. Het ontdubbelen van herhaalde weergaven werkt voor deze pagina’s nu per pad, zodat twee verschillende “overige” pagina’s die binnen hetzelfde ontdubbelvenster worden bekeken, allebei meetellen.
- Klikken op een link met data-turf-click leggen nu ook de bestemmings-URL van de link vast, zichtbaar in het nieuwe vak “Bestemmingen van aangeklikte links” op de pagina Klikken.
- Nieuwe verkeersbron “Push-berichtgevingen”: bezoeken met utm_medium=push (bijv. via een klik op een melding van een service worker) tellen niet langer als “Direct”.
1.26.0
- Dagelijkse lijngrafieken “Trend laadtijd” en “Trend tijd/bezoek” toegevoegd aan de pagina Analyse, naast de bestaande heatmap met piekuren.
- Added a “PWA vs. browser” breakdown to the Statistics page: detects
whether a pageview ran inside an installed PWA (Add to Home Screen /
Install app) or a normal browser tab. This is a rough estimate of active
PWA usage, not a hard install count – browsers don’t report installs to
the server.
1.25.2
- 1.25.1 teruggedraaid: “mln” voor miljoenen leest ook op Nederlandse sites prima, dus de afkorting “k”/”M” is weer een vast achtervoegsel in plaats van een vertaalbare tekst.
1.25.1
- Opgelost: de afgekorte aantallen weergaven/bezoekers die in 1.25.0 zijn toegevoegd, toonden altijd het Nederlandse “mln” voor miljoenen, ook op Engelse (en andere) sites. De achtervoegsels “k”/”M” zijn nu vertaalbaar, zodat andere talen dan het Nederlands “1.2M” tonen in plaats van “1,2 mln”.
1.25.0
- Grote aantallen weergaven/bezoekers worden nu afgekort getoond (“12,3k”, “1,2 mln”) in de totalentegels, de shortcode-widget [turf_stats] en de weergaventeller die bezoekers bij losse berichten zien – zodat grote getallen in hun vaste ruimte blijven passen. Tabellen en CSV-exports tonen nog steeds exacte getallen.
- Opgelost: de knop “Ga naar datum” toonde in elke taal behalve het Nederlands het Nederlandse woord “Toon” in plaats van “Show”.
1.24.0
- De pagina Statistieken laadt nu merkbaar sneller: de meeste vakken (uitsplitsingen naar apparaat/browser/OS/land, bronnen, UTM-campagnes, toppagina’s/-termen, piekuren, enz.) laden hun data op de achtergrond direct nadat de pagina verschijnt, in plaats van dat je moet wachten tot elke query klaar is.
- De zwaarste statistiek-queries worden nu een paar minuten gecachet, zodat het herladen van de pagina of het wisselen van periode niet telkens dezelfde trage databasequery herhaalt.
- Visuele opfrisbeurt van de pagina Statistieken: uitsplitsingslijsten, de totalentegels, de dagelijkse grafiek en de rapporttabellen (toppagina’s, top-zoektermen, 404’s, klikken, enz.) hebben nu één consistente, compactere look met een markering per rij bij hoveren en een balk over de volle breedte achter elk uitsplitsingsitem in plaats van een apart klein balkje – ook de uitsplitsing op de pagina Bots, die nu overeenkomt met de rest van de plugin in plaats van een eigen oudere stijl te gebruiken. Verversen is niet meer nodig om het nieuwe uiterlijk te zien.
- Nieuwe sorteerbare kolom “Weergaven” in de berichten-/paginalijst (en elk ander bijgehouden berichttype), zodat je weergaveaantallen ziet zonder de lijst te verlaten.
- Opgelost: de tabellen “Van/Naar” (sessieroutes) en uitgaande links toonden hun tweede kolom rechts uitgelijnd in plaats van links.
- Opgelost: de toggle “Toon meer” werkte niet in vakken die hun data op de achtergrond laden.
1.23.0
- Aangepaste periodes: kies elke gewenste start- en einddatum in plaats van alleen de vaste voorinstellingen, en sla veelgebruikte periodes op onder een naam om er later snel naar terug te gaan.
- CSV-export voor de vakken met het totaaloverzicht, toppagina’s, top-referrers, de uitsplitsing naar apparaat/browser/OS, zoektermen en 404’s – volgt de periode die op het scherm staat (ook een aangepaste periode).
- Wekelijks/maandelijks e-mailrapport: een samenvatting van je statistieken die volgens een terugkerend schema naar een of meer adressen wordt verzonden, met een knop “Stuur nu een test-e-mail” om opmaak en aflevering te controleren zonder op het schema te wachten.
- Opgelost: verschillende op periode gefilterde vakken (404’s, statistieken per auteur, uitsplitsingen van klikken en uitgaande links, WooCommerce-funnel, heatmap met piekuren) namen ongemerkt data mee tot “nu” in plaats van te stoppen aan het einde van “Gisteren” of een gekozen datum – dit gold alleen voor die twee periodekeuzes, niet voor de tabbladen dag/week/maand.
- Nederlandse (nl_NL) vertaling geüpdatet voor alle nieuwe strings.
1.22.0
- Het volgen van de campagneparameter
utm_content(bijv. link_in_bio van Instagram) naast de bestaandeutm_source/utm_medium/utm_campaign, met een bijbehorend uitsplitsingsvak “Campagne-content (UTM)”.
1.21.1
- Opgelost: de vakken “Formulieren”, “Top-zoektermen” en “Meest besproken” op de pagina’s Analyse en Statistieken verdwenen ongemerkt bij elke periode behalve “Altijd” – een kapot datumfilter maakte de onderliggende query ongeldige SQL, waardoor die stilletjes mislukte en het vak werd weggelaten.
1.21.0
- Nieuwe shortcode
[turf_stats]: een overzichtstabel (nu online, vandaag, gisteren, laatste 7 dagen, laatste 28 dagen) voor een Tekst-/HTML-widget in de zijbalk of een Shortcode-blok, met de attributenmetric(weergaven/bezoekers),layout(tabel/lijst, de lay-out) enitemsom te bepalen welke rijen getoond worden. - Opgelost: een beschadigd Nederlands (nl_NL) .mo-bestand (een dubbele bron-string “Online now” zorgde dat het niet compileerde, en het gecompileerde bestand zelf was geen geldig gesorteerd .mo-bestand) – Nederlandse vertalingen werden ongemerkt niet geladen.
1.20.3
- De labels van de uitsplitsing naar schermresolutie zijn nu Engelse bron-strings met Nederlandse vertalingen in het taalbestand (stonden per ongeluk in het Nederlands in de code).
- De berekening van het venster voor de dagelijkse grafiek is ondergebracht in een gedeelde helperfunctie turf_day_window(), zodat de vensters van één dag en 7 dagen de tijdzonelogica niet langer dupliceren.
- Opgelost: TURF_VERSION (de cache-busting-versie voor alle geladen JS/CSS) bleef sinds de release van 1.20.0 hangen op 1.19.0 – elke wijziging aan assets is sindsdien uitgeleverd onder een ongewijzigde versie-string.
1.20.2
- Opgelost: de dagelijkse staafgrafiek op de tabbladen Vandaag/Gisteren/vaste datum toonde alleen de ankerdatum (plus een fractie van de dag ervoor bij een niet-UTC sitetijdzone) in plaats van het bedoelde contextvenster van 7 dagen. De grafiekquery bestrijkt nu de 7 dagen eindigend op de geselecteerde dag, overeenkomend met de 7 balken die worden getekend. Regressie sinds 1.20.0 (datumnavigatie).
1.20.1
- Schermresolutie: het JavaScript voor het volgen valt terug op viewport innerWidth/innerHeight wanneer window.screen 0 rapporteert of ontbreekt (in-app webviews, browsers met bescherming tegen fingerprinting), zodat minder weergaven onder “onbekend” belanden.
- De uitsplitsing naar schermresolutie scheidt nu weergaven via de app/REST API (die het JavaScript voor het volgen nooit uitvoeren en terecht geen schermgrootte hebben) van echte browserweergaven die er geen rapporteerden, in plaats van beide samen te voegen in één categorie “onbekend”.
1.20.0
- Datumnavigatie toegevoegd (ingebouwde datumkiezer, tabblad Gisteren), met een correctie voor de interne markering van een vaste datum.
- Toggle ‘Toon meer’ toegevoegd bij de top-referrers (toont er 10, onthult tot 50).
- Dashboardwidget toegevoegd (nu online, weergaven/bezoekers van vandaag met % t.o.v. gisteren), met hergebruik van de vormgeving van de overzichtskaarten.
- Uitstelmogelijkheid toegevoegd voor het verzoek om een beoordeling (willekeurig 30-90 dagen, maximaal 3 keer, daarna permanent).
- Apparaatklasse-label toegevoegd (Telefoon/Tablet/Desktop) bij schermresolutie.
- Opgelost: overflow in de 90-dagengrafiek (gat + horizontale scroll).
- Nederlandse vertalingen voor nieuwe strings.
1.19.0
- Nieuw uitsplitsingsvak “Schermresolutie”: de schermgrootte van bezoekers (in CSS-pixels) wordt bij elke weergave vastgelegd. De nieuwe databasekolommen worden bij de update automatisch toegevoegd.
- Nieuw statistiekvak “Gem. laadtijd”: laadtijden van pagina’s worden gemeten in de browser van de bezoeker via de Navigation Timing API en per periode gemiddeld.
- Het vak “Nu online” krijgt een live lijst “Nu bekeken” met de pagina’s waar huidige bezoekers zich bevinden, ververst bij dezelfde controle elke 20 seconden.
- De uurgrafiek van bezoekers is herzien: een vaste 24-uursas met een gestippelde lijn voor “gisteren”, voor directe vergelijking met de vorige dag.
- De dagelijkse balken voor weergaven/bezoekers tonen nu hun waarden in de grafiek, met een labelgrootte die zich aanpast aan de dichtheid bij de 30- en 90-dagenweergaven.
- Het Cache-blok geeft nu een toelichting wanneer een cachelaag wordt gedetecteerd maar (bijna) geen van de gevolgde paginaweergaven serveert.
- Veel snellere import van oude weergaveaantallen: een voorronde via de Jetpack-toplijst dekt de meest bekeken berichten in één aanvraag af, batches op de beheerpagina worden gelijktijdig uitgevoerd, en het WP-CLI commando krijgt de opties –offset/–limit.
- Nederlandse (nl_NL) vertaling geüpdatet voor alle nieuwe strings.
1.18.1
- Schermafbeeldingen toegevoegd voor de vermelding op wordpress.org (overzicht Statistieken, Analyse, Bots & LLM’s) en de bijbehorende sectie == Screenshots ==. Geen wijzigingen in de werking of in het volgen.
1.18.0
- De op GitHub gebaseerde updatecontrole is volledig verwijderd (updater.php en de meegeleverde library) – releases worden nu rechtstreeks naar WordPress.org gepubliceerd via een GitHub Action, en updates worden door wordpress.org afgehandeld zoals bij elke andere gehoste plugin.
- Opgelost: de sleepvolgorde en de in-/uitklapstatus van postboxen werden niet echt opgeslagen: de beheerpagina’s misten de nonce-velden waar de eigen postbox-AJAX-handlers van WordPress core naar zoeken, waardoor die aanvragen ongemerkt mislukten. Volgorde en inklapstatus worden nu per gebruiker correct opgeslagen.
- De site-specifieke integratie met de begeleidende app “Dorpsapp” is nu een generiek, opt-in connector-app-mechanisme (
turf_connector_app_route_patterns/ turf_connector_app_label filters) – geen gedragsverandering, tenzij je het oude filterturf_dorpsapp_route_patternsgebruikte, dat is hernoemd. - Een link naar GitHub-issues (bugrapporten/functievoorstellen) toegevoegd aan de FAQ.
- De import van oude weergaveaantallen (Jetpack Stats / de oude entry-views-plugin) is nu ook beschikbaar als beheerpagina “Statistieken > Importeren”, naast het bestaande WP-CLI-commando
wp turf-stats import-legacy-views– dezelfde import, uitgevoerd in kleine AJAX-batches met een voortgangsbalk in plaats van de commandoregel.
1.17.2
- Opgelost: een WordPress.org indieningsfout doordat de headers Plugin URI en Author URI naar dezelfde URL wezen. Author URI wijst nu naar het GitHub-profiel van de auteur in plaats van naar de plugin-repository.
1.17.1
- De resterende waarschuwingen van de WordPress.org Plugin Check zijn opgelost: de inmiddels overbodige aanroep van load_plugin_textdomain() is verwijderd (vertalingen voor op wp.org gehoste plugins laden sinds WP 4.6 automatisch) en de optionele REST-debuglogger is van annotaties voorzien. Geen wijzigingen in de werking of in het volgen.
1.17.0
- WordPress.org compliance-release: readme.txt, uninstall.php met opt-in dataverwijdering, directe-toegangsbeveiliging op alle bestanden, en de GitHub-updatecontrole maakt geen deel meer uit van de WordPress.org build (updates komen van wordpress.org).
1.16.1
- Lange lijsten worden nu vóór de eerste weergave ingeklapt (CSS), waardoor de laadtijdsprong die in 1.16.0 werd geïntroduceerd, is verdwenen.
1.16.0
- Inzicht in cache-offload (% vanuit cache geserveerd, met laagdetectie).
- Rapportage landingspagina’s met bounce percentage per landingspagina.
- Blokken zonder data voor de geselecteerde periode worden volledig verborgen.
- Alle lijsten gebruiken één toggle Toon meer / Toon minder op de plek zelf; paginering aan de serverkant is verwijderd.
1.15.0
- Tweetalig: Engelse bron-strings met een meegeleverde Nederlandse (nl_NL) vertaling.
1.14.0
- Ruwe (niet-ontdubbelde) telling van weergaven, weergaven per bezoeker, gemiddelde bezoekduur, een grafiek met bezoekers per uur voor “Vandaag”, en het volgen van uitgaande links met volledige URL inclusief de bronpagina.
Eerder
- Zie https://github.com/fbloemhof/turf-stats/releases voor de volledige geschiedenis.
