Skip to main content
OmniSearches automatically enriches search results with relevant images fetched from Wikimedia Commons, providing visual context for queries about places, concepts, and topics.

Overview

When you search for topics that benefit from visual representation, OmniSearches includes an image gallery sourced from Wikimedia Commons. This feature is available in Default, Exhaustive, and Reasoning modes.
Image galleries are automatically generated when the AI determines that visual content would enhance the response, particularly for geographical, historical, or conceptual queries.

How It Works

1

AI Selection

The AI model determines when images would be valuable and includes image references in its response:
IMAGES:
1. [Eiffel Tower][wikipedia][Iconic iron lattice tower in Paris][Eiffel Tower at sunset]
2. [Louvre Museum][wikipedia][World's largest art museum][The Louvre pyramid entrance]
...
2

Image Fetching

The server processes these references and fetches actual image URLs from Wikimedia Commons API:
const apiUrl = `https://commons.wikimedia.org/w/api.php?action=query&generator=search&gsrnamespace=6&gsrsearch=${searchQuery}&gsrlimit=1&prop=imageinfo&iiprop=url|size&iiurlwidth=400&maxage=3600&smaxage=3600&format=json&origin=*`;
3

Gallery Rendering

Images are displayed in a responsive grid gallery with captions and full-screen preview capabilities.

Image Format Specification

The AI generates image references in a specific format:
[Search Title][Source][Caption][Alt Text]
Search Title
string
required
The search query used to find the image on Wikimedia Commons
Source
string
default:"wikipedia"
The image source (currently supports wikipedia, pexels, unsplash, pixabay)
Caption
string
required
Description displayed below the image
Alt Text
string
required
Accessibility text for screen readers

Wikimedia Commons Integration

The image fetching system uses the Wikimedia Commons API to retrieve high-quality, freely-licensed images:
// From server/routes.ts and client/src/lib/ImageUtils.ts

export async function getImageUrlFromSource({ 
  searchTitle, 
  source, 
  caption, 
  alt 
}: ImageSource): Promise<string> {
  const sourceType = source.split('=')[1]?.toLowerCase() || '';
  const searchQuery = encodeURIComponent(searchTitle.toLowerCase().trim());

  switch (sourceType) {
    case 'wikipedia': {
      const apiUrl = `https://commons.wikimedia.org/w/api.php
        ?action=query
        &generator=search
        &gsrnamespace=6
        &gsrsearch=${searchQuery}
        &gsrlimit=1
        &prop=imageinfo
        &iiprop=url|size
        &iiurlwidth=400
        &maxage=3600
        &smaxage=3600
        &format=json
        &origin=*`;
      
      const response = await fetch(apiUrl);
      const data = await response.json();
      
      const pages = data.query?.pages || {};
      const firstPage = Object.values(pages)[0];
      const imageUrl = firstPage?.imageinfo?.[0]?.thumburl 
                    || firstPage?.imageinfo?.[0]?.url;
      
      return imageUrl || '';
    }
    // Other sources...
  }
}
  • action=query: Perform a query operation
  • generator=search: Generate page list from search results
  • gsrnamespace=6: Search in File namespace (images)
  • gsrsearch=...: The search query
  • gsrlimit=1: Return only the best match
  • prop=imageinfo: Get image information
  • iiprop=url|size: Include URL and size information
  • iiurlwidth=400: Generate 400px wide thumbnail
  • maxage=3600: Cache for 1 hour
  • origin=*: Enable CORS

Image Processing Flow

Server Processing

The server extracts and processes images before sending the response:
// Extract image references from AI response
const IMAGES_REGEX = /IMAGES:\s*((?:\d+\.\s*\[([^\]]+)\]\[([^\]]+)\]\[([^\]]+)\]\[([^\]]+)\]\s*\n*)*)/s;

async function extractAndRemoveRelatedQuestionsAndImages(text: string) {
  const imageMatches = text.match(IMAGES_REGEX);
  const images: Array<{ url: string; caption: string; alt: string }> = [];
  
  if (imageMatches) {
    const imageSection = imageMatches[1];
    const imageLines = imageSection.split('\n').filter(line => line.trim());
    
    // Process all images concurrently
    const imagePromises = imageLines.map(async (line) => {
      const parts = line.match(/\d+\.\s*\[(.*?)\]\[(.*?)\]\[(.*?)\]\[(.*?)\]/);
      if (parts) {
        const [_, searchTitle, source, caption, alt] = parts;
        const url = await getImageUrlFromSource({ 
          searchTitle, source, caption, alt 
        });
        if (url !== '') {
          return { url, caption, alt };
        }
      }
      return null;
    });

    const resolvedImages = await Promise.all(imagePromises);
    images.push(...resolvedImages.filter(img => img !== null));
  }
  
  return { cleanText, relatedQuestions, images };
}
Images are fetched concurrently using Promise.all() for optimal performance.

Mode-Specific Behavior

Default Mode

4-8 ImagesIncludes relevant images when appropriate for the query. Shows 4 images initially with option to expand.

Exhaustive Mode

10+ ImagesComprehensive image galleries with more visual content to support in-depth research.

Reasoning Mode

4-8 ImagesStrategically selected images based on reasoning analysis of the query.
Concise Mode and Search Mode do not include image galleries to maintain focus on quick, text-based results.

Responsive Grid Layout

/* Grid automatically adjusts based on screen size */
grid-cols-2         /* Mobile: 2 columns */
sm:grid-cols-3      /* Tablet: 3 columns */
lg:grid-cols-4      /* Desktop: 4 columns */

Progressive Disclosure

For galleries with more than 4 images:
1

Initial View

Display first 4 images with “Show N more” button
2

Expanded View

Show all images with “Show less” button
3

Full Screen

Click any image to view in full-screen modal with caption

Animations

// Staggered fade-in for each image
<motion.div
  initial={{ opacity: 0, scale: 0.95 }}
  animate={{ opacity: 1, scale: 1 }}
  transition={{ delay: index * 0.1 }}  // 100ms delay between images
>

Accessibility Features

Every image includes descriptive alt text for screen readers:
<img alt="Eiffel Tower at sunset" />
  • Tab through images
  • Enter/Space to open full-screen view
  • Escape to close modal
<div role="dialog" aria-modal="true" aria-labelledby="modal-title">
  <img src="..." />
  <p id="modal-title">Image caption</p>
</div>

Example Response

Here’s what a typical image-enhanced search looks like:
Tell me about Paris landmarks

Supported Image Sources

While Wikimedia Commons is the primary source, the system supports:
SourceStatusAPI Required
Wikimedia Commons✅ ActiveNo
Pexels🚧 PlannedYes
Unsplash🚧 PlannedYes
Pixabay🚧 PlannedYes
Wikimedia Commons is preferred because it provides high-quality, freely-licensed images without requiring API keys.

Error Handling

The system gracefully handles image fetch failures:
try {
  const response = await fetch(apiUrl);
  const data = await response.json();
  const imageUrl = extractImageUrl(data);
  return imageUrl || '';  // Return empty string on failure
} catch (error) {
  console.error('Error fetching Wikipedia image:', error);
  return '';  // Fail silently, don't break the response
}
If an image fails to load, it’s silently excluded from the gallery rather than showing a broken image or error.

Performance Optimization

Concurrent Fetching

// All images are fetched in parallel
const imagePromises = imageLines.map(async (line) => {
  // Fetch image URL...
});

const resolvedImages = await Promise.all(imagePromises);

Caching

Wikimedia API responses are cached for 1 hour:
maxage=3600&smaxage=3600

Thumbnail Sizing

iiurlwidth=400
Requests 400px wide thumbnails instead of full-resolution images for faster loading.

Search Modes

Learn which modes support image galleries

Related Questions

Discover other AI-generated enhancements

Build docs developers (and LLMs) love