Skip to content

Ads ​

Banners and AdSense or Ad Manager units in zones of the site's pages, in turn, with counts; ads.txt; the shop's products as a feed for Google Merchant Center and Meta Catalog.

kitloom/ads · admins: kitloom/ads-filament, kitloom/ads-nova

Video lessons ​

Recorded in the Filament admin; the Nova admin works the same way.

Show ads on your site: your own banners and code, Google AdSense units and Google Ad Manager units, each in the places you choose, taking turns, with how often each was seen and clicked in the last 7 days.

Getting started ​

  1. Ads → Ads → New Ad. Choose the kind and fill in what it asks for. A banner is an image and a link. For AdSense or Ad Manager, first enter your publisher ID or network code on Ads → Settings.
  2. Ads → Zones → New Zone. A zone is a place on your pages. Give it a name, choose where it goes and tick the ads that take turns there.
  3. Open a page of your site in a private window. Signed in as an administrator or editor you see no ads, on purpose.

Where a zone goes ​

Banners that take turns in a zone
  • Where I put it. You place it yourself: the Ad zone widget on Appearance → Widgets, the shortcode the zones list shows ([ad zone="sidebar"]), or the Shortcode menu of the visual editor. [ad id="12"] shows one ad without a zone.
  • Before the text, after the text, after a paragraph. The module places it in the text of a single post or page, on the types you tick. A paragraph inside a quote, a list, a figure or a table does not count. A text with fewer paragraphs gets the ad at its end, unless you tick Leave out a text with fewer paragraphs.

A zone can be limited to phones or to desktops, and can have a line above the ad, such as "Advertisement". The line on the Settings page is used for a zone without its own.

Taking turns ​

Each visitor gets one ad of the zone, chosen when the page opens, by weight: an ad of weight 3 is shown three times as often as one of weight 1. An ad with dates shows only between them, also on a page kept in the cache. A paused ad stays in its zones and is left out.

A paid link has rel="sponsored nofollow", as Google asks, and goes straight to the advertiser. Views count an ad at least half on the screen. Clicks count the links of your own banners and code: for AdSense and Ad Manager, trust their own reports.

Who sees none ​

  • Roles. Signed-in users with a role on Roles that see no ads, administrators and editors by default, see no zones and none of the networks' scripts.
  • One page. No ads on this page on the form of a post or page, for people who manage ads, leaves out every zone there and AdSense auto ads. Use it for a privacy policy or a page the network's rules keep ads off.

With the Cookie Consent module, AdSense, Ad Manager and HTML ads wait for the visitor's consent to marketing. An image of your own sets no cookies, so it waits for nothing; on the form of an image or an HTML ad you can choose otherwise. Without that module everything is shown.

ads.txt ​

AdSense, ads.txt and who sees no ads

/ads.txt serves the lines you enter on the Settings page. Once the AdSense publisher ID is set, Google's own line is added when it is missing. With neither, the address answers 404. A file of your own in the web root is served instead.

Product feed ​

A product feed for Google Merchant Center

With the shop, Ads → Settings has the address of a feed of your products, the file Google Merchant Center, Meta Catalog, Pinterest and Microsoft Merchant read. Paste it into the network as a scheduled feed and choose how often it fetches.

  • What goes in. Published products: one line for a simple product, one for each enabled variation of a variable one. Hidden products, products behind a password, drafts, grouped and external products stay out.
  • What is left out and why. A product without a price or an image cannot be listed. The page lists them with the reason, so you can put them right.
  • The fields. The title, the short description (or the text), the first image and up to ten of the gallery, the stock status, the price as your catalogue shows it, and the sale price. The GTIN comes from the product's global unique ID. A variation's attributes named color, size, material or pattern go in their own fields.
  • Brand and category. The brand is the product's product_brand term, or Brand of the products for the rest. Google product category holds for the whole site; leave it empty and Google chooses.
  • How fresh. The feed is built every 6 hours by the scheduler, which you can change, or when you ask with Build the feed now (a queue worker does it, if the site has one). php artisan ads:feed builds it from the console.
  • Who can read it. The address holds a key, so your prices are not at an address anyone guesses. New feed address changes it when it got out, and every network then needs the new one.

AI agents ​

An agent connected through kitloom/ai works here with the rights of the user whose key it holds. ads_list, ads_create and ads_update for the ads, ad_zones_list, ad_zones_create and ad_zones_update for the zones, ads_stats for the counts, ads_feed_status for the product feed. "Pause the spring sale banners." "Put this new banner after the second paragraph of posts, from Monday to Friday." "Which ad got the most clicks this month?"

Nothing is deleted: an agent pauses instead. An HTML ad needs manage_ad_snippets like anyone else's, and the publisher ID and network code stay on the Settings page for people to change. Every save is the writer's, with the agent's user as the actor.

Permissions ​

PermissionWhat it gives
manage_adsThe ads and zones, and No ads on this page
manage_ad_snippetsWriting an ad as HTML, since it runs on every visitor's page. Administrators by default
manage_optionsAds → Settings with the product feed, since a publisher ID decides who is paid

With a Content Security Policy ​

kitloom/security's policy is told the hosts of the networks that are running, as a best effort: Google says the hosts its ad code uses change over time and supports only a strict, nonce-based policy for AdSense. Try a site with ads on the report-only header first. The hosts an HTML ad of your own uses are yours to add.

For developers ​

php
use Kitloom\Ads\AdWriter;
use Kitloom\Ads\ZoneWriter;

$ad = app(AdWriter::class)->create([
    'name' => 'Spring sale',
    'kind' => 'image',
    'weight' => 3,
    'settings' => ['attachment_id' => 12, 'url' => 'https://example.com/sale'],
], $user);

$zone = app(ZoneWriter::class)->create(['name' => 'Sidebar'], $user);
app(ZoneWriter::class)->setAds($zone, [$ad->id], $user);

The page cache keeps one page for every visitor, and a Vue or React theme puts a widget's HTML in with v-html, where a script never runs. So the server draws every candidate of a zone in a <template>, and one script in the page's footer picks. Counts are per ad per zone per day, nothing about who saw an ad, so there is no personal data to export or erase.

php artisan ads:import takes the AdSense publisher ID from Site Kit by Google. AdSaved and AdZoneSaved announce what the writers save.

kitloom — modules and themes for Laravel.
Contact · Pricing · Services · License · Refunds · Privacy · Community · YouTube · [email protected]