Skip to content

Commit 6dcf4e5

Browse files
docs: PPE docs improvements (#1948)
1 parent 4b8bb6e commit 6dcf4e5

File tree

6 files changed

+233
-78
lines changed

6 files changed

+233
-78
lines changed

apify-api/openapi/paths/actor-runs/actor-runs@{runId}@charge.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,12 @@ post:
77
The event you are charging for must be one of the configured events in your Actor. If the Actor is not set up as pay per event, or if the event is not configured,
88
the endpoint will return an error. The endpoint must be called from the Actor run itself, with the same API token that the run was started with.
99
10+
:::info Learn more about pay-per-event pricing
11+
12+
For more details about pay-per-event (PPE) pricing, refer to our [PPE documentation](/platform/actors/publishing/monetize/pay-per-event).
13+
14+
:::
15+
1016
operationId: PostChargeRun
1117
parameters:
1218
- name: runId

sources/academy/ai/ai-agents.mdx

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -251,6 +251,12 @@ Common issues and solutions:
251251

252252
Apify's pay-per-event (PPE) pricing model allows charging users based on specific triggered events through the API or SDKs.
253253

254+
:::info How pay-per-event pricing works
255+
256+
If you want more details about PPE pricing, refer to our [PPE documentation](/platform/actors/publishing/monetize/pay-per-event).
257+
258+
:::
259+
254260
### Step 1: Define chargeable events
255261

256262
You can configure charges for events like the Actor starting, a task completing successfully, or custom events such as specific API calls.

sources/academy/platform/get_most_of_actors/store_basics/how_actor_monetization_works.md

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,11 @@ Monetizing your Actor on the Apify platform involves several key steps:
3333
- 2nd user starts their trial but pays next month.
3434
- 3rd user on a free plan finishes the trial without upgrading to a paid plan and can’t use the Actor further.
3535

36-
Learn more about the rental pricing model in our [documentation](/platform/actors/publishing/monetize#rental-pricing-model).
36+
:::info Rental pricing details
37+
38+
If you want more details about rental pricing, refer to our [rental pricing documentation](/platform/actors/publishing/monetize/rental).
39+
40+
:::
3741

3842
### Pay-per-result pricing model
3943

@@ -49,7 +53,11 @@ Learn more about the rental pricing model in our [documentation](/platform/actor
4953
- Dataset storage: $1 per 1,000 GB-hours
5054
- _Example_: you set a price of $1 per 1,000 results. Two users generate 50,000 and 20,000 results, paying $50 and $20, respectively. If the platform usage costs are $5 and $2, your profit is $49.
5155

52-
Learn more about the pay-per-result pricing model in our [documentation](/platform/actors/publishing/monetize#pay-per-result-pricing-model).
56+
:::info Pay-per-result details
57+
58+
If you want more details about PPR pricing, refer to our [PPR documentation](/platform/actors/publishing/monetize/pay-per-result).
59+
60+
:::
5361

5462
### Pay-per-event pricing model
5563

@@ -77,7 +85,11 @@ Learn more about the pay-per-result pricing model in our [documentation](/platfo
7785
- This comes up to $1.625 of total revenue
7886
- That means if platform usage costs are $0.365 for user A and $0.162 for user B your profit is $4.748
7987

80-
Learn more about the pay-per-event pricing model in our [documentation](/platform/actors/publishing/monetize#pay-per-event-pricing-model).
88+
:::info Pay-per-event details
89+
90+
If you want more details about PPE pricing, refer to our [PPE documentation](/platform/actors/publishing/monetize/pay-per-event).
91+
92+
:::
8193

8294
## Setting up monetization
8395

sources/platform/actors/publishing/monetize/index.mdx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ The following table compares the two main pricing models available for monetizin
3535
| AI/MCP compatibility | ❌ Not compatible | ✅ Fully compatible | ✅ Fully compatible |
3636
| User cost predictability| Unpredictable (rental + usage) | Predictable | Predictable |
3737
| Store discounts | ❌ Single price only | ✅ Store discounts available | ✅ Store discounts available |
38-
| Marketing boost | Standard visibility | Priority store placement | Priority store placement |
38+
| Marketing boost | Standard visibility | Standard visibility | Priority store placement |
3939
| Commission opportunities| Standard 20% | Standard 20% | Promotional 0% periods |
4040
| Custom event billing | Not available | Not available | ✅ Charge for any event |
4141
| Per-result billing | Not available | ✅ Charge per dataset item | Optional (via event) |

sources/platform/actors/publishing/monetize/pay_per_event.mdx

Lines changed: 129 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,11 @@ The PPE pricing model offers a flexible monetization option for Actors on Apify
1616

1717
PPE lets you define pricing for individual events. You can charge for specific events directly from your Actor using the [JS](/sdk/js/reference/class/Actor#charge)/[Python](/sdk/python/reference/class/Actor#charge) SDK, or by calling the [PPE charging API](/api/v2/post-charge-run) directly. Common events include Actor start, dataset item creation, and external API calls.
1818

19-
The details on how your cost is computed can be found in [Example of a PPE pricing model](#example-of-a-ppe-pricing-model).
19+
The details on how your cost is computed can be found in [Example of a PPE pricing](#example-of-a-ppe-pricing).
2020

2121
:::tip Additional benefits
2222

23-
Actors that implement PPE pricing receive additional benefits, including increased visibility in Apify Store and enhanced discoverability for users looking for monetized solutions.
23+
Actors that implement PPE pricing receive additional benefits, including increased visibility in Apify Store and enhanced discoverability.
2424

2525
:::
2626

@@ -132,44 +132,36 @@ When using [Crawlee](https://crawlee.dev/), use `crawler.autoscaledPool.abort()`
132132

133133
## Best practices for PPE Actors
134134

135-
Use our SDKs ([JS](/sdk/js/) and, [Python](/sdk/python/) or use [`apify actor charge`](/cli/docs/next/reference#apify-actor-charge-eventname) when using our Apify CLI) to simplify PPE implementation into your Actor. This tool can handle pricing, usage tracking, idempotency keys, API errors, and, event charging via an API.
135+
Use our [SDKs](/sdk) (JS and, Python or use [`apify actor charge`](/cli/docs/next/reference#apify-actor-charge-eventname) when using our Apify CLI) to simplify PPE implementation into your Actor. SDKs help you handle pricing, usage tracking, idempotency keys, API errors, and, event charging via an API. You can also choose not to use it, but then you must handle API integration and possible edge cases manually.
136136

137-
You can also choose not to use it, but then you must handle API integration and possible edge cases manually.
138-
139-
### Set memory limits
140-
141-
Set memory limits using `minMemoryMbytes` and `maxMemoryMbytes` in your [`actor.json`](https://docs.apify.com/platform/actors/development/actor-definition/actor-json) file to control platform usage costs.
142-
143-
```json
144-
{
145-
"actorSpecification": 1,
146-
"name": "name-of-my-scraper",
147-
"version": "0.0",
148-
"minMemoryMbytes": 512,
149-
"maxMemoryMbytes": 1024,
150-
}
151-
```
137+
### Use synthetic start event `apify-actor-start`
152138

153-
:::note Memory requirements for browser-based scraping
139+
:::info Synthetic Actor recommended
154140

155-
When using browser automation tools like Puppeteer or Playwright for web scraping, increase the memory limits to accommodate the browser's memory usage.
141+
We recommend using the synthetic Actor start event in PPE Actors. It benefits both you and your users.
156142

157143
:::
158144

159-
### Use synthetic start event `apify-actor-start`
160-
161-
This event is automatically charged by the Apify platform when an Actor is started or resurrected.
145+
Starting an Actor takes time, and creates additional cost for the Actor creator, because the profit equals revenue minus platform costs.
162146

163-
Users of your Actor are charged one event for each GB of memory used by the Actor (at least one event per run). We _strongly_ suggest setting the price of this event to $0.0001 to remain competitive in the Store and attractive for your customers. If you define this event, you also save 5 seconds of Actor runtime from each Actor run, which won't be deducted from your payout profits.
147+
One of the options to charge for the time spent on starting the Actor is to charge an “Actor start” event. Unfortunately, this makes your Actor comparably expensive with other tools on the market (outside of [Apify Store](/platform/console/store)) that do not incur this startup cost.
164148

165-
:::note Automatic charging of synthetic start event
149+
We want to make it easier for Actor creators to stay competitive, but also help them to be profitable. Therefore, we have the Apify Actor synthetic start event `apify-actor-start`. This event is enabled by default for all new PPE Actors, and when you use it Apify will cover the compute unit cost of the first 5 seconds of every Actor run.
166150

167-
You must _not_ manually charge for the synthetic start event (`apify-actor-start`) in your Actor code.
151+
The default price of the event is set intentionally low. This pricing means that the free 5 seconds of compute we provide costs us more than the revenue generated from the event. We've made this investment to _support our creator community_ by reducing your startup costs while keeping your Actors competitively priced for users.
168152

169-
If you attempt to charge this event yourself, the operation will fail.
170-
This event is _always_ charged automatically by the Apify platform whenever your Actor starts or is resurrected.
153+
#### How the synthetic start event works
171154

172-
:::
155+
- The Apify Actor start event is _automatically enabled_ for all new PPE Actors. For existing Actors, you can enable it in Apify Console.
156+
- Apify _automatically charges_ the event.
157+
- You must _not_ manually charge for the synthetic start event (`apify-actor-start`) in your Actor code. If you attempt to charge this event yourself, the operation will fail.
158+
- The default price of the event is _$0.00005_, which equals _$0.05 per 1,000 starts_. We recommend keeping the default price to keep your Actors competitive.
159+
- The number of events charged _depends on the memory_ of the Actor run. Up to and including 1 GB of RAM, the event is charged once. Then it's charged once for each extra GB of memory. For example:
160+
- 128 MB RAM: 1 event, $0.00005
161+
- 1 GB RAM: 1 event, $0.00005
162+
- 4 GB RAM: 4 events, $0.0002
163+
- You can increase the price of the event if you wish, but you _won't get more free compute_.
164+
- You can delete the event if you wish, but if you do, you will _lose the free 5 seconds_ of compute.
173165

174166
#### Synthetic start event for new Actors
175167

@@ -179,18 +171,40 @@ For new Actors, this event is added automatically as you can see on the followin
179171

180172
#### Synthetic start event for existing Actors
181173

182-
If you have existing Actors, you can add this event manually in Apify Console.
174+
If you have existing Actors, you can add this event manually in Apify Console in the **Publication** tab.
183175

184176
#### Synthetic start event for Actors with start event
185177

186178
Your Actor might already have a start event defined, such as `actor-start` or another variant of the event name. In this case, you can choose whether to use the synthetic start event or keep the existing start event.
187179

188-
If you want to use the synthetic start event, remove the existing start event from your Actor and add the synthetic start event in Apify Console.
180+
If you want to use the synthetic start event, remove the existing start event from your Actor and add the synthetic start event in Apify Console in the **Publication** tab.
181+
182+
### Set memory limits
183+
184+
Set memory limits using `minMemoryMbytes` and `maxMemoryMbytes` in your [`actor.json`](https://docs.apify.com/platform/actors/development/actor-definition/actor-json) file to control platform usage costs.
185+
186+
```json
187+
{
188+
"actorSpecification": 1,
189+
"name": "name-of-my-scraper",
190+
"version": "0.0",
191+
"minMemoryMbytes": 512,
192+
"maxMemoryMbytes": 1024,
193+
}
194+
```
195+
196+
:::note Memory requirements for browser-based scraping
197+
198+
When using browser automation tools like Puppeteer or Playwright for web scraping, increase the memory limits to accommodate the browser's memory usage.
199+
200+
:::
189201

190202
### Charge for invalid input
191203

192204
Charge for things like URLs that appear valid but lead to errors (like 404s) since you had to open the page to discover the error. Return error items with proper error codes and messages instead of failing the entire Actor run.
193205

206+
The snippet below shows how you can charge for invalid inputs using `Actor.pushData` when a dataset item is created and the `scraped-result` event is charged.
207+
194208
<Tabs groupId="main">
195209
<TabItem value="JavaScript" label="JavaScript">
196210

@@ -279,9 +293,9 @@ However, we acknowledge that some events don't produce tangible results (such as
279293

280294
Examples:
281295

282-
- _`scraped-product` event_: Each charge adds one product record to the dataset
283-
- _`processed-image` event_: Each charge adds one processed image to the dataset
284-
- _`extracted-review` event_: Each charge adds one review to the dataset
296+
- _`post` event_: Each charge adds one social media post to the dataset
297+
- _`profile` event_: Each charge adds one user profile to the dataset
298+
- _`processed-image` event_: Each charge adds one processed image to the dataset
285299
- _`ai-analysis` event_: Each charge processes one document through an AI workflow (no tangible output, but valuable processing)
286300

287301
:::note Additional context
@@ -294,35 +308,97 @@ You can display a status message or push a record to the dataset to inform users
294308

295309
If you're not using the Apify SDKs (JS/Python), you need to handle idempotency (ensuring the same operation produces the same result when called multiple times) manually to prevent charging the same event multiple times.
296310

297-
## Example of a PPE pricing model
311+
## Example of a PPE pricing
298312

299-
You make your Actor PPE and set the following pricing:
313+
You create a social media monitoring Actor with the following pricing:
300314

301-
- _`actor-start` event_: $0.10 per start
302-
- _`scraped-product` event_: $0.01 per product
303-
- _`scraped-product-detail` event_: $0.05 per detail
304-
- _`ai-analysis` event_: $0.15 per analysis
315+
- `post`: $0.002 per post - count every social media post you extract.
316+
- `profile`: $0.005 per profile - count every user profile you extract.
317+
- `sentiment-analysis`: $0.01 per post - count every post analyzed for sentiment, engagement metrics, and content classification using external LLM APIs.
305318

306-
During the first month, three users use your Actor:
319+
:::info Fixed pricing vs. usage-based pricing
307320

308-
- _User 1 (paid plan)_: Starts Actor 5 times, scrapes 1,000 products, makes 50 product details, runs 30 AI analyses
309-
- Charges: 5 × $0.10 + 1,000 × $0.01 + 50 × $0.05 + 30 × $0.15 = $0.50 + $10.00 + $2.50 + $4.50 = $17.50
310-
- _User 2 (paid plan)_: Starts Actor 2 times, scrapes 500 products, makes 20 product details, runs 10 AI analyses
311-
- Charges: 2 × $0.10 + 500 × $0.01 + 20 × $0.05 + 10 × $0.15 = $0.20 + $5.00 + $1.00 + $1.50 = $7.70
312-
- _User 3 (free plan)_: Starts Actor 1 time, scrapes 100 products, makes 5 product details, runs 3 AI analyses
313-
- Charges: 1 × $0.10 + 100 × $0.01 + 5 × $0.05 + 3 × $0.15 = $0.10 + $1.00 + $0.25 + $0.45 = $1.80
321+
You have two main strategies for charging AI-related operations:
314322

315-
Let's say the underlying platform usage for the first user is $3.20, for the second $1.50, and for the third $0.40.
323+
1. _Fixed event pricing_ (like `sentiment-analysis` above): Charge a fixed amount per operation, regardless of actual LLM costs
324+
2. _Usage-based pricing_: Use events like `llm-token` that charge based on actual LLM usage costs
316325

317-
Your profit is computed only from the first two users, since they are on Apify paid plans. The revenue breakdown is:
326+
Fixed pricing is simpler for users to predict, while usage-based pricing more accurately reflects your actual costs.
327+
328+
:::
318329

319-
- _Total revenue_: $17.50 + $7.70 = $25.20
320-
- _Total underlying cost_: $3.20 + $1.50 = $4.70
321-
- _Your profit_: 80% of revenue minus costs = 0.8 × $25.20 - $4.70 = $15.46
330+
### Pricing breakdown by user
331+
332+
<table>
333+
<thead>
334+
<tr>
335+
<th>User</th>
336+
<th style={{whiteSpace: 'nowrap'}}>Plan</th>
337+
<th style={{width: '45%'}}>Events</th>
338+
<th style={{width: '35%'}}>Charges</th>
339+
<th style={{whiteSpace: 'nowrap'}}>Total</th>
340+
<th style={{whiteSpace: 'nowrap'}}>Platform cost</th>
341+
</tr>
342+
</thead>
343+
<tbody>
344+
<tr>
345+
<td>1</td>
346+
<td style={{whiteSpace: 'nowrap'}}>Paid plan</td>
347+
<td>
348+
<div style={{marginBottom: '4px'}}>5,000 × <code>post</code></div>
349+
<div>1,000 × <code>sentiment-analysis</code></div>
350+
</td>
351+
<td>
352+
<div style={{marginBottom: '4px'}}>5,000 × $0.002</div>
353+
<div>1,000 × $0.01</div>
354+
</td>
355+
<td><strong>$20</strong></td>
356+
<td>$2.50</td>
357+
</tr>
358+
<tr>
359+
<td>2</td>
360+
<td style={{whiteSpace: 'nowrap'}}>Paid plan</td>
361+
<td>
362+
<div style={{marginBottom: '4px'}}>3,000 × <code>post</code></div>
363+
<div>500 × <code>sentiment-analysis</code></div>
364+
</td>
365+
<td>
366+
<div style={{marginBottom: '4px'}}>3,000 × $0.002</div>
367+
<div>500 × $0.01</div>
368+
</td>
369+
<td><strong>$11</strong></td>
370+
<td>$1.50</td>
371+
</tr>
372+
<tr>
373+
<td>3</td>
374+
<td style={{whiteSpace: 'nowrap'}}>Free plan</td>
375+
<td>
376+
<div style={{marginBottom: '4px'}}>1,000 × <code>post</code></div>
377+
<div>100 × <code>sentiment-analysis</code></div>
378+
</td>
379+
<td>
380+
<div style={{marginBottom: '4px'}}>1,000 × $0.002</div>
381+
<div>100 × $0.01</div>
382+
</td>
383+
<td><strong>$3</strong></td>
384+
<td>$0.40</td>
385+
</tr>
386+
</tbody>
387+
</table>
388+
389+
Your profit and costs are computed _only from the first two users_ since they are on Apify paid plans.
390+
391+
The platform usage costs are just examples, but you can see the actual costs in the [Computing your costs for PPE and PPR Actors](/platform/actors/publishing/monetize/pricing-and-costs#computing-your-costs-for-ppe-and-ppr-actors) section.
392+
393+
### Revenue breakdown
394+
395+
- _Revenue (paid users only)_: $20 + $11 = _\$31_
396+
- _Platform cost (paid users only)_: $2.50 + $1.50 = _\$4_
397+
- _Profit_: 0.8 × $31 − $4 = _\$20.80_
322398

323399
## Event names
324400

325-
To implement PPE pricing, you need to define specific events in your Actor code. You can retrieve the list of available pricing event names using the [Get Actor](https://apify.com/docs/api/v2/act-get) API endpoint.
401+
If you need to know your event names, you can retrieve the list of available pricing event names using the [Get Actor](https://apify.com/docs/api/v2/act-get) API endpoint.
326402

327403
## Next steps
328404

0 commit comments

Comments
 (0)