@corsair-dev/worldnewsapi 0.1.0 → 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -26,11 +26,11 @@ WORLD_NEWS_API_KEY=your_api_key_here
26
26
 
27
27
  ```ts
28
28
  import { createCorsair } from 'corsair';
29
- import { worldNewsApi } from '@corsair-dev/worldnewsapi';
29
+ import { worldnewsapi } from '@corsair-dev/worldnewsapi';
30
30
 
31
31
  const app = createCorsair({
32
32
  plugins: [
33
- worldNewsApi({
33
+ worldnewsapi({
34
34
  // Explicit key, or automatically resolved from WORLD_NEWS_API_KEY / key manager
35
35
  key: process.env.WORLD_NEWS_API_KEY,
36
36
  }),
package/dist/index.d.ts CHANGED
@@ -216,7 +216,7 @@ export declare const worldNewsApiAuthConfig: {
216
216
  export type BaseWorldNewsApiPlugin<T extends WorldNewsApiPluginOptions> = CorsairPlugin<'worldnewsapi', typeof WorldNewsApiSchema, typeof worldNewsApiEndpointsNested, typeof worldNewsApiWebhooksNested, T, typeof defaultAuthType>;
217
217
  export type InternalWorldNewsApiPlugin = BaseWorldNewsApiPlugin<WorldNewsApiPluginOptions>;
218
218
  export type ExternalWorldNewsApiPlugin<T extends WorldNewsApiPluginOptions> = BaseWorldNewsApiPlugin<T>;
219
- export declare function worldNewsApi<const T extends WorldNewsApiPluginOptions>(incomingOptions?: WorldNewsApiPluginOptions & T): ExternalWorldNewsApiPlugin<T>;
219
+ export declare function worldnewsapi<const T extends WorldNewsApiPluginOptions>(incomingOptions?: WorldNewsApiPluginOptions & T): ExternalWorldNewsApiPlugin<T>;
220
220
  export type { ParsedRssFeed, ParsedRssItem, WorldNewsQuotaInfo, } from './client';
221
221
  export type { WorldNewsApiEndpointInputs, WorldNewsApiEndpointOutputs, WorldNewsArticle, } from './endpoints/types';
222
222
  //# sourceMappingURL=index.d.ts.map
package/dist/index.js CHANGED
@@ -1 +1 @@
1
- import{AuthMissingError as Pe}from"corsair/core";import{logEventFromContext as We}from"corsair/core";import{request as ae}from"corsair/http";import{ZodError as le}from"zod";var u=class extends Error{constructor(o,s,i){super(o);this.status=s;this.code=i;this.name="WorldNewsApiError"}},ce="https://api.worldnewsapi.com";function h(t){if(!t||typeof t!="string")throw new u("Invalid URL provided: URL must be a non-empty string",400,"INVALID_URL");let n;try{n=new URL(t)}catch{throw new u(`Malformed URL: "${t}"`,400,"MALFORMED_URL")}if(n.protocol!=="http:"&&n.protocol!=="https:")throw new u(`Unsupported protocol: "${n.protocol}". Only http and https URLs are permitted.`,400,"INVALID_PROTOCOL");let o=n.hostname.toLowerCase();if(ue(o))throw new u(`Access to private or local network hosts (${o}) is not permitted.`,400,"SSRF_PROTECTED");return n}function S(t){return!!(/^127\.\d{1,3}\.\d{1,3}\.\d{1,3}$/.test(t)||/^10\.\d{1,3}\.\d{1,3}\.\d{1,3}$/.test(t)||/^192\.168\.\d{1,3}\.\d{1,3}$/.test(t)||/^172\.(1[6-9]|2\d|3[0-1])\.\d{1,3}\.\d{1,3}$/.test(t)||/^169\.254\.\d{1,3}\.\d{1,3}$/.test(t)||t==="0.0.0.0")}function ue(t){let n=t.replace(/^\[|\]$/g,"").toLowerCase();if(n==="localhost"||n==="::1"||n==="::"||n==="0:0:0:0:0:0:0:1"||n.endsWith(".localhost")||n.endsWith(".local")||n.endsWith(".internal"))return!0;let o=/^::ffff:(\d{1,3}(?:\.\d{1,3}){3})$/.exec(n);if(o?.[1]&&S(o[1]))return!0;let s=/^::ffff:([0-9a-f]{1,4}):([0-9a-f]{1,4})$/.exec(n);if(s?.[1]&&s[2]){let i=parseInt(s[1],16),a=parseInt(s[2],16),d=`${i>>8&255}.${i&255}.${a>>8&255}.${a&255}`;if(S(d))return!0}return!!(S(n)||n.includes(":")&&(n.startsWith("fe80:")||n.startsWith("fc")||n.startsWith("fd")))}function f(t){let n=h(t);return n.username="",n.password="",`${n.origin}${n.pathname}`}function de(t){return t.replace(/&lt;/g,"<").replace(/&gt;/g,">").replace(/&quot;/g,'"').replace(/&apos;/g,"'").replace(/&amp;/g,"&").replace(/&#(\d+);/g,(n,o)=>L(parseInt(o,10))).replace(/&#x([0-9a-fA-F]+);/g,(n,o)=>L(parseInt(o,16)))}function L(t){return!Number.isFinite(t)||t<0||t>1114111||t>=55296&&t<=57343?"":String.fromCodePoint(t)}function pe(t){return t.replace(/<!\[CDATA\[([\s\S]*?)\]\]>/g,"$1")}function l(t,n){if(!t)return;let o=new RegExp(`<(?:[a-zA-Z0-9_-]+:)?${n}[^>]*>([\\s\\S]*?)<\\/(?:[a-zA-Z0-9_-]+:)?${n}>`,"i"),s=t.match(o);if(!(!s||s[1]===void 0))return de(pe(s[1].trim()))}function v(t){if(!t||typeof t!="string")throw new u("Empty or invalid RSS feed content",422,"MALFORMED_RSS");let n=t.match(/<channel[^>]*>([\s\S]*?)<\/channel>/i);if(!n)throw new u("RSS response is missing a channel element",422,"MALFORMED_RSS");let o=n[1]??"",s=l(o,"title"),i=l(o,"link"),a=l(o,"description"),d=l(o,"pubDate"),x=l(o,"lastBuildDate"),D=l(o,"language"),A=/<item[^>]*>([\s\S]*?)<\/item>/gi,y=[],I;for(;(I=A.exec(o))!==null;){let p=I[1]??"",J=l(p,"title"),ee=l(p,"link"),te=l(p,"guid"),ne=l(p,"pubDate"),oe=l(p,"description"),se=l(p,"author")??l(p,"creator"),re=l(p,"category"),P=p.match(/<enclosure[^>]*url=["']([^"']+)["'][^>]*\/?>/i),ie=P?P[1]:void 0;y.push({title:J,link:ee,guid:te,pubDate:ne,description:oe,author:se,category:re,enclosureUrl:ie})}return{title:s,link:i,description:a,pubDate:d,lastBuildDate:x,language:D,items:y,rawXml:t}}async function c(t,n,o={},s){if(!n||!n.trim())throw new u("World News API key is required. Set WORLD_NEWS_API_KEY environment variable or pass key option.",401,"AUTH_MISSING");let{method:i="GET",query:a,timeout:d=25e3}=o,x={BASE:ce,VERSION:"1.0.0",WITH_CREDENTIALS:!1,CREDENTIALS:"omit",TIMEOUT:d,TOKEN:void 0,HEADERS:{"x-api-key":n.trim(),Accept:t.endsWith(".rss")?"application/xml, text/xml, application/rss+xml":"application/json"}},A=await ae(x,{method:i,url:t,mediaType:"application/json; charset=utf-8",query:a});try{return s.parse(A)}catch(y){throw y instanceof le?new u("World News API returned a payload that does not match the documented schema",422,"INVALID_RESPONSE"):y}}import{z as e}from"zod";var E=e.iso.date(),F=e.string().refine(t=>{if(E.safeParse(t).success)return!0;let n=/^(\d{4}-\d{2}-\d{2}) (\d{2}):(\d{2}):(\d{2})$/.exec(t);if(!n||!E.safeParse(n[1]).success)return!1;let o=Number(n[2]),s=Number(n[3]),i=Number(n[4]);return o<24&&s<60&&i<60},"Date must be YYYY-MM-DD or YYYY-MM-DD HH:MM:SS"),M=e.object({id:e.number(),title:e.string(),text:e.string().optional(),summary:e.string().nullable().optional(),url:e.string(),image:e.string().nullable().optional(),video:e.string().nullable().optional(),publish_date:e.string().optional(),author:e.string().nullable().optional(),authors:e.array(e.string().nullable()).optional(),category:e.string().optional(),language:e.string().optional(),source_country:e.string().optional(),sentiment:e.number().optional()}),we=e.object({title:e.string().optional(),url:e.string(),width:e.number().optional(),height:e.number().optional()}),me=e.object({title:e.string().optional(),url:e.string(),summary:e.string().optional(),duration:e.number().optional(),thumbnail:e.string().optional()}),ge=e.object({name:e.string(),type:e.string(),sentiment:e.number().optional()}),he=e.object({title:e.string().optional(),link:e.string().optional(),guid:e.string().optional(),pubDate:e.string().optional(),description:e.string().optional(),author:e.string().optional(),category:e.string().optional(),enclosureUrl:e.string().optional()}),fe=e.object({name:e.string(),url:e.string(),language:e.string().optional(),country:e.string().optional()}),Ne=e.object({sourceCountry:e.string().length(2).describe('The 2-letter ISO 3166 country code for which top news should be retrieved (e.g., "us", "in", "gb").'),language:e.string().length(2).describe('The 2-letter ISO 639-1 language code of the top news (e.g., "en", "es", "fr").'),date:E.optional().describe("The date for which the top news should be retrieved (YYYY-MM-DD). Defaults to today."),headlinesOnly:e.boolean().optional().describe("Whether to only return basic headline fields (id, title, url). Defaults to false."),maxNewsPerCluster:e.number().int().min(1).max(100).optional().describe("How many news articles to return per story cluster. Default is 1.")}),be=e.object({url:e.string().url().describe("The URL of the news article to extract into structured data."),analyze:e.boolean().optional().describe("Whether to analyze the extracted news (extract named entities, detect sentiment, etc.). Defaults to false.")}),ye=e.object({url:e.string().url().describe("The webpage or site URL from which news article links should be extracted."),analyze:e.boolean().optional().describe("Whether to analyze extracted links. Defaults to false."),prefix:e.string().max(100).optional().describe("The prefix that discovered news links must start with."),subDomain:e.boolean().optional().describe("Whether to include links to news articles on sub-domains. Defaults to true.")}),xe=e.object({location:e.string().min(1).max(1e3).describe('The address or location name to geocode (e.g., "Tokyo, Japan" or "Mumbai, India").')}),Ae=e.object({url:e.string().url().describe("The URL of the news website/page to convert into an RSS 2.0 feed."),extractNews:e.boolean().optional().describe("Whether to extract full article text/data for each item in the feed (costs additional quota). Defaults to false.")}),Se=e.object({name:e.string().min(3).max(1e3).describe('The (partial) name of the news source to search for (e.g. "bbc", "reuters", "times").')}),Ee=e.object({text:e.string().min(3).max(100).optional().describe("Search query text. Supports implicit AND, OR, negation with -, parentheses, and quotes for exact phrases."),textMatchIndexes:e.string().optional().describe('Where to search for text: "title", "content", or "title,content".'),sourceCountry:e.string().length(2).optional().describe("Filter by 2-letter ISO 3166 country code."),language:e.string().length(2).optional().describe("Filter by 2-letter ISO 639-1 language code."),minSentiment:e.number().min(-1).max(1).optional().describe("Minimum sentiment score between -1.0 (very negative) and 1.0 (very positive)."),maxSentiment:e.number().min(-1).max(1).optional().describe("Maximum sentiment score between -1.0 and 1.0."),earliestPublishDate:F.optional().describe("Filter for news published on or after this timestamp (YYYY-MM-DD HH:MM:SS or YYYY-MM-DD)."),latestPublishDate:F.optional().describe("Filter for news published on or before this timestamp (YYYY-MM-DD HH:MM:SS or YYYY-MM-DD)."),newsSources:e.string().optional().describe('Comma-separated list of up to 10 news sources (e.g., "bbc.co.uk,nytimes.com").'),authors:e.string().optional().describe("Comma-separated list of author names."),categories:e.string().optional().describe("Comma-separated categories (politics, sports, business, technology, entertainment, health, science, etc.)."),entities:e.string().optional().describe('Filter by semantic entities (e.g., "ORG:Tesla,PER:Elon Musk").'),locationFilter:e.string().optional().describe('Filter by geographic radius in the format "latitude,longitude,radius in km" (radius: 1-100).'),sort:e.string().optional().describe('Sort criteria, typically "publish-time".'),sortDirection:e.enum(["ASC","DESC"]).optional().describe('Sort direction: "ASC" or "DESC". Defaults to DESC for publish-time.'),offset:e.number().int().min(0).max(1e5).optional().describe("Number of results to skip for pagination."),number:e.number().int().min(1).max(100).optional().describe("Number of results to return (1-100). Defaults to 10.")}).refine(t=>t.text!==void 0||t.sourceCountry!==void 0||t.language!==void 0||t.minSentiment!==void 0||t.maxSentiment!==void 0||t.earliestPublishDate!==void 0||t.latestPublishDate!==void 0||t.newsSources!==void 0||t.authors!==void 0||t.categories!==void 0||t.entities!==void 0||t.locationFilter!==void 0,{message:"At least one search filter is required"}),W=e.object({top_news:e.array(e.object({news:e.array(M)})),language:e.string().optional(),country:e.string().optional()}),k=e.object({title:e.string().optional(),text:e.string().optional(),url:e.string().optional(),image:e.string().nullable().optional(),images:e.array(we).optional(),video:e.string().nullable().optional(),videos:e.array(me).optional(),publish_date:e.string().optional(),author:e.string().nullable().optional(),authors:e.array(e.string().nullable()).optional(),language:e.string().optional(),source_country:e.string().optional(),sentiment:e.number().optional(),entities:e.array(ge).optional()}),R=e.object({status:e.string().optional(),news_links:e.array(e.string())}),C=e.object({latitude:e.number(),longitude:e.number(),city:e.string().optional()}),T=e.object({title:e.string().optional(),link:e.string().optional(),description:e.string().optional(),pubDate:e.string().optional(),lastBuildDate:e.string().optional(),language:e.string().optional(),items:e.array(he),rawXml:e.string().optional()}),_=e.object({available:e.number(),sources:e.array(fe)}),O=e.object({offset:e.number(),number:e.number(),available:e.number(),news:e.array(M)}),w={"news.topNews":Ne,"news.extractNews":be,"news.extractNewsLinks":ye,"news.getGeoCoordinates":xe,"news.newsWebsiteToRssFeed":Ae,"news.searchNewsSources":Se,"news.searchNews":Ee},m={"news.topNews":W,"news.extractNews":k,"news.extractNewsLinks":R,"news.getGeoCoordinates":C,"news.newsWebsiteToRssFeed":T,"news.searchNewsSources":_,"news.searchNews":O};var G=async(t,n)=>{h(n.url);let o=f(n.url),s={url:n.url,analyze:n.analyze},i=await c("extract-news",t.key,{method:"GET",query:s},k);try{await t.db.extractedArticles.upsertByEntityId(o,{url:o,title:i.title,text:i.text,image:i.image,video:i.video,publish_date:i.publish_date,author:i.author,authors:i.authors,language:i.language,source_country:i.source_country,sentiment:i.sentiment,extractedAt:new Date})}catch{}return await We(t,"worldnewsapi.news.extractNews",{url:o,title:i.title},"completed"),i};import{logEventFromContext as ke}from"corsair/core";var q=async(t,n)=>{h(n.url);let o={url:n.url,analyze:n.analyze,prefix:n.prefix,"sub-domain":n.subDomain},s=await c("extract-news-links",t.key,{method:"GET",query:o},R);return await ke(t,"worldnewsapi.news.extractNewsLinks",{url:f(n.url),linksCount:s.news_links?.length??0},"completed"),s};import{logEventFromContext as Re}from"corsair/core";var z=async(t,n)=>{let o={location:n.location},s=await c("geo-coordinates",t.key,{method:"GET",query:o},C);try{await t.db.geoCoordinates.upsertByEntityId(n.location,{location:n.location,latitude:s.latitude,longitude:s.longitude,city:s.city,resolvedAt:new Date})}catch{}return await Re(t,"worldnewsapi.news.getGeoCoordinates",{location:n.location,latitude:s.latitude,longitude:s.longitude},"completed"),s};import{logEventFromContext as Ce}from"corsair/core";import{z as Te}from"zod";var U=async(t,n)=>{h(n.url);let o=f(n.url),s={url:n.url,"extract-news":n.extractNews},i=await c("feed.rss",t.key,{method:"GET",query:s},Te.string()),a=v(i),d=T.parse({title:a.title,link:a.link,description:a.description,pubDate:a.pubDate,lastBuildDate:a.lastBuildDate,language:a.language,items:a.items,rawXml:a.rawXml});return await Ce(t,"worldnewsapi.news.newsWebsiteToRssFeed",{url:o,itemsCount:d.items.length},"completed"),d};import{logEventFromContext as _e}from"corsair/core";var Y=async(t,n)=>{let o={text:n.text,"text-match-indexes":n.textMatchIndexes,"source-country":n.sourceCountry,language:n.language,"min-sentiment":n.minSentiment,"max-sentiment":n.maxSentiment,"earliest-publish-date":n.earliestPublishDate,"latest-publish-date":n.latestPublishDate,"news-sources":n.newsSources,authors:n.authors,categories:n.categories,entities:n.entities,"location-filter":n.locationFilter,sort:n.sort,"sort-direction":n.sortDirection,offset:n.offset,number:n.number},s=await c("search-news",t.key,{method:"GET",query:o},O);if(s.news&&Array.isArray(s.news))for(let i of s.news)try{await t.db.articles.upsertByEntityId(String(i.id),{...i,createdAt:new Date})}catch{}return await _e(t,"worldnewsapi.news.searchNews",{query:n.text,resultCount:s.news?.length??0,available:s.available},"completed"),s};import{logEventFromContext as Oe}from"corsair/core";var j=async(t,n)=>{let o={name:n.name},s=await c("search-news-sources",t.key,{method:"GET",query:o},_);if(s.sources&&Array.isArray(s.sources))for(let i of s.sources)try{await t.db.sources.upsertByEntityId(i.url||i.name,{...i,searchedAt:new Date})}catch{}return await Oe(t,"worldnewsapi.news.searchNewsSources",{name:n.name,availableCount:s.available},"completed"),s};import{logEventFromContext as De}from"corsair/core";var B=async(t,n)=>{let o={"source-country":n.sourceCountry,language:n.language,date:n.date,"headlines-only":n.headlinesOnly,"max-news-per-cluster":n.maxNewsPerCluster},s=await c("top-news",t.key,{method:"GET",query:o},W);if(s.top_news&&Array.isArray(s.top_news)){for(let i of s.top_news)if(i.news&&Array.isArray(i.news))for(let a of i.news)try{await t.db.articles.upsertByEntityId(String(a.id),{...a,createdAt:new Date})}catch{}}return await De(t,"worldnewsapi.news.topNews",{sourceCountry:n.sourceCountry,language:n.language,clustersCount:s.top_news?.length??0},"completed"),s};var g={topNews:B,extractNews:G,extractNewsLinks:q,getGeoCoordinates:z,newsWebsiteToRssFeed:U,searchNewsSources:j,searchNews:Y};import{ApiError as H}from"corsair/http";function N(t){if(t instanceof H||t instanceof u)return t.status}function b(t){return t instanceof Error?t.message.toLowerCase():""}function Ie(t){return t instanceof H?t.retryAfter:void 0}var $={RATE_LIMIT_ERROR:{match:(t,n)=>{if(N(t)===429)return!0;let o=b(t);return o.includes("rate_limit")||o.includes("ratelimit")||o.includes("429")||o.includes("too many requests")},handler:async(t,n)=>({maxRetries:5,headersRetryAfterMs:Ie(t)})},QUOTA_ERROR:{match:(t,n)=>{if(N(t)===402)return!0;let o=b(t);return o.includes("quota exceeded")||o.includes("payment required")},handler:async(t,n)=>({maxRetries:0})},AUTH_ERROR:{match:(t,n)=>{if(N(t)===401)return!0;let o=b(t);return o.includes("unauthorized")||o.includes("invalid api key")||o.includes("auth_missing")||o.includes("authentication failed")},handler:async(t,n)=>({maxRetries:0})},PERMISSION_ERROR:{match:(t,n)=>{if(N(t)===403)return!0;let o=b(t);return o.includes("forbidden")||o.includes("access denied")||o.includes("insufficient_permissions")},handler:async(t,n)=>({maxRetries:0})},NOT_FOUND_ERROR:{match:(t,n)=>{if(N(t)===404)return!0;let o=b(t);return o.includes("not found")||o.includes("404")},handler:async(t,n)=>({maxRetries:0})},BAD_REQUEST_ERROR:{match:(t,n)=>{if(N(t)===400)return!0;let o=b(t);return o.includes("bad request")||o.includes("invalid_url")||o.includes("malformed_url")||o.includes("invalid_protocol")||o.includes("ssrf_protected")},handler:async(t,n)=>({maxRetries:0})},DEFAULT:{match:(t,n)=>!0,handler:async(t,n)=>({maxRetries:0})}};import{z as r}from"zod";var K=r.object({id:r.number(),title:r.string(),text:r.string().optional(),summary:r.string().nullable().optional(),url:r.string(),image:r.string().nullable().optional(),video:r.string().nullable().optional(),publish_date:r.string().optional(),author:r.string().nullable().optional(),authors:r.array(r.string().nullable()).optional(),category:r.string().optional(),language:r.string().optional(),source_country:r.string().optional(),sentiment:r.number().optional(),createdAt:r.coerce.date().optional()}),X=r.object({url:r.string(),title:r.string().optional(),text:r.string().optional(),image:r.string().nullable().optional(),video:r.string().nullable().optional(),publish_date:r.string().optional(),author:r.string().nullable().optional(),authors:r.array(r.string().nullable()).optional(),language:r.string().optional(),source_country:r.string().optional(),sentiment:r.number().optional(),extractedAt:r.coerce.date().optional()}),V=r.object({location:r.string(),latitude:r.number(),longitude:r.number(),city:r.string().optional(),resolvedAt:r.coerce.date().optional()}),Q=r.object({name:r.string(),url:r.string(),language:r.string().optional(),country:r.string().optional(),searchedAt:r.coerce.date().optional()});var Z={version:"1.0.0",entities:{articles:K,extractedArticles:X,geoCoordinates:V,sources:Q}};var Le={news:{topNews:g.topNews,extractNews:g.extractNews,extractNewsLinks:g.extractNewsLinks,getGeoCoordinates:g.getGeoCoordinates,newsWebsiteToRssFeed:g.newsWebsiteToRssFeed,searchNewsSources:g.searchNewsSources,searchNews:g.searchNews}},ve={},Fe={"news.topNews":{input:w["news.topNews"],output:m["news.topNews"]},"news.extractNews":{input:w["news.extractNews"],output:m["news.extractNews"]},"news.extractNewsLinks":{input:w["news.extractNewsLinks"],output:m["news.extractNewsLinks"]},"news.getGeoCoordinates":{input:w["news.getGeoCoordinates"],output:m["news.getGeoCoordinates"]},"news.newsWebsiteToRssFeed":{input:w["news.newsWebsiteToRssFeed"],output:m["news.newsWebsiteToRssFeed"]},"news.searchNewsSources":{input:w["news.searchNewsSources"],output:m["news.searchNewsSources"]},"news.searchNews":{input:w["news.searchNews"],output:m["news.searchNews"]}},Me="api_key",Ge={"news.topNews":{riskLevel:"read",description:"Get the top news from a country in a specific language for a given date. The top news are clustered from multiple sources in the specified country."},"news.extractNews":{riskLevel:"read",description:"Extract a news article from a website to a well-structured JSON object, including title, text, images, videos, publish date, authors, language, and sentiment."},"news.extractNewsLinks":{riskLevel:"read",description:"Extract news article links from a website or webpage, with optional filtering by URL prefix and subdomain inclusion."},"news.getGeoCoordinates":{riskLevel:"read",description:"Retrieve latitude and longitude of a location name to fill the location-filter parameter in news search operations."},"news.newsWebsiteToRssFeed":{riskLevel:"read",description:"Convert any news website page into an RSS feed with the latest news from that page."},"news.searchNewsSources":{riskLevel:"read",description:"Search whether a news source is being monitored by the World News API."},"news.searchNews":{riskLevel:"read",description:"Search and filter news by text, date, location, category, language, and more."}},qe={api_key:{}};function Ut(t={}){let n={...t,authType:t.authType??Me};return{id:"worldnewsapi",authConfig:qe,schema:Z,options:n,hooks:n.hooks,endpoints:Le,webhooks:ve,endpointMeta:Ge,endpointSchemas:Fe,webhookSchemas:{},errorHandlers:{...$,...n.errorHandlers},keyBuilder:async(o,s)=>{if(s==="endpoint"&&n.key)return n.key;if(s==="endpoint"&&o.authType==="api_key"){let i=await o.keys.get_api_key();if(i)return i}throw new Pe("worldnewsapi","api_key")}}}export{Ut as worldNewsApi,qe as worldNewsApiAuthConfig,Fe as worldNewsApiEndpointSchemas};
1
+ import{AuthMissingError as Pe}from"corsair/core";import{logEventFromContext as We}from"corsair/core";import{request as ae}from"corsair/http";import{ZodError as le}from"zod";var u=class extends Error{constructor(o,s,i){super(o);this.status=s;this.code=i;this.name="WorldNewsApiError"}},ce="https://api.worldnewsapi.com";function h(t){if(!t||typeof t!="string")throw new u("Invalid URL provided: URL must be a non-empty string",400,"INVALID_URL");let n;try{n=new URL(t)}catch{throw new u(`Malformed URL: "${t}"`,400,"MALFORMED_URL")}if(n.protocol!=="http:"&&n.protocol!=="https:")throw new u(`Unsupported protocol: "${n.protocol}". Only http and https URLs are permitted.`,400,"INVALID_PROTOCOL");let o=n.hostname.toLowerCase();if(ue(o))throw new u(`Access to private or local network hosts (${o}) is not permitted.`,400,"SSRF_PROTECTED");return n}function S(t){return!!(/^127\.\d{1,3}\.\d{1,3}\.\d{1,3}$/.test(t)||/^10\.\d{1,3}\.\d{1,3}\.\d{1,3}$/.test(t)||/^192\.168\.\d{1,3}\.\d{1,3}$/.test(t)||/^172\.(1[6-9]|2\d|3[0-1])\.\d{1,3}\.\d{1,3}$/.test(t)||/^169\.254\.\d{1,3}\.\d{1,3}$/.test(t)||t==="0.0.0.0")}function ue(t){let n=t.replace(/^\[|\]$/g,"").toLowerCase();if(n==="localhost"||n==="::1"||n==="::"||n==="0:0:0:0:0:0:0:1"||n.endsWith(".localhost")||n.endsWith(".local")||n.endsWith(".internal"))return!0;let o=/^::ffff:(\d{1,3}(?:\.\d{1,3}){3})$/.exec(n);if(o?.[1]&&S(o[1]))return!0;let s=/^::ffff:([0-9a-f]{1,4}):([0-9a-f]{1,4})$/.exec(n);if(s?.[1]&&s[2]){let i=parseInt(s[1],16),a=parseInt(s[2],16),d=`${i>>8&255}.${i&255}.${a>>8&255}.${a&255}`;if(S(d))return!0}return!!(S(n)||n.includes(":")&&(n.startsWith("fe80:")||n.startsWith("fc")||n.startsWith("fd")))}function f(t){let n=h(t);return n.username="",n.password="",`${n.origin}${n.pathname}`}function de(t){return t.replace(/&lt;/g,"<").replace(/&gt;/g,">").replace(/&quot;/g,'"').replace(/&apos;/g,"'").replace(/&amp;/g,"&").replace(/&#(\d+);/g,(n,o)=>L(parseInt(o,10))).replace(/&#x([0-9a-fA-F]+);/g,(n,o)=>L(parseInt(o,16)))}function L(t){return!Number.isFinite(t)||t<0||t>1114111||t>=55296&&t<=57343?"":String.fromCodePoint(t)}function pe(t){return t.replace(/<!\[CDATA\[([\s\S]*?)\]\]>/g,"$1")}function l(t,n){if(!t)return;let o=new RegExp(`<(?:[a-zA-Z0-9_-]+:)?${n}[^>]*>([\\s\\S]*?)<\\/(?:[a-zA-Z0-9_-]+:)?${n}>`,"i"),s=t.match(o);if(!(!s||s[1]===void 0))return de(pe(s[1].trim()))}function v(t){if(!t||typeof t!="string")throw new u("Empty or invalid RSS feed content",422,"MALFORMED_RSS");let n=t.match(/<channel[^>]*>([\s\S]*?)<\/channel>/i);if(!n)throw new u("RSS response is missing a channel element",422,"MALFORMED_RSS");let o=n[1]??"",s=l(o,"title"),i=l(o,"link"),a=l(o,"description"),d=l(o,"pubDate"),x=l(o,"lastBuildDate"),D=l(o,"language"),A=/<item[^>]*>([\s\S]*?)<\/item>/gi,y=[],I;for(;(I=A.exec(o))!==null;){let p=I[1]??"",J=l(p,"title"),ee=l(p,"link"),te=l(p,"guid"),ne=l(p,"pubDate"),oe=l(p,"description"),se=l(p,"author")??l(p,"creator"),re=l(p,"category"),P=p.match(/<enclosure[^>]*url=["']([^"']+)["'][^>]*\/?>/i),ie=P?P[1]:void 0;y.push({title:J,link:ee,guid:te,pubDate:ne,description:oe,author:se,category:re,enclosureUrl:ie})}return{title:s,link:i,description:a,pubDate:d,lastBuildDate:x,language:D,items:y,rawXml:t}}async function c(t,n,o={},s){if(!n||!n.trim())throw new u("World News API key is required. Set WORLD_NEWS_API_KEY environment variable or pass key option.",401,"AUTH_MISSING");let{method:i="GET",query:a,timeout:d=25e3}=o,x={BASE:ce,VERSION:"1.0.0",WITH_CREDENTIALS:!1,CREDENTIALS:"omit",TIMEOUT:d,TOKEN:void 0,HEADERS:{"x-api-key":n.trim(),Accept:t.endsWith(".rss")?"application/xml, text/xml, application/rss+xml":"application/json"}},A=await ae(x,{method:i,url:t,mediaType:"application/json; charset=utf-8",query:a});try{return s.parse(A)}catch(y){throw y instanceof le?new u("World News API returned a payload that does not match the documented schema",422,"INVALID_RESPONSE"):y}}import{z as e}from"zod";var E=e.iso.date(),F=e.string().refine(t=>{if(E.safeParse(t).success)return!0;let n=/^(\d{4}-\d{2}-\d{2}) (\d{2}):(\d{2}):(\d{2})$/.exec(t);if(!n||!E.safeParse(n[1]).success)return!1;let o=Number(n[2]),s=Number(n[3]),i=Number(n[4]);return o<24&&s<60&&i<60},"Date must be YYYY-MM-DD or YYYY-MM-DD HH:MM:SS"),M=e.object({id:e.number(),title:e.string(),text:e.string().optional(),summary:e.string().nullable().optional(),url:e.string(),image:e.string().nullable().optional(),video:e.string().nullable().optional(),publish_date:e.string().optional(),author:e.string().nullable().optional(),authors:e.array(e.string().nullable()).optional(),category:e.string().optional(),language:e.string().optional(),source_country:e.string().optional(),sentiment:e.number().optional()}),we=e.object({title:e.string().optional(),url:e.string(),width:e.number().optional(),height:e.number().optional()}),me=e.object({title:e.string().optional(),url:e.string(),summary:e.string().optional(),duration:e.number().optional(),thumbnail:e.string().optional()}),ge=e.object({name:e.string(),type:e.string(),sentiment:e.number().optional()}),he=e.object({title:e.string().optional(),link:e.string().optional(),guid:e.string().optional(),pubDate:e.string().optional(),description:e.string().optional(),author:e.string().optional(),category:e.string().optional(),enclosureUrl:e.string().optional()}),fe=e.object({name:e.string(),url:e.string(),language:e.string().optional(),country:e.string().optional()}),Ne=e.object({sourceCountry:e.string().length(2).describe('The 2-letter ISO 3166 country code for which top news should be retrieved (e.g., "us", "in", "gb").'),language:e.string().length(2).describe('The 2-letter ISO 639-1 language code of the top news (e.g., "en", "es", "fr").'),date:E.optional().describe("The date for which the top news should be retrieved (YYYY-MM-DD). Defaults to today."),headlinesOnly:e.boolean().optional().describe("Whether to only return basic headline fields (id, title, url). Defaults to false."),maxNewsPerCluster:e.number().int().min(1).max(100).optional().describe("How many news articles to return per story cluster. Default is 1.")}),be=e.object({url:e.string().url().describe("The URL of the news article to extract into structured data."),analyze:e.boolean().optional().describe("Whether to analyze the extracted news (extract named entities, detect sentiment, etc.). Defaults to false.")}),ye=e.object({url:e.string().url().describe("The webpage or site URL from which news article links should be extracted."),analyze:e.boolean().optional().describe("Whether to analyze extracted links. Defaults to false."),prefix:e.string().max(100).optional().describe("The prefix that discovered news links must start with."),subDomain:e.boolean().optional().describe("Whether to include links to news articles on sub-domains. Defaults to true.")}),xe=e.object({location:e.string().min(1).max(1e3).describe('The address or location name to geocode (e.g., "Tokyo, Japan" or "Mumbai, India").')}),Ae=e.object({url:e.string().url().describe("The URL of the news website/page to convert into an RSS 2.0 feed."),extractNews:e.boolean().optional().describe("Whether to extract full article text/data for each item in the feed (costs additional quota). Defaults to false.")}),Se=e.object({name:e.string().min(3).max(1e3).describe('The (partial) name of the news source to search for (e.g. "bbc", "reuters", "times").')}),Ee=e.object({text:e.string().min(3).max(100).optional().describe("Search query text. Supports implicit AND, OR, negation with -, parentheses, and quotes for exact phrases."),textMatchIndexes:e.string().optional().describe('Where to search for text: "title", "content", or "title,content".'),sourceCountry:e.string().length(2).optional().describe("Filter by 2-letter ISO 3166 country code."),language:e.string().length(2).optional().describe("Filter by 2-letter ISO 639-1 language code."),minSentiment:e.number().min(-1).max(1).optional().describe("Minimum sentiment score between -1.0 (very negative) and 1.0 (very positive)."),maxSentiment:e.number().min(-1).max(1).optional().describe("Maximum sentiment score between -1.0 and 1.0."),earliestPublishDate:F.optional().describe("Filter for news published on or after this timestamp (YYYY-MM-DD HH:MM:SS or YYYY-MM-DD)."),latestPublishDate:F.optional().describe("Filter for news published on or before this timestamp (YYYY-MM-DD HH:MM:SS or YYYY-MM-DD)."),newsSources:e.string().optional().describe('Comma-separated list of up to 10 news sources (e.g., "bbc.co.uk,nytimes.com").'),authors:e.string().optional().describe("Comma-separated list of author names."),categories:e.string().optional().describe("Comma-separated categories (politics, sports, business, technology, entertainment, health, science, etc.)."),entities:e.string().optional().describe('Filter by semantic entities (e.g., "ORG:Tesla,PER:Elon Musk").'),locationFilter:e.string().optional().describe('Filter by geographic radius in the format "latitude,longitude,radius in km" (radius: 1-100).'),sort:e.string().optional().describe('Sort criteria, typically "publish-time".'),sortDirection:e.enum(["ASC","DESC"]).optional().describe('Sort direction: "ASC" or "DESC". Defaults to DESC for publish-time.'),offset:e.number().int().min(0).max(1e5).optional().describe("Number of results to skip for pagination."),number:e.number().int().min(1).max(100).optional().describe("Number of results to return (1-100). Defaults to 10.")}).refine(t=>t.text!==void 0||t.sourceCountry!==void 0||t.language!==void 0||t.minSentiment!==void 0||t.maxSentiment!==void 0||t.earliestPublishDate!==void 0||t.latestPublishDate!==void 0||t.newsSources!==void 0||t.authors!==void 0||t.categories!==void 0||t.entities!==void 0||t.locationFilter!==void 0,{message:"At least one search filter is required"}),W=e.object({top_news:e.array(e.object({news:e.array(M)})),language:e.string().optional(),country:e.string().optional()}),k=e.object({title:e.string().optional(),text:e.string().optional(),url:e.string().optional(),image:e.string().nullable().optional(),images:e.array(we).optional(),video:e.string().nullable().optional(),videos:e.array(me).optional(),publish_date:e.string().optional(),author:e.string().nullable().optional(),authors:e.array(e.string().nullable()).optional(),language:e.string().optional(),source_country:e.string().optional(),sentiment:e.number().optional(),entities:e.array(ge).optional()}),R=e.object({status:e.string().optional(),news_links:e.array(e.string())}),C=e.object({latitude:e.number(),longitude:e.number(),city:e.string().optional()}),T=e.object({title:e.string().optional(),link:e.string().optional(),description:e.string().optional(),pubDate:e.string().optional(),lastBuildDate:e.string().optional(),language:e.string().optional(),items:e.array(he),rawXml:e.string().optional()}),_=e.object({available:e.number(),sources:e.array(fe)}),O=e.object({offset:e.number(),number:e.number(),available:e.number(),news:e.array(M)}),w={"news.topNews":Ne,"news.extractNews":be,"news.extractNewsLinks":ye,"news.getGeoCoordinates":xe,"news.newsWebsiteToRssFeed":Ae,"news.searchNewsSources":Se,"news.searchNews":Ee},m={"news.topNews":W,"news.extractNews":k,"news.extractNewsLinks":R,"news.getGeoCoordinates":C,"news.newsWebsiteToRssFeed":T,"news.searchNewsSources":_,"news.searchNews":O};var G=async(t,n)=>{h(n.url);let o=f(n.url),s={url:n.url,analyze:n.analyze},i=await c("extract-news",t.key,{method:"GET",query:s},k);try{await t.db.extractedArticles.upsertByEntityId(o,{url:o,title:i.title,text:i.text,image:i.image,video:i.video,publish_date:i.publish_date,author:i.author,authors:i.authors,language:i.language,source_country:i.source_country,sentiment:i.sentiment,extractedAt:new Date})}catch{}return await We(t,"worldnewsapi.news.extractNews",{url:o,title:i.title},"completed"),i};import{logEventFromContext as ke}from"corsair/core";var q=async(t,n)=>{h(n.url);let o={url:n.url,analyze:n.analyze,prefix:n.prefix,"sub-domain":n.subDomain},s=await c("extract-news-links",t.key,{method:"GET",query:o},R);return await ke(t,"worldnewsapi.news.extractNewsLinks",{url:f(n.url),linksCount:s.news_links?.length??0},"completed"),s};import{logEventFromContext as Re}from"corsair/core";var z=async(t,n)=>{let o={location:n.location},s=await c("geo-coordinates",t.key,{method:"GET",query:o},C);try{await t.db.geoCoordinates.upsertByEntityId(n.location,{location:n.location,latitude:s.latitude,longitude:s.longitude,city:s.city,resolvedAt:new Date})}catch{}return await Re(t,"worldnewsapi.news.getGeoCoordinates",{location:n.location,latitude:s.latitude,longitude:s.longitude},"completed"),s};import{logEventFromContext as Ce}from"corsair/core";import{z as Te}from"zod";var U=async(t,n)=>{h(n.url);let o=f(n.url),s={url:n.url,"extract-news":n.extractNews},i=await c("feed.rss",t.key,{method:"GET",query:s},Te.string()),a=v(i),d=T.parse({title:a.title,link:a.link,description:a.description,pubDate:a.pubDate,lastBuildDate:a.lastBuildDate,language:a.language,items:a.items,rawXml:a.rawXml});return await Ce(t,"worldnewsapi.news.newsWebsiteToRssFeed",{url:o,itemsCount:d.items.length},"completed"),d};import{logEventFromContext as _e}from"corsair/core";var Y=async(t,n)=>{let o={text:n.text,"text-match-indexes":n.textMatchIndexes,"source-country":n.sourceCountry,language:n.language,"min-sentiment":n.minSentiment,"max-sentiment":n.maxSentiment,"earliest-publish-date":n.earliestPublishDate,"latest-publish-date":n.latestPublishDate,"news-sources":n.newsSources,authors:n.authors,categories:n.categories,entities:n.entities,"location-filter":n.locationFilter,sort:n.sort,"sort-direction":n.sortDirection,offset:n.offset,number:n.number},s=await c("search-news",t.key,{method:"GET",query:o},O);if(s.news&&Array.isArray(s.news))for(let i of s.news)try{await t.db.articles.upsertByEntityId(String(i.id),{...i,createdAt:new Date})}catch{}return await _e(t,"worldnewsapi.news.searchNews",{query:n.text,resultCount:s.news?.length??0,available:s.available},"completed"),s};import{logEventFromContext as Oe}from"corsair/core";var j=async(t,n)=>{let o={name:n.name},s=await c("search-news-sources",t.key,{method:"GET",query:o},_);if(s.sources&&Array.isArray(s.sources))for(let i of s.sources)try{await t.db.sources.upsertByEntityId(i.url||i.name,{...i,searchedAt:new Date})}catch{}return await Oe(t,"worldnewsapi.news.searchNewsSources",{name:n.name,availableCount:s.available},"completed"),s};import{logEventFromContext as De}from"corsair/core";var B=async(t,n)=>{let o={"source-country":n.sourceCountry,language:n.language,date:n.date,"headlines-only":n.headlinesOnly,"max-news-per-cluster":n.maxNewsPerCluster},s=await c("top-news",t.key,{method:"GET",query:o},W);if(s.top_news&&Array.isArray(s.top_news)){for(let i of s.top_news)if(i.news&&Array.isArray(i.news))for(let a of i.news)try{await t.db.articles.upsertByEntityId(String(a.id),{...a,createdAt:new Date})}catch{}}return await De(t,"worldnewsapi.news.topNews",{sourceCountry:n.sourceCountry,language:n.language,clustersCount:s.top_news?.length??0},"completed"),s};var g={topNews:B,extractNews:G,extractNewsLinks:q,getGeoCoordinates:z,newsWebsiteToRssFeed:U,searchNewsSources:j,searchNews:Y};import{ApiError as H}from"corsair/http";function N(t){if(t instanceof H||t instanceof u)return t.status}function b(t){return t instanceof Error?t.message.toLowerCase():""}function Ie(t){return t instanceof H?t.retryAfter:void 0}var $={RATE_LIMIT_ERROR:{match:(t,n)=>{if(N(t)===429)return!0;let o=b(t);return o.includes("rate_limit")||o.includes("ratelimit")||o.includes("429")||o.includes("too many requests")},handler:async(t,n)=>({maxRetries:5,headersRetryAfterMs:Ie(t)})},QUOTA_ERROR:{match:(t,n)=>{if(N(t)===402)return!0;let o=b(t);return o.includes("quota exceeded")||o.includes("payment required")},handler:async(t,n)=>({maxRetries:0})},AUTH_ERROR:{match:(t,n)=>{if(N(t)===401)return!0;let o=b(t);return o.includes("unauthorized")||o.includes("invalid api key")||o.includes("auth_missing")||o.includes("authentication failed")},handler:async(t,n)=>({maxRetries:0})},PERMISSION_ERROR:{match:(t,n)=>{if(N(t)===403)return!0;let o=b(t);return o.includes("forbidden")||o.includes("access denied")||o.includes("insufficient_permissions")},handler:async(t,n)=>({maxRetries:0})},NOT_FOUND_ERROR:{match:(t,n)=>{if(N(t)===404)return!0;let o=b(t);return o.includes("not found")||o.includes("404")},handler:async(t,n)=>({maxRetries:0})},BAD_REQUEST_ERROR:{match:(t,n)=>{if(N(t)===400)return!0;let o=b(t);return o.includes("bad request")||o.includes("invalid_url")||o.includes("malformed_url")||o.includes("invalid_protocol")||o.includes("ssrf_protected")},handler:async(t,n)=>({maxRetries:0})},DEFAULT:{match:(t,n)=>!0,handler:async(t,n)=>({maxRetries:0})}};import{z as r}from"zod";var K=r.object({id:r.number(),title:r.string(),text:r.string().optional(),summary:r.string().nullable().optional(),url:r.string(),image:r.string().nullable().optional(),video:r.string().nullable().optional(),publish_date:r.string().optional(),author:r.string().nullable().optional(),authors:r.array(r.string().nullable()).optional(),category:r.string().optional(),language:r.string().optional(),source_country:r.string().optional(),sentiment:r.number().optional(),createdAt:r.coerce.date().optional()}),X=r.object({url:r.string(),title:r.string().optional(),text:r.string().optional(),image:r.string().nullable().optional(),video:r.string().nullable().optional(),publish_date:r.string().optional(),author:r.string().nullable().optional(),authors:r.array(r.string().nullable()).optional(),language:r.string().optional(),source_country:r.string().optional(),sentiment:r.number().optional(),extractedAt:r.coerce.date().optional()}),V=r.object({location:r.string(),latitude:r.number(),longitude:r.number(),city:r.string().optional(),resolvedAt:r.coerce.date().optional()}),Q=r.object({name:r.string(),url:r.string(),language:r.string().optional(),country:r.string().optional(),searchedAt:r.coerce.date().optional()});var Z={version:"1.0.0",entities:{articles:K,extractedArticles:X,geoCoordinates:V,sources:Q}};var Le={news:{topNews:g.topNews,extractNews:g.extractNews,extractNewsLinks:g.extractNewsLinks,getGeoCoordinates:g.getGeoCoordinates,newsWebsiteToRssFeed:g.newsWebsiteToRssFeed,searchNewsSources:g.searchNewsSources,searchNews:g.searchNews}},ve={},Fe={"news.topNews":{input:w["news.topNews"],output:m["news.topNews"]},"news.extractNews":{input:w["news.extractNews"],output:m["news.extractNews"]},"news.extractNewsLinks":{input:w["news.extractNewsLinks"],output:m["news.extractNewsLinks"]},"news.getGeoCoordinates":{input:w["news.getGeoCoordinates"],output:m["news.getGeoCoordinates"]},"news.newsWebsiteToRssFeed":{input:w["news.newsWebsiteToRssFeed"],output:m["news.newsWebsiteToRssFeed"]},"news.searchNewsSources":{input:w["news.searchNewsSources"],output:m["news.searchNewsSources"]},"news.searchNews":{input:w["news.searchNews"],output:m["news.searchNews"]}},Me="api_key",Ge={"news.topNews":{riskLevel:"read",description:"Get the top news from a country in a specific language for a given date. The top news are clustered from multiple sources in the specified country."},"news.extractNews":{riskLevel:"read",description:"Extract a news article from a website to a well-structured JSON object, including title, text, images, videos, publish date, authors, language, and sentiment."},"news.extractNewsLinks":{riskLevel:"read",description:"Extract news article links from a website or webpage, with optional filtering by URL prefix and subdomain inclusion."},"news.getGeoCoordinates":{riskLevel:"read",description:"Retrieve latitude and longitude of a location name to fill the location-filter parameter in news search operations."},"news.newsWebsiteToRssFeed":{riskLevel:"read",description:"Convert any news website page into an RSS feed with the latest news from that page."},"news.searchNewsSources":{riskLevel:"read",description:"Search whether a news source is being monitored by the World News API."},"news.searchNews":{riskLevel:"read",description:"Search and filter news by text, date, location, category, language, and more."}},qe={api_key:{}};function Ut(t={}){let n={...t,authType:t.authType??Me};return{id:"worldnewsapi",authConfig:qe,schema:Z,options:n,hooks:n.hooks,endpoints:Le,webhooks:ve,endpointMeta:Ge,endpointSchemas:Fe,webhookSchemas:{},errorHandlers:{...$,...n.errorHandlers},keyBuilder:async(o,s)=>{if(s==="endpoint"&&n.key)return n.key;if(s==="endpoint"&&o.authType==="api_key"){let i=await o.keys.get_api_key();if(i)return i}throw new Pe("worldnewsapi","api_key")}}}export{qe as worldNewsApiAuthConfig,Fe as worldNewsApiEndpointSchemas,Ut as worldnewsapi};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@corsair-dev/worldnewsapi",
3
- "version": "0.1.0",
3
+ "version": "0.1.1",
4
4
  "description": "WorldNewsApi plugin for Corsair",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -24,18 +24,24 @@
24
24
  "tsup": "^8.0.1",
25
25
  "typescript": "^5.9.3",
26
26
  "zod": "^4.1.13",
27
- "corsair": "0.1.125"
27
+ "corsair": "0.1.130"
28
28
  },
29
29
  "keywords": [
30
30
  "corsair",
31
31
  "worldnewsapi",
32
32
  "plugin"
33
33
  ],
34
- "author": "",
34
+ "author": "Corsair (https://corsair.dev)",
35
35
  "license": "Apache-2.0",
36
36
  "files": [
37
37
  "dist"
38
38
  ],
39
+ "repository": {
40
+ "type": "git",
41
+ "url": "git+https://github.com/corsairdev/corsair.git",
42
+ "directory": "packages/worldnewsapi"
43
+ },
44
+ "homepage": "https://docs.corsair.dev/plugins/worldnewsapi",
39
45
  "scripts": {
40
46
  "build": "node -e \"require('fs').rmSync('dist',{recursive:true,force:true})\" && tsc --build --force && tsup",
41
47
  "typecheck": "tsc --noEmit",