<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Sergio Morales</title>
    <description>The latest articles on DEV Community by Sergio Morales (@sergio_morales_c705507bcd).</description>
    <link>https://dev.to/sergio_morales_c705507bcd</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3968661%2F70652500-afed-4852-8ad8-7eff0371f0fe.png</url>
      <title>DEV Community: Sergio Morales</title>
      <link>https://dev.to/sergio_morales_c705507bcd</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/sergio_morales_c705507bcd"/>
    <language>en</language>
    <item>
      <title>I Built an API That Turns Any Website Into JSON Using Just CSS Selectors</title>
      <dc:creator>Sergio Morales</dc:creator>
      <pubDate>Sun, 14 Jun 2026 18:29:11 +0000</pubDate>
      <link>https://dev.to/sergio_morales_c705507bcd/i-built-an-api-that-turns-any-website-into-json-using-just-css-selectors-56i1</link>
      <guid>https://dev.to/sergio_morales_c705507bcd/i-built-an-api-that-turns-any-website-into-json-using-just-css-selectors-56i1</guid>
      <description>&lt;p&gt;I've written a lot of scrapers. The HTML parsing part is never the interesting part — and it's always the part that takes the longest. You know what data you want. You know where it lives on the page. Getting it out shouldn't require 40 lines of cheerio and a prayer.&lt;/p&gt;

&lt;p&gt;So I built StructAPI. You send a URL and CSS selectors. You get JSON.&lt;/p&gt;

&lt;h2&gt;
  
  
  The pitch
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-s&lt;/span&gt; &lt;span class="nt"&gt;-X&lt;/span&gt; POST https://structapi.duckdns.org/extract &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-API-Key: &lt;/span&gt;&lt;span class="nv"&gt;$KEY&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "url": "https://news.ycombinator.com",
    "fields": [
      {"name": "title", "selector": ".titleline &amp;gt; a"},
      {"name": "link", "selector": ".titleline &amp;gt; a", "attr": "href"}
    ]
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"title"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Show HN: A thing"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"link"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://thing.com"&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"title"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Why databases are weird"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"link"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://dbpost.com"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it. Define fields. Get structured data. No HTML in between.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why this exists
&lt;/h2&gt;

&lt;p&gt;Every scraping API I found falls into two camps:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Camp 1 — The proxy layer&lt;/strong&gt; (ScrapingBee, ScraperAPI, BrightData): They handle IP rotation, captcha solving, browser rendering — then dump raw HTML on you. The parsing is still your problem. You're paying for unblocking, not extraction.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Camp 2 — The black box&lt;/strong&gt; (Diffbot): They auto-extract structured data with AI. Works great until it doesn't — and you can't tell it which fields you care about. If the AI picks wrong, that's that. Also: $299/month minimum.&lt;/p&gt;

&lt;p&gt;StructAPI sits in a third camp: &lt;strong&gt;you define the schema, we return the data.&lt;/strong&gt; No AI guessing. No raw HTML to parse. Just CSS selectors → JSON.&lt;/p&gt;

&lt;h2&gt;
  
  
  Pricing
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Tier&lt;/th&gt;
&lt;th&gt;Requests&lt;/th&gt;
&lt;th&gt;Price&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Free&lt;/td&gt;
&lt;td&gt;100/mo&lt;/td&gt;
&lt;td&gt;$0&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Starter&lt;/td&gt;
&lt;td&gt;10,000/mo&lt;/td&gt;
&lt;td&gt;$29/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Pro&lt;/td&gt;
&lt;td&gt;50,000/mo&lt;/td&gt;
&lt;td&gt;$99/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Scale&lt;/td&gt;
&lt;td&gt;200,000/mo&lt;/td&gt;
&lt;td&gt;$299/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;No credit card for the free tier. Proxy rotation and JS rendering come with paid plans (launching after first paying customers).&lt;/p&gt;

&lt;h2&gt;
  
  
  What's next
&lt;/h2&gt;

&lt;p&gt;The API is live now. If you're tired of writing HTML parsers for every project, give it a shot.&lt;/p&gt;

&lt;p&gt;Sign up: &lt;a href="https://structapi.duckdns.org/keys" rel="noopener noreferrer"&gt;https://structapi.duckdns.org/keys&lt;/a&gt;&lt;br&gt;
Docs: &lt;a href="https://structapi.duckdns.org/docs" rel="noopener noreferrer"&gt;https://structapi.duckdns.org/docs&lt;/a&gt;&lt;br&gt;
GitHub: &lt;a href="https://github.com/92SM/structapi" rel="noopener noreferrer"&gt;https://github.com/92SM/structapi&lt;/a&gt;&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>api</category>
      <category>scraping</category>
      <category>showdev</category>
    </item>
    <item>
      <title>I Built an API That Turns Any Website Into JSON Using Just CSS Selectors</title>
      <dc:creator>Sergio Morales</dc:creator>
      <pubDate>Wed, 10 Jun 2026 22:54:02 +0000</pubDate>
      <link>https://dev.to/sergio_morales_c705507bcd/i-built-an-api-that-turns-any-website-into-json-using-just-css-selectors-1fd1</link>
      <guid>https://dev.to/sergio_morales_c705507bcd/i-built-an-api-that-turns-any-website-into-json-using-just-css-selectors-1fd1</guid>
      <description>&lt;p&gt;I've written a lot of scrapers. The HTML parsing part is never the interesting part — and it's always the part that takes the longest. You know what data you want. You know where it lives on the page. Getting it out shouldn't require 40 lines of cheerio and a prayer.&lt;/p&gt;

&lt;p&gt;So I built StructAPI. You send a URL and CSS selectors. You get JSON.&lt;/p&gt;

&lt;h2&gt;
  
  
  The pitch
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-s&lt;/span&gt; &lt;span class="nt"&gt;-X&lt;/span&gt; POST https://structapi.duckdns.org/extract &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-API-Key: &lt;/span&gt;&lt;span class="nv"&gt;$KEY&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "url": "https://news.ycombinator.com",
    "fields": [
      {"name": "title", "selector": ".titleline &amp;gt; a"},
      {"name": "link", "selector": ".titleline &amp;gt; a", "attr": "href"}
    ]
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"title"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Show HN: A thing"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"link"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://thing.com"&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"title"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Why databases are weird"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"link"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://dbpost.com"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it. Define fields. Get structured data. No HTML in between.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why this exists
&lt;/h2&gt;

&lt;p&gt;Every scraping API I found falls into two camps:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Camp 1 — The proxy layer&lt;/strong&gt; (ScrapingBee, ScraperAPI, BrightData): They handle IP rotation, captcha solving, browser rendering — then dump raw HTML on you. The parsing is still your problem. You're paying for unblocking, not extraction.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Camp 2 — The black box&lt;/strong&gt; (Diffbot): They auto-extract structured data with AI. Works great until it doesn't — and you can't tell it which fields you care about. If the AI picks wrong, that's that. Also: $299/month minimum.&lt;/p&gt;

&lt;p&gt;StructAPI sits in a third camp: &lt;strong&gt;you define the schema, we return the data.&lt;/strong&gt; No AI guessing. No raw HTML to parse. Just CSS selectors → JSON.&lt;/p&gt;

&lt;h2&gt;
  
  
  Pricing
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Tier&lt;/th&gt;
&lt;th&gt;Requests&lt;/th&gt;
&lt;th&gt;Price&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Free&lt;/td&gt;
&lt;td&gt;100/mo&lt;/td&gt;
&lt;td&gt;$0&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Starter&lt;/td&gt;
&lt;td&gt;10,000/mo&lt;/td&gt;
&lt;td&gt;$29/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Pro&lt;/td&gt;
&lt;td&gt;50,000/mo&lt;/td&gt;
&lt;td&gt;$99/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Scale&lt;/td&gt;
&lt;td&gt;200,000/mo&lt;/td&gt;
&lt;td&gt;$299/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;No credit card for the free tier. Proxy rotation and JS rendering come with paid plans (launching after first paying customers).&lt;/p&gt;

&lt;h2&gt;
  
  
  What's next
&lt;/h2&gt;

&lt;p&gt;The API is live now. If you're tired of writing HTML parsers for every project, give it a shot.&lt;/p&gt;

&lt;p&gt;Sign up: &lt;a href="https://structapi.duckdns.org/keys" rel="noopener noreferrer"&gt;https://structapi.duckdns.org/keys&lt;/a&gt;&lt;br&gt;
Docs: &lt;a href="https://structapi.duckdns.org/docs" rel="noopener noreferrer"&gt;https://structapi.duckdns.org/docs&lt;/a&gt;&lt;br&gt;
GitHub: &lt;a href="https://github.com/92SM/structapi" rel="noopener noreferrer"&gt;https://github.com/92SM/structapi&lt;/a&gt;&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>api</category>
      <category>scraping</category>
      <category>showdev</category>
    </item>
    <item>
      <title>I Built a $29/Month API That Turns Any Website Into Structured JSON (No AI Black Box)</title>
      <dc:creator>Sergio Morales</dc:creator>
      <pubDate>Thu, 04 Jun 2026 17:57:54 +0000</pubDate>
      <link>https://dev.to/sergio_morales_c705507bcd/i-built-a-29month-api-that-turns-any-website-into-structured-json-no-ai-black-box-385a</link>
      <guid>https://dev.to/sergio_morales_c705507bcd/i-built-a-29month-api-that-turns-any-website-into-structured-json-no-ai-black-box-385a</guid>
      <description>&lt;p&gt;I've written a lot of scrapers. The HTML parsing part is never the interesting part — it's the part that takes the longest. You know what data you want. You know where it lives on the page. Getting it out shouldn't require 40 lines of cheerio and a prayer.&lt;/p&gt;

&lt;p&gt;So I built an API that takes CSS selectors and gives you JSON. That's it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-s&lt;/span&gt; &lt;span class="nt"&gt;-X&lt;/span&gt; POST https://structapi.duckdns.org/extract   &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-API-Key: &lt;/span&gt;&lt;span class="nv"&gt;$KEY&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;   &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt;   &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "url": "https://news.ycombinator.com",
    "fields": [
      {"name": "title", "selector": ".titleline &amp;gt; a"},
      {"name": "link", "selector": ".titleline &amp;gt; a", "attr": "href"}
    ]
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Returns:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"success"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"data"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"title"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Show HN: StructAPI — Turn websites into JSON"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"link"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://structapi.duckdns.org"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You define fields with CSS selectors. You get back an object matching your schema. No HTML in the middle.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why I built this
&lt;/h2&gt;

&lt;p&gt;Every scraping API I tried falls into one of two buckets:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Proxy-first services&lt;/strong&gt; (ScrapingBee, ScraperAPI, BrightData) — they do the unblocking, rotating IPs, captcha solving — and then dump raw HTML on you. You still have to parse it.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;AI extraction&lt;/strong&gt; (Diffbot, $299/mo) — they extract structured data but you can't control the schema. The AI picks what it thinks is relevant. If it picks wrong, tough luck.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;I wanted the middle ground: you control the extraction, I handle the HTTP. CSS selectors are the interface — they're precise, testable, and every developer already knows them.&lt;/p&gt;

&lt;h2&gt;
  
  
  What it does
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;/extract&lt;/code&gt;&lt;/strong&gt; — You provide a URL and an array of field definitions (name + CSS selector). We fetch the page, run the selectors, return JSON. Single values, arrays, attribute extraction, nested selectors — all work.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;/auto&lt;/code&gt;&lt;/strong&gt; — Don't know the selectors? We auto-detect title, headings, links, images, and paragraphs from any URL. Good for quick looks, not for production.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;/usage&lt;/code&gt;&lt;/strong&gt; — Check your current month's request count and remaining quota.&lt;/p&gt;

&lt;h2&gt;
  
  
  What it costs
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Tier&lt;/th&gt;
&lt;th&gt;Requests/mo&lt;/th&gt;
&lt;th&gt;Price&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Free&lt;/td&gt;
&lt;td&gt;100&lt;/td&gt;
&lt;td&gt;$0&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Starter&lt;/td&gt;
&lt;td&gt;10,000&lt;/td&gt;
&lt;td&gt;$29/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Pro&lt;/td&gt;
&lt;td&gt;50,000&lt;/td&gt;
&lt;td&gt;$99/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Scale&lt;/td&gt;
&lt;td&gt;200,000&lt;/td&gt;
&lt;td&gt;$299/mo&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Free tier: no credit card needed. Run &lt;code&gt;curl -X POST https://structapi.duckdns.org/keys -H "Content-Type: application/json" -d '{}'&lt;/code&gt; and you get a key back.&lt;/p&gt;

&lt;h2&gt;
  
  
  What it doesn't do (yet)
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;JS rendering (React, Vue SPAs) — static HTML extraction only for now&lt;/li&gt;
&lt;li&gt;IP rotation / residential proxies — coming after first 5 paid customers&lt;/li&gt;
&lt;li&gt;Captcha solving — not planning to support this&lt;/li&gt;
&lt;li&gt;Screenshots or PDFs — text extraction only&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  How it's built
&lt;/h2&gt;

&lt;p&gt;Node.js on Express with better-sqlite3 for usage tracking. Stripe for billing (checkout, webhooks, customer portal). Caddy reverse-proxies to provide HTTPS. Hosted on a $12/mo VPS.&lt;/p&gt;

&lt;p&gt;Source code on GitHub: &lt;a href="https://github.com/92SM/structapi" rel="noopener noreferrer"&gt;https://github.com/92SM/structapi&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Try it
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Get a free key&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST https://structapi.duckdns.org/keys &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{}'&lt;/span&gt;

&lt;span class="c"&gt;# Extract data&lt;/span&gt;
&lt;span class="nv"&gt;KEY&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;"***"&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST https://structapi.duckdns.org/extract   &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-API-Key: &lt;/span&gt;&lt;span class="nv"&gt;$KEY&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;   &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt;   &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"url":"https://example.com","fields":[{"name":"h1","selector":"h1"}]}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Docs: &lt;a href="https://structapi.duckdns.org/docs" rel="noopener noreferrer"&gt;https://structapi.duckdns.org/docs&lt;/a&gt;&lt;/p&gt;

</description>
      <category>showdev</category>
      <category>api</category>
      <category>webscraping</category>
      <category>javascript</category>
    </item>
  </channel>
</rss>
