kip
ex_cldr Core Team
I’ll shortly be launching Text, a nascent text analysis library.
Current functionality
In this early version (not ready for prime time) it includes:
- Word counting
- N-gram generation
- Language detection (of about 250 languages with pluggable vocabularies and pluggable correlation models)
- An English inflector (singular to plural) using a non-regex algorithmic approach
Future functionality
-
A language stemmer - as soon as I finishing writing the snowball compiler
-
Parts of speech tagger
Collaboration encouraged
-
Contributions in all areas are most welcome
-
Non-english speakers who would like to contribute to non-english inflectors are particularly welcome
Next steps
After some polishing this weekend I will publish a version to hex.
Trending in Announcing
Flop is an Elixir library that applies filtering, ordering and pagination parameters to your Ecto queries.
offset-based pagination with...
New
I needed to reuse React components from my Chrome extension in my Phoenix/LiveView backend. I noticed that for Svelte/Vue, there are live...
New
I released Doggo, a collection of unstyled Phoenix components.
https://github.com/woylie/doggo
Features
Unstyled Phoenix components....
New
Edit: 2026 May 15 - This post is archived.
Mob is alive!!
Main docs: mob v0.7.11 — Documentation
A bit of explanation for the slightly c...
New
Hey, I’m Jesse and I’m the main contributor behind Dexter, a full-featured, lightning-fast Elixir LSP optimized for large codebases. It s...
New
Hi everyone,
I’ve been working on this protobuf library for 3 years. We use it in the company I work for, EasyMile, to communicate with ...
New
Hi there! We created Gust: A task orchestrator inspired by Airflow.
For those who have never heard about Aiflow, it’s a Python-based wor...
New
Other Trending Topics
I am happy to introduce the very α version of the new programming language compiled to BEAM.
Welcome Cure.
It has literally three kille...
New
Hi everyone!
The first release candidate for the Expert language server project is now available!
We’ve published a press release detai...
New
With AI doing more of the implementation work, I’ve been wondering how much coding I should deliberately keep doing myself.
My main conc...
New
This showed up on my feed.. anyone heard of it? Just hype?
Ox Alpha is a reasoning model designed for coding, sustained ag...
New
Hey folks,
I just published a post about Hologram’s funding and where the project goes next - the short version:
Curiosum as Main Spons...
New
A little off-topic, but I feel like people here have a good head on their shoulders.
I used to be quite good at making software. Was luc...
New
Categories:
Sub Categories:
Forums
Popular Tags
- #ecto
- #liveview
- #troubleshooting
- #learning-elixir
- #library
- #deployment
- #erlang
- #testing
- #genserver
- #mix
- #absinthe
- #remote-other
- #otp
- #plug
- #how-to-question
- #macros
- #postgres
- #elixirconf
- #channels
- #exunit
- #discussion
- #code-sync
- #podcasts
- #javascript
- #onsite
- #dialyzer
- #docker
- #authentication
- #umbrella
- #full-time-contract
- #podcasts-by-brainlid
- #ecto-query
- #ai
- #elixirconf-us
- #blog-post
- #elixir-ls
- #phoenix_html
- #iex
- #graphql
- #genstage
- #websockets
- #supervisor
- #advent-of-code
- #distillery
- #processes
- #api
- #forms
- #elixirconf-eu
- #metaprogramming
- #hex










Showing Posts 19 to 10- Show Best Posts
- Show All (oldest first)
- Show All (newest first)
kip
I’ve published a couple of updates in the last week. I think that pretty much all I need in a text analysis library but I’m more than happy to take feature requests.
[0.6.0] — 2026-05-04
Added
Text.Extract— twitter-text-quality URL and email extraction with full UTS #46 IDNA, IANA TLD validation, and UTR #39 single-script defence against homograph attacks. Public API isurls/2,emails/2,all/2,split/2, andautolink/2; options include:require_scheme,:tld_mode,:eai,:strict_idn, and:twitter_quirks.Text.Extract.split/2— splits text into an interleaved list of plain-string fragments and validated entity maps, byte-for-byte round-trippable to the original. The building block for custom rendering of extracted URLs/emails into anchors, mentions, badges, or link-preview cards.Text.Extract.autolink/2— wraps URLs and emails in HTML<a>anchors, returningPhoenix.HTML.safe()for drop-in Phoenix template use. Display text preserves the original Unicode (bücher.de); thehrefuses Punycode (xn--bcher-kva.de).mix text.download_tlds— refreshes the bundled IANA TLD list atpriv/extract/tlds.txt.--diffpreviews added/removed entries;--forceoverwrites unconditionally.Text.WordCloud.to_d3_cloud/2— adaptsterms/2output into the[%{text, size}, …]shape consumed by d3-cloud. Supports:linear(default) and:sqrtsizing; shares the:font_size_rangevocabulary withText.WordCloud.Layout.[0.5.0] — 2026-05-02
Added
Text.Phonetic.NYSIIS— New York State Identification and Intelligence System phonetic encoding (Taft, 1970). Designed as a Soundex successor for English personal-name matching; produces pronounceable letter codes rather than digits and is more discriminating than Soundex on common name variations.Text.Phonetic.Cologne— Kölner Phonetik (Postel, 1969), the German-language counterpart to Soundex. Optimized for German spelling variants —Müller/Mueller/MullerandMeyer/Mayer/Maier/Meiercollapse to single codes.Text.Phonetic.DoubleMetaphone— Lawrence Philips’ Double Metaphone (2000), the de-facto standard for fuzzy English-name matching with non-Anglo origins. Returns a{primary, alternate}code pair so the same Anglicised name can match across multiple plausible pronunciations (e.g.Smith↔Schmidt,Catherine↔Katherine). Handles Germanic, Italian, Spanish, French, Greek, and Slavic patterns.match?/2(andmatch?/3where options apply) on everyText.Phonetic.*module for direct equality comparison without manualencode/2 == encode/2boilerplate.Text.Phonetic.DoubleMetaphone.match?/3checks all four primary/alternate combinations.Text.Clean.unaccent/1— strip diacritics and fold non-decomposable Latin letters (Þ→Th,ß→ss,Æ→AE,ł→l,đ→d) by delegating toUnicode.Transform.LatinAscii.transform/1. Also exposed as the:unaccentoption onText.Clean.clean/2.Text.Distancegains four set-based similarity metrics over character n-grams:jaccard/3,sorensen_dice/3,tanimoto/3(alias forjaccard/3), andcosine/3. All accept an:noption for configurable shingle size (default 2). Operate at the grapheme level for Unicode correctness.Text.Inflect.En.singularize/2andText.Inflect.En.singularize_noun/2— invert the existing pluralizer. Combines reverse lookup of Conway’s irregular tables, explicit suffix rules for unambiguous English plural forms (-ies,-shes/-ches/-xes/-zes/-sses), small whitelists for Greek-derived-is/-esplurals (analyses → analysis) and English-usplurals (geniuses → genius), and apluralize/2round-trip search to validate other candidates.Text.Readability.dale_chall/2andText.Readability.spache/2— the two classic word-list readability indices, backed by bundled easy-words lists inpriv/readability/(Dale-Chall 2,949 words, Spache 1,063 words; both sourced from the MIT-licensedpy-readability-metricsdistribution of the public-domain originals).statistics/2now also returns:difficult_wordsand:unfamiliar_wordscounts.Text.Hyphenationbundles six additional language packs:de-1996,fr,es,it,nl,pt. All loaded at compile time with zero I/O, joining the existingen-uspack. Source: hyph-utf8 upstream; per-file licenses (MIT/X11/BSD/LPPL) are preserved in each.texheader.Text.WordFreqbundles six additional frequency tables at the same top-30,000 cap as English:de,fr,es,it,nl,pt. Source: Hermit Dave’s MIT-licensed FrequencyWords OpenSubtitles 2018 corpus.Text.Emoji.sentiment/1andText.Emoji.text_sentiment/1— per-emoji and aggregate sentiment scoring backed by the bundled Emoji Sentiment Ranking v1.0 (Kralj Novak et al., 2015; ~750 emoji with negative/neutral/positive proportions and an aggregate score in[-1.0, 1.0]). Aggregate scoring is occurrence-weighted to match the original paper.kip
I’ve published Text 0.4.0 today with seven new NLP modules (all native Elixir, no NIF or ML).
They cover the kinds of preprocessing you might reach for once your sentiment / classification / search pipeline outgrows
String.split/1.This release represents a largely feature complete text library from my perspective. Happy to take feature suggestions though.
A few of the more immediately useful additions in this release:
Text.Clean— pipeline-style normalisationWhitespace, control characters, smart quotes, mojibake, NFC/NFKC. Composable; defaults are sensible.
Text.Truecase— restore casing for ALL-CAPS or lowercased textPOS-aware heuristics for proper nouns, acronyms, and sentence starts. Useful when an upstream system has destroyed the casing (chat logs, OCR, screaming customer feedback).
Text.Emoji— detection, stripping, counting, conversionBacked by the
:unicodepackage’s emoji property tables, so it recognises every codepoint flagged emoji in the current Unicode release — no shipped JSON.Text.Hyphenation— Knuth–Liang TeX-pattern hyphenationShips en-US patterns baked in (~5 000). Other languages load from any standard
hyph-*.texfile.Text.PII— detect & redact common identifiersPhone, email, credit-card-shaped digits, IBANs, IPv4/IPv6, US SSN. Pattern-based — fast and deterministic. The right tool for “please don’t paste this into the LLM” preflight; pair with a stricter checker if you need legal-grade accuracy.
Text.Spell— Norvig-style spelling suggestionsEdit-distance candidates ranked by frequency in
Text.WordFreq(the 30,000-word English frequency table that also ships in 0.4.0).Text.Summarize— extractive summarisation via TextRankSentence-graph TextRank with configurable similarity (
:cosineor:jaccard) and target length.kip
There are two companion libraries also published today:
.sblfiles and cross-compile them to Elixir.text_stemmer is an optional dependency for text which can be used to tune word clouds.
These two are 100% LLM generated. It took 4 complete days for Claude (Sonnet) to implement. It’s a classic LLM opportunity. Formal specification, canonical implementations, complete conformance testing suites. Prompt the LLM and then go work on something else.
kip
Well, instead of shortly, what I should have said is in about 6 years. But fear not:
See the YouTube video if the meme isn’t familiar to you.
A lot has change in the NLP world since 2020 and the new, modernised and thoroughly renovated text 0.3.0 is now available on Hex.
Features
Language identification
Text.Language.Classifier.Fasttextis a pure-Elixir port of lid.176, validated bit-for-bit against fastText’s reference. 176 languages, ~100 µs per prediction with EXLA.Sentiment, POS, NER
Multilingual sentiment via bundled AFINN lexicons (default) or XLM-RoBERTa through Bumblebee (optional). Part-of-speech tagging and multilingual named-entity recognition via Bumblebee, with
mix text.download_modelsto pre-fetch the weights at deploy time.Word clouds
A new
Text.WordCloudmodule with six scoring backends — YAKE! by default, plus frequency, RAKE, TextRank, TF-IDF, and a KeyBERT variant for users who configure Bumblebee.Text.WordCloud.Layoutdoes Wordle-style spiral packing (with:radialand:spiralorientation modes for sunburst and vortex looks), andText.WordCloud.SVGproduces renderer-agnostic output that plays nicely withColor.Palettefor coordinated tonal-scale colour ramps. You can see some examples in the guide.Fundamentals
Also includes bundled stopwords for ~60 languages from stopwords-iso, and optional Snowball stemming via
:text_stemmerto consolidate morphological variants in word clouds.Optional ML
Heavy ML deps (
:bumblebee,:exla, KeyBERT) are all optional. Without them, the package still does most of what it does — just without the neural-quality ceiling. Same goes for:color(SVG palettes),:localize(CLDR locale resolution), and:text_stemmer.tfwright
I’m really interested in using this library in a project of mine, in particular to generate something similar to “word clouds” where common significant words are highlighted. Is that something you are planning on supporting? Please let me know if there’s any part I can help out with.
kip
Thanks much for the link. I’m a bit challenged reading these imperative implementations for two reasons: (a) such ugly code compared to using pattern matching for most of it as one would in Elixir and (b) as a result, I just want the rules. Megaphone I can find them, but not double.
Maybe I’ll do a basic Metaphone implementation first and at least move forward …
rengel
Just stumbled upon this post. In case you didn’t konw:
kip
Just a little fun addition over coffee this morning - deriving a CLDR locale from natural language. I’ll publish it to hex after I add some tests.
Examples
sorentwo
I (we, at dscout) definitely have a usecase for nearly all of this work . I hope to contribute in the future, and would love to support the effort financially if you decide to make that possible
.
smolcatgirl
I think this is cool but i dont have a usecase for it. Keep up the good work