Module:Gallery/doc
This is the documentation page for Module:Gallery
This module builds MediaWiki <gallery> tags from either hand-built item lists or Cargo query results. It is the single place gallery HTML gets generated on HopperWiki — templates should never write <gallery> markup by hand.
Architecture
The module is layered so that a new gallery "flavor" (a new Cargo table, a new JSON dataset, a new domain like species or resources) can be added without touching the rendering layer.
| Layer 1 · Render | Layer 2 · Normalize | Layer 3 · Pipeline | Layer 4 · Flavor |
|---|---|---|---|
|
|
|
|
Thin wrapper functions (e.g. |
Design intent: keep new domains as Layer 4 wrappers around the existing pipeline, not new copies of the pipeline. Only reach for a new Layer 2 normalizer (parallel to items_from_cargo_rows) if a data source genuinely isn't Cargo-shaped — e.g. a JSON-backed gallery. Don't build a config-driven meta-system to unify Cargo and JSON sources pre-emptively; two concrete flavors is not yet a pattern that needs its own abstraction.
Functions
p.build_gallery(items, options)
Lowest-level builder. Emits a raw <gallery> tag.
| Parameter | Notes |
|---|---|
items |
Array of tables: image (required — filename, with or without File: prefix), caption (optional, may contain wikilinks), link (optional click target), alt (optional alt text)
|
options.mode |
packed, packed-hover, nolines, traditional, slideshow
|
options.heights / widths |
e.g. "200px"
|
options.perrow |
Images per row |
options.caption |
Overall gallery caption (not per-image) |
options.showfilename |
"yes" or "no"
|
p.build_modern_gallery(items, options)
Same signature as build_gallery, wrapped in a modern-gallery styled <div>. Adds options.show_captions ("hover" default, or "always") which picks packed-hover vs nolines mode automatically when options.mode isn't set explicitly. Used directly by Module:Geography's species_gallery_for_geography, which builds its own items from a JSON dataset rather than Cargo.
p.items_from_cargo_rows(cargo_results, config)
Normalizes raw Cargo rows into the item shape build_gallery expects. This is the function to reuse if you're writing a new Cargo-backed flavor by hand rather than going through cargo_gallery_pipeline.
| Parameter | Notes |
|---|---|
config.focal_field |
Required. Field whose value becomes the caption text and the grouping key. |
config.image_field |
Required. Field containing the image filename. File: prefix is added automatically if missing (case-insensitive check).
|
config.placeholder_image |
Fallback image used when a row's image field is empty. |
config.name_array |
Optional ordered array of focal_field values — controls both which rows are included and their display order. Omit to include everything in query order.
|
config.link_config.image_link_field |
Cargo field to read for the image's click target. Default "image_link".
|
config.link_config.caption_link_field |
Cargo field to read for the caption's link target. Default "caption_link".
|
config.link_config.enable_caption_links |
Boolean, default true. Set false to render captions as plain text with no wikilink.
|
config.link_config.fallback_image_link / fallback_caption_link |
Used when the row has no value for the configured link field. If omitted, both default to the row's focal_field value — i.e. images and captions link to the item's own page unless told otherwise.
|
config.link_config.no_link_field |
Optional field name. When a row's value for this field is truthy (anything except empty/"0"/"false"/"no"), that row's caption renders as plain text, overriding enable_caption_links for that row only — other rows in the same gallery are unaffected. Use this to mix "will eventually get a page" items (still linked/red-linked) with "will never get its own page" items (e.g. an external organization or a person who's intentionally data-only) inside a single gallery.
|
Returns items, nil on success, or nil, error_message if there's nothing to render (empty results, or no rows matched a given name_array). Callers must check for nil before passing to build_gallery.
p.cargo_gallery_pipeline(frame)
The generic #invoke entry point. Runs a Cargo query from template args, then Layers 2 and 1.
Required args
| Parameter | Notes |
|---|---|
cargo_table |
Cargo table to query. |
cargo_fields |
Comma-separated fields to fetch. |
Field configuration
| Parameter | Default | Notes |
|---|---|---|
cargo_focal_field |
— | Shorthand that sets both search_field and display_field to the same field. Kept for backward compatibility with older templates.
|
search_field |
cargo_focal_field |
Field used in the WHERE clause. |
search_field_type |
cargo_focal_field_type, else "string" |
Passed to Module:Cargo query utilities' build_where_clause — use "list_of_string" for HOLDS-type fields.
|
display_field |
cargo_focal_field |
Field shown as the caption/grouping key. Can differ from search_field.
|
image_field |
"Image" |
Field holding the image filename. |
placeholder_image |
"No image available.svg" |
Used when a row's image field is empty. |
Filtering
| Parameter | Notes |
|---|---|
names |
Comma-separated values to include. Also controls display order (see name_array above). Filters on search_field.
|
not_values |
Comma-separated values to exclude. |
cargo_where |
Escape hatch — raw WHERE clause, bypasses names/not_values entirely when set.
|
limit |
Hard cap passed to the Cargo query. |
Linking (optional)
| Parameter | Notes |
|---|---|
image_link_field |
Cargo field for the image's click target. If omitted, images link to their own display_field page.
|
caption_link_field |
Cargo field for the caption's link target. If omitted, captions link to their own display_field page.
|
enable_caption_links |
"false" to render plain-text captions with no link. Anything else (including omitted) means true.
|
fallback_image_link / fallback_caption_link |
Override the "link to own page" default without pointing at a Cargo field. |
no_link_field |
Cargo field to check per-row for an "opt out of linking" flag (truthy value means plain text, overriding enable_caption_links for that row only). Use this to mix linkable and never-linkable items in one gallery — e.g. a boolean Never_gets_page column on the Organization or Person table.
|
Display
| Parameter | Default | Notes |
|---|---|---|
gallery_mode |
"packed" |
Passed straight through to build_gallery's options.mode.
|
heights |
"200px" |
Passed straight through to build_gallery's options.heights.
|
widths |
(unset) | Passed straight through to build_gallery's options.widths. Omitted entirely unless given.
|
perrow |
(unset) | Passed straight through to build_gallery's options.perrow.
|
p.get_species_gallery(frame)
Species-flavored wrapper. Pre-fills cargo_gallery_pipeline's args for the common case — querying Image filtered by Species — then delegates. See #Adding a new flavor for the pattern this demonstrates.
Notable implementation detail: it edits frame.args directly rather than calling getArgs(frame) first. getArgs returns a copy; edits to that copy would not be visible to cargo_gallery_pipeline's own getArgs(frame) call. Any new wrapper that pre-fills args before delegating to cargo_gallery_pipeline must follow the same approach.
Examples
Generic pipeline, minimal args
{{#invoke:Gallery
|cargo_gallery_pipeline
|cargo_table=Species
|cargo_fields=Species, Image
|cargo_focal_field=Species
}}From templates/Species gallery.wiki. Images and captions both link to each species' own page (no image_link_field/caption_link_field given, so the default-to-own-page fallback applies).
Generic pipeline, list-type search field with custom link fields
{{#invoke:Gallery|get_species_gallery
|cargo_table=Image
|cargo_fields=Species, Image,
|search_field=Species
|search_field_type=list_of_string
|display_field=Species
|image_field=Image
|image_link_field=Image
|caption_link_field=Species
|enable_caption_links=false
|gallery_mode=packed-hover
}}From templates/Images for species.wiki. Note enable_caption_links=false — captions render as plain species names, no link — while the image itself still links via image_link_field=Image (clicking the photo opens the file page).
Pass-through wrapper with a single templated arg
{{#invoke:Gallery|cargo_gallery_pipeline|limit={{{limit|}}}}}From templates/Get cargo gallery.wiki — the rest of the args are expected to be supplied by whatever calls this template.
Adding a new flavor
To add a gallery for a new Cargo-backed domain (a new table, or the same table queried differently):
- Write a wrapper function
p.get_<domain>_gallery(frame)in this module, modeled onp.get_species_gallery. - Edit
frame.argsdirectly (not agetArgs(frame)copy) to pre-fillcargo_table,cargo_fields,search_field,display_field,image_field, and any link/display defaults specific to the domain. - Delegate to
p.cargo_gallery_pipeline(frame)— do not duplicate the query/normalize/render logic. - Add a template under
templates/that calls{{#invoke:Gallery|get_<domain>_gallery|...}}, exposing only the args callers actually need to vary.
For a JSON-backed (non-Cargo) domain, follow Module:Geography's species_gallery_for_geography as the reference: build the items array by hand (matching the {image, caption, link, alt} shape) and call p.build_modern_gallery directly, skipping Layers 2–3 entirely since they're Cargo-specific. Only extract a shared JSON-side normalizer (parallel to items_from_cargo_rows) once a second JSON-backed gallery actually needs one — don't build it speculatively.
Known gotchas
| Situation | What happens | Fix |
|---|---|---|
Image filename already has a lowercase file: prefix |
build_gallery's prefix check is case-sensitive (^File:) — a lowercase prefix isn't recognized as already-prefixed and gets double-prefixed |
Don't pre-prefix filenames when building items by hand; let build_gallery or items_from_cargo_rows (which does a case-insensitive check) add it
|
| Breaks the gallery line's pipe-delimited syntax | — but avoid feeding free-text fields into caption/link without checking
| |
Calling items_from_cargo_rows or cargo_gallery_pipeline without checking for a nil return |
Passing nil items into build_gallery errors |
Always check the err second return before rendering; cargo_gallery_pipeline already does this and renders a gallery-error span instead
|
Module family
| Module | Role |
|---|---|
Module:Arguments |
Frame argument processing (getArgs)
|
Module:String utilities |
parse_csv_to_table for names/not_values
|
Module:Cargo query utilities |
build_where_clause — schema-aware WHERE clause construction
|
Module:Geography |
Calls p.build_modern_gallery directly for its JSON-backed species_gallery_for_geography flavor
|