I made 1,700 assets. 58 are live on Adobe. That gap is the whole post.
First batch ran clean through my generator. Files looked right in the preview folder. I built the CSV, hit upload, and waited. Most of it never shipped. Some got rejected on metadata. Some sat in review and never cleared. A few went live. One sold for $0.99.
The generator did its job. It produced images. What it could not do was tell me whether those images would survive a platform review. That is a different question, and it needs a different pass. A second model that looks at the asset the way the platform will.
The maker model only makes
A generation model is optimized to produce output. Given a prompt, it returns a file. It has no view of Adobe's review criteria, no view of Vecteezy's header rules, no view of what your own catalogue already contains. It cannot tell you the title is 4 characters too long, or the keywords repeat, or the file is a near-duplicate of asset 913.
So the maker model is a producer, not a judge. Treat it that way. Everything it emits is a draft, not a shippable file, no matter how good the preview looks.
Second model checks the things that reject you
The reject reasons are boring and mechanical. That is good, because a second pass can catch nearly all of them before you upload.
Metadata first. Each channel demands a header it will not bend on. Adobe wants its 5-column header. Vecteezy wants 4 columns. Dreamstime wants 15. A wrong header means the whole CSV is refused instantly, not one row, the file. My make_metadata.py writes the header each platform demands and nothing else, so the format never drifts between batches.
Then the per-asset checks. Title present and not the raw filename. Keywords non-empty and not duplicated. File type matches what the channel accepts. The second model reads each draft and returns a pass or a fix list. No upload happens on a fail.
Then the catalogue check. This is the one a maker model can never do alone. Before an asset ships, compare it against what you already posted. Near-duplicates are a fast route to a flagged account, and you will not spot them by eye across 1,700 files.
Run the second pass as a separate job, not the same context
The obvious shortcut is to ask the maker model to review its own output in the same run. Do not. It shares the blind spots that produced the draft. It will approve what it just made.
Keep it as a distinct job. Different model, different prompt, reads the file cold. In my pipeline it runs through a local proxy that routes to a second model, and an orchestrator schedules it, retries on failure, and holds the queue. Cost is near zero because it is text in, verdict out. The expensive part is image generation, and the second pass never generates an image.
The rule I enforce: no file reaches the upload folder without a verdict attached. Drafts live in assets/. Only passed files move to output/.
It runs on almost nothing
All of this ran on 1 vCPU, 2 GB RAM, no GPU. The review pass is cheap, but the habits matter on a box that small.
One process at a time. Never fan out image jobs in parallel on a single core. Free memory between items with gc.collect() after each asset. Measure peak RSS, not average, with resource.getrusage(RUSAGE_SELF).ru_maxrss, because the average hides the spike that kills you. For heavy render steps, one file per subprocess so memory returns to the OS. Render previews at the resolution you actually need, 60 dpi for inspection beats 300.
I also keep an upload ledger. upload_tracker.py remembers what shipped, because running the same batch twice is the fastest way to get flagged. The second model will not save you from a double-post. The tracker will.
Where the numbers landed
1,700 assets made. 58 live on Adobe. First sale $0.99. The kit that packaged 39 products, 856 MB of output, came out of roughly 19,000 lines of pipeline code and 300+ pages of research behind the rules the scripts enforce. None of that is impressive on its own. What changed the ratio was adding the second pass before shipping instead of after the reject email.
If you want the exact tools, the metadata builder, the ledger, the Markdown to PDF step, and the packager that renders a cover and thumbnail, they are bundled in the playbook built from this work. It is the same pipeline that ran on the tiny server, with the review step included.
Building digital products? Free guides & kits for digital product sellers.
Top comments (0)