Skip to content

Search App Reference

The Search app provides a unified search interface across all entity types in the Bifolk application. It uses an adapter pattern to search hives, queens, honey batches, inventory items, breeding records, and more from a single search bar.

Overview

Location: app/search/

Purpose: Global cross-entity search with live modal search and advanced filtering

Key Models: None (uses models from other apps via search adapters)

Dependencies: hives, breeding, warehouse, organizations


File Structure

search/
├── apps.py                # AppConfig
├── forms.py               # GlobalSearchForm, AdvancedSearchForm
├── views.py               # SearchResultsView, search_api
├── urls.py                # 2 URL patterns
├── services/
│   ├── __init__.py
│   ├── search_service.py  # GlobalSearchService, PaginatedSearchResult
│   └── adapters/
│       ├── __init__.py        # Re-exports all adapters
│       ├── base.py            # BaseSearchAdapter, SearchResult
│       ├── hive_adapters.py   # 7 adapters (Hive, Queen, HoneyBatch, HoneyBucket, HoneyJar, HiveInspection, HarvestRecord)
│       ├── warehouse_adapters.py  # 3 adapters (InventoryItem, ProductSale, WarehouseLocation)
│       └── breeding_adapters.py   # 2 adapters (QueenBreeding, ColonySplit)
├── templates/search/
│   ├── search_results.html    # Full-page search results with filters
│   └── _search_modal.html     # Global search modal (included in base template)
└── tests/
    ├── __init__.py
    ├── test_search_service.py # Service layer tests
    ├── test_adapters.py       # Adapter tests
    └── test_views.py          # View tests

Views

SearchResultsView

Full-page search results view with advanced filtering.

  • Location: app/search/views.py:16
  • Type: Class-based (TemplateView)
  • Authentication: Required (LoginRequiredMixin)
  • Template: search/search_results.html
  • URL: /search/ (name: search:results)

Display Modes:

Mode Condition Behavior
Grouped No filters active Results grouped by entity type, 20 per type
Flat Filters active (entity type, org, date range) Flat paginated list, 20 per page

Query Parameters:

Parameter Type Description
q string Search term (minimum 2 characters)
entity_types list Entity types to filter by
organization integer Organization ID to filter by
date_from date Start date filter (ISO format)
date_to date End date filter (ISO format)
page integer Page number for flat mode pagination

The advanced search page always shows the organization filter regardless of the current site-wide organization selector, allowing users to search across all their organizations.

search_api(request)

JSON API endpoint for live search results, used by the search modal.

  • Location: app/search/views.py:153
  • Type: Function-based view
  • Authentication: Required (@login_required)
  • URL: /search/api/ (name: search:api)

Query Parameters:

Parameter Type Description
q string Search term (minimum 2 characters)
types string Comma-separated entity types (optional)

Response Format:

{
  "results": {
    "hive": [
      {
        "entity_type": "hive",
        "entity_type_display": "Hive",
        "id": 1,
        "display_name": "Garden Hive",
        "url": "/hives/1/",
        "subtitle": "My Organization",
        "context": "good",
        "organization_name": "My Organization"
      }
    ]
  },
  "total_count": 1,
  "error": null
}

Forms

GlobalSearchForm

  • Location: app/search/forms.py:7
  • Fields: q (CharField, min_length=2, max_length=200)
  • Purpose: Simple search input used in the search modal

AdvancedSearchForm

  • Location: app/search/forms.py:24
  • Purpose: Advanced search form with filtering options

Fields:

Field Type Description
q CharField Search query (min 2, max 200 characters)
entity_types MultipleChoiceField Entity type checkboxes (dynamic choices)
organization ChoiceField Organization dropdown (dynamic, hidden if only one org)
date_from DateField Start date filter
date_to DateField End date filter

Constructor Parameters:

Parameter Purpose
user Populate organization choices from user memberships
current_organization If set, hides organization field
entity_type_choices List of (value, label) tuples for entity types

Validation: Ensures date_from is before date_to when both are provided.


Services

GlobalSearchService

Location: app/search/services/search_service.py:41

Orchestrates searching across all registered search adapters. Coordinates 12 adapters and aggregates results.

Configuration:

Property Value
MIN_QUERY_LENGTH 2
ADAPTERS 12 registered adapters (see Adapter Registry below)

Methods:

Method Purpose Returns
search(search_term, user, ...) Search grouped by entity type dict[str, list[SearchResult]]
search_flat(search_term, user, ...) Search as flat list list[SearchResult]
search_paginated(search_term, user, ..., page, per_page) Search with pagination PaginatedSearchResult
get_available_entity_types() List all entity types with display names list[dict]
get_entity_type_choices() Entity types as form choices list[tuple[str, str]]

All search methods accept these common parameters:

Parameter Type Description
search_term str Search query (minimum 2 characters)
user User The requesting user
request HttpRequest (optional) For current organization context
entity_types list[str] (optional) Filter by entity types
date_from date (optional) Start date filter
date_to date (optional) End date filter
organization_id int (optional) Filter by specific organization

PaginatedSearchResult

Location: app/search/services/search_service.py:27

Dataclass for paginated search results.

Fields:

Field Type Description
results list[SearchResult] Results for current page
total_count int Total results across all pages
page int Current page number
per_page int Results per page
total_pages int Total number of pages
has_next bool Whether a next page exists
has_previous bool Whether a previous page exists

Search Adapters

The search app uses an adapter pattern where each adapter is responsible for searching a single model type and returning standardized SearchResult objects.

BaseSearchAdapter

Location: app/search/services/adapters/base.py:56

Abstract base class that all search adapters must extend.

Required Overrides:

Method Purpose
get_model() Return the model class to search
get_entity_type_display() Return translated display name
get_search_q(search_term) Return Q object for search filtering
result_to_search_result(obj) Convert model instance to SearchResult

Optional Overrides:

Method Purpose
get_base_queryset(user, request) Custom organization filtering (default: select_related('organization') + filter_by_user_organizations)
apply_organization_filter(queryset, organization_id) Custom org filter (default: organization_id=organization_id)
apply_date_filter(queryset, date_from, date_to) Custom date filtering (default: uses primary_date_field)

Properties:

Property Default Purpose
entity_type '' Internal identifier (e.g., 'hive')
default_limit 10 Maximum results per search
primary_date_field 'created_at' Field used for date range filtering

SearchResult

Location: app/search/services/adapters/base.py:18

Standardized dataclass for search results.

Fields:

Field Type Default Description
entity_type str (required) Internal type identifier
entity_type_display str (required) Translated display name
id int (required) Primary key of matched entity
display_name str (required) Main display text
url str (required) URL to entity detail view
subtitle str '' Secondary text (location, status)
context str '' Status indicator (good, warning, etc.)
organization_name str '' Organization name

Adapter Registry

All 12 registered adapters, organized by source app:

Hive Adapters (services/adapters/hive_adapters.py):

Adapter Entity Type Default Limit Date Field Searchable Fields
HiveSearchAdapter hive 10 installation_date name, display_name, notes
QueenSearchAdapter queen 10 created_at breed, identification_number, breeder_name, notes
HoneyBatchSearchAdapter honey_batch 5 created_date charge_identifier, notes
HoneyBucketSearchAdapter honey_bucket 5 created_at bucket_number, notes
HoneyJarSearchAdapter honey_jar 5 created_at jar_number, notes
HiveInspectionSearchAdapter hive_inspection 5 inspection_date notes, disease_notes, pest_notes
HarvestRecordSearchAdapter harvest_record 5 harvest_date notes

Warehouse Adapters (services/adapters/warehouse_adapters.py):

Adapter Entity Type Default Limit Date Field Searchable Fields
InventoryItemSearchAdapter inventory_item 10 created_at name, item_type, description
ProductSaleSearchAdapter product_sale 5 sale_date customer_name, notes
WarehouseLocationSearchAdapter warehouse_location 5 created_at name, description

Breeding Adapters (services/adapters/breeding_adapters.py):

Adapter Entity Type Default Limit Date Field Searchable Fields
QueenBreedingSearchAdapter queen_breeding 5 breeding_date breed_line, notes, drone_source
ColonySplitSearchAdapter colony_split 5 split_date notes

Custom Organization Filtering

Some adapters override get_base_queryset and apply_organization_filter because their models do not have a direct organization field:

Adapter Organization Path
HoneyBucketSearchAdapter batch__organization
HoneyJarSearchAdapter bucket__batch__organization
HiveInspectionSearchAdapter hive__organization
HarvestRecordSearchAdapter organization (direct, with prefetch of hives)

Templates

search_results.html

Full-page search results template. Includes:

  • Search input with submit button
  • Collapsible filter panel (entity type checkboxes, organization dropdown, date range)
  • Select All / Clear All buttons for entity type checkboxes
  • Grouped results view (cards by entity type with icon per type)
  • Flat results view with pagination
  • Status badges with color-coded context (good/warning/critical)
  • Empty state and minimum character length messages

_search_modal.html

Global search modal included in the base template. Features:

  • Large search input with keyboard hint (Esc to close)
  • Loading spinner
  • Empty state and no-results messages
  • Dynamic results container (populated via JavaScript and the search API)
  • Keyboard navigation hints (arrow keys, Enter)
  • Link to advanced search page

URL Configuration

URL View Name
/search/ SearchResultsView search:results
/search/api/ search_api search:api

Key Features

  • Unified Search: Search across 12 entity types from a single input
  • Adapter Pattern: Each model type has its own adapter for customized search behavior
  • Live Search Modal: Real-time search results via JSON API as the user types
  • Advanced Filtering: Filter by entity type, organization, and date range
  • Two Display Modes: Grouped by entity type (no filters) or flat paginated list (with filters)
  • Organization-Aware: Results filtered by user's accessible organizations
  • Cross-Organization Search: Advanced search ignores site-wide org selector, searches all user orgs
  • Minimum Query Length: Requires at least 2 characters to prevent overly broad searches
  • Keyboard Navigation: Modal supports arrow key navigation and Enter to open

See Also

  • Hives App - Hive, Queen, Batch, Inspection models searched by this app
  • Warehouse App - Inventory, Sale, Location models searched by this app
  • Breeding App - QueenBreeding, ColonySplit models searched by this app
  • Organizations App - Organization filtering used by all adapters