Files
amazon-book-search/lib/index.js
sbilketay 5991736cd4 feat: Add raw description field and fix npm test compatibility
Major improvements and bug fixes:

🔧 Core Features:
- Add descriptionRaw field to API response (Amazon original text)
- Maintain backward compatibility with existing description field
- Enable comparison between raw and AI-enhanced descriptions

🛠️ Technical Fixes:
- Fix npm test compatibility issues (Chai, Mocha, Cheerio versions)
- Resolve ES module vs CommonJS conflicts
- Fix module variable references and error handling
- Update Gemini AI model to gemini-2.0-flash

🔒 Security:
- Remove hardcoded API keys from source code and tests
- Add input validation for ISBN parameters
- Improve error handling with proper message formatting

 Testing:
- Add comprehensive test coverage for raw description feature
- Fix all test failures (15/15 tests passing)
- Add comparison tests between raw and Gemini descriptions

📚 Documentation:
- Add comprehensive analysis and troubleshooting reports
- Document Gemini AI integration and API usage
- Include build and deployment guides

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <[email protected]>
2025-11-09 15:59:09 +03:00

82 lines
2.3 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
const { extractBookId, extractBookDetails } = require("./module");
const config = require("../config");
const axios = require("axios");
class AmazonBookSearch {
constructor(location) {
if (location !== "tr" && location !== "en") {
throw new Error("Invalid location! Must be 'tr' or 'en'");
}
this.url = location === "tr" ? config.tr_base_url : config.en_base_url;
const fetchBookId = async (isbn) => {
const headers = config.headers;
try {
const url = encodeURI(this.url + isbn);
const response = await axios.get(url, { headers });
if (!response.data) {
throw new Error("Kitap bilgisi bulunamadı!");
}
const bookId = extractBookId(response.data);
return bookId;
} catch (error) {
throw new Error(error.message);
}
};
this.getBookDetails = async (isbn, geminiApiKey) => {
// Input validation
if (!isbn || typeof isbn !== 'string') {
throw new Error("ISBN is required and must be a string");
}
// Clean ISBN (remove hyphens and spaces) and validate format
const cleanIsbn = isbn.replace(/[-\s]/g, '');
if (!/^\d{10}(\d{3})?$/.test(cleanIsbn)) {
throw new Error("Invalid ISBN format. Must be 10 or 13 digits");
}
const headers = config.headers;
try {
const bookId = await fetchBookId(cleanIsbn);
const url = encodeURI(
location === "tr"
? config.tr_detail_url + bookId
: config.en_detail_url + bookId
);
// Add delay to avoid rate limiting
await new Promise(resolve => setTimeout(resolve, config.fetchTimeout));
const response = await axios.get(url, { headers });
if (!response.data) {
throw new Error("Book details not found!");
}
const details = await extractBookDetails(
response.data,
cleanIsbn,
geminiApiKey,
location
);
return details;
} catch (error) {
throw new Error(error.message);
}
};
}
}
module.exports = AmazonBookSearch;
// Example usage:
// const AmazonBookSearch = require('./index.js');
//
// const bookSearch = new AmazonBookSearch("tr");
// const bookDetails = await bookSearch.getBookDetails("9944824453", process.env.GEMINI_API_KEY);
// console.log(bookDetails);