exa-js 1.0.12 → 1.0.14-beta.0

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
@@ -14,11 +14,66 @@ npm install exa-js
14
14
 
15
15
  ## Initialization
16
16
  ```js
17
- import Exa from "exa-node"
17
+ import Exa from "exa-js"
18
18
 
19
19
  const exa = new Exa(process.env.EXA_API_KEY)
20
20
  ```
21
21
 
22
+ ### Common commands
23
+
24
+ ```js
25
+
26
+ // Basic search
27
+ const basicResults = await exa.search("This is a Exa query:");
28
+
29
+ // Autoprompted search
30
+ const autoPromptedResults = await exa.search("autopromptable query", { useAutoprompt: true });
31
+
32
+ // Search with date filters
33
+ const dateFilteredResults = await exa.search("This is a Exa query:", {
34
+ startPublishedDate: "2019-01-01",
35
+ endPublishedDate: "2019-01-31"
36
+ });
37
+
38
+ // Search with domain filters
39
+ const domainFilteredResults = await exa.search("This is a Exa query:", {
40
+ includeDomains: ["www.cnn.com", "www.nytimes.com"]
41
+ });
42
+
43
+ // Search and get text contents
44
+ const searchAndTextResults = await exa.searchAndContents("This is a Exa query:", { text: true });
45
+
46
+ // Search and get highlights
47
+ const searchAndHighlightsResults = await exa.searchAndContents("This is a Exa query:", { highlights: true });
48
+
49
+ // Search and get contents with contents options
50
+ const searchAndCustomContentsResults = await exa.searchAndContents("This is a Exa query:", {
51
+ text: { includeHtmlTags: true, maxCharacters: 1000 },
52
+ highlights: { highlightsPerUrl: 2, numSentences: 1, query: "This is the highlight query:" }
53
+ });
54
+
55
+ // Find similar documents
56
+ const similarResults = await exa.findSimilar("https://example.com");
57
+
58
+ // Find similar excluding source domain
59
+ const similarExcludingSourceResults = await exa.findSimilar("https://example.com", { excludeSourceDomain: true });
60
+
61
+ // Find similar with contents
62
+ const similarWithContentsResults = await exa.findSimilarAndContents("https://example.com", { text: true, highlights: true });
63
+
64
+ // Get text contents
65
+ const textContentsResults = await exa.getContents(["ids"], { text: true });
66
+
67
+ // Get highlights
68
+ const highlightsContentsResults = await exa.getContents(["ids"], { highlights: true });
69
+
70
+ // Get contents with contents options
71
+ const customContentsResults = await exa.getContents(["ids"], {
72
+ text: { includeHtmlTags: true, maxCharacters: 1000 },
73
+ highlights: { highlightsPerUrl: 2, numSentences: 1, query: "This is the highlight query:" }
74
+ });
75
+ ```
76
+
22
77
  ### `exa.search(query: string, options?: SearchOptions): Promise<SearchResponse>`
23
78
  Performs a search on the Exa system with the given parameters.
24
79
 
package/dist/index.d.ts CHANGED
@@ -11,6 +11,8 @@
11
11
  * @property {boolean} [useAutoprompt] - If true, converts query to a Metaphor query.
12
12
  * @property {string} [type] - Type of search, 'keyword' or 'neural'.
13
13
  * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.
14
+ * @property {string[]} [includeText] - List of strings that must be present in webpage text of results. Currently only supports 1 string of up to 5 words.
15
+ * @property {string[]} [excludeText] - List of strings that must not be present in webpage text of results. Currently only supports 1 string of up to 5 words.
14
16
  */
15
17
  type BaseSearchOptions = {
16
18
  numResults?: number;
@@ -21,11 +23,12 @@ type BaseSearchOptions = {
21
23
  startPublishedDate?: string;
22
24
  endPublishedDate?: string;
23
25
  category?: string;
26
+ includeText?: string[];
27
+ excludeText?: string[];
24
28
  };
25
29
  /**
26
30
  * Search options for performing a search query.
27
- * @typedef {Object} ContentsOptions
28
- * @property {string[]} [formats] - An array of format types asked for. Currently supports `extract` (first 1000 tokens) and `text` (full parsed HTML text). If this isn't specified, defaults to `extract`.
31
+ * @typedef {Object} RegularSearchOptions
29
32
  */
30
33
  type RegularSearchOptions = BaseSearchOptions & {
31
34
  useAutoprompt?: boolean;
@@ -43,6 +46,8 @@ type RegularSearchOptions = BaseSearchOptions & {
43
46
  * @property {string} [endPublishedDate] - End date for results based on published date.
44
47
  * @property {boolean} [excludeSourceDomain] - If true, excludes links from the base domain of the input.
45
48
  * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.
49
+ * @property {string[]} [includeText] - List of strings that must be present in webpage text of results. Currently only supports 1 string of up to 5 words.
50
+ * @property {string[]} [excludeText] - List of strings that must not be present in webpage text of results. Currently only supports 1 string of up to 5 words.
46
51
  */
47
52
  type FindSimilarOptions = BaseSearchOptions & {
48
53
  excludeSourceDomain?: boolean;
@@ -52,11 +57,22 @@ type FindSimilarOptions = BaseSearchOptions & {
52
57
  * @typedef {Object} ContentsOptions
53
58
  * @property {TextContentsOptions | boolean} [text] - Options for retrieving text contents.
54
59
  * @property {HighlightsContentsOptions | boolean} [highlights] - Options for retrieving highlights.
60
+ * @property {SummaryContentsOptions | boolean} [summary] - Options for retrieving summary.
61
+ * @property {LivecrawlOptions} [livecrawl] - Options for livecrawling contents. Default is "never" for neural/auto search, "fallback" for keyword search.
62
+ * @property {boolean} [filterEmptyResults] - If true, filters out results with no contents. Default is true.
55
63
  */
56
64
  type ContentsOptions = {
57
65
  text?: TextContentsOptions | true;
58
66
  highlights?: HighlightsContentsOptions | true;
67
+ summary?: SummaryContentsOptions | true;
68
+ livecrawl?: LivecrawlOptions;
69
+ filterEmptyResults?: boolean;
59
70
  };
71
+ /**
72
+ * Options for livecrawling contents
73
+ * @typedef {string} LivecrawlOptions
74
+ */
75
+ type LivecrawlOptions = "never" | "fallback" | "always";
60
76
  /**
61
77
  * Options for retrieving text from page.
62
78
  * @typedef {Object} TextContentsOptions
@@ -79,6 +95,14 @@ type HighlightsContentsOptions = {
79
95
  numSentences?: number;
80
96
  highlightsPerUrl?: number;
81
97
  };
98
+ /**
99
+ * Options for retrieving summary from page.
100
+ * @typedef {Object} SummaryContentsOptions
101
+ * @property {string} [query] - The query string to use for summary generation.
102
+ */
103
+ type SummaryContentsOptions = {
104
+ query?: string;
105
+ };
82
106
  /**
83
107
  * @typedef {Object} TextResponse
84
108
  * @property {string} text - Text from page
@@ -95,14 +119,21 @@ type HighlightsResponse = {
95
119
  highlights: string[];
96
120
  highlightScores: number[];
97
121
  };
122
+ /**
123
+ * @typedef {Object} SummaryResponse
124
+ * @property {string} summary - The generated summary of the page content.
125
+ */
126
+ type SummaryResponse = {
127
+ summary: string;
128
+ };
98
129
  type Default<T extends {}, U> = [keyof T] extends [never] ? U : T;
99
130
  /**
100
131
  * @typedef {Object} ContentsResultComponent
101
- * Depending on 'ContentsOptions', this yields either a 'TextResponse', a 'HighlightsResponse', both, or an empty object.
132
+ * Depending on 'ContentsOptions', this yields a combination of 'TextResponse', 'HighlightsResponse', 'SummaryResponse', or an empty object.
102
133
  *
103
134
  * @template T - A type extending from 'ContentsOptions'.
104
135
  */
105
- type ContentsResultComponent<T extends ContentsOptions> = Default<(T['text'] extends (object | true) ? TextResponse : {}) & (T['highlights'] extends (object | true) ? HighlightsResponse : {}), TextResponse>;
136
+ type ContentsResultComponent<T extends ContentsOptions> = Default<(T["text"] extends object | true ? TextResponse : {}) & (T["highlights"] extends object | true ? HighlightsResponse : {}) & (T["summary"] extends object | true ? SummaryResponse : {}), TextResponse>;
106
137
  /**
107
138
  * Represents a search result object.
108
139
  * @typedef {Object} Result
@@ -144,12 +175,12 @@ declare class Exa {
144
175
  */
145
176
  constructor(apiKey?: string, baseURL?: string);
146
177
  /**
147
- * Makes a request to the Exa API.
148
- * @param {string} endpoint - The API endpoint to call.
149
- * @param {string} method - The HTTP method to use.
150
- * @param {any} [body] - The request body for POST requests.
151
- * @returns {Promise<any>} The response from the API.
152
- */
178
+ * Makes a request to the Exa API.
179
+ * @param {string} endpoint - The API endpoint to call.
180
+ * @param {string} method - The HTTP method to use.
181
+ * @param {any} [body] - The request body for POST requests.
182
+ * @returns {Promise<any>} The response from the API.
183
+ */
153
184
  private request;
154
185
  /**
155
186
  * Performs a search with a Exa prompt-engineered query.
@@ -188,4 +219,4 @@ declare class Exa {
188
219
  getContents<T extends ContentsOptions>(ids: string | string[] | SearchResult[], options?: T): Promise<SearchResponse<T>>;
189
220
  }
190
221
 
191
- export { BaseSearchOptions, ContentsOptions, ContentsResultComponent, Default, FindSimilarOptions, HighlightsContentsOptions, HighlightsResponse, RegularSearchOptions, SearchResponse, SearchResult, TextContentsOptions, TextResponse, Exa as default };
222
+ export { BaseSearchOptions, ContentsOptions, ContentsResultComponent, Default, FindSimilarOptions, HighlightsContentsOptions, HighlightsResponse, LivecrawlOptions, RegularSearchOptions, SearchResponse, SearchResult, SummaryContentsOptions, SummaryResponse, TextContentsOptions, TextResponse, Exa as default };
package/dist/index.js CHANGED
@@ -45,7 +45,9 @@ var Exa = class {
45
45
  if (!apiKey) {
46
46
  apiKey = process.env.EXASEARCH_API_KEY;
47
47
  if (!apiKey) {
48
- throw new Error("API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)");
48
+ throw new Error(
49
+ "API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)"
50
+ );
49
51
  }
50
52
  }
51
53
  this.headers = new import_cross_fetch.Headers({
@@ -55,12 +57,12 @@ var Exa = class {
55
57
  });
56
58
  }
57
59
  /**
58
- * Makes a request to the Exa API.
59
- * @param {string} endpoint - The API endpoint to call.
60
- * @param {string} method - The HTTP method to use.
61
- * @param {any} [body] - The request body for POST requests.
62
- * @returns {Promise<any>} The response from the API.
63
- */
60
+ * Makes a request to the Exa API.
61
+ * @param {string} endpoint - The API endpoint to call.
62
+ * @param {string} method - The HTTP method to use.
63
+ * @param {any} [body] - The request body for POST requests.
64
+ * @returns {Promise<any>} The response from the API.
65
+ */
64
66
  async request(endpoint, method, body) {
65
67
  const response = await (0, import_cross_fetch.default)(this.baseURL + endpoint, {
66
68
  method,
@@ -91,12 +93,22 @@ var Exa = class {
91
93
  * @returns {Promise<SearchResponse>} A list of relevant search results.
92
94
  */
93
95
  async searchAndContents(query, options) {
94
- const { text, highlights, ...rest } = options || {};
96
+ const {
97
+ text,
98
+ highlights,
99
+ summary,
100
+ livecrawl,
101
+ filterEmptyResults,
102
+ ...rest
103
+ } = options || {};
104
+ const isBeta = process.env.NPM_CONFIG_TAG === "beta";
95
105
  return await this.request("/search", "POST", {
96
106
  query,
97
- contents: !text && !highlights ? { text: true } : {
107
+ contents: !text && !highlights && !summary ? { text: true, ...isBeta ? { livecrawl, filterEmptyResults } : {} } : {
98
108
  ...text ? { text } : {},
99
- ...highlights ? { highlights } : {}
109
+ ...highlights ? { highlights } : {},
110
+ ...summary ? { summary } : {},
111
+ ...isBeta ? { livecrawl, filterEmptyResults } : {}
100
112
  },
101
113
  ...rest
102
114
  });
@@ -117,12 +129,22 @@ var Exa = class {
117
129
  * @returns {Promise<SearchResponse>} A list of similar search results.
118
130
  */
119
131
  async findSimilarAndContents(url, options) {
120
- const { text, highlights, ...rest } = options || {};
132
+ const {
133
+ text,
134
+ highlights,
135
+ summary,
136
+ livecrawl,
137
+ filterEmptyResults,
138
+ ...rest
139
+ } = options || {};
140
+ const isBeta = process.env.NPM_CONFIG_TAG === "beta";
121
141
  return await this.request("/findSimilar", "POST", {
122
142
  url,
123
- contents: !text && !highlights ? { text: true } : {
143
+ contents: !text && !highlights && !summary ? { text: true, ...isBeta ? { livecrawl, filterEmptyResults } : {} } : {
124
144
  ...text ? { text } : {},
125
- ...highlights ? { highlights } : {}
145
+ ...highlights ? { highlights } : {},
146
+ ...summary ? { summary } : {},
147
+ ...isBeta ? { livecrawl, filterEmptyResults } : {}
126
148
  },
127
149
  ...rest
128
150
  });
@@ -134,6 +156,8 @@ var Exa = class {
134
156
  * @returns {Promise<GetContentsResponse>} A list of document contents.
135
157
  */
136
158
  async getContents(ids, options) {
159
+ const { livecrawl, filterEmptyResults, ...rest } = options || {};
160
+ const isBeta = process.env.NPM_CONFIG_TAG === "beta";
137
161
  if (ids.length === 0) {
138
162
  throw new Error("Must provide at least one ID");
139
163
  }
@@ -145,7 +169,11 @@ var Exa = class {
145
169
  } else {
146
170
  requestIds = ids.map((result) => result.id);
147
171
  }
148
- return await this.request(`/contents`, "POST", { ids: requestIds, ...options });
172
+ return await this.request(`/contents`, "POST", {
173
+ ids: requestIds,
174
+ ...isBeta ? { livecrawl, filterEmptyResults } : {},
175
+ ...rest
176
+ });
149
177
  }
150
178
  };
151
179
  var src_default = Exa;
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts"],"sourcesContent":["import fetch, { Headers } from 'cross-fetch';\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} SearchOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude in the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [useAutoprompt] - If true, converts query to a Metaphor query.\n * @property {string} [type] - Type of search, 'keyword' or 'neural'.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n */\nexport type BaseSearchOptions = {\n numResults?: number;\n includeDomains?: string[];\n excludeDomains?: string[];\n startCrawlDate?: string;\n endCrawlDate?: string;\n startPublishedDate?: string;\n endPublishedDate?: string;\n category?: string;\n};\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} ContentsOptions\n * @property {string[]} [formats] - An array of format types asked for. Currently supports `extract` (first 1000 tokens) and `text` (full parsed HTML text). If this isn't specified, defaults to `extract`.\n */\nexport type RegularSearchOptions = BaseSearchOptions & {\n useAutoprompt?: boolean;\n type?: string;\n}\n\n/**\n * Options for finding similar links.\n * @typedef {Object} FindSimilarOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude from the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [excludeSourceDomain] - If true, excludes links from the base domain of the input.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n */\nexport type FindSimilarOptions = BaseSearchOptions & {\n excludeSourceDomain?: boolean;\n}\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} ContentsOptions\n * @property {TextContentsOptions | boolean} [text] - Options for retrieving text contents.\n * @property {HighlightsContentsOptions | boolean} [highlights] - Options for retrieving highlights.\n */\nexport type ContentsOptions = {\n text?: TextContentsOptions | true;\n highlights?: HighlightsContentsOptions | true;\n};\n\n/**\n * Options for retrieving text from page.\n * @typedef {Object} TextContentsOptions\n * @property {number} [maxCharacters] - The maximum number of characters to return.\n * @property {boolean} [includeHtmlTags] - If true, includes HTML tags in the returned text. Default: false\n */\nexport type TextContentsOptions = {\n maxCharacters?: number;\n includeHtmlTags?: boolean;\n}\n\n/**\n * Options for retrieving highlights from page.\n * @typedef {Object} HighlightsContentsOptions\n * @property {string} [query] - The query string to use for highlights search.\n * @property {number} [numSentences] - The number of sentences to return for each highlight.\n * @property {number} [highlightsPerUrl] - The number of highlights to return for each URL.\n */\nexport type HighlightsContentsOptions = {\n query?: string;\n numSentences?: number;\n highlightsPerUrl?: number;\n}\n\n\n/**\n * @typedef {Object} TextResponse\n * @property {string} text - Text from page\n */\nexport type TextResponse = { text: string };\n\n/**\n * @typedef {Object} HighlightsResponse\n * @property {string[]} highlights - The highlights as an array of strings.\n * @property {number[]} highlightScores - The corresponding scores as an array of floats, 0 to 1\n */\nexport type HighlightsResponse = { highlights: string[], highlightScores: number[] };\n\nexport type Default<T extends {}, U> = [keyof T] extends [never] ? U : T;\n\n/**\n * @typedef {Object} ContentsResultComponent\n * Depending on 'ContentsOptions', this yields either a 'TextResponse', a 'HighlightsResponse', both, or an empty object.\n *\n * @template T - A type extending from 'ContentsOptions'.\n */\nexport type ContentsResultComponent<T extends ContentsOptions> =\n Default<(T['text'] extends (object | true) ? TextResponse : {}) &\n (T['highlights'] extends (object | true) ? HighlightsResponse : {}), TextResponse>;\n\n\n/**\n * Represents a search result object.\n * @typedef {Object} Result\n * @property {string} title - The title of the search result.\n * @property {string} url - The URL of the search result.\n * @property {string} [publishedDate] - The estimated creation date of the content.\n * @property {string} [author] - The author of the content, if available.\n * @property {number} [score] - Similarity score between the query/url and the result.\n * @property {string} id - The temporary ID for the document.\n */\nexport type SearchResult<T extends ContentsOptions = {}> = {\n title: string | null;\n url: string;\n publishedDate?: string;\n author?: string;\n score?: number;\n id: string;\n} & ContentsResultComponent<T>;\n\n/**\n * Represents a search response object.\n * @typedef {Object} SearchResponse\n * @property {Result[]} results - The list of search results.\n * @property {string} [autopromptString] - The autoprompt string, if applicable.\n */\nexport type SearchResponse<T extends ContentsOptions = {}> = {\n results: SearchResult<T>[];\n autopromptString?: string;\n}\n\n/**\n * The Exa class encapsulates the API's endpoints.\n */\nclass Exa {\n private baseURL: string;\n private headers: Headers;\n\n /**\n * Constructs the Exa API client.\n * @param {string} apiKey - The API key for authentication.\n * @param {string} [baseURL] - The base URL of the Exa API.\n */\n constructor(\n apiKey?: string,\n baseURL: string = \"https://api.exa.ai\"\n ) {\n this.baseURL = baseURL;\n if (!apiKey) {\n apiKey = process.env.EXASEARCH_API_KEY;\n if (!apiKey) {\n throw new Error(\"API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)\");\n }\n }\n this.headers = new Headers({\n \"x-api-key\": apiKey,\n \"Content-Type\": \"application/json\",\n \"User-Agent\": \"exa-node 1.0.27\",\n });\n }\n\n /**\n* Makes a request to the Exa API.\n* @param {string} endpoint - The API endpoint to call.\n* @param {string} method - The HTTP method to use.\n* @param {any} [body] - The request body for POST requests.\n* @returns {Promise<any>} The response from the API.\n*/\n private async request(\n endpoint: string,\n method: string,\n body?: any\n ): Promise<any> {\n const response = await fetch(this.baseURL + endpoint, {\n method,\n headers: this.headers,\n body: body ? JSON.stringify(body) : undefined,\n });\n\n if (!response.ok) {\n const message = (await response.json()).error;\n throw new Error(\n `Request failed with status ${response.status}. ${message}`\n );\n }\n\n return await response.json();\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async search(query: string, options?: RegularSearchOptions): Promise<SearchResponse> {\n return await this.request(\"/search\", 'POST', { query, ...options });\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query and returns the contents of the documents.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async searchAndContents<T extends ContentsOptions>(query: string, options?: RegularSearchOptions & T): Promise<SearchResponse<T>> {\n const { text, highlights, ...rest } = options || {};\n return await this.request(\"/search\", 'POST', {\n query,\n contents: (!text && !highlights) ? { text: true } : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {})\n },\n ...rest\n });\n }\n\n /**\n * Finds similar links to the provided URL.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilar(\n url: string,\n options?: FindSimilarOptions\n ): Promise<SearchResponse> {\n return await this.request(\"/findSimilar\", 'POST', { url, ...options });\n }\n\n /**\n * Finds similar links to the provided URL and returns the contents of the documents.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilarAndContents<T extends ContentsOptions>(url: string, options?: FindSimilarOptions & T): Promise<SearchResponse<T>> {\n const { text, highlights, ...rest } = options || {};\n return await this.request(\"/findSimilar\", 'POST', {\n url,\n contents: (!text && !highlights) ? { text: true } : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {})\n },\n ...rest\n });\n }\n\n /**\n * Retrieves contents of documents based on a list of document IDs.\n * @param {string | string[] | SearchResult[]} ids - An array of document IDs.\n * @param {ContentsOptions} [options] - Additional options for retrieving document contents.\n * @returns {Promise<GetContentsResponse>} A list of document contents.\n */\n async getContents<T extends ContentsOptions>(ids: string | string[] | SearchResult[], options?: T): Promise<SearchResponse<T>> {\n if (ids.length === 0) {\n throw new Error(\"Must provide at least one ID\");\n }\n let requestIds: string[];\n if (typeof ids === \"string\") {\n requestIds = [ids];\n } else if (typeof ids[0] === \"string\") {\n requestIds = ids as string[];\n } else {\n requestIds = (ids as SearchResult[]).map((result) => result.id);\n }\n return await this.request(`/contents`, 'POST', { ids: requestIds, ...options, });\n }\n}\n\nexport default Exa;\n"],"mappings":"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","names":["fetch"]}
1
+ {"version":3,"sources":["../src/index.ts"],"sourcesContent":["import fetch, { Headers } from \"cross-fetch\";\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} SearchOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude in the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [useAutoprompt] - If true, converts query to a Metaphor query.\n * @property {string} [type] - Type of search, 'keyword' or 'neural'.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n * @property {string[]} [includeText] - List of strings that must be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n * @property {string[]} [excludeText] - List of strings that must not be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n */\nexport type BaseSearchOptions = {\n numResults?: number;\n includeDomains?: string[];\n excludeDomains?: string[];\n startCrawlDate?: string;\n endCrawlDate?: string;\n startPublishedDate?: string;\n endPublishedDate?: string;\n category?: string;\n includeText?: string[];\n excludeText?: string[];\n};\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} RegularSearchOptions\n */\nexport type RegularSearchOptions = BaseSearchOptions & {\n useAutoprompt?: boolean;\n type?: string;\n};\n\n/**\n * Options for finding similar links.\n * @typedef {Object} FindSimilarOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude from the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [excludeSourceDomain] - If true, excludes links from the base domain of the input.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n * @property {string[]} [includeText] - List of strings that must be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n * @property {string[]} [excludeText] - List of strings that must not be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n */\nexport type FindSimilarOptions = BaseSearchOptions & {\n excludeSourceDomain?: boolean;\n};\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} ContentsOptions\n * @property {TextContentsOptions | boolean} [text] - Options for retrieving text contents.\n * @property {HighlightsContentsOptions | boolean} [highlights] - Options for retrieving highlights.\n * @property {SummaryContentsOptions | boolean} [summary] - Options for retrieving summary.\n * @property {LivecrawlOptions} [livecrawl] - Options for livecrawling contents. Default is \"never\" for neural/auto search, \"fallback\" for keyword search.\n * @property {boolean} [filterEmptyResults] - If true, filters out results with no contents. Default is true.\n */\nexport type ContentsOptions = {\n text?: TextContentsOptions | true;\n highlights?: HighlightsContentsOptions | true;\n summary?: SummaryContentsOptions | true;\n livecrawl?: LivecrawlOptions;\n filterEmptyResults?: boolean;\n};\n\n/**\n * Options for livecrawling contents\n * @typedef {string} LivecrawlOptions\n */\nexport type LivecrawlOptions = \"never\" | \"fallback\" | \"always\";\n\n/**\n * Options for retrieving text from page.\n * @typedef {Object} TextContentsOptions\n * @property {number} [maxCharacters] - The maximum number of characters to return.\n * @property {boolean} [includeHtmlTags] - If true, includes HTML tags in the returned text. Default: false\n */\nexport type TextContentsOptions = {\n maxCharacters?: number;\n includeHtmlTags?: boolean;\n};\n\n/**\n * Options for retrieving highlights from page.\n * @typedef {Object} HighlightsContentsOptions\n * @property {string} [query] - The query string to use for highlights search.\n * @property {number} [numSentences] - The number of sentences to return for each highlight.\n * @property {number} [highlightsPerUrl] - The number of highlights to return for each URL.\n */\nexport type HighlightsContentsOptions = {\n query?: string;\n numSentences?: number;\n highlightsPerUrl?: number;\n};\n\n/**\n * Options for retrieving summary from page.\n * @typedef {Object} SummaryContentsOptions\n * @property {string} [query] - The query string to use for summary generation.\n */\nexport type SummaryContentsOptions = {\n query?: string;\n};\n\n/**\n * @typedef {Object} TextResponse\n * @property {string} text - Text from page\n */\nexport type TextResponse = { text: string };\n\n/**\n * @typedef {Object} HighlightsResponse\n * @property {string[]} highlights - The highlights as an array of strings.\n * @property {number[]} highlightScores - The corresponding scores as an array of floats, 0 to 1\n */\nexport type HighlightsResponse = {\n highlights: string[];\n highlightScores: number[];\n};\n\n/**\n * @typedef {Object} SummaryResponse\n * @property {string} summary - The generated summary of the page content.\n */\nexport type SummaryResponse = { summary: string };\n\nexport type Default<T extends {}, U> = [keyof T] extends [never] ? U : T;\n\n/**\n * @typedef {Object} ContentsResultComponent\n * Depending on 'ContentsOptions', this yields a combination of 'TextResponse', 'HighlightsResponse', 'SummaryResponse', or an empty object.\n *\n * @template T - A type extending from 'ContentsOptions'.\n */\nexport type ContentsResultComponent<T extends ContentsOptions> = Default<\n (T[\"text\"] extends object | true ? TextResponse : {}) &\n (T[\"highlights\"] extends object | true ? HighlightsResponse : {}) &\n (T[\"summary\"] extends object | true ? SummaryResponse : {}),\n TextResponse\n>;\n\n/**\n * Represents a search result object.\n * @typedef {Object} Result\n * @property {string} title - The title of the search result.\n * @property {string} url - The URL of the search result.\n * @property {string} [publishedDate] - The estimated creation date of the content.\n * @property {string} [author] - The author of the content, if available.\n * @property {number} [score] - Similarity score between the query/url and the result.\n * @property {string} id - The temporary ID for the document.\n */\nexport type SearchResult<T extends ContentsOptions = {}> = {\n title: string | null;\n url: string;\n publishedDate?: string;\n author?: string;\n score?: number;\n id: string;\n} & ContentsResultComponent<T>;\n\n/**\n * Represents a search response object.\n * @typedef {Object} SearchResponse\n * @property {Result[]} results - The list of search results.\n * @property {string} [autopromptString] - The autoprompt string, if applicable.\n */\nexport type SearchResponse<T extends ContentsOptions = {}> = {\n results: SearchResult<T>[];\n autopromptString?: string;\n};\n\n/**\n * The Exa class encapsulates the API's endpoints.\n */\nclass Exa {\n private baseURL: string;\n private headers: Headers;\n\n /**\n * Constructs the Exa API client.\n * @param {string} apiKey - The API key for authentication.\n * @param {string} [baseURL] - The base URL of the Exa API.\n */\n constructor(apiKey?: string, baseURL: string = \"https://api.exa.ai\") {\n this.baseURL = baseURL;\n if (!apiKey) {\n apiKey = process.env.EXASEARCH_API_KEY;\n if (!apiKey) {\n throw new Error(\n \"API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)\"\n );\n }\n }\n this.headers = new Headers({\n \"x-api-key\": apiKey,\n \"Content-Type\": \"application/json\",\n \"User-Agent\": \"exa-node 1.0.27\",\n });\n }\n\n /**\n * Makes a request to the Exa API.\n * @param {string} endpoint - The API endpoint to call.\n * @param {string} method - The HTTP method to use.\n * @param {any} [body] - The request body for POST requests.\n * @returns {Promise<any>} The response from the API.\n */\n private async request(\n endpoint: string,\n method: string,\n body?: any\n ): Promise<any> {\n const response = await fetch(this.baseURL + endpoint, {\n method,\n headers: this.headers,\n body: body ? JSON.stringify(body) : undefined,\n });\n\n if (!response.ok) {\n const message = (await response.json()).error;\n throw new Error(\n `Request failed with status ${response.status}. ${message}`\n );\n }\n\n return await response.json();\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async search(\n query: string,\n options?: RegularSearchOptions\n ): Promise<SearchResponse> {\n return await this.request(\"/search\", \"POST\", { query, ...options });\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query and returns the contents of the documents.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async searchAndContents<T extends ContentsOptions>(\n query: string,\n options?: RegularSearchOptions & T\n ): Promise<SearchResponse<T>> {\n const {\n text,\n highlights,\n summary,\n livecrawl,\n filterEmptyResults,\n ...rest\n } = options || {};\n const isBeta = process.env.NPM_CONFIG_TAG === \"beta\";\n return await this.request(\"/search\", \"POST\", {\n query,\n contents:\n !text && !highlights && !summary\n ? { text: true, ...(isBeta ? { livecrawl, filterEmptyResults } : {}) }\n : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {}),\n ...(summary ? { summary } : {}),\n ...(isBeta ? { livecrawl, filterEmptyResults } : {}),\n },\n ...rest,\n });\n }\n\n /**\n * Finds similar links to the provided URL.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilar(\n url: string,\n options?: FindSimilarOptions\n ): Promise<SearchResponse> {\n return await this.request(\"/findSimilar\", \"POST\", { url, ...options });\n }\n\n /**\n * Finds similar links to the provided URL and returns the contents of the documents.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilarAndContents<T extends ContentsOptions>(\n url: string,\n options?: FindSimilarOptions & T\n ): Promise<SearchResponse<T>> {\n const {\n text,\n highlights,\n summary,\n livecrawl,\n filterEmptyResults,\n ...rest\n } = options || {};\n const isBeta = process.env.NPM_CONFIG_TAG === \"beta\";\n return await this.request(\"/findSimilar\", \"POST\", {\n url,\n contents:\n !text && !highlights && !summary\n ? { text: true, ...(isBeta ? { livecrawl, filterEmptyResults } : {}) }\n : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {}),\n ...(summary ? { summary } : {}),\n ...(isBeta ? { livecrawl, filterEmptyResults } : {}),\n },\n ...rest,\n });\n }\n\n /**\n * Retrieves contents of documents based on a list of document IDs.\n * @param {string | string[] | SearchResult[]} ids - An array of document IDs.\n * @param {ContentsOptions} [options] - Additional options for retrieving document contents.\n * @returns {Promise<GetContentsResponse>} A list of document contents.\n */\n async getContents<T extends ContentsOptions>(\n ids: string | string[] | SearchResult[],\n options?: T\n ): Promise<SearchResponse<T>> {\n const { livecrawl, filterEmptyResults, ...rest } = options || {};\n const isBeta = process.env.NPM_CONFIG_TAG === \"beta\";\n if (ids.length === 0) {\n throw new Error(\"Must provide at least one ID\");\n }\n let requestIds: string[];\n if (typeof ids === \"string\") {\n requestIds = [ids];\n } else if (typeof ids[0] === \"string\") {\n requestIds = ids as string[];\n } else {\n requestIds = (ids as SearchResult[]).map((result) => result.id);\n }\n return await this.request(`/contents`, \"POST\", {\n ids: requestIds,\n ...(isBeta ? { livecrawl, filterEmptyResults } : {}),\n ...rest,\n });\n }\n}\n\nexport default Exa;\n"],"mappings":"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","names":["fetch"]}
package/dist/index.mjs CHANGED
@@ -11,7 +11,9 @@ var Exa = class {
11
11
  if (!apiKey) {
12
12
  apiKey = process.env.EXASEARCH_API_KEY;
13
13
  if (!apiKey) {
14
- throw new Error("API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)");
14
+ throw new Error(
15
+ "API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)"
16
+ );
15
17
  }
16
18
  }
17
19
  this.headers = new Headers({
@@ -21,12 +23,12 @@ var Exa = class {
21
23
  });
22
24
  }
23
25
  /**
24
- * Makes a request to the Exa API.
25
- * @param {string} endpoint - The API endpoint to call.
26
- * @param {string} method - The HTTP method to use.
27
- * @param {any} [body] - The request body for POST requests.
28
- * @returns {Promise<any>} The response from the API.
29
- */
26
+ * Makes a request to the Exa API.
27
+ * @param {string} endpoint - The API endpoint to call.
28
+ * @param {string} method - The HTTP method to use.
29
+ * @param {any} [body] - The request body for POST requests.
30
+ * @returns {Promise<any>} The response from the API.
31
+ */
30
32
  async request(endpoint, method, body) {
31
33
  const response = await fetch(this.baseURL + endpoint, {
32
34
  method,
@@ -57,12 +59,22 @@ var Exa = class {
57
59
  * @returns {Promise<SearchResponse>} A list of relevant search results.
58
60
  */
59
61
  async searchAndContents(query, options) {
60
- const { text, highlights, ...rest } = options || {};
62
+ const {
63
+ text,
64
+ highlights,
65
+ summary,
66
+ livecrawl,
67
+ filterEmptyResults,
68
+ ...rest
69
+ } = options || {};
70
+ const isBeta = process.env.NPM_CONFIG_TAG === "beta";
61
71
  return await this.request("/search", "POST", {
62
72
  query,
63
- contents: !text && !highlights ? { text: true } : {
73
+ contents: !text && !highlights && !summary ? { text: true, ...isBeta ? { livecrawl, filterEmptyResults } : {} } : {
64
74
  ...text ? { text } : {},
65
- ...highlights ? { highlights } : {}
75
+ ...highlights ? { highlights } : {},
76
+ ...summary ? { summary } : {},
77
+ ...isBeta ? { livecrawl, filterEmptyResults } : {}
66
78
  },
67
79
  ...rest
68
80
  });
@@ -83,12 +95,22 @@ var Exa = class {
83
95
  * @returns {Promise<SearchResponse>} A list of similar search results.
84
96
  */
85
97
  async findSimilarAndContents(url, options) {
86
- const { text, highlights, ...rest } = options || {};
98
+ const {
99
+ text,
100
+ highlights,
101
+ summary,
102
+ livecrawl,
103
+ filterEmptyResults,
104
+ ...rest
105
+ } = options || {};
106
+ const isBeta = process.env.NPM_CONFIG_TAG === "beta";
87
107
  return await this.request("/findSimilar", "POST", {
88
108
  url,
89
- contents: !text && !highlights ? { text: true } : {
109
+ contents: !text && !highlights && !summary ? { text: true, ...isBeta ? { livecrawl, filterEmptyResults } : {} } : {
90
110
  ...text ? { text } : {},
91
- ...highlights ? { highlights } : {}
111
+ ...highlights ? { highlights } : {},
112
+ ...summary ? { summary } : {},
113
+ ...isBeta ? { livecrawl, filterEmptyResults } : {}
92
114
  },
93
115
  ...rest
94
116
  });
@@ -100,6 +122,8 @@ var Exa = class {
100
122
  * @returns {Promise<GetContentsResponse>} A list of document contents.
101
123
  */
102
124
  async getContents(ids, options) {
125
+ const { livecrawl, filterEmptyResults, ...rest } = options || {};
126
+ const isBeta = process.env.NPM_CONFIG_TAG === "beta";
103
127
  if (ids.length === 0) {
104
128
  throw new Error("Must provide at least one ID");
105
129
  }
@@ -111,7 +135,11 @@ var Exa = class {
111
135
  } else {
112
136
  requestIds = ids.map((result) => result.id);
113
137
  }
114
- return await this.request(`/contents`, "POST", { ids: requestIds, ...options });
138
+ return await this.request(`/contents`, "POST", {
139
+ ids: requestIds,
140
+ ...isBeta ? { livecrawl, filterEmptyResults } : {},
141
+ ...rest
142
+ });
115
143
  }
116
144
  };
117
145
  var src_default = Exa;
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts"],"sourcesContent":["import fetch, { Headers } from 'cross-fetch';\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} SearchOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude in the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [useAutoprompt] - If true, converts query to a Metaphor query.\n * @property {string} [type] - Type of search, 'keyword' or 'neural'.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n */\nexport type BaseSearchOptions = {\n numResults?: number;\n includeDomains?: string[];\n excludeDomains?: string[];\n startCrawlDate?: string;\n endCrawlDate?: string;\n startPublishedDate?: string;\n endPublishedDate?: string;\n category?: string;\n};\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} ContentsOptions\n * @property {string[]} [formats] - An array of format types asked for. Currently supports `extract` (first 1000 tokens) and `text` (full parsed HTML text). If this isn't specified, defaults to `extract`.\n */\nexport type RegularSearchOptions = BaseSearchOptions & {\n useAutoprompt?: boolean;\n type?: string;\n}\n\n/**\n * Options for finding similar links.\n * @typedef {Object} FindSimilarOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude from the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [excludeSourceDomain] - If true, excludes links from the base domain of the input.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n */\nexport type FindSimilarOptions = BaseSearchOptions & {\n excludeSourceDomain?: boolean;\n}\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} ContentsOptions\n * @property {TextContentsOptions | boolean} [text] - Options for retrieving text contents.\n * @property {HighlightsContentsOptions | boolean} [highlights] - Options for retrieving highlights.\n */\nexport type ContentsOptions = {\n text?: TextContentsOptions | true;\n highlights?: HighlightsContentsOptions | true;\n};\n\n/**\n * Options for retrieving text from page.\n * @typedef {Object} TextContentsOptions\n * @property {number} [maxCharacters] - The maximum number of characters to return.\n * @property {boolean} [includeHtmlTags] - If true, includes HTML tags in the returned text. Default: false\n */\nexport type TextContentsOptions = {\n maxCharacters?: number;\n includeHtmlTags?: boolean;\n}\n\n/**\n * Options for retrieving highlights from page.\n * @typedef {Object} HighlightsContentsOptions\n * @property {string} [query] - The query string to use for highlights search.\n * @property {number} [numSentences] - The number of sentences to return for each highlight.\n * @property {number} [highlightsPerUrl] - The number of highlights to return for each URL.\n */\nexport type HighlightsContentsOptions = {\n query?: string;\n numSentences?: number;\n highlightsPerUrl?: number;\n}\n\n\n/**\n * @typedef {Object} TextResponse\n * @property {string} text - Text from page\n */\nexport type TextResponse = { text: string };\n\n/**\n * @typedef {Object} HighlightsResponse\n * @property {string[]} highlights - The highlights as an array of strings.\n * @property {number[]} highlightScores - The corresponding scores as an array of floats, 0 to 1\n */\nexport type HighlightsResponse = { highlights: string[], highlightScores: number[] };\n\nexport type Default<T extends {}, U> = [keyof T] extends [never] ? U : T;\n\n/**\n * @typedef {Object} ContentsResultComponent\n * Depending on 'ContentsOptions', this yields either a 'TextResponse', a 'HighlightsResponse', both, or an empty object.\n *\n * @template T - A type extending from 'ContentsOptions'.\n */\nexport type ContentsResultComponent<T extends ContentsOptions> =\n Default<(T['text'] extends (object | true) ? TextResponse : {}) &\n (T['highlights'] extends (object | true) ? HighlightsResponse : {}), TextResponse>;\n\n\n/**\n * Represents a search result object.\n * @typedef {Object} Result\n * @property {string} title - The title of the search result.\n * @property {string} url - The URL of the search result.\n * @property {string} [publishedDate] - The estimated creation date of the content.\n * @property {string} [author] - The author of the content, if available.\n * @property {number} [score] - Similarity score between the query/url and the result.\n * @property {string} id - The temporary ID for the document.\n */\nexport type SearchResult<T extends ContentsOptions = {}> = {\n title: string | null;\n url: string;\n publishedDate?: string;\n author?: string;\n score?: number;\n id: string;\n} & ContentsResultComponent<T>;\n\n/**\n * Represents a search response object.\n * @typedef {Object} SearchResponse\n * @property {Result[]} results - The list of search results.\n * @property {string} [autopromptString] - The autoprompt string, if applicable.\n */\nexport type SearchResponse<T extends ContentsOptions = {}> = {\n results: SearchResult<T>[];\n autopromptString?: string;\n}\n\n/**\n * The Exa class encapsulates the API's endpoints.\n */\nclass Exa {\n private baseURL: string;\n private headers: Headers;\n\n /**\n * Constructs the Exa API client.\n * @param {string} apiKey - The API key for authentication.\n * @param {string} [baseURL] - The base URL of the Exa API.\n */\n constructor(\n apiKey?: string,\n baseURL: string = \"https://api.exa.ai\"\n ) {\n this.baseURL = baseURL;\n if (!apiKey) {\n apiKey = process.env.EXASEARCH_API_KEY;\n if (!apiKey) {\n throw new Error(\"API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)\");\n }\n }\n this.headers = new Headers({\n \"x-api-key\": apiKey,\n \"Content-Type\": \"application/json\",\n \"User-Agent\": \"exa-node 1.0.27\",\n });\n }\n\n /**\n* Makes a request to the Exa API.\n* @param {string} endpoint - The API endpoint to call.\n* @param {string} method - The HTTP method to use.\n* @param {any} [body] - The request body for POST requests.\n* @returns {Promise<any>} The response from the API.\n*/\n private async request(\n endpoint: string,\n method: string,\n body?: any\n ): Promise<any> {\n const response = await fetch(this.baseURL + endpoint, {\n method,\n headers: this.headers,\n body: body ? JSON.stringify(body) : undefined,\n });\n\n if (!response.ok) {\n const message = (await response.json()).error;\n throw new Error(\n `Request failed with status ${response.status}. ${message}`\n );\n }\n\n return await response.json();\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async search(query: string, options?: RegularSearchOptions): Promise<SearchResponse> {\n return await this.request(\"/search\", 'POST', { query, ...options });\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query and returns the contents of the documents.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async searchAndContents<T extends ContentsOptions>(query: string, options?: RegularSearchOptions & T): Promise<SearchResponse<T>> {\n const { text, highlights, ...rest } = options || {};\n return await this.request(\"/search\", 'POST', {\n query,\n contents: (!text && !highlights) ? { text: true } : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {})\n },\n ...rest\n });\n }\n\n /**\n * Finds similar links to the provided URL.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilar(\n url: string,\n options?: FindSimilarOptions\n ): Promise<SearchResponse> {\n return await this.request(\"/findSimilar\", 'POST', { url, ...options });\n }\n\n /**\n * Finds similar links to the provided URL and returns the contents of the documents.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilarAndContents<T extends ContentsOptions>(url: string, options?: FindSimilarOptions & T): Promise<SearchResponse<T>> {\n const { text, highlights, ...rest } = options || {};\n return await this.request(\"/findSimilar\", 'POST', {\n url,\n contents: (!text && !highlights) ? { text: true } : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {})\n },\n ...rest\n });\n }\n\n /**\n * Retrieves contents of documents based on a list of document IDs.\n * @param {string | string[] | SearchResult[]} ids - An array of document IDs.\n * @param {ContentsOptions} [options] - Additional options for retrieving document contents.\n * @returns {Promise<GetContentsResponse>} A list of document contents.\n */\n async getContents<T extends ContentsOptions>(ids: string | string[] | SearchResult[], options?: T): Promise<SearchResponse<T>> {\n if (ids.length === 0) {\n throw new Error(\"Must provide at least one ID\");\n }\n let requestIds: string[];\n if (typeof ids === \"string\") {\n requestIds = [ids];\n } else if (typeof ids[0] === \"string\") {\n requestIds = ids as string[];\n } else {\n requestIds = (ids as SearchResult[]).map((result) => result.id);\n }\n return await this.request(`/contents`, 'POST', { ids: requestIds, ...options, });\n }\n}\n\nexport default Exa;\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../src/index.ts"],"sourcesContent":["import fetch, { Headers } from \"cross-fetch\";\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} SearchOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude in the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [useAutoprompt] - If true, converts query to a Metaphor query.\n * @property {string} [type] - Type of search, 'keyword' or 'neural'.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n * @property {string[]} [includeText] - List of strings that must be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n * @property {string[]} [excludeText] - List of strings that must not be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n */\nexport type BaseSearchOptions = {\n numResults?: number;\n includeDomains?: string[];\n excludeDomains?: string[];\n startCrawlDate?: string;\n endCrawlDate?: string;\n startPublishedDate?: string;\n endPublishedDate?: string;\n category?: string;\n includeText?: string[];\n excludeText?: string[];\n};\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} RegularSearchOptions\n */\nexport type RegularSearchOptions = BaseSearchOptions & {\n useAutoprompt?: boolean;\n type?: string;\n};\n\n/**\n * Options for finding similar links.\n * @typedef {Object} FindSimilarOptions\n * @property {number} [numResults] - Number of search results to return. Default 10. Max 10 for basic plans.\n * @property {string[]} [includeDomains] - List of domains to include in the search.\n * @property {string[]} [excludeDomains] - List of domains to exclude from the search.\n * @property {string} [startCrawlDate] - Start date for results based on crawl date.\n * @property {string} [endCrawlDate] - End date for results based on crawl date.\n * @property {string} [startPublishedDate] - Start date for results based on published date.\n * @property {string} [endPublishedDate] - End date for results based on published date.\n * @property {boolean} [excludeSourceDomain] - If true, excludes links from the base domain of the input.\n * @property {string} [category] - A data category to focus on, with higher comprehensivity and data cleanliness. Currently, the only category is company.\n * @property {string[]} [includeText] - List of strings that must be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n * @property {string[]} [excludeText] - List of strings that must not be present in webpage text of results. Currently only supports 1 string of up to 5 words.\n */\nexport type FindSimilarOptions = BaseSearchOptions & {\n excludeSourceDomain?: boolean;\n};\n\n/**\n * Search options for performing a search query.\n * @typedef {Object} ContentsOptions\n * @property {TextContentsOptions | boolean} [text] - Options for retrieving text contents.\n * @property {HighlightsContentsOptions | boolean} [highlights] - Options for retrieving highlights.\n * @property {SummaryContentsOptions | boolean} [summary] - Options for retrieving summary.\n * @property {LivecrawlOptions} [livecrawl] - Options for livecrawling contents. Default is \"never\" for neural/auto search, \"fallback\" for keyword search.\n * @property {boolean} [filterEmptyResults] - If true, filters out results with no contents. Default is true.\n */\nexport type ContentsOptions = {\n text?: TextContentsOptions | true;\n highlights?: HighlightsContentsOptions | true;\n summary?: SummaryContentsOptions | true;\n livecrawl?: LivecrawlOptions;\n filterEmptyResults?: boolean;\n};\n\n/**\n * Options for livecrawling contents\n * @typedef {string} LivecrawlOptions\n */\nexport type LivecrawlOptions = \"never\" | \"fallback\" | \"always\";\n\n/**\n * Options for retrieving text from page.\n * @typedef {Object} TextContentsOptions\n * @property {number} [maxCharacters] - The maximum number of characters to return.\n * @property {boolean} [includeHtmlTags] - If true, includes HTML tags in the returned text. Default: false\n */\nexport type TextContentsOptions = {\n maxCharacters?: number;\n includeHtmlTags?: boolean;\n};\n\n/**\n * Options for retrieving highlights from page.\n * @typedef {Object} HighlightsContentsOptions\n * @property {string} [query] - The query string to use for highlights search.\n * @property {number} [numSentences] - The number of sentences to return for each highlight.\n * @property {number} [highlightsPerUrl] - The number of highlights to return for each URL.\n */\nexport type HighlightsContentsOptions = {\n query?: string;\n numSentences?: number;\n highlightsPerUrl?: number;\n};\n\n/**\n * Options for retrieving summary from page.\n * @typedef {Object} SummaryContentsOptions\n * @property {string} [query] - The query string to use for summary generation.\n */\nexport type SummaryContentsOptions = {\n query?: string;\n};\n\n/**\n * @typedef {Object} TextResponse\n * @property {string} text - Text from page\n */\nexport type TextResponse = { text: string };\n\n/**\n * @typedef {Object} HighlightsResponse\n * @property {string[]} highlights - The highlights as an array of strings.\n * @property {number[]} highlightScores - The corresponding scores as an array of floats, 0 to 1\n */\nexport type HighlightsResponse = {\n highlights: string[];\n highlightScores: number[];\n};\n\n/**\n * @typedef {Object} SummaryResponse\n * @property {string} summary - The generated summary of the page content.\n */\nexport type SummaryResponse = { summary: string };\n\nexport type Default<T extends {}, U> = [keyof T] extends [never] ? U : T;\n\n/**\n * @typedef {Object} ContentsResultComponent\n * Depending on 'ContentsOptions', this yields a combination of 'TextResponse', 'HighlightsResponse', 'SummaryResponse', or an empty object.\n *\n * @template T - A type extending from 'ContentsOptions'.\n */\nexport type ContentsResultComponent<T extends ContentsOptions> = Default<\n (T[\"text\"] extends object | true ? TextResponse : {}) &\n (T[\"highlights\"] extends object | true ? HighlightsResponse : {}) &\n (T[\"summary\"] extends object | true ? SummaryResponse : {}),\n TextResponse\n>;\n\n/**\n * Represents a search result object.\n * @typedef {Object} Result\n * @property {string} title - The title of the search result.\n * @property {string} url - The URL of the search result.\n * @property {string} [publishedDate] - The estimated creation date of the content.\n * @property {string} [author] - The author of the content, if available.\n * @property {number} [score] - Similarity score between the query/url and the result.\n * @property {string} id - The temporary ID for the document.\n */\nexport type SearchResult<T extends ContentsOptions = {}> = {\n title: string | null;\n url: string;\n publishedDate?: string;\n author?: string;\n score?: number;\n id: string;\n} & ContentsResultComponent<T>;\n\n/**\n * Represents a search response object.\n * @typedef {Object} SearchResponse\n * @property {Result[]} results - The list of search results.\n * @property {string} [autopromptString] - The autoprompt string, if applicable.\n */\nexport type SearchResponse<T extends ContentsOptions = {}> = {\n results: SearchResult<T>[];\n autopromptString?: string;\n};\n\n/**\n * The Exa class encapsulates the API's endpoints.\n */\nclass Exa {\n private baseURL: string;\n private headers: Headers;\n\n /**\n * Constructs the Exa API client.\n * @param {string} apiKey - The API key for authentication.\n * @param {string} [baseURL] - The base URL of the Exa API.\n */\n constructor(apiKey?: string, baseURL: string = \"https://api.exa.ai\") {\n this.baseURL = baseURL;\n if (!apiKey) {\n apiKey = process.env.EXASEARCH_API_KEY;\n if (!apiKey) {\n throw new Error(\n \"API key must be provided as an argument or as an environment variable (EXASEARCH_API_KEY)\"\n );\n }\n }\n this.headers = new Headers({\n \"x-api-key\": apiKey,\n \"Content-Type\": \"application/json\",\n \"User-Agent\": \"exa-node 1.0.27\",\n });\n }\n\n /**\n * Makes a request to the Exa API.\n * @param {string} endpoint - The API endpoint to call.\n * @param {string} method - The HTTP method to use.\n * @param {any} [body] - The request body for POST requests.\n * @returns {Promise<any>} The response from the API.\n */\n private async request(\n endpoint: string,\n method: string,\n body?: any\n ): Promise<any> {\n const response = await fetch(this.baseURL + endpoint, {\n method,\n headers: this.headers,\n body: body ? JSON.stringify(body) : undefined,\n });\n\n if (!response.ok) {\n const message = (await response.json()).error;\n throw new Error(\n `Request failed with status ${response.status}. ${message}`\n );\n }\n\n return await response.json();\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async search(\n query: string,\n options?: RegularSearchOptions\n ): Promise<SearchResponse> {\n return await this.request(\"/search\", \"POST\", { query, ...options });\n }\n\n /**\n * Performs a search with a Exa prompt-engineered query and returns the contents of the documents.\n * @param {string} query - The query string.\n * @param {SearchOptions} [options] - Additional search options.\n * @returns {Promise<SearchResponse>} A list of relevant search results.\n */\n async searchAndContents<T extends ContentsOptions>(\n query: string,\n options?: RegularSearchOptions & T\n ): Promise<SearchResponse<T>> {\n const {\n text,\n highlights,\n summary,\n livecrawl,\n filterEmptyResults,\n ...rest\n } = options || {};\n const isBeta = process.env.NPM_CONFIG_TAG === \"beta\";\n return await this.request(\"/search\", \"POST\", {\n query,\n contents:\n !text && !highlights && !summary\n ? { text: true, ...(isBeta ? { livecrawl, filterEmptyResults } : {}) }\n : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {}),\n ...(summary ? { summary } : {}),\n ...(isBeta ? { livecrawl, filterEmptyResults } : {}),\n },\n ...rest,\n });\n }\n\n /**\n * Finds similar links to the provided URL.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilar(\n url: string,\n options?: FindSimilarOptions\n ): Promise<SearchResponse> {\n return await this.request(\"/findSimilar\", \"POST\", { url, ...options });\n }\n\n /**\n * Finds similar links to the provided URL and returns the contents of the documents.\n * @param {string} url - The URL for which to find similar links.\n * @param {FindSimilarOptions} [options] - Additional options for finding similar links.\n * @returns {Promise<SearchResponse>} A list of similar search results.\n */\n async findSimilarAndContents<T extends ContentsOptions>(\n url: string,\n options?: FindSimilarOptions & T\n ): Promise<SearchResponse<T>> {\n const {\n text,\n highlights,\n summary,\n livecrawl,\n filterEmptyResults,\n ...rest\n } = options || {};\n const isBeta = process.env.NPM_CONFIG_TAG === \"beta\";\n return await this.request(\"/findSimilar\", \"POST\", {\n url,\n contents:\n !text && !highlights && !summary\n ? { text: true, ...(isBeta ? { livecrawl, filterEmptyResults } : {}) }\n : {\n ...(text ? { text } : {}),\n ...(highlights ? { highlights } : {}),\n ...(summary ? { summary } : {}),\n ...(isBeta ? { livecrawl, filterEmptyResults } : {}),\n },\n ...rest,\n });\n }\n\n /**\n * Retrieves contents of documents based on a list of document IDs.\n * @param {string | string[] | SearchResult[]} ids - An array of document IDs.\n * @param {ContentsOptions} [options] - Additional options for retrieving document contents.\n * @returns {Promise<GetContentsResponse>} A list of document contents.\n */\n async getContents<T extends ContentsOptions>(\n ids: string | string[] | SearchResult[],\n options?: T\n ): Promise<SearchResponse<T>> {\n const { livecrawl, filterEmptyResults, ...rest } = options || {};\n const isBeta = process.env.NPM_CONFIG_TAG === \"beta\";\n if (ids.length === 0) {\n throw new Error(\"Must provide at least one ID\");\n }\n let requestIds: string[];\n if (typeof ids === \"string\") {\n requestIds = [ids];\n } else if (typeof ids[0] === \"string\") {\n requestIds = ids as string[];\n } else {\n requestIds = (ids as SearchResult[]).map((result) => result.id);\n }\n return await this.request(`/contents`, \"POST\", {\n ids: requestIds,\n ...(isBeta ? { livecrawl, filterEmptyResults } : {}),\n ...rest,\n });\n }\n}\n\nexport default Exa;\n"],"mappings":"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","names":[]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "exa-js",
3
- "version": "1.0.12",
3
+ "version": "1.0.14-beta.0",
4
4
  "description": "Exa SDK for Node.js and the browser",
5
5
  "publishConfig": {
6
6
  "access": "public"
@@ -25,15 +25,21 @@
25
25
  "build": "tsup",
26
26
  "test": "vitest run",
27
27
  "generate-docs": "typedoc --plugin typedoc-plugin-markdown --out docs src/index.ts",
28
+ "build:beta": "cross-env NPM_CONFIG_TAG=beta npm run build",
29
+ "version:beta": "npm version --no-git-tag-version 1.0.14-beta.0",
30
+ "version:stable": "npm version patch",
31
+ "publish:beta": "npm run version:beta && npm run build:beta && npm publish --tag beta",
32
+ "publish:stable": "npm run version:stable && npm run build && npm publish",
28
33
  "prepublishOnly": "npm run build"
29
34
  },
30
35
  "license": "MIT",
31
36
  "devDependencies": {
37
+ "cross-env": "^7.0.3",
32
38
  "prettier": "2.8.4",
33
39
  "tsup": "6.6.3",
34
- "typescript": "4.9.5",
35
40
  "typedoc": "^0.25.4",
36
41
  "typedoc-plugin-markdown": "^3.17.1",
42
+ "typescript": "4.9.5",
37
43
  "vitest": "0.28.5"
38
44
  },
39
45
  "dependencies": {