openvibers/openvibe.sources Commits
Sources: Porkbun's public domain price list (every TLD it sells), seeded disabled for OpenVibe.Host's domain comparison (#70)
Changes
@@@ -28,7 +28,7 @@"api","manual"],-- "seededSources": 39,++ "seededSources": 40,"enabledSources": 35,"deployed": true,"deployment": "Deployed with `sudo ovhost deploy sources`: /opt/openvibe.sources, unit openvibe-sources, 127.0.0.1:4720, principal sources. On 2026-10-16, 35 of 39 sources were enabled in production (reviews 19, trade 4, news 4, hosting 3, coupons 2, and blog, crowdfunding and deals 1 each), with 17,965 items from 2,156 fetch runs; they feed OpenVibe.Deals, News, Reviews, Trade, Host, Coupons, Blog's desks and Deals' crowdfunding search. Restore drill passed 2026-09-23.",@@@ -1140,6 +1140,33 @@"sensitivity": "none","default_indexability": "noindex"},++ {++ "key": "porkbun-tld-pricing",++ "name": "Porkbun domain prices (every TLD it sells)",++ "type": "api",++ "category": "hosting",++ "homepage_url": "https://porkbun.com/products/domains",++ "endpoints": [{++ "url": "https://api.porkbun.com/api/json/v3/pricing/get",++ "format": "json",++ "items_path": "pricing",++ "items_shape": "map",++ "item_kind": "tld_price",++ "max_bytes": 1048576,++ "fields": { "identity": "$key", "title": "$key" },++ "extra": { "registration": "registration", "renewal": "renewal", "transfer": "transfer", "special_type": "specialType" }++ }],++ "robots_note": "robots.txt checked 2026-10-16: https://api.porkbun.com/robots.txt answers 404 (openresty), so the API host publishes no robots.txt rules; a 404 is treated as no restrictions (never guessed as a disallow). porkbun.com's own robots.txt disallows /api/* on porkbun.com, a different host that is not fetched. The fetcher re-checks robots.txt on every run.",++ "terms_note": "Porkbun's API v3 documentation (https://porkbun.com/llms/pricing, https://porkbun.com/api/json/v3/documentation) names GET /api/json/v3/pricing/get 'Retrieve domain pricing (public)' and says it 'does not require authentication'; prices are in US dollars. The legal hub (https://porkbun.com/legal) lists no API agreement, and the Product Terms of Service (https://porkbun.com/legal/agreement/product_terms_of_service) has no clause on automated access, API use or republishing prices (read 2026-10-16). One request a day. Attribute Porkbun by linking https://porkbun.com/products/domains; show each price as an observation 'checked on <date>', never a current price, and imply no endorsement. Handshake names (specialType 'handshake') are not ICANN TLDs; OpenVibe.Host leaves them out.",++ "license_note": "Domain prices are Porkbun's data (https://porkbun.com/products/domains). No licence to republish them was found; attribute Porkbun and link the price list; no endorsement implied.",++ "min_interval_ms": 60000,++ "poll_interval_sec": 86400,++ "max_items": 1200,++ "enabled": false,++ "review_required": true,++ "sensitivity": "none",++ "default_indexability": "noindex"++ },{"key": "lowendtalk-offers","name": "LowEndTalk: the Offers board",nnew file mode 100644@@@ -0,0 +1,48 @@++{++ "status": "SUCCESS",++ "pricing": {++ "0zebra": {++ "registration": "3.63",++ "renewal": "8.20",++ "transfer": "8.20",++ "coupons": [],++ "specialType": "handshake"++ },++ "com": {++ "registration": "11.08",++ "renewal": "11.08",++ "transfer": "11.08",++ "coupons": []++ },++ "com.mx": {++ "registration": "11.33",++ "renewal": "23.32",++ "transfer": "23.32",++ "coupons": []++ },++ "dev": {++ "registration": "8.75",++ "renewal": "12.87",++ "transfer": "12.87",++ "coupons": []++ },++ "protection": {++ "registration": "2,060.25",++ "renewal": "2,060.25",++ "transfer": "2,060.25",++ "coupons": []++ },++ "security": {++ "registration": "2,060.25",++ "renewal": "2,060.25",++ "transfer": "2,060.25",++ "coupons": []++ },++ "xn--q9jyb4c": {++ "registration": "7.43",++ "renewal": "7.43",++ "transfer": "7.43",++ "coupons": []++ }++ }++}@@@ -75,6 +75,22 @@ t('Linode /v4/linode/types: identity id, title label, dotted price.monthly/hourl});});++t('Porkbun prices: one item per TLD from the keyed price list, the prices as Porkbun writes them (Host parses them)', () => {++ const s = seed('porkbun-tld-pricing');++ assert.deepStrictEqual([s.type, s.category, s.enabled, s.review_required], ['api', 'hosting', false, true]);++ const ep = endpoint('porkbun-tld-pricing');++ assert.strictEqual(api.checkMapping(ep), null);++ assert.strictEqual(validateSource(s).max_items, 1200, 'Porkbun sells about 900 names; the whole list fits');++ const r = api.parse(fx('porkbun-pricing.json'), { url: ep.url, endpoint: ep });++ assert.strictEqual(r.skipped, 0);++ assert.deepStrictEqual(r.items.map((i) => i.identity), ['0zebra', 'com', 'com.mx', 'dev', 'protection', 'security', 'xn--q9jyb4c']);++ assert.ok(r.items.every((i) => i.kind === 'tld_price' && i.title === i.identity));++ const by = Object.fromEntries(r.items.map((i) => [i.identity, i.fields]));++ assert.deepStrictEqual(by.dev, { registration: '8.75', renewal: '12.87', transfer: '12.87', special_type: null });++ assert.strictEqual(by.security.registration, '2,060.25', 'thousands separators are kept as given');++ assert.strictEqual(by['0zebra'].special_type, 'handshake', 'Handshake names are marked, for Host to leave out');++});++t('the registry accepts category hosting and refuses an unknown category', () => {const rec = validateSource(seed('vultr-plans'));assert.strictEqual(rec.category, 'hosting');
@@ -28,7 +28,7 @@
@@ -28,7 +28,7 @@
"api",
"api",
"manual"
"manual"
],
],
- "seededSources": 39,
+ "seededSources": 40,
"enabledSources": 35,
"enabledSources": 35,
"deployed": true,
"deployed": true,
"deployment": "Deployed with `sudo ovhost deploy sources`: /opt/openvibe.sources, unit openvibe-sources, 127.0.0.1:4720, principal sources. On 2026-10-16, 35 of 39 sources were enabled in production (reviews 19, trade 4, news 4, hosting 3, coupons 2, and blog, crowdfunding and deals 1 each), with 17,965 items from 2,156 fetch runs; they feed OpenVibe.Deals, News, Reviews, Trade, Host, Coupons, Blog's desks and Deals' crowdfunding search. Restore drill passed 2026-09-23.",
"deployment": "Deployed with `sudo ovhost deploy sources`: /opt/openvibe.sources, unit openvibe-sources, 127.0.0.1:4720, principal sources. On 2026-10-16, 35 of 39 sources were enabled in production (reviews 19, trade 4, news 4, hosting 3, coupons 2, and blog, crowdfunding and deals 1 each), with 17,965 items from 2,156 fetch runs; they feed OpenVibe.Deals, News, Reviews, Trade, Host, Coupons, Blog's desks and Deals' crowdfunding search. Restore drill passed 2026-09-23.",
@@ -1140,6 +1140,33 @@
@@ -1140,6 +1140,33 @@
"sensitivity": "none",
"sensitivity": "none",
"default_indexability": "noindex"
"default_indexability": "noindex"
},
},
+ {
+ "key": "porkbun-tld-pricing",
+ "name": "Porkbun domain prices (every TLD it sells)",
+ "type": "api",
+ "category": "hosting",
+ "homepage_url": "https://porkbun.com/products/domains",
+ "endpoints": [{
+ "url": "https://api.porkbun.com/api/json/v3/pricing/get",
+ "format": "json",
+ "items_path": "pricing",
+ "items_shape": "map",
+ "item_kind": "tld_price",
+ "max_bytes": 1048576,
+ "fields": { "identity": "$key", "title": "$key" },
+ "extra": { "registration": "registration", "renewal": "renewal", "transfer": "transfer", "special_type": "specialType" }
+ }],
+ "robots_note": "robots.txt checked 2026-10-16: https://api.porkbun.com/robots.txt answers 404 (openresty), so the API host publishes no robots.txt rules; a 404 is treated as no restrictions (never guessed as a disallow). porkbun.com's own robots.txt disallows /api/* on porkbun.com, a different host that is not fetched. The fetcher re-checks robots.txt on every run.",
+ "terms_note": "Porkbun's API v3 documentation (https://porkbun.com/llms/pricing, https://porkbun.com/api/json/v3/documentation) names GET /api/json/v3/pricing/get 'Retrieve domain pricing (public)' and says it 'does not require authentication'; prices are in US dollars. The legal hub (https://porkbun.com/legal) lists no API agreement, and the Product Terms of Service (https://porkbun.com/legal/agreement/product_terms_of_service) has no clause on automated access, API use or republishing prices (read 2026-10-16). One request a day. Attribute Porkbun by linking https://porkbun.com/products/domains; show each price as an observation 'checked on <date>', never a current price, and imply no endorsement. Handshake names (specialType 'handshake') are not ICANN TLDs; OpenVibe.Host leaves them out.",
+ "license_note": "Domain prices are Porkbun's data (https://porkbun.com/products/domains). No licence to republish them was found; attribute Porkbun and link the price list; no endorsement implied.",
+ "min_interval_ms": 60000,
+ "poll_interval_sec": 86400,
+ "max_items": 1200,
+ "enabled": false,
+ "review_required": true,
+ "sensitivity": "none",
+ "default_indexability": "noindex"
+ },
{
{
"key": "lowendtalk-offers",
"key": "lowendtalk-offers",
"name": "LowEndTalk: the Offers board",
"name": "LowEndTalk: the Offers board",
new file mode 100644
new file mode 100644
@@ -0,0 +1,48 @@
@@ -0,0 +1,48 @@
+{
+ "status": "SUCCESS",
+ "pricing": {
+ "0zebra": {
+ "registration": "3.63",
+ "renewal": "8.20",
+ "transfer": "8.20",
+ "coupons": [],
+ "specialType": "handshake"
+ },
+ "com": {
+ "registration": "11.08",
+ "renewal": "11.08",
+ "transfer": "11.08",
+ "coupons": []
+ },
+ "com.mx": {
+ "registration": "11.33",
+ "renewal": "23.32",
+ "transfer": "23.32",
+ "coupons": []
+ },
+ "dev": {
+ "registration": "8.75",
+ "renewal": "12.87",
+ "transfer": "12.87",
+ "coupons": []
+ },
+ "protection": {
+ "registration": "2,060.25",
+ "renewal": "2,060.25",
+ "transfer": "2,060.25",
+ "coupons": []
+ },
+ "security": {
+ "registration": "2,060.25",
+ "renewal": "2,060.25",
+ "transfer": "2,060.25",
+ "coupons": []
+ },
+ "xn--q9jyb4c": {
+ "registration": "7.43",
+ "renewal": "7.43",
+ "transfer": "7.43",
+ "coupons": []
+ }
+ }
+}
@@ -75,6 +75,22 @@ t('Linode /v4/linode/types: identity id, title label, dotted price.monthly/hourl
@@ -75,6 +75,22 @@ t('Linode /v4/linode/types: identity id, title label, dotted price.monthly/hourl
});
});
});
});
+t('Porkbun prices: one item per TLD from the keyed price list, the prices as Porkbun writes them (Host parses them)', () => {
+ const s = seed('porkbun-tld-pricing');
+ assert.deepStrictEqual([s.type, s.category, s.enabled, s.review_required], ['api', 'hosting', false, true]);
+ const ep = endpoint('porkbun-tld-pricing');
+ assert.strictEqual(api.checkMapping(ep), null);
+ assert.strictEqual(validateSource(s).max_items, 1200, 'Porkbun sells about 900 names; the whole list fits');
+ const r = api.parse(fx('porkbun-pricing.json'), { url: ep.url, endpoint: ep });
+ assert.strictEqual(r.skipped, 0);
+ assert.deepStrictEqual(r.items.map((i) => i.identity), ['0zebra', 'com', 'com.mx', 'dev', 'protection', 'security', 'xn--q9jyb4c']);
+ assert.ok(r.items.every((i) => i.kind === 'tld_price' && i.title === i.identity));
+ const by = Object.fromEntries(r.items.map((i) => [i.identity, i.fields]));
+ assert.deepStrictEqual(by.dev, { registration: '8.75', renewal: '12.87', transfer: '12.87', special_type: null });
+ assert.strictEqual(by.security.registration, '2,060.25', 'thousands separators are kept as given');
+ assert.strictEqual(by['0zebra'].special_type, 'handshake', 'Handshake names are marked, for Host to leave out');
+});
+
t('the registry accepts category hosting and refuses an unknown category', () => {
t('the registry accepts category hosting and refuses an unknown category', () => {
const rec = validateSource(seed('vultr-plans'));
const rec = validateSource(seed('vultr-plans'));
assert.strictEqual(rec.category, 'hosting');
assert.strictEqual(rec.category, 'hosting');