One link, many destinations

Alap: Links with choice - one click, a menu of places to go

Alap is a small JavaScript library for web pages. You list your links once, in a JSON file, and give each one some tags. Any ordinary link on your page can then ask for a set of them, such as every New York bridge, and when a reader clicks it, Alap shows that set as a menu.

Try it: click many destinations above.

1How a link becomes a menu

Click bridges to open its menu. The link asks for .nyc + .bridge, and the five entries in links.json tagged both nyc and bridge become the menu.

1The menu in the browser

Walk across one of the great New York bridges.

3The data links.json
{
  "allLinks": {
    "brooklyn":     { "tags": ["nyc", "bridge"], "label": "Brooklyn Bridge",
                      "url": "https://en.wikipedia.org/wiki/Brooklyn_Bridge" },    "manhattan":    { "tags": ["nyc", "bridge"], "label": "Manhattan Bridge",
                      "url": "https://en.wikipedia.org/wiki/Manhattan_Bridge" },    "williamsburg": { "tags": ["nyc", "bridge"], "label": "Williamsburg Bridge",
                      "url": "https://en.wikipedia.org/wiki/Williamsburg_Bridge" },    "queensboro":   { "tags": ["nyc", "bridge"], "label": "Queensboro Bridge",
                      "url": "https://en.wikipedia.org/wiki/Queensboro_Bridge" },    "gwb":          { "tags": ["nyc", "bridge"], "label": "George Washington Bridge",
                      "url": "https://en.wikipedia.org/wiki/George_Washington_Bridge" },    "golden":       { "tags": ["sf", "bridge"], "label": "Golden Gate",
                      "url": "https://en.wikipedia.org/wiki/Golden_Gate_Bridge" },    "katz":         { "tags": ["nyc", "food"], "label": "Katz's Delicatessen",
                      "url": "https://katzsdelicatessen.com" }  }
}

Try other expressions

Expression Menu Try it
.bridge The five New York bridges, Golden Gate bridges
.nyc The five New York bridges, Katz's New York
.nyc + .bridge The five New York bridges NYC bridges

Point at a row to see which entries in links.json it matches. Click a link to open its menu.

2Start with a link you already have

A link today

<a href="https://en.wikipedia.org/wiki/Brooklyn_Bridge">bridges</a>

The same link with Alap

<a href="https://en.wikipedia.org/wiki/Brooklyn_Bridge"
   class="alap" data-alap-linkitems=".nyc + .bridge">bridges</a>

It stays a real link. If JavaScript doesn't load, it still goes to its href. With Alap running, a click opens a menu instead. Here it is live: bridges.

3Why it helps

The links live in one place. Change a URL once and every menu that uses it changes too. Add a new bridge with the bridge tag and it shows up in every bridge menu, with no edits to your pages.

A traditional link is a demand — one URL, chosen by the author.
An Alap link is an invitation — a set of options, chosen by the reader.

Three operators

Expression Meaning Try it
.nyc + .bridge AND — links with both tags both
.sf | .food OR — links with either tag either
.nyc - .bridge WITHOUT — remove the second set from the first without

There's more when you need it: grouping, saved macros, live sources and sorting. See the expression language docs.

Quick start

<script type="module">
  import { AlapUI } from 'alap';
  import config from './links.json' with { type: 'json' };
  new AlapUI(config);
</script>

<a href="https://en.wikipedia.org/wiki/Bridge" class="alap" data-alap-linkitems=".bridge">bridges</a>

Using a framework? Alap also has React, Vue, Svelte, Astro, Alpine, Solid and Qwik adapters, plus a <alap-link> web component. No dependencies, 30 KB gzipped. Parsers for Python, PHP, Go, Rust, Ruby and Java. See all options.