Tagify
A lightweight, framework-agnostic tags input component that turns any input or textarea into a fully customizable tag editor.
Repository Health
Technical Analysis
Tagify transforms a plain HTML input or textarea into a rich tags-input UI component, offering a highly customizable, dependency-free, and fast tag editor usable in Vanilla JS, React, Vue, and Angular projects. It supports whitelist-based autocomplete suggestions, mixed-content tagging (inline hashtag/mention-style tagging within free text), single-value mode, drag-and-drop tag sorting, and persisted state, all while emitting a wide surface of granular DOM events for custom integrations.
Built by yairEO and actively maintained with dedicated framework wrapper entry points, Tagify ships as an ES module and UMD bundle with sub-path exports for React (@yaireo/tagify/react) and Vue-specific wrappers. Its SCSS-based theming exposes CSS custom properties for full visual customization without needing to override library internals, letting it fit into existing design systems while keeping a small runtime footprint.
What You Get
- A vanilla JS
Tagifyconstructor plus dedicated React and Vue wrapper components - Whitelist-backed autocomplete dropdown with customizable matching and templates
- Mixed-content and single-value modes for inline or classic multi-tag inputs
- SCSS/CSS custom-property theming for full visual control without overriding internals
- A documented events API (
add,remove,edit:*,dropdown:*,invalid, etc.) for custom integrations
Common Use Cases
- Tag/category pickers in admin and content-authoring forms
- Hashtag/mention composers using mixed-content mode
- Autocomplete filters constrained to a whitelist of valid values
- Multi-recipient (email/contact) input fields with inline validation
Under The Hood
Architecture
Tagify is built as a single constructor function (Tagify(input, settings)) whose prototype is composed from separate concern-specific modules — parts/dropdown.js, parts/persist.js, parts/events.js, parts/templates.js, and EventDispatcher.js — merged onto Tagify.prototype rather than kept as independently instantiated collaborators. Core state (this.state, this.value, this.DOM) is mutated directly by event handlers in parts/events.js, which then dispatch custom events through EventDispatcher for consumers to observe; the React and Vue wrappers reach into this same internal state and helper methods rather than going through a narrow public API, so the core instance is the de facto contract every integration depends on.
Tech Stack
The library is plain ES modules with no TypeScript, built via Gulp orchestrating Rollup and SWC (rollup-plugin-swc3, @rollup/plugin-terser) into a UMD bundle (dist/tagify.js) and an ESM build (dist/tagify.esm.js), with SCSS compiled through gulp-sass for the companion stylesheet. End-to-end testing runs on Playwright, and the package declares no runtime dependencies of its own — only optional peer dependencies on React, react-dom, and prop-types for the bundled React wrapper — keeping the core bundle small.
Code Quality
Testing is uneven: tests/basic.spec.js is an active Playwright suite asserting against real rendered tag DOM structure, while the older test/tagify.test.js (Jest + Puppeteer) is left in the repo with its actual assertions commented out. There is no TypeScript and no CI workflow configuration found under .github/workflows to automatically run lint or tests on pull requests, though an .eslintrc enforces baseline style locally. Error handling favors defensive guards over thrown exceptions — for example, constructing Tagify on a missing element logs a warning and returns a no-op Proxy mock instead of failing.
API Design
The public surface is a single constructor, new Tagify(input, settings), paired with an extensive settings object and a broad, granular events API covering nearly every interaction lifecycle moment (add, remove, edit:start, edit:updated, dropdown:show, invalid, and more). Dedicated React and Vue components translate props and callbacks into calls against the vanilla core, so framework consumers rarely touch the imperative API directly. Getting started requires minimal boilerplate — a single call with a whitelist array — though advanced modes like mixed-content tagging and drag-sort integration require reading further into the README rather than being self-discoverable from the API alone.
Used by 2 apps in this directory
lila (Lichess)
Community
The forever-free, ad-free, open-source chess server powering millions of real-time games, AI analysis, puzzles, and tournaments worldwide.
Operational
Analytics · Automation · Monitoring
Open-source event tracker with real-time push notifications and action buttons for tech founders.