Weekly campaign report — 2026-08-10 to 2026-08-15, against 2026-08-03 to 2026-08-08

Two ad accounts bought this app in this window and both are ours: across the six UTC days 2026-08-10 to 2026-08-15 the portfolio spent $3,770.14, of which B1 took $3,329.00 and the two shared Nomad Node accounts, which began buying on 08-11, took $441.14. B1 got 3,550 installs at $0.938 against $3,812.43 and 5,663 at $0.673 in the same six days a week earlier; it booked $8,384.94 and sealed $2,542.76 inside the days themselves. The week is six days of seven, because 2026-08-16 had not closed when this was cut, and it is read against the matched six days of the week before. Our records read 1.09 of Meta's booked value on B1's own clock, outside the documented 0.91 to 1.06 band. Definitions, the report clock and the three revenue measures are in the appendix.

1Overview

2026-08-03..2026-08-082026-08-10..2026-08-15change
spend$3,812.43$3,329.00−12.7%
impressions529,309354,790−33.0%
CPM7.209.38+30.3%
clicks28,44722,152−22.1%
CTR5.37%6.24%+16.2%
installs (Meta)5,6633,550−37.3%
click→install19.91%16.03%−19.5%
CPI$0.673$0.938+39.3%
registrations (ours)6,3504,758−25.1%
booked$8,146.98 (2.14)$8,384.94 (2.52)+2.9%
within-day$3,976.77 (1.04)$2,542.76 (0.76)−36.1%
cohort @ 24h$4,939.27 (1.30) at 100%$3,227.88 (0.97) at 90%not comparable — see Caveats
within-day payers296213−83

Cohort value — ARPU and ARPPU at d0, d3 and d7

Keyed on the INSTALL day and measured from each user's own install stamp: dN is their first (N+1) x 24 h. ARPU is Adjust's own series, the one the partner's dashboard reports; ARPPU is our payment ledger, because Adjust exposes no cumulative distinct-payer count. A horizon the window has not lived through yet is left empty rather than written as zero.

appARPU (d0)ARPU (d3)ARPU (d7)ARPPU (d0)ARPPU (d3)ARPPU (d7)installs
Vloom$0.6099$0.9397$1.3412$11.80$15.64$21.566,093

Portfolio spend, both windows: $3,812.43 then $3,770.14. The earlier window is B1 alone; the shared accounts had not started.

One campaign, Worldwide, took 100.0% of B1; the earlier window was not single-campaign. Any account-level line across the two carries a campaign-mix change.

Installs got two fifths dearer on slightly less money. CPI $0.673 → $0.938, spend −12.7%, installs −37.3%.

Booked rose while within-day fell — an ageing cohort. The share of booked revenue from installs inside the window went 48.8% to 30.3%.

The pooled CPM and CTR rows point the opposite way from the hour-matched read, and section 3 names the one hour behind it.

Click→install fell on both reads, and it is where the CPI rise sits. 19.91% to 16.03% pooled, lower in 23 of 24 matched hours.

2The two ad accounts, side by side

Both accounts are ours: B1, act 1738541847343652, campaigns bailingxia_; and the two shared Nomad Node accounts, acts 835434076171203 and 3267486106793669, whose campaigns for this app are 0811_ and 0814_*. Those two accounts also carry other products and none of that is counted here. The shared pair started on 2026-08-11, so its column covers five of this window's six days while B1's covers all six. Spend is each account's own export; registrations and the three revenue measures are our own records, taken across everything each account's campaigns carried, which is why B1's row here does not match the ad-id-scoped totals in the sections below to the cent.

accountspendregistrationsbookedbROASwithin-daywROAScohort@24hcROAS
B1 (ours)$3,329.004,751$8,389.932.52$2,547.750.77$3,232.870.97
Nomad Node (shared)$441.141,710$921.512.09$669.741.52$825.681.87
Portfolio$3,770.146,461$9,311.432.47$3,217.490.85$4,058.551.08

Rank on within-day and cohort@24h, never booked; here the rankings disagree. Booked credits B1 with weeks of accumulated cohort the shared buy has not had.

A ninth of the money brought a quarter of the new users, which is what lifts the portfolio's two inheritance-free returns above B1's own.

The shared accounts' export carries no Ad ID, campaign name, clicks, leads or country. So sections 3 to 7 are B1 alone.

3Hourly, B1, 2026-08-10 to 2026-08-15

B1 alone, on the report clock. The axis is hour of day pooled across the six days of the window, not a clock: each bucket holds six instances of that hour, so this table is read for diurnal shape and never as a timeline. Delivery columns are Meta's instrument on both sides of every ratio. Payer rate, ARPU and ARPPU are ours on both sides. The two install counts are never crossed. ours is our registrations in that hour bucket; cov is that bucket's cohort coverage at H=24.

hrspendimprCPMclicksCTRinstclk→iCPIourscovbookedbROASwithinwROASwPaycohortcROAS
0$97.7710,1029.686536.46%9614.7%$1.018114100%$404.464.14$174.761.7911$174.761.79
1$100.0511,0139.086165.59%8614.0%$1.163122100%$414.544.14$214.062.1410$214.062.14
2$110.1611,7689.366835.80%10615.5%$1.039151100%$215.951.96$135.741.2311$135.741.23
3$116.5712,6769.207305.76%11415.6%$1.023151100%$162.821.40$41.550.365$41.550.36
4$111.4013,4498.287805.80%12115.5%$0.921157100%$341.643.07$32.870.306$35.930.32
5$116.9614,4128.127895.47%14017.7%$0.835193100%$461.603.95$91.610.788$91.610.78
6$122.6313,9968.767715.51%11715.2%$1.048168100%$298.052.43$81.060.665$90.370.74
7$184.6219,0209.711,2956.81%18914.6%$0.977275100%$320.141.73$213.731.1613$244.851.33
8$158.0918,1228.721,1106.13%18016.2%$0.878234100%$464.742.94$189.541.2012$189.541.20
9$161.3218,1948.871,0815.94%17416.1%$0.927226100%$354.092.19$170.411.0615$177.001.10
10$171.7618,5789.251,0875.85%17215.8%$0.999234100%$391.682.28$97.090.576$134.950.79
11$156.7616,9349.261,0226.04%15315.0%$1.02519783%$335.262.14$96.160.618$148.030.94
12$154.6615,6649.871,0026.40%14814.8%$1.04520383%$140.310.91$35.220.236$38.280.25
13$134.5015,3038.791,0536.88%16615.8%$0.81023783%$297.222.21$50.570.388$57.100.42
14$141.8411,62712.208847.60%15417.4%$0.92119985%$289.732.04$147.481.0413$186.221.31
15$168.6017,5399.611,1896.78%19516.4%$0.86525284%$395.532.35$84.310.5010$92.870.55
16$172.0620,2538.501,2065.95%20917.3%$0.82327782%$395.312.30$102.420.6012$138.860.81
17$185.6620,8998.881,2816.13%18714.6%$0.99327684%$481.582.59$102.300.5510$128.400.69
18$176.0618,3209.611,1616.34%20217.4%$0.87225779%$401.442.28$124.980.717$163.990.93
19$154.8114,76710.489086.15%16418.1%$0.94422376%$377.442.44$103.770.678$125.880.81
20$110.1211,2129.827726.89%13317.2%$0.82817583%$358.663.26$88.870.817$272.492.47
21$118.039,94911.866926.96%11516.6%$1.02614682%$504.374.27$88.600.7510$113.590.96
22$104.3910,23310.206916.75%10214.8%$1.02314083%$216.502.07$15.050.142$15.050.14
23$100.1810,7609.316966.47%12718.2%$0.78915183%$361.903.61$60.610.6110$216.782.16
all$3,329.00354,7909.3822,1526.24%3,55016.0%$0.9384,75890%$8,384.942.52$2,542.760.76213$3,227.880.97

⚠ Payer counts per hour bucket run 0 to 9 on any one day. An hourly ARPPU on one payer is that payer's basket. Read the all row for level and the buckets for shape.

Coverage is 100% through bucket 10, 76% to 85% after it, 90% overall. Every cohort figure here can only rise, and 0.97 is a floor.

The buy sits in the account's morning. Buckets 7 to 19 each carry over $130 — on B1's UTC-7 clock, its own first thirteen hours.

Bucket 14 buys the thinnest, dearest impressions, and it is a standing feature: 08-14 alone 1,453 impressions at CPM 11.15, 08-15 alone 1,743 at 13.68.

CPI swings less across the clock than return, and part of return's swing is within-day censoring: buckets 20 and 23 more than triple on cohort@24h.

2026-08-16T16:04:13.071808 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 3 6 9 12 15 18 21 hour (UTC) 0 25 50 75 100 125 150 175 USD hour of day, pooled across the 6 days of the period — a pooling, not a timeline Spend by hour 0 3 6 9 12 15 18 21 hour (UTC) 10000 12000 14000 16000 18000 20000 impressions Impressions and installs by hour impressions installs 80 100 120 140 160 180 200 installs (Meta Leads) The period's motion — whole account, 2026-08-10..2026-08-15 (UTC)
The period's motion: spend by hour, and impressions against installs
2026-08-16T16:04:13.221573 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 4 8 12 16 20 hour (UTC) 5.5 6.0 6.5 7.0 7.5 CTR % CTR 0 4 8 12 16 20 hour (UTC) 8 9 10 11 12 USD per 1,000 impressions CPM 0 4 8 12 16 20 hour (UTC) 14 15 16 17 18 installs / clicks % hour of day, pooled across the 6 days of the period — a pooling, not a timeline Click → install 0 4 8 12 16 20 hour (UTC) 0.8 0.9 1.0 1.1 USD Cost per install Delivery by hour — whole account, 2026-08-10..2026-08-15 (UTC)
CTR, CPM, click-to-install and CPI by hour, whole account

Against the prior period, hour matched to hour

Hours both periods delivered in, on the UTC clock: 00, 01, 02, 03, 04, 05, 06, 07, 08, 09, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23. Only the shared hours are compared. Each bucket pools that hour across the 6 days of the period, so the floor for reading one is 50 impressions a day, 300 across the period.

Counting which way each shared hour points, which needs no weighting and asks only for a direction:

metrichours 2026-08-10..2026-08-15 ran higherhours it ran lowersign test
CPM3 of 2421 of 24p = 0.000
CTR2 of 2422 of 24p = 0.000
click→install1 of 2423 of 24p = 0.000
CPI23 of 241 of 24p = 0.000

A sign test throws magnitude away and buys weight-free direction with it.

All four separate, and two contradict the pooled rows in section 5. When weighted and unweighted reads disagree this hard, the weights are the finding.

The weights sit in the earlier window's bucket 14 — the rejected spill build (DECISION_LOG.md #50), over a third of its impressions in one hour.

Click→install and CPI agree on both reads. The step from click to install is where this window lost its volume, and no weighting rescues it.

2026-08-16T16:04:13.399995 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 5 10 15 20 hour (UTC) 2 3 4 5 6 7 8 9 CTR % CTR 2026-08-03..2026-08-08 2026-08-10..2026-08-15 0 5 10 15 20 hour (UTC) 2 4 6 8 10 12 USD per 1,000 impressions CPM 0 5 10 15 20 hour (UTC) 10 15 20 25 installs / clicks % hour of day, pooled across the 6 days of the period — a pooling, not a timeline Click → install 0 5 10 15 20 hour (UTC) 0.6 0.7 0.8 0.9 1.0 1.1 USD Cost per install Delivery by hour — 2026-08-10..2026-08-15 against 2026-08-03..2026-08-08, shared hours only (UTC)
The same four ratios with the prior period laid over the period, shared hours only
The full hour-by-hour pairing, 2026-08-03..2026-08-08 → 2026-08-10..2026-08-15

Every shared hour, 2026-08-03..2026-08-08 → 2026-08-10..2026-08-15. All columns are Meta's instrument on both sides of each ratio. Revenue is deliberately absent: per-hour payer counts run 0-3, so an hourly revenue column would be one person's basket read as a rate.

hrimpressionsCPMCTRclick→installCPI
008,955 → 10,10211.45 → 9.687.59% → 6.46%24.7% → 14.7%0.611 → 1.018
0110,919 → 11,0139.30 → 9.087.62% → 5.59%20.9% → 14.0%0.583 → 1.163
0212,427 → 11,7689.17 → 9.367.13% → 5.80%21.0% → 15.5%0.613 → 1.039
0313,421 → 12,6769.02 → 9.207.19% → 5.76%22.2% → 15.6%0.566 → 1.023
0414,359 → 13,44910.17 → 8.287.16% → 5.80%23.2% → 15.5%0.611 → 0.921
0515,996 → 14,41210.33 → 8.127.26% → 5.47%22.4% → 17.7%0.635 → 0.835
0615,413 → 13,99610.34 → 8.767.64% → 5.51%24.9% → 15.2%0.544 → 1.048
0713,858 → 19,02011.04 → 9.717.23% → 6.81%21.6% → 14.6%0.709 → 0.977
0813,214 → 18,1229.83 → 8.726.84% → 6.13%21.0% → 16.2%0.683 → 0.878
0914,187 → 18,1949.55 → 8.876.34% → 5.94%23.7% → 16.1%0.636 → 0.927
1013,758 → 18,57810.42 → 9.256.45% → 5.85%22.2% → 15.8%0.728 → 0.999
1112,601 → 16,93410.67 → 9.266.56% → 6.04%22.8% → 15.0%0.715 → 1.025
1211,642 → 15,66411.06 → 9.876.52% → 6.40%20.8% → 14.8%0.815 → 1.045
1313,030 → 15,30311.36 → 8.796.63% → 6.88%22.9% → 15.8%0.748 → 0.810
14196,105 → 11,6271.42 → 12.202.07% → 7.60%6.5% → 17.4%1.057 → 0.921
1518,977 → 17,53910.03 → 9.617.88% → 6.78%19.5% → 16.4%0.652 → 0.865
1619,049 → 20,2539.63 → 8.507.24% → 5.95%18.7% → 17.3%0.711 → 0.823
1722,084 → 20,8999.70 → 8.886.90% → 6.13%20.4% → 14.6%0.691 → 0.993
1820,398 → 18,32010.62 → 9.617.26% → 6.34%21.4% → 17.4%0.683 → 0.872
1916,922 → 14,76711.62 → 10.487.59% → 6.15%23.1% → 18.1%0.662 → 0.944
2015,110 → 11,21211.62 → 9.828.13% → 6.89%24.8% → 17.2%0.576 → 0.828
2113,332 → 9,94912.72 → 11.868.69% → 6.96%23.5% → 16.6%0.624 → 1.026
2212,338 → 10,23312.74 → 10.208.54% → 6.75%23.8% → 14.8%0.626 → 1.023
2311,214 → 10,76013.22 → 9.318.05% → 6.47%22.6% → 18.2%0.727 → 0.789

4Country, 2026-08-10 to 2026-08-16

2026-08-23T13:56:10.952769 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ IN US GB MX ID PH TR MY AR CA AU DE 0 200 400 600 800 USD delivery raked onto the report clock against two measured margins; revenue is the report period Spend against within-day revenue by country — 2026-08-10..2026-08-16 spend within-day revenue
Spend against within-day revenue, by country
2026-08-23T13:56:10.990827 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ −0.04 −0.02 0.00 0.02 0.04 USD per install Cost per install by country — 2026-08-10..2026-08-16 (report clock)
Cost per install by country

(i) The portfolio by country, 2026-08-10..2026-08-16. On the report clock. Meta serves no hour x country grid, so each country cut is raked from its own Meta day onto UTC; our own columns were already there.

ccspendshareimpressionsCPMregistrations (ours)cost/regwithin-daywROASpayers
IN$927.0924.3%118,688$7.811,940$0.478$775.020.84140
US$528.5513.9%14,808$35.69347$1.523$654.941.2486
GB$148.823.9%6,569$22.65149$0.999$257.471.7322
MX$148.013.9%23,147$6.39382$0.387$132.010.8931
ID$140.693.7%24,701$5.70596$0.236$52.880.3820
PH$109.822.9%49,081$2.24465$0.236$72.000.6611
TR$91.182.4%5,037$18.10191$0.477$161.771.7717
MY$89.212.3%14,997$5.95192$0.465$65.320.7315
AR$85.512.2%6,983$12.25174$0.491$42.910.5015
CA$76.422.0%3,229$23.6764$1.194$143.331.8815
AU$70.931.9%2,735$25.9356$1.267$48.790.699
DE$65.911.7%2,080$31.6961$1.081$35.840.5414

207 further countries are not listed, $1,331.59 between them (34.9% of this block).

Absent from the table above, by name: HR1. Their spend is in every day-grain table; only their country split is missing.

(ii) The same cut per account, 2026-08-10..2026-08-16.

B1

ccspendshareimpressionsCPMregistrations (ours)cost/regwithin-daywROASpayers
IN$927.0924.3%118,688$7.811,521$0.610$509.320.55118
US$528.5513.9%14,808$35.69286$1.848$543.101.0374
GB$148.823.9%6,569$22.65129$1.154$245.391.6520
MX$148.013.9%23,147$6.39256$0.578$81.370.5525
ID$140.693.7%24,701$5.70315$0.447$27.940.2015
PH$109.822.9%49,081$2.24370$0.297$37.140.3410
TR$91.182.4%5,037$18.10132$0.691$128.741.4111
MY$89.212.3%14,997$5.95147$0.607$54.550.6112
AR$85.512.2%6,983$12.25131$0.653$32.930.3913
CA$76.422.0%3,229$23.6761$1.253$107.681.4114
AU$70.931.9%2,735$25.9348$1.478$14.520.207
DE$65.911.7%2,080$31.6956$1.177$35.840.5414

206 further countries are not listed, $1,331.59 between them (34.9% of this block).

Nomad Node

ccspendshareimpressionsCPMregistrations (ours)cost/regwithin-daywROASpayers
AE$0.000.0%0—18$0.000$0.00—0
AL$0.000.0%0—1$0.000$0.00—0
AM$0.000.0%0—3$0.000$34.99—1
AO$0.000.0%0—1$0.000$0.00—0
AR$0.000.0%0—43$0.000$9.98—2
AU$0.000.0%0—8$0.000$34.28—2
AZ$0.000.0%0—3$0.000$0.00—0
BA$0.000.0%0—3$0.000$0.00—0
BD$0.000.0%0—8$0.000$0.00—0
BE$0.000.0%0—2$0.000$0.00—0
BG$0.000.0%0—4$0.000$5.74—1
BN$0.000.0%0—2$0.000$0.00—0

102 further countries are not listed, $0.00 between them (0.0% of this block).

KBM1

ccspendshareimpressionsCPMregistrations (ours)cost/regwithin-daywROASpayers
US$0.000.0%0—9$0.000$4.99—1

HR1 — no country block: it delivered nothing on this day, a measured zero.

Reconciliation over the period. Every per-country cell is an allocation across hours; every total is measured. Each account's raked country total equals its bought spend for these days: B1 $3,813.74; Nomad Node $631.70; KBM1 $20.22. The per-day reconciliations, naming the Meta days each figure was raked from, are on the daily pages.

5Aggregate, both periods, B1

Pooled over the 24 hours both periods delivered in, on the UTC clock. Meta's instrument on both sides of every ratio.

spendimpressionsCPMclicksCTRinstallsclick→installCPI
2026-08-03..2026-08-08$3,812.43529,3097.2028,4475.37%5,66319.91%$0.673
2026-08-10..2026-08-15$3,329.00354,7909.3822,1526.24%3,55016.03%$0.938

Pooling across hours weights each hour by what it delivered. The hourly pairing is the unweighted read of the same two periods; where they disagree, the mix moved.

They disagree on two rows of four, and section 3 names why. Click→install and CPI agree on both reads; carry those two forward.

The mix-neutral account line, in section 6, reads CPM $6.73 → $9.38 on either mix: one campaign delivered here, so there is nothing to neutralise.

The three measures side by side

measure2026-08-03..2026-08-082026-08-10..2026-08-15moves after the period closes?
booked$8,146.98 (2.14)$8,384.94 (2.52)settled
within-day$3,976.77 (1.04)$2,542.76 (0.76)never
cohort @ 24h$4,939.27 (1.30) at 100%$3,227.88 (0.97) at 90%still rising

The three measures disagree, and within-day is the one to read: it cannot inherit. Cohort is 90% covered, so its 0.97 is a floor.

Booked revenue by how long its payer had been installed

installed2026-08-03..2026-08-082026-08-10..2026-08-15
the same day$3,976.77 (48.8%)$2,542.76 (30.3%)
one day earlier$1,251.12 (15.4%)$998.56 (11.9%)
two days earlier$940.70 (11.5%)$691.07 (8.2%)
three days earlier$473.53 (5.8%)$641.37 (7.6%)
four days earlier$401.58 (4.9%)$415.33 (5.0%)
five days earlier$192.61 (2.4%)$544.63 (6.5%)
six days earlier$425.87 (5.2%)$367.84 (4.4%)
seven days earlier$282.05 (3.5%)$602.49 (7.2%)

Over one day the same-day row and the within-day total are the same number seen twice. Over a window the split is by how long each payer had been installed, and the lag-0 row is still exactly the within-day total, which is what makes the split worth drawing.

Under a third of B1's booked revenue came from arrivals inside the window. The five- and seven-day rows rose; every row inside three days fell.

2026-08-16T16:04:13.677087 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ booked within-day cohort @ 24h 0 1000 2000 3000 4000 5000 6000 7000 8000 USD 2.14 1.04 1.30 2.52 0.76 0.97 the number above each bar is that measure's ROAS against the same period's spend The three revenue measures, 2026-08-03..2026-08-08 against 2026-08-10..2026-08-15 (UTC) 2026-08-03..2026-08-08 2026-08-10..2026-08-15
The three revenue measures on both periods, ROAS above each bar
2026-08-16T16:04:13.730582 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 2026-08-03..2026-08-08 2026-08-10..2026-08-15 0 1000 2000 3000 4000 5000 6000 7000 8000 USD the bottom segment IS the within-day figure: the same number seen twice Booked revenue by how long its payer had been installed (UTC) paid the day they installed one day after two days after three days after four or more days after
Booked revenue by how long its payer had been installed

6B1's campaigns, side by side

Delivery is Meta's instrument on both sides of every ratio; every revenue measure is ours. Cohort horizon H=24h. Report clock UTC. Rank on CPM, cost per click and CPI only — geography is the treatment here, which is what makes those comparable across campaigns, while revenue still needs 16 payers (DECISION_LOG.md #37, #48) and a campaign under that bar carries a direction and never a magnitude.

campaignspendshareimpressionsimpr shareCPMclicksCTRcost/clickinstallsCPIwithin-daywROASpayers
Worldwide$3,329.00100.0%354,790100.0%9.3822,1526.24%$0.1503,550$0.938$2,529.090.76210

Booking with no delivery, and excluded from every rate above: T1 (Jul 23) 0 installs (Meta), 1 registrations (ours), $0.00 within-day; T2 (Jul 23) 0 installs (Meta), 2 registrations (ours), $0.00 within-day; T3 (Jul 23) 0 installs (Meta), 13 registrations (ours), $0.00 within-day; T1 (Jul 25) 0 installs (Meta), 16 registrations (ours), $0.00 within-day; T2 (Jul 25) 0 installs (Meta), 22 registrations (ours), $0.00 within-day; T3 (Jul 25, India/SEA) 0 installs (Meta), 204 registrations (ours), $3.56 within-day; German (DE/AT/CH) 0 installs (Meta), 4 registrations (ours), $0.00 within-day; Earner (retired 08-03) 0 installs (Meta), 507 registrations (ours), $10.11 within-day. Counting them would put installs into the CPI denominator against spend that never happened.

Account CPM $6.73 → $9.38 (39.4%). Held to 2026-08-03..2026-08-08's campaign mix it is $9.38 (39.4%) — the difference between those two is the campaign mix.

One campaign delivered all six days; eight retired ones booked without delivering. Their revenue sits outside every rate above, lifting section 5's account total.

The standing charts for this section plot spend share, CPM and CPI by campaign across the run. One campaign has delivered on every day in the window, so all three would be a single flat line and the chart generator emits none.

7Inside B1's worldwide campaign

B1's worldwide campaign, which took 100.0% of B1's spend across the window: $3,329.00, 354,790 impressions, 3,550 installs at $0.938, and $2,529.09 of within-day revenue at a return of 0.76 from 210 payers.

Structure over the period

The five-cell split test ran into 08-11 and the campaign changed shape twice after it, so this window is not one regime.

Each asset sat alone in its own ad set, so the ad-set row is the asset row and the tables below are labelled by asset.

No per-asset comparison here is regime-matched: bikini and lounge ran only in the split test, bodysuit plus one day alone, pool5 mostly alone at three times the budget.

The same campaign, hour matched to hour

Sections 3 and 5 compare the whole of B1 across the two windows, and the earlier one also ran the earner and the German buys. Scoped to this campaign, both sides are the same campaign and the mix drops out.

Hours both periods delivered in, on the UTC clock: 00, 01, 02, 03, 04, 05, 06, 07, 08, 09, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23. Only the shared hours are compared. Each bucket pools that hour across the 6 days of the period, so the floor for reading one is 50 impressions a day, 300 across the period.

Counting which way each shared hour points, which needs no weighting and asks only for a direction:

metrichours 2026-08-10..2026-08-15 ran higherhours it ran lowersign test
CPM5 of 2419 of 24p = 0.007
CTR3 of 2421 of 24p = 0.000
click→install1 of 2423 of 24p = 0.000
CPI23 of 241 of 24p = 0.000

A sign test throws magnitude away and buys weight-free direction with it.

Dropping the other campaigns loosens CPM and leaves the other three alone. Click to install holds on every cut of these two windows.

2026-08-16T16:05:12.304928 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 5 10 15 20 hour (UTC) 2 3 4 5 6 7 8 9 CTR % CTR 2026-08-03..2026-08-08 2026-08-10..2026-08-15 0 5 10 15 20 hour (UTC) 2 4 6 8 10 12 USD per 1,000 impressions CPM 0 5 10 15 20 hour (UTC) 10 15 20 25 installs / clicks % hour of day, pooled across the 6 days of the period — a pooling, not a timeline Click → install 0 5 10 15 20 hour (UTC) 0.5 0.6 0.7 0.8 0.9 1.0 1.1 USD Cost per install Delivery by hour — 2026-08-10..2026-08-15 against 2026-08-03..2026-08-08, shared hours only (UTC)
The same four ratios with the prior period laid over the period, shared hours only
The full hour-by-hour pairing, worldwide campaign, 2026-08-03..2026-08-08 → 2026-08-10..2026-08-15

Every shared hour, 2026-08-03..2026-08-08 → 2026-08-10..2026-08-15. All columns are Meta's instrument on both sides of each ratio. Revenue is deliberately absent: per-hour payer counts run 0-3, so an hourly revenue column would be one person's basket read as a rate.

hrimpressionsCPMCTRclick→installCPI
008,845 → 10,10210.97 → 9.687.60% → 6.46%24.0% → 14.7%0.603 → 1.018
0110,847 → 11,0139.07 → 9.087.58% → 5.59%20.9% → 14.0%0.572 → 1.163
0212,320 → 11,7688.85 → 9.367.13% → 5.80%20.9% → 15.5%0.593 → 1.039
0313,224 → 12,6768.52 → 9.207.18% → 5.76%22.3% → 15.6%0.531 → 1.023
0413,567 → 13,4499.38 → 8.287.02% → 5.80%23.2% → 15.5%0.576 → 0.921
0513,679 → 14,4129.63 → 8.126.94% → 5.47%23.1% → 17.7%0.602 → 0.835
0612,631 → 13,9969.31 → 8.767.43% → 5.51%24.0% → 15.2%0.523 → 1.048
0710,607 → 19,0209.96 → 9.716.91% → 6.81%21.0% → 14.6%0.686 → 0.977
089,649 → 18,1229.66 → 8.726.45% → 6.13%19.8% → 16.2%0.758 → 0.878
0910,284 → 18,1949.26 → 8.875.78% → 5.94%22.1% → 16.1%0.727 → 0.927
1010,397 → 18,57810.28 → 9.256.05% → 5.85%21.0% → 15.8%0.809 → 0.999
1111,415 → 16,93410.51 → 9.266.23% → 6.04%21.1% → 15.0%0.800 → 1.025
1211,484 → 15,66410.65 → 9.876.53% → 6.40%20.0% → 14.8%0.815 → 1.045
1312,902 → 15,30311.06 → 8.796.65% → 6.88%22.1% → 15.8%0.751 → 0.810
14195,854 → 11,6271.36 → 12.202.06% → 7.60%6.4% → 17.4%1.034 → 0.921
1518,683 → 17,5399.24 → 9.617.89% → 6.78%19.2% → 16.4%0.610 → 0.865
1618,794 → 20,2539.17 → 8.507.28% → 5.95%18.5% → 17.3%0.681 → 0.823
1721,871 → 20,8999.29 → 8.886.88% → 6.13%20.1% → 14.6%0.670 → 0.993
1820,176 → 18,32010.32 → 9.617.30% → 6.34%21.3% → 17.4%0.663 → 0.872
1916,758 → 14,76711.41 → 10.487.63% → 6.15%22.9% → 18.1%0.653 → 0.944
2014,962 → 11,21211.29 → 9.828.14% → 6.89%24.6% → 17.2%0.563 → 0.828
2113,003 → 9,94911.99 → 11.868.72% → 6.96%23.1% → 16.6%0.595 → 1.026
2212,042 → 10,23312.08 → 10.208.61% → 6.75%23.6% → 14.8%0.594 → 1.023
2311,047 → 10,76012.33 → 9.318.07% → 6.47%22.3% → 18.2%0.685 → 0.789

The same campaign, both windows pooled

Pooled over the 24 hours both periods delivered in, on the UTC clock. Meta's instrument on both sides of every ratio.

spendimpressionsCPMclicksCTRinstallsclick→installCPI
2026-08-03..2026-08-08$3,399.41505,0416.7326,4795.24%5,13319.39%$0.662
2026-08-10..2026-08-15$3,329.00354,7909.3822,1526.24%3,55016.03%$0.938

Pooling across hours weights each hour by what it delivered. The hourly pairing is the unweighted read of the same two periods; where they disagree, the mix moved.

The account's headline movement survives taking the campaign mix out: almost the same money in both windows, a third fewer installs.

The $6.73 here is the baseline the mix-neutral line uses, against $7.20 for the account earlier; the difference is the earner and the German buys.

A. Per asset — delivery

Meta's instrument on both sides of every ratio. Our registrations never enter this table.

assetspendimpressionsCPMclicksCTRinstallsclick→installCPI
E2/pool5$1,768.24222,8327.9414,2906.41%2,07714.53%$0.851
E2/bodysuit$860.6773,46511.724,0735.54%84220.67%$1.022
E2/bikini$355.3727,04113.141,7366.42%33319.18%$1.067
E2/lounge$344.7231,45210.962,0536.53%29214.22%$1.181
E2/mugshot$0.000—0—0——
E2/spill$0.000—0—0——
E2/spill2$0.000—0—6—$0.000

B. Per asset — the three revenue measures

Ours on every column. Meta can express only booked, so it rides bracketed beside that column and never as a row. Payers are distinct people, never transactions. Cohort horizon H=24h, 90% covered on this period. Report clock UTC.

assetbookedbROAS (Meta)within-daywROAScohort@HcROASpayerspayer%ARPUARPPUlargest payer
E2/pool5$3,250.191.84 (2.20)$1,623.700.92$1,959.201.111356.0%0.72012.035.6%
E2/bodysuit$1,834.612.13 (1.99)$530.540.62$675.840.79515.2%0.54410.407.2%
E2/bikini$565.221.59 (1.42)$149.440.42$158.930.4592.3%0.38416.6045.8%
E2/lounge$929.302.70 (2.61)$225.410.65$268.590.78154.8%0.71815.0318.9%
E2/mugshot$5.74— (—)$0.00—$0.00—00.0%0.000——
E2/spill$0.00— (—)$0.00—$0.00—00.0%0.000——
E2/spill2$631.99— (—)$0.00—$148.31—00.0%0.000——

The 16-payer bar (#37): any row above whose payer count is under 16 is a direction and never a magnitude.

Two rows clear the 16-payer bar and two do not, so lounge's 0.65 and bikini's 0.42 are directions; pool5 and bodysuit bought under different budgets.

pool5's revenue is the least concentrated the series has produced; nearly half of bikini's is one payer.

The instrument disagreement is per asset as well as per country. The account-level gate of 1.09 is the sum of rows pulling both ways.

C. Per asset — country mix

⚠ This table is cut on the META day, while every other table on this page is on the UTC clock. Meta serves no hour × country grid, so per-country delivery exists only on the ad account's own UTC-7 day and cannot be restitched. It is a seven-hour-offset window against tables A and B above; read it for mix, never for level against them.

The last column is the share of that asset's own within-day revenue that came from the United States: where it far exceeds the US spend share, the return is a property of the geography the asset bought.

assetspendIndia %US %other %US % of its revenue
E2/pool5$1,811.7923.3%13.9%62.8%13.4%
E2/bodysuit$840.0531.6%13.1%55.3%28.6%
E2/bikini$324.5728.1%14.0%57.8%7.3%
E2/lounge$313.4819.0%10.0%71.0%33.6%

Only pool5's American revenue share is close to its spend share. Of the two readable rows, the higher return leans on the United States least.

India took a third of bodysuit's buy and a fifth of lounge's, at 0.53 within-day for the account — a lower ceiling before creative.

The regime read

A regime is a stretch over which the ad set's daily budget did not change. It matters because the budget is a geography dial on this account: raising it buys wider and cheaper countries, so two creatives measured across a budget change are compared on different audiences (DECISION_LOG.md #47).

Three of them here, and no comparison in this window is regime-matched: four arms at $150 each until 07:00 UTC on 08-11, bodysuit alone at $450 from 20:22 UTC on 08-11, pool5 alone at $450 from 21:18 UTC on 08-12.

The period across the run

2026-08-16T16:05:12.697373 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 2 4 6 8 10 12 14 16 18 20 22 hour (UTC) 4 5 6 7 8 CTR % hour of day, pooled across the 6 days of the period — a pooling, not a timeline CTR by hour — every asset, 2026-08-10..2026-08-15 (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge
CTR by hour, one line per asset
2026-08-16T16:05:12.820284 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 2 4 6 8 10 12 14 16 18 20 22 hour (UTC) 5 10 15 20 25 30 installs / clicks % hour of day, pooled across the 6 days of the period — a pooling, not a timeline Click → install by hour — every asset, 2026-08-10..2026-08-15 (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge
Click-to-install by hour, one line per asset
2026-08-16T16:05:12.881804 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 2 4 6 8 10 12 14 16 18 20 22 hour (UTC) 0.5 1.0 1.5 2.0 2.5 3.0 3.5 4.0 4.5 USD hour of day, pooled across the 6 days of the period — a pooling, not a timeline Cost per install by hour — every asset, 2026-08-10..2026-08-15 (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge
Cost per install by hour, one line per asset
2026-08-16T16:05:12.760464 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 0 2 4 6 8 10 12 14 16 18 20 22 hour (UTC) 6 8 10 12 14 16 18 20 22 USD per 1,000 impressions hour of day, pooled across the 6 days of the period — a pooling, not a timeline CPM by hour — every asset, 2026-08-10..2026-08-15 (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge
CPM by hour, one line per asset
2026-08-16T16:05:12.995442 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ E2/pool5 E2/bodysuit E2/bikini E2/lounge 0 20 40 60 80 100 % of that asset's spend Where each asset bought — share of its own spend by region, 2026-08-10..2026-08-15 (META days) IN US ID MX GB PH other
Where each asset bought: share of its own spend by region
2026-08-16T16:05:13.072808 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ E2/pool5 E2/bodysuit E2/bikini E2/lounge 0 1 2 3 4 5 USD per install Cost per install by region — every asset, 2026-08-10..2026-08-15 (META days) IN US ID MX GB PH
Cost per install by region, every asset
2026-08-16T16:05:13.125642 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ E2/pool5 E2/bodysuit E2/bikini E2/lounge 0 50 100 150 200 250 300 350 USD Within-day revenue by region — every asset, 2026-08-10..2026-08-15 (META days) IN US ID MX GB PH
Within-day revenue by region, every asset
2026-08-16T16:05:13.215145 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 08-10 08-11 08-12 08-13 08-14 08-15 day (UTC) 0 2 4 6 8 10 payers / installs % Payer rate by day — every asset (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge E2/spill2
Payer rate by day, one line per asset
2026-08-16T16:05:13.270638 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 08-10 08-11 08-12 08-13 08-14 08-15 day (UTC) 0.0 0.2 0.4 0.6 0.8 1.0 1.2 within-day USD per install ARPU by day — every asset (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge E2/spill2
ARPU by day, one line per asset
2026-08-16T16:05:13.322917 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 08-10 08-11 08-12 08-13 08-14 08-15 day (UTC) 0 5 10 15 20 25 within-day USD per payer ARPPU by day — every asset (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge
ARPPU by day, one line per asset
2026-08-16T16:05:13.377204 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ 08-10 08-11 08-12 08-13 08-14 08-15 day (UTC) 0.4 0.6 0.8 1.0 1.2 1.4 1.6 1.8 revenue / spend Within-day ROAS by day — every asset (UTC) E2/pool5 E2/bodysuit E2/bikini E2/lounge
Within-day ROAS by day, one line per asset
2026-08-16T16:05:13.447067 image/svg+xml Matplotlib v3.11.1, https://matplotlib.org/ CTR click→install CPI payer rate * ARPU * wROAS * 0.0 0.2 0.4 0.6 0.8 1.0 normalised across the period (1.0 = best of the pack) * axis sits under the 16-payer bar on most days: direction only, never a level. Assets under 20 installs on the period are not plotted. Composite — every asset across every measure, 2026-08-10..2026-08-15 E2/pool5 E2/bodysuit E2/bikini E2/lounge
Composite: every asset across every measure, normalised across the period

Money-chart markers are hollow where the point sits under 16 payers, and assets under 20 installs on the day are dropped from the composite and the region charts. Delivery is plotted hourly because CTR, click-to-install, CPI and CPM are single-clock quantities on hundreds to thousands of impressions an hour. Money is plotted per day, because payers run 0 to 2 per asset per hour and an hourly ARPPU is one person's basket. There is deliberately no hourly revenue chart.

8Caveats

⚠⚠ This is six of seven days and both windows are six days long on purpose. 2026-08-16 had not closed when the data was cut, so the week is 08-10 to 08-15. The week before it ran 08-03 to 08-09, and the comparison uses its matched six days, 08-03 to 08-08. Levels are therefore comparable between the two columns of every table on this page. Set against a full seven-day week, every total here would read as a fall that is nothing but the missing day.

⚠ The cohort figure is 90% covered, so every cohort number on this page is a floor. Coverage runs 100% through hour bucket 10 and 76% to 85% after it, because the payment cut is 2026-08-16 10:59 UTC and the last day's later installs have not lived their 24 hours. The 0.97 on this page will rise. It cannot be set against the earlier window's frozen 1.30 as though the two were the same kind of number, and every window-over-window claim above rests on within-day, which is sealed at midnight.

⚠ The instrument gate reads 1.09 on the META clock, outside the documented 0.91 to 1.06 band. Our records booked $8,255.22 on B1's own days against Meta's $7,594.11. That reading is B1-scoped on both sides: measures.py selects Meta rows by Ad ID against the run config's map and the shared accounts' ads are not in it, so the gap is B1's own. The gate bounds any sentence that compares our number against Meta's, and the bracketed (Meta) columns are the only place on this page it applies. It does not touch within-day or cohort@24h, which never read Meta's revenue column at all. The UTC-clock run prints its own ratio beside the campaign aggregate and marks it as not a valid check, because Meta's conversion value sits on its conversion hour and cannot be restitched into a UTC day. The figure quoted here is the META-clock one.

⚠ The two accounts are on different clocks and neither offset is assumed. B1 is fixed at UTC-7, so its UTC day is stitched from two account days. The Nomad Node accounts run on UTC+0, so their reporting day is the UTC day and nothing is stitched; stitching them on B1's offset would move their spend seven hours. Both offsets were recovered from data by correlating each account's hourly impressions against our own registrations from its campaigns, which are true UTC, and the derivation lives in ad_ops/daily_report_format.md.

⚠ The comparison window contains 2026-08-03, and one hour of it owns two of the pooled rows. The rejected spill build put 181,927 impressions into hour bucket 14 of that window at CPM 0.52 and CTR 1.60% on $95.44 of spend (DECISION_LOG.md #50). That is most of what holds the earlier window's pooled CPM at 7.20 and its pooled CTR at 5.37%, and it is why those two comparisons invert when the same hours are matched one to one. Nothing about this window's buying is in either baseline.

⚠ The window spans two budget changes and a change of arms. Four arms at $150 through 08-11, one arm at $450 after it, with the arm itself swapped on 08-12. No per-asset comparison on this page is regime-matched, and nothing here can say whether the account-level CPI rise came from the auction or from the budget.

The shared accounts enter section 2 and no other table on this page. Their export carries no Ad ID, so every table from section 3 down scopes to the ad ids in the run config and that traffic is not among them. Their column preset is not ours to control, and the only join key their files offer is the ad set name, which is not a key this report will select on. Their column also covers five days against B1's six, which is a further reason the two rows are read on rates.

The country section and table C are B1's own account days, seven hours offset from every other table. They are read for mix, never for level.

The FX table is two weeks old. Revenue in 33 currencies is converted at rates pulled on 2026-08-02, and it prices every day in this window.

9What would settle the open questions

Whether the auction got dearer or the budget bought it. CPI rose from $0.673 to $0.938 across a window that changed shape twice, and both explanations fit. A week left untouched at one budget on one arm answers it at no extra cost, and the account has been in that state since 08-12.

Whether the shared buy's 1.52 survives its own cohort ageing. It leads B1 on both measures that cannot inherit, on five days of history and a payer count this cut does not carry. Two more weeks of it under the same per-account battery would say whether the cheap install keeps paying or whether the lead is the youth of the cohort read from the other side.

Whether the 1.09 gate is the FX table. With the payment join repaired, the FX table's age is the last named candidate in the instrument reconciliation and it has never been tested. Repricing this window at current rates is an afternoon and it closes the file.

10What this hands to the next read

The next weekly inherits one arm at one budget, two ad accounts buying from its first hour to its last, and a cohort that will be fully matured when it is cut. It can do what this one cannot, which is read the CPI level as a fact about the buy.

It also inherits a comparison window free of the spill hour on both sides, so its pooled CPM and CTR rows will agree with its hour-matched ones or disagree for a reason that is about buying.

11Reproduce

Report clock UTC. B1's exports are stamped in its own account zone (UTC-7), so every B1 delivery row is restitched from two Meta days; the Nomad Node exports are stamped UTC+0 and are not restitched. The country tables and table C are not restitched and are labelled where they appear.

run_runs/2026-08-16_periods/
the account split, section 2_runs/2026-08-16_receipt_series/portfolio_split.py, window rows in portfolio_periods.txt; the shared accounts' hourly exports under acct2/
payment cut2026-08-16 10:59 UTC, which is 2026-08-16 03:59 on B1's own clock
Meta exportsday and country×day pulled as one range; hourly per day, all 24 buckets verified
registrationsadjust_sink push merged onto the Telegram-parsed ledger, carrying the account UUID the payment join needs
paymentsin-app-purchase API, full history, joined on the numeric user id where present and on the account UUID where not
FX_runs/2026-08-02_today_read/fx_rates.json
regimesthe budget changes are taken from the 08-11 and 08-12 dailies, which recorded them from the campaign's activity history on the day
python -m ad_ops.measures      --config _runs/2026-08-16_periods/run_config.json \
    --period 2026-08-10..2026-08-15 --prev-period 2026-08-03..2026-08-08
python -m ad_ops.report_tables --config _runs/2026-08-16_periods/run_config.json \
    --period 2026-08-10..2026-08-15 --prev-period 2026-08-03..2026-08-08 --campaign-table
python -m ad_ops.report_charts --config _runs/2026-08-16_periods/run_config.json \
    --period 2026-08-10..2026-08-15 --out ad_ops/figures/week_2026-08-10 \
    --md _runs/2026-08-16_periods/chartblock_week_2026-08-10.md --relpath figures/week_2026-08-10

The same three instruments the dailies run, over a window instead of a day, on both the UTC and the META configs. The META run is what the instrument gate is read from; the UTC run is everything else on this page.

12Appendix — definitions

The report clock is a UTC day, and this report is six of them. Adjust reports in UTC, so a UTC-bucketed report lines up with the attribution dashboard without anyone converting in their head. B1 is fixed at UTC-7, so a UTC day on that account is account day D−1 17:00 to 23:59 plus account day D 00:00 to 16:59. The Nomad Node accounts run on UTC+0 and are not restitched.

The hourly axis is hour of day pooled across the window. Six days of an hour land in one bucket, so a bucket must clear 300 impressions before it is compared, against 50 on a single day. Read those tables and charts for diurnal shape and never as a timeline.

Three things the clock does not reach, each labelled where it appears. Table C's per-asset country mix cannot follow it: the rake is per ACCOUNT, against that account's own hourly margin, and an asset has no hourly margin of its own. The instrument check is invalid off the account's clock, because Meta's conversion value sits on its conversion hour and cannot honestly be restitched. And the estimator runs on Meta's clock deliberately, because its subject is delivery windows and a budget change is an instant on the account's own clock.

The three revenue measures, never one, never mixed, always labelled:

measurecountsmoves after the period closes?
bookedrevenue that arrived inside the window, whatever day its payer installedsettles about four hours after midnight, then fixed. Meta's own number is this basis
within-dayinstalled on a day and paid before that day closednever. Sealed at midnight
cohort at Heach day's installs, counted within H hours of each person's own install. House horizon H=24rises until every install has lived H hours, then frozen. Always state coverage

A window whose spend is falling reads high on booked and low on the other two, purely because the buyers it inherited are still paying. Use within-day for window-over-window, because it is immutable and needs no horizon. Use cohort at a fixed horizon to compare hours to each other, because within-day censors by hour of day. Booked is what Meta will quote at you, so it is reported to explain the gap and never to rank.

Over a window, booked splits by how long each payer had been installed. The lag-0 row of that split is exactly the within-day total, which is the identity that makes the split worth drawing.

Two install counts exist and they are never crossed. Meta's Leads and our own registrations disagree by 5 to 10%. Meta's is used for the delivery funnel, so CPI and click→install have both numerator and denominator on one instrument. Ours is used for payer rate and every revenue measure, so the payers and the installs they came from are the same population.

A regime is a stretch over which the ad set's daily budget did not change. The budget is a geography dial on this account, so two creatives measured across a budget change were compared on different audiences. This window holds three regimes: four arms at $150 each, bodysuit alone at $450, and pool5 alone at $450.

The 16-payer bar (DECISION_LOG.md #37): below roughly 16 payers a revenue figure is a direction and not a magnitude. Revenue per install on this account is a near-zero vector with rare large entries, so separating two creatives by 20% needs of the order of fifteen thousand installs per arm, which no arm on this account has reached.

Internal — noindex. Not for distribution outside the team.