{"version":3,"sources":["../src/core/utils.ts","../src/core/styles.ts","../src/core/client.ts","../src/frameworks/next.ts"],"names":[],"mappings":";AAGO,SAAS,aAAa,KAAqB;AAChD,SAAO,IAAI,QAAQ,aAAa,CAAC,GAAG,WAAW,OAAO,YAAY,CAAC;AACrE;AAKO,SAAS,cAAiB,KAAa;AAC5C,MAAI,QAAQ,QAAQ,QAAQ,QAAW;AACrC,WAAO;AAAA,EACT;AAEA,MAAI,MAAM,QAAQ,GAAG,GAAG;AACtB,WAAO,IAAI,IAAI,CAAC,SAAS,cAAc,IAAI,CAAC;AAAA,EAC9C;AAEA,MAAI,OAAO,QAAQ,UAAU;AAC3B,UAAM,SAA8B,CAAC;AAErC,eAAW,OAAO,KAAK;AACrB,UAAI,OAAO,UAAU,eAAe,KAAK,KAAK,GAAG,GAAG;AAClD,cAAM,WAAW,aAAa,GAAG;AACjC,eAAO,QAAQ,IAAI,cAAc,IAAI,GAAG,CAAC;AAAA,MAC3C;AAAA,IACF;AAEA,WAAO;AAAA,EACT;AAEA,SAAO;AACT;AAuBO,SAAS,gBACd,UACA,QACQ;AACR,QAAM,eAAe,OAAO,KAAK,MAAM,EACpC,KAAK,EACL,IAAI,CAAC,QAAQ,GAAG,GAAG,IAAI,OAAO,GAAG,CAAC,EAAE,EACpC,KAAK,GAAG;AAEX,SAAO,GAAG,QAAQ,IAAI,YAAY;AACpC;AAKO,SAAS,cAAc,MAAc,QAAwB;AAElE,MAAI,CAAC;AAAM,WAAO;AAGlB,MAAI,KAAK,SAAS,SAAS,GAAG;AAE5B,WAAO,KAAK;AAAA,MACV;AAAA,MACA;AAAA,EAAc,MAAM;AAAA,IACtB;AAAA,EACF;AAGA,SAAO,UAAU,MAAM,WAAW,IAAI;AACxC;;;ACnFO,IAAM,sBAAsB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAmP5B,IAAM,2BAA2B;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA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","sourcesContent":["/**\n * Converts a snake_case string to camelCase\n */\nexport function snakeToCamel(str: string): string {\n  return str.replace(/_([a-z])/g, (_, letter) => letter.toUpperCase());\n}\n\n/**\n * Deep transforms object keys from snake_case to camelCase\n */\nexport function normalizeKeys<T>(obj: any): T {\n  if (obj === null || obj === undefined) {\n    return obj;\n  }\n\n  if (Array.isArray(obj)) {\n    return obj.map((item) => normalizeKeys(item)) as unknown as T;\n  }\n\n  if (typeof obj === 'object') {\n    const newObj: Record<string, any> = {};\n\n    for (const key in obj) {\n      if (Object.prototype.hasOwnProperty.call(obj, key)) {\n        const camelKey = snakeToCamel(key);\n        newObj[camelKey] = normalizeKeys(obj[key]);\n      }\n    }\n\n    return newObj as T;\n  }\n\n  return obj as T;\n}\n\n/**\n * Check if we're in a browser environment\n */\nexport function isBrowser(): boolean {\n  return typeof window !== 'undefined';\n}\n\n/**\n * Check if we're in a Node.js environment\n */\nexport function isNode(): boolean {\n  return (\n    typeof process !== 'undefined' &&\n    process.versions != null &&\n    process.versions.node != null\n  );\n}\n\n/**\n * Create a unique ID for deduplication\n */\nexport function createRequestId(\n  endpoint: string,\n  params: Record<string, any>\n): string {\n  const sortedParams = Object.keys(params)\n    .sort()\n    .map((key) => `${key}=${params[key]}`)\n    .join('&');\n\n  return `${endpoint}?${sortedParams}`;\n}\n\n/**\n * Add HTML styles for content rendering\n */\nexport function addHtmlStyles(html: string, styles: string): string {\n  // If HTML is empty, return it as is\n  if (!html) return html;\n\n  // Check if there's already a <style> tag\n  if (html.includes('<style>')) {\n    // Replace existing style tag with combined styles\n    return html.replace(\n      /<style>([\\s\\S]*?)<\\/style>/,\n      `<style>$1\\n${styles}</style>`\n    );\n  }\n\n  // If no style tag exists, add it at the beginning\n  return `<style>${styles}</style>${html}`;\n}\n","/**\n * Default CSS styles for blog content\n */\nexport const DEFAULT_BLOG_STYLES = `\n/* Base styles */\n.next-blog-ai-content {\n  line-height: 1.6;\n  color: inherit;\n  max-width: 100%;\n  margin: 0 auto;\n}\n\n/* Headings */\n.next-blog-ai-content h1,\n.next-blog-ai-content h2,\n.next-blog-ai-content h3,\n.next-blog-ai-content h4,\n.next-blog-ai-content h5,\n.next-blog-ai-content h6 {\n  margin-top: 2rem;\n  margin-bottom: 1rem;\n  font-weight: 600;\n  line-height: 1.25;\n  color: inherit;\n}\n\n.next-blog-ai-content h1 {\n  font-size: 2.25rem;\n}\n\n.next-blog-ai-content h2 {\n  font-size: 1.75rem;\n  border-bottom: 1px solid #eee;\n  padding-bottom: 0.3rem;\n}\n\n.next-blog-ai-content h3 {\n  font-size: 1.5rem;\n}\n\n.next-blog-ai-content h4 {\n  font-size: 1.25rem;\n}\n\n.next-blog-ai-content h5, .next-blog-ai-content h6 {\n  font-size: 1rem;\n}\n\n/* Paragraphs and text */\n.next-blog-ai-content p {\n  margin-top: 0;\n  margin-bottom: 1.5rem;\n}\n\n.next-blog-ai-content strong {\n  font-weight: 600;\n}\n\n.next-blog-ai-content em {\n  font-style: italic;\n}\n\n/* Lists */\n.next-blog-ai-content ul,\n.next-blog-ai-content ol {\n  margin-top: 0;\n  margin-bottom: 1.5rem;\n  padding-left: 2rem;\n}\n\n.next-blog-ai-content li {\n  margin-bottom: 0.5rem;\n}\n\n.next-blog-ai-content li > ul,\n.next-blog-ai-content li > ol {\n  margin-top: 0.5rem;\n  margin-bottom: 0.5rem;\n}\n\n/* Links */\n.next-blog-ai-content a {\n  color: #0070f3;\n  text-decoration: none;\n}\n\n.next-blog-ai-content a:hover {\n  text-decoration: underline;\n}\n\n/* Blockquotes */\n.next-blog-ai-content blockquote {\n  margin: 1.5rem 0;\n  padding: 0.5rem 1rem;\n  border-left: 4px solid #ddd;\n  color: #666;\n  background-color: #f9f9f9;\n}\n\n.next-blog-ai-content blockquote > :first-child {\n  margin-top: 0;\n}\n\n.next-blog-ai-content blockquote > :last-child {\n  margin-bottom: 0;\n}\n\n/* Code blocks */\n.next-blog-ai-content pre {\n  margin: 1.5rem 0;\n  padding: 1rem;\n  overflow: auto;\n  background-color: #f6f8fa;\n  border-radius: 3px;\n  font-size: 0.875rem;\n}\n\n.next-blog-ai-content code {\n  font-size: 0.875rem;\n  padding: 0.2em 0.4em;\n  background-color: rgba(27, 31, 35, 0.05);\n  border-radius: 3px;\n}\n\n.next-blog-ai-content pre code {\n  padding: 0;\n  background-color: transparent;\n}\n\n/* Tables */\n.next-blog-ai-content table {\n  width: 100%;\n  border-collapse: collapse;\n  margin: 1.5rem 0;\n}\n\n.next-blog-ai-content table th,\n.next-blog-ai-content table td {\n  padding: 0.5rem 1rem;\n  border: 1px solid #e1e4e8;\n}\n\n.next-blog-ai-content table th {\n  background-color: #f6f8fa;\n  font-weight: 600;\n  text-align: left;\n}\n\n.next-blog-ai-content table tr:nth-child(even) {\n  background-color: #f7f7f7;\n}\n\n/* Images */\n.next-blog-ai-content img {\n  max-width: 100%;\n  height: auto;\n  display: block;\n  margin: 1.5rem auto;\n}\n\n.next-blog-ai-content figure {\n  margin: 1.5rem auto;\n  text-align: center;\n}\n\n.next-blog-ai-content figcaption {\n  font-size: 0.875rem;\n  color: #666;\n  margin-top: 0.5rem;\n}\n\n/* Comments */\n.next-blog-ai-comments {\n  margin-top: 3rem;\n  border-top: 1px solid #eee;\n  padding-top: 2rem;\n}\n\n.next-blog-ai-comment {\n  margin-bottom: 2rem;\n  padding: 1rem;\n  background-color: #f9f9f9;\n  border-radius: 4px;\n}\n\n.next-blog-ai-comment-header {\n  display: flex;\n  justify-content: space-between;\n  margin-bottom: 0.5rem;\n}\n\n.next-blog-ai-comment-author {\n  font-weight: 600;\n}\n\n.next-blog-ai-comment-date {\n  color: #666;\n  font-size: 0.875rem;\n}\n\n.next-blog-ai-comment-content {\n  line-height: 1.5;\n}\n\n/* Comment form */\n.next-blog-ai-comment-form {\n  margin-top: 2rem;\n}\n\n.next-blog-ai-comment-form label {\n  display: block;\n  margin-bottom: 0.5rem;\n  font-weight: 600;\n}\n\n.next-blog-ai-comment-form input,\n.next-blog-ai-comment-form textarea {\n  width: 100%;\n  padding: 0.5rem;\n  margin-bottom: 1rem;\n  border: 1px solid #ddd;\n  border-radius: 4px;\n}\n\n.next-blog-ai-comment-form textarea {\n  min-height: 6rem;\n}\n\n.next-blog-ai-comment-form button {\n  background-color: #0070f3;\n  color: white;\n  border: none;\n  padding: 0.5rem 1rem;\n  border-radius: 4px;\n  cursor: pointer;\n  font-weight: 500;\n}\n\n.next-blog-ai-comment-form button:hover {\n  background-color: #0060df;\n}\n`;\n\n/**\n * Default CSS styles for blog list\n */\nexport const DEFAULT_BLOG_LIST_STYLES = `\n/* Blog post list - Grid View (Default) */\n.next-blog-ai-list {\n  display: grid;\n  grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));\n  gap: 2rem;\n  margin: 2rem 0;\n}\n\n@media (max-width: 768px) {\n  .next-blog-ai-list {\n    grid-template-columns: 1fr;\n  }\n}\n\n/* Post content padding for grid view */\n.next-blog-ai-post-content {\n  padding: 1.5rem;\n  display: flex;\n  flex-direction: column;\n}\n\n/* List View Styles */\n.next-blog-ai-list.list-view {\n  display: block;\n}\n\n.next-blog-ai-list.list-view .next-blog-ai-post-card {\n  display: flex;\n  flex-direction: row;\n  margin-bottom: 2rem;\n  border-radius: 8px;\n  overflow: hidden;\n  box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);\n  transition: transform 0.2s, box-shadow 0.2s;\n}\n\n.next-blog-ai-list.list-view .next-blog-ai-post-card:hover {\n  transform: translateY(-4px);\n  box-shadow: 0 10px 15px rgba(0, 0, 0, 0.1);\n}\n\n.next-blog-ai-list.list-view .next-blog-ai-post-image {\n  width: 250px;\n  min-width: 250px;\n  height: 180px;\n  padding-bottom: 0;\n  position: relative;\n  background-color: #f0f0f0;\n}\n\n.next-blog-ai-list.list-view .next-blog-ai-post-image img {\n  position: absolute;\n  top: 0;\n  left: 0;\n  width: 100%;\n  height: 100%;\n  object-fit: cover;\n}\n\n.next-blog-ai-list.list-view .next-blog-ai-post-content {\n  flex: 1;\n  padding: 1.5rem;\n  display: flex;\n  flex-direction: column;\n}\n\n/* Make sure grid view items display correctly */\n.next-blog-ai-list:not(.list-view) .next-blog-ai-post-card {\n  display: flex;\n  flex-direction: column;\n  border-radius: 8px;\n  overflow: hidden;\n  box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);\n  transition: transform 0.2s, box-shadow 0.2s;\n}\n\n/* Responsive adjustments for list view */\n@media (max-width: 768px) {\n  .next-blog-ai-list.list-view .next-blog-ai-post-card {\n    flex-direction: column;\n  }\n  \n  .next-blog-ai-list.list-view .next-blog-ai-post-image {\n    width: 100%;\n    height: 0;\n    padding-bottom: 56.25%; /* 16:9 aspect ratio */\n  }\n}\n\n.next-blog-ai-post-card {\n  display: flex;\n  flex-direction: column;\n  border-radius: 8px;\n  overflow: hidden;\n  box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);\n  transition: transform 0.2s, box-shadow 0.2s;\n}\n\n.next-blog-ai-post-title {\n  font-size: 1.25rem;\n  font-weight: 600;\n  margin-top: 0;\n  margin-bottom: 0.5rem;\n  color: #111;\n}\n\n.next-blog-ai-post-title a {\n  color: inherit;\n  text-decoration: none;\n}\n\n.next-blog-ai-post-title a:hover {\n  color: #0070f3;\n}\n\n.next-blog-ai-post-meta {\n  font-size: 0.875rem;\n  color: #666;\n  margin-bottom: 1rem;\n  display: flex;\n  align-items: center;\n  gap: 1rem;\n}\n\n.next-blog-ai-post-excerpt {\n  margin-bottom: 1.5rem;\n  flex-grow: 1;\n}\n\n.next-blog-ai-post-footer {\n  margin-top: auto;\n  display: flex;\n  justify-content: space-between;\n  align-items: center;\n}\n\n.next-blog-ai-read-more {\n  color: #0070f3;\n  text-decoration: none;\n  font-weight: 500;\n  font-size: 0.875rem;\n}\n\n.next-blog-ai-read-more:hover {\n  text-decoration: underline;\n}\n\n.next-blog-ai-comments-count {\n  font-size: 0.875rem;\n  color: #666;\n}\n\n/* Pagination */\n.next-blog-ai-pagination {\n  display: flex;\n  justify-content: center;\n  margin: 3rem 0;\n  gap: 0.5rem;\n}\n\n.next-blog-ai-pagination-item {\n  display: inline-flex;\n  align-items: center;\n  justify-content: center;\n  min-width: 2.5rem;\n  height: 2.5rem;\n  padding: 0 0.75rem;\n  border-radius: 4px;\n  background-color: #f0f0f0;\n  color: #333;\n  text-decoration: none;\n  font-weight: 500;\n}\n\n.next-blog-ai-pagination-item:hover {\n  background-color: #e0e0e0;\n}\n\n.next-blog-ai-pagination-item.active {\n  background-color: #0070f3;\n  color: white;\n}\n\n.next-blog-ai-pagination-item.disabled {\n  color: #999;\n  pointer-events: none;\n}\n`;\n","import {\n  ApiResponse,\n  BlogListOptions,\n  BlogListResponse,\n  BlogListSEOOptions,\n  BlogListSEOResponse,\n  BlogPostOptions,\n  BlogPostResponse,\n  CacheOptions,\n  CommentData,\n  CommentResponse,\n  ContentFormat,\n  ErrorResponse,\n  NextBlogAIConfig,\n  RetryOptions,\n  SEOOptions,\n  SEOResponse,\n  BlogSlugsOptions,\n  BlogSlugsResponse,\n  BlogListDisplayFormat,\n} from './types';\nimport { normalizeKeys, createRequestId, addHtmlStyles } from './utils';\nimport { DEFAULT_BLOG_STYLES, DEFAULT_BLOG_LIST_STYLES } from './styles';\n\n/**\n * Default API URL\n * @private\n */\nconst DEFAULT_API_URL = 'https://next-blog-ai.com/api/blog';\n\n/**\n * Get the API URL based on the environment\n * @private\n */\nfunction getApiUrl(): string {\n  // Only use development URL if an explicit environment variable is set\n  // This should only be used by the package developers internally\n  if (\n    typeof process !== 'undefined' &&\n    process.env &&\n    process.env.NEXT_BLOG_AI_LOCAL_DEVELOPMENT === 'true'\n  ) {\n    // Allow configuring the development URL via env var\n    return process.env.NEXT_BLOG_AI_DEV_URL || 'http://localhost:3000/api/blog';\n  }\n\n  // For all other cases, including when users are developing with our package\n  return DEFAULT_API_URL;\n}\n\n/**\n * Default cache TTL (0 = no caching)\n */\nconst DEFAULT_CACHE_TTL = 0;\n\n/**\n * NextBlogAI Client\n * Main class for interacting with the Next-Blog-AI API\n */\nexport class NextBlogAI {\n  private apiKey: string;\n  private apiUrl: string;\n  private defaultFormat: ContentFormat;\n  private defaultBlogListDisplay: BlogListDisplayFormat;\n  private defaultCacheTTL: number;\n  private cache: Map<string, { data: any; timestamp: number }>;\n  private retryOptions: Required<RetryOptions>;\n  private pendingRequests: Map<string, Promise<ApiResponse<any>>>;\n  private customStyles: {\n    blogContent?: string;\n    blogList?: string;\n  };\n  private defaultFetchOptions?: Record<string, any>;\n\n  /**\n   * Default retry options\n   */\n  private static readonly DEFAULT_RETRY_OPTIONS: Required<RetryOptions> = {\n    maxRetries: 3,\n    initialDelay: 300,\n    backoffFactor: 2,\n    maxDelay: 10000,\n    jitter: true,\n  };\n\n  /**\n   * Create a new instance of NextBlogAI client\n   */\n  constructor(config: NextBlogAIConfig) {\n    if (!config.apiKey) {\n      throw new Error('API key is required');\n    }\n\n    this.apiKey = config.apiKey;\n    this.apiUrl = getApiUrl();\n    this.defaultFormat = config.defaultFormat || 'html';\n    this.defaultBlogListDisplay = config.defaultBlogListDisplay || 'grid';\n    this.defaultCacheTTL = config.defaultCacheTTL || DEFAULT_CACHE_TTL;\n    this.cache = new Map();\n    this.pendingRequests = new Map();\n    this.customStyles = {\n      blogContent: config.styles?.blogContent,\n      blogList: config.styles?.blogList,\n    };\n    this.defaultFetchOptions = config.defaultFetchOptions;\n\n    // Initialize retry options with defaults\n    this.retryOptions = {\n      ...NextBlogAI.DEFAULT_RETRY_OPTIONS,\n      ...config.retry,\n    };\n  }\n\n  /**\n   * Generate a cache key from the request parameters\n   */\n  private generateCacheKey(\n    endpoint: string,\n    params: Record<string, any>\n  ): string {\n    const sortedParams = Object.keys(params)\n      .sort()\n      .map((key) => `${key}=${params[key]}`)\n      .join('&');\n\n    return `${endpoint}?${sortedParams}`;\n  }\n\n  /**\n   * Get data from cache if available and not expired\n   */\n  private getFromCache<T>(cacheKey: string, options?: CacheOptions): T | null {\n    if (options?.bypassCache) {\n      return null;\n    }\n\n    const cachedData = this.cache.get(cacheKey);\n    if (!cachedData) {\n      return null;\n    }\n\n    const ttl = options?.ttl ?? this.defaultCacheTTL;\n    const now = Date.now();\n    const expirationTime = cachedData.timestamp + ttl * 1000;\n\n    if (now > expirationTime) {\n      this.cache.delete(cacheKey);\n      return null;\n    }\n\n    return cachedData.data;\n  }\n\n  /**\n   * Store data in cache\n   */\n  private storeInCache<T>(cacheKey: string, data: T): void {\n    this.cache.set(cacheKey, {\n      data,\n      timestamp: Date.now(),\n    });\n  }\n\n  /**\n   * Calculate retry delay with exponential backoff and optional jitter\n   */\n  private getRetryDelay(attempt: number): number {\n    const { initialDelay, backoffFactor, maxDelay, jitter } = this.retryOptions;\n\n    // Calculate exponential backoff\n    let delay = initialDelay * Math.pow(backoffFactor, attempt);\n\n    // Apply maximum delay cap\n    delay = Math.min(delay, maxDelay);\n\n    // Add jitter if enabled (±25% randomization)\n    if (jitter) {\n      const jitterFactor = 0.25;\n      const randomFactor = 1 - jitterFactor + Math.random() * jitterFactor * 2;\n      delay = delay * randomFactor;\n    }\n\n    return delay;\n  }\n\n  /**\n   * Sleep for specified milliseconds\n   */\n  private async sleep(ms: number): Promise<void> {\n    return new Promise((resolve) => setTimeout(resolve, ms));\n  }\n\n  /**\n   * Make API request with proper error handling and retry mechanism\n   */\n  private async makeRequest<T>(\n    endpoint: string,\n    params: Record<string, any> = {},\n    options: {\n      method?: string;\n      body?: any;\n      cache?: CacheOptions;\n    } = {}\n  ): Promise<ApiResponse<T>> {\n    const method = options.method || 'GET';\n    const requestParams = { ...params, api_key: this.apiKey };\n\n    // Generate cache key and check cache for GET requests\n    let cacheKey = '';\n    if (method === 'GET') {\n      cacheKey = this.generateCacheKey(endpoint, requestParams);\n      const cachedData = this.getFromCache<T>(cacheKey, options.cache);\n      if (cachedData) {\n        return { data: cachedData };\n      }\n    }\n\n    // For GET requests, check if there's already a pending request for this exact data\n    // This helps deduplicate concurrent requests to the same endpoint with the same params\n    if (method === 'GET') {\n      const requestId = createRequestId(endpoint, requestParams);\n      const pendingRequest = this.pendingRequests.get(requestId);\n\n      if (pendingRequest) {\n        // Return the existing promise to avoid duplicate requests\n        return pendingRequest as Promise<ApiResponse<T>>;\n      }\n\n      // Create a new request promise\n      const requestPromise = this.executeRequest<T>(\n        endpoint,\n        method,\n        requestParams,\n        options,\n        cacheKey\n      );\n\n      // Store the promise in the pendingRequests map\n      this.pendingRequests.set(requestId, requestPromise);\n\n      // Clean up after request completes\n      requestPromise.finally(() => {\n        this.pendingRequests.delete(requestId);\n      });\n\n      return requestPromise;\n    }\n\n    // For non-GET requests, just execute directly without deduplication\n    return this.executeRequest<T>(\n      endpoint,\n      method,\n      requestParams,\n      options,\n      cacheKey\n    );\n  }\n\n  /**\n   * Execute the actual API request with retries\n   */\n  private async executeRequest<T>(\n    endpoint: string,\n    method: string,\n    requestParams: Record<string, any>,\n    options: { body?: any; cache?: CacheOptions },\n    cacheKey: string\n  ): Promise<ApiResponse<T>> {\n    // Setup for retries\n    let attempt = 0;\n    const maxRetries = this.retryOptions.maxRetries;\n\n    while (true) {\n      try {\n        const url = new URL(`${this.apiUrl}/${endpoint}`);\n\n        // Add query parameters for GET requests\n        if (method === 'GET') {\n          Object.entries(requestParams).forEach(([key, value]) => {\n            if (value !== undefined && value !== null) {\n              url.searchParams.append(key, String(value));\n            }\n          });\n        }\n\n        // Combine default fetch options with request-specific fetch options\n        const fetchOptions = {\n          ...this.defaultFetchOptions,\n          ...options.cache?.fetchOptions,\n        };\n\n        const response = await fetch(url.toString(), {\n          method,\n          headers: {\n            'Content-Type': 'application/json',\n          },\n          body:\n            method !== 'GET'\n              ? JSON.stringify({ ...options.body, api_key: this.apiKey })\n              : undefined,\n          // Apply framework-specific fetch options if present\n          ...fetchOptions,\n        });\n\n        // Check if response is retriable (5xx errors or specific 4xx errors)\n        const isRetriableStatus =\n          response.status >= 500 ||\n          response.status === 429 || // Too Many Requests\n          response.status === 408; // Request Timeout\n\n        if (!response.ok) {\n          const errorData = await response\n            .json()\n            .catch(() => ({ error: 'Unknown error' }));\n          const error: ErrorResponse = {\n            message: errorData.error || 'An unknown error occurred',\n            status: response.status,\n            code: errorData.code || `HTTP_${response.status}`,\n          };\n\n          // If the error is retriable and we haven't exceeded max retries\n          if (isRetriableStatus && attempt < maxRetries) {\n            attempt++;\n            const delay = this.getRetryDelay(attempt);\n            await this.sleep(delay);\n            continue; // Try again\n          }\n\n          return { error };\n        }\n\n        // Parse and normalize the response data\n        const rawData = await response.json();\n        const normalizedData = normalizeKeys<T>(rawData);\n\n        // Enhance HTML content with styles if needed\n        if (\n          endpoint === 'list' &&\n          normalizedData &&\n          typeof normalizedData === 'object'\n        ) {\n          const listData = normalizedData as any;\n          if (listData.format === 'html' && 'content' in listData) {\n            // Add custom styles to the HTML content\n            const styles =\n              this.customStyles.blogList || DEFAULT_BLOG_LIST_STYLES;\n\n            // Apply display format class to HTML content\n            const displayFormat =\n              requestParams.display || this.defaultBlogListDisplay;\n\n            // Add the display class to the container\n            const displayClass =\n              displayFormat === 'list' ? 'list-view' : 'grid-view';\n            listData.content = listData.content.replace(\n              'class=\"next-blog-ai-list\"',\n              `class=\"next-blog-ai-list ${displayClass}\"`\n            );\n\n            listData.content = addHtmlStyles(listData.content, styles);\n          }\n        } else if (\n          endpoint === 'post' &&\n          normalizedData &&\n          typeof normalizedData === 'object'\n        ) {\n          const postData = normalizedData as any;\n          if (postData.format === 'html' && 'content' in postData) {\n            // Add custom styles to the HTML content\n            const styles = this.customStyles.blogContent || DEFAULT_BLOG_STYLES;\n            postData.content = addHtmlStyles(postData.content, styles);\n\n            // Also style the comments if present\n            if (\n              'comments' in postData &&\n              typeof postData.comments === 'string'\n            ) {\n              postData.comments = addHtmlStyles(postData.comments, styles);\n            }\n\n            // And the comment form\n            if (\n              'commentForm' in postData &&\n              typeof postData.commentForm === 'string'\n            ) {\n              postData.commentForm = addHtmlStyles(\n                postData.commentForm,\n                styles\n              );\n            }\n          }\n        }\n\n        // Cache the result for GET requests\n        if (method === 'GET' && cacheKey) {\n          this.storeInCache(cacheKey, normalizedData);\n        }\n\n        return { data: normalizedData };\n      } catch (err) {\n        // Network errors are retriable\n        if (attempt < maxRetries) {\n          attempt++;\n          const delay = this.getRetryDelay(attempt);\n          await this.sleep(delay);\n          continue; // Try again\n        }\n\n        const error: ErrorResponse = {\n          message:\n            err instanceof Error ? err.message : 'Network error occurred',\n          status: 0,\n          code: 'NETWORK_ERROR',\n        };\n        return { error };\n      }\n    }\n  }\n\n  /**\n   * Get a list of blog posts\n   */\n  async getBlogPosts(\n    options: BlogListOptions = {}\n  ): Promise<ApiResponse<BlogListResponse>> {\n    const params = {\n      page: options.page || 1,\n      per_page: options.perPage || 10,\n      format: options.format || this.defaultFormat,\n      display: options.display || this.defaultBlogListDisplay,\n    };\n\n    return this.makeRequest<BlogListResponse>('list', params, {\n      cache: options.cache,\n    });\n  }\n\n  /**\n   * Get a single blog post by slug\n   */\n  async getBlogPost(\n    slug: string,\n    options: BlogPostOptions = {}\n  ): Promise<ApiResponse<BlogPostResponse>> {\n    if (!slug) {\n      return {\n        error: {\n          message: 'Slug is required',\n          status: 400,\n        },\n      };\n    }\n\n    const params = {\n      slug,\n      format: options.format || this.defaultFormat,\n    };\n\n    return this.makeRequest<BlogPostResponse>('post', params, {\n      cache: options.cache,\n    });\n  }\n\n  /**\n   * Submit a comment on a blog post\n   */\n  async submitComment(\n    data: CommentData\n  ): Promise<ApiResponse<CommentResponse>> {\n    if (!data.postId) {\n      return {\n        error: {\n          message: 'Post ID is required',\n          status: 400,\n        },\n      };\n    }\n\n    if (!data.authorName) {\n      return {\n        error: {\n          message: 'Author name is required',\n          status: 400,\n        },\n      };\n    }\n\n    if (!data.content) {\n      return {\n        error: {\n          message: 'Comment content is required',\n          status: 400,\n        },\n      };\n    }\n\n    return this.makeRequest<CommentResponse>(\n      'comment',\n      {},\n      {\n        method: 'POST',\n        body: {\n          post_id: data.postId,\n          author_name: data.authorName,\n          author_email: data.authorEmail,\n          content: data.content,\n        },\n      }\n    );\n  }\n\n  /**\n   * Get only SEO metadata for a blog post by slug\n   * Optimized version that doesn't fetch the full content\n   */\n  async getBlogPostSEO(\n    slug: string,\n    options: SEOOptions = {}\n  ): Promise<ApiResponse<SEOResponse>> {\n    if (!slug) {\n      return {\n        error: {\n          message: 'Slug is required',\n          status: 400,\n        },\n      };\n    }\n\n    const params = {\n      slug,\n      seo_only: true,\n    };\n\n    return this.makeRequest<SEOResponse>('post/seo', params, {\n      cache: options.cache,\n    });\n  }\n\n  /**\n   * Get only SEO metadata for blog list\n   * Optimized version that doesn't fetch the full content\n   */\n  async getBlogListSEO(\n    options: BlogListSEOOptions = {}\n  ): Promise<ApiResponse<BlogListSEOResponse>> {\n    const params = {\n      page: options.page || 1,\n      per_page: options.perPage || 10,\n      seo_only: true,\n    };\n\n    return this.makeRequest<BlogListSEOResponse>('list/seo', params, {\n      cache: options.cache,\n    });\n  }\n\n  /**\n   * Get all blog post slugs\n   * Useful for static site generation in frameworks like Next.js\n   */\n  async getAllBlogSlugs(\n    options: BlogSlugsOptions = {}\n  ): Promise<ApiResponse<BlogSlugsResponse>> {\n    const params = {};\n\n    return this.makeRequest<BlogSlugsResponse>('slugs', params, {\n      cache: options.cache,\n    });\n  }\n\n  /**\n   * Clear the entire cache\n   */\n  clearCache(): void {\n    this.cache.clear();\n  }\n\n  /**\n   * Clear a specific item from the cache\n   */\n  clearCacheItem(endpoint: string, params: Record<string, any>): void {\n    const cacheKey = this.generateCacheKey(endpoint, params);\n    this.cache.delete(cacheKey);\n  }\n\n  /**\n   * Set custom styles for HTML content\n   */\n  setStyles(styles: { blogContent?: string; blogList?: string }): void {\n    if (styles.blogContent) {\n      this.customStyles.blogContent = styles.blogContent;\n    }\n\n    if (styles.blogList) {\n      this.customStyles.blogList = styles.blogList;\n    }\n  }\n}\n\n/**\n * Factory function to create a new NextBlogAI instance\n */\nexport function createNextBlogAI(config: NextBlogAIConfig): NextBlogAI {\n  // Apply default fetch options for Next.js if not specified\n  const configWithDefaults = {\n    ...config,\n    defaultFetchOptions: config.defaultFetchOptions || {\n      cache: 'no-store' as RequestCache,\n      next: {\n        revalidate: 0,\n      },\n    },\n  };\n\n  return new NextBlogAI(configWithDefaults);\n}\n","import { NextBlogAI, createNextBlogAI } from '../core/client';\nimport {\n  ApiResponse,\n  BlogListOptions,\n  BlogListResponse,\n  BlogListSEOOptions,\n  BlogListSEOResponse,\n  BlogPostOptions,\n  BlogPostResponse,\n  CacheOptions,\n  SEOOptions,\n  SEOResponse,\n  BlogSlugsOptions,\n  BlogSlugsResponse,\n} from '../core/types';\n\n/**\n * Next.js specific caching options\n */\nexport interface NextCacheOptions {\n  /**\n   * Next.js revalidation time in seconds\n   * When set to 0, cache will be bypassed completely (equivalent to dynamic: true)\n   */\n  revalidate?: number;\n\n  /**\n   * Force dynamic rendering without caching\n   */\n  dynamic?: boolean;\n}\n\n/**\n * Blog list options with Next.js specific caching\n */\nexport interface NextBlogListOptions extends Omit<BlogListOptions, 'cache'> {\n  /**\n   * Next.js specific caching options\n   */\n  next?: NextCacheOptions;\n}\n\n/**\n * Blog post options with Next.js specific caching\n */\nexport interface NextBlogPostOptions extends Omit<BlogPostOptions, 'cache'> {\n  /**\n   * Next.js specific caching options\n   */\n  next?: NextCacheOptions;\n}\n\n/**\n * SEO options with Next.js specific caching\n */\nexport interface NextSEOOptions extends Omit<SEOOptions, 'cache'> {\n  /**\n   * Next.js specific caching options\n   */\n  next?: NextCacheOptions;\n}\n\n/**\n * Blog list SEO options with Next.js specific caching\n */\nexport interface NextBlogListSEOOptions\n  extends Omit<BlogListSEOOptions, 'cache'> {\n  /**\n   * Next.js specific caching options\n   */\n  next?: NextCacheOptions;\n}\n\n/**\n * Blog slugs options with Next.js specific caching\n */\nexport interface NextBlogSlugsOptions extends Omit<BlogSlugsOptions, 'cache'> {\n  /**\n   * Next.js specific caching options\n   */\n  next?: NextCacheOptions;\n}\n\n/**\n * Map Next.js caching options to NextBlogAI cache options\n */\nfunction mapNextCacheOptions(\n  options?: NextCacheOptions\n): CacheOptions | undefined {\n  if (!options) {\n    return undefined;\n  }\n\n  // Create cache options with Next.js specific fetch directives\n  return {\n    ttl: options.revalidate,\n    bypassCache: options.dynamic || options.revalidate === 0,\n    // Include the framework-specific fetch options\n    fetchOptions: {\n      cache:\n        options.dynamic || options.revalidate === 0\n          ? ('no-store' as RequestCache)\n          : ('force-cache' as RequestCache),\n      next: {\n        revalidate: options.revalidate,\n      },\n    },\n    next: options,\n  };\n}\n\n/**\n * Higher-order function that wraps a NextBlogAI method with Next.js caching\n */\nexport function withNextCache<T, O extends object>(\n  fn: (client: NextBlogAI, ...args: any[]) => Promise<ApiResponse<T>>\n) {\n  return function (\n    client: NextBlogAI,\n    ...args: any[]\n  ): Promise<ApiResponse<T>> {\n    // Map Next.js options to NextBlogAI cache options\n    const lastArg = args[args.length - 1];\n    if (lastArg && typeof lastArg === 'object' && 'next' in lastArg) {\n      // Clone the options and remove 'next'\n      const { next, ...rest } = lastArg;\n\n      // Map Next.js cache options to normal cache options\n      const options = {\n        ...rest,\n        cache: mapNextCacheOptions(next),\n      };\n\n      // Replace the last argument\n      args[args.length - 1] = options;\n    }\n\n    return fn(client, ...args);\n  };\n}\n\n/**\n * Get blog posts with Next.js caching\n */\nexport async function getBlogPostsWithNextCache(\n  client: NextBlogAI,\n  options: NextBlogListOptions = {}\n): Promise<ApiResponse<BlogListResponse>> {\n  const cacheOptions = mapNextCacheOptions(options.next);\n\n  // Remove the next property to avoid conflicts\n  const { next, ...restOptions } = options;\n\n  return client.getBlogPosts({\n    ...restOptions,\n    cache: cacheOptions,\n  });\n}\n\n/**\n * Get a blog post with Next.js caching\n */\nexport async function getBlogPostWithNextCache(\n  client: NextBlogAI,\n  slug: string,\n  options: NextBlogPostOptions = {}\n): Promise<ApiResponse<BlogPostResponse>> {\n  const cacheOptions = mapNextCacheOptions(options.next);\n\n  // Remove the next property to avoid conflicts\n  const { next, ...restOptions } = options;\n\n  return client.getBlogPost(slug, {\n    ...restOptions,\n    cache: cacheOptions,\n  });\n}\n\n/**\n * Get blog post SEO metadata with Next.js caching\n */\nexport async function getBlogPostSEOWithNextCache(\n  client: NextBlogAI,\n  slug: string,\n  options: NextSEOOptions = {}\n): Promise<ApiResponse<SEOResponse>> {\n  const cacheOptions = mapNextCacheOptions(options.next);\n\n  // Remove the next property to avoid conflicts\n  const { next, ...restOptions } = options;\n\n  return client.getBlogPostSEO(slug, {\n    ...restOptions,\n    cache: cacheOptions,\n  });\n}\n\n/**\n * Get blog list SEO metadata with Next.js caching\n */\nexport async function getBlogListSEOWithNextCache(\n  client: NextBlogAI,\n  options: NextBlogListSEOOptions = {}\n): Promise<ApiResponse<BlogListSEOResponse>> {\n  const cacheOptions = mapNextCacheOptions(options.next);\n\n  // Remove the next property to avoid conflicts\n  const { next, ...restOptions } = options;\n\n  return client.getBlogListSEO({\n    ...restOptions,\n    cache: cacheOptions,\n  });\n}\n\n/**\n * Get all blog slugs with Next.js caching\n */\nexport async function getAllBlogSlugsWithNextCache(\n  client: NextBlogAI,\n  options: NextBlogSlugsOptions = {}\n): Promise<ApiResponse<BlogSlugsResponse>> {\n  const cacheOptions = mapNextCacheOptions(options.next);\n\n  // Remove the next property to avoid conflicts\n  const { next, ...restOptions } = options;\n\n  return client.getAllBlogSlugs({\n    ...restOptions,\n    cache: cacheOptions,\n  });\n}\n\n// Export a convenience function for Next.js projects\nexport function createNextBlogAIForNextJs(\n  apiKey: string,\n  defaultCacheOptions: NextCacheOptions = { revalidate: 0 }\n): {\n  client: NextBlogAI;\n  getBlogPosts: (\n    options?: NextBlogListOptions\n  ) => Promise<ApiResponse<BlogListResponse>>;\n  getBlogPost: (\n    slug: string,\n    options?: NextBlogPostOptions\n  ) => Promise<ApiResponse<BlogPostResponse>>;\n  getBlogPostSEO: (\n    slug: string,\n    options?: NextSEOOptions\n  ) => Promise<ApiResponse<SEOResponse>>;\n  getBlogListSEO: (\n    options?: NextBlogListSEOOptions\n  ) => Promise<ApiResponse<BlogListSEOResponse>>;\n  getAllBlogSlugs: (\n    options?: NextBlogSlugsOptions\n  ) => Promise<ApiResponse<BlogSlugsResponse>>;\n} {\n  // Create the client - no need to pass fetch options here\n  // as they will be included in each request's cache options\n  const client = new NextBlogAI({ apiKey });\n\n  // Helper to merge default cache options with user-provided options\n  const mergeWithDefaults = (options?: NextCacheOptions) => {\n    if (!defaultCacheOptions) return options;\n    return {\n      ...defaultCacheOptions,\n      ...options,\n    };\n  };\n\n  return {\n    client,\n    getBlogPosts: (options = {}) => {\n      // Apply default cache options if user didn't specify their own\n      const finalOptions = {\n        ...options,\n        next: options.next || mergeWithDefaults(options.next),\n      };\n      return getBlogPostsWithNextCache(client, finalOptions);\n    },\n    getBlogPost: (slug, options = {}) => {\n      const finalOptions = {\n        ...options,\n        next: options.next || mergeWithDefaults(options.next),\n      };\n      return getBlogPostWithNextCache(client, slug, finalOptions);\n    },\n    getBlogPostSEO: (slug, options = {}) => {\n      const finalOptions = {\n        ...options,\n        next: options.next || mergeWithDefaults(options.next),\n      };\n      return getBlogPostSEOWithNextCache(client, slug, finalOptions);\n    },\n    getBlogListSEO: (options = {}) => {\n      const finalOptions = {\n        ...options,\n        next: options.next || mergeWithDefaults(options.next),\n      };\n      return getBlogListSEOWithNextCache(client, finalOptions);\n    },\n    getAllBlogSlugs: (options = {}) => {\n      const finalOptions = {\n        ...options,\n        next: options.next || mergeWithDefaults(options.next),\n      };\n      return getAllBlogSlugsWithNextCache(client, finalOptions);\n    },\n  };\n}\n"]}