Generate a slug – transliteration with a lot of options

Overview

SpeakingURL

Build Status NPM version Bower version Gem Version Gitter Flattr

Generate a slug with a lot of options; create a so-called Semantic URL or 'Clean URL' or 'Pretty URL' or 'nice-looking URL' or 'Speaking URL' or 'user-friendly URL' or 'SEO-friendly URL' from a string. This module aims to transliterate the input string.

For use in browser and server - no dependencies!

NPM Badge

Module Status

Installation

npm

npm install speakingurl --save

yarn

yarn add speakingurl --dev

Bower

bower install --save speakingurl

Component

component install pid/speakingurl

Ruby on Rails

# Add to Gemfile
gem 'speakingurl-rails'

Download Package

copy the file speakingurl.min.js to your script directory

CDN/cloudflare

available versions:

CDN/maxcdn

available versions:

Usage

getSlug(input, [options]);

input: {string} to convert

options {object|string} config object or separator string (see below)

  • options {object}

    • separator {string} default: '-'
      • char that replaces the whitespaces
    • lang {string|boolean} default: 'en' // ISO 639-1 Codes
      • language specific transliteration (
        • 'ar' // Arabic
        • 'az' // Azerbaijani*
        • 'cs' // Czech
        • 'de' // German
        • 'dv' // Divehi
        • 'en' // English
        • 'es' // Spanish
        • 'fa' // Persian
        • 'fi' // Finnish
        • 'fr' // French
        • 'ge' // Georgian
        • 'gr' // Greek*
        • 'hu' // Hungarian
        • 'it' // Italian
        • 'lt' // Lithuanian*
        • 'lv' // Latvian
        • 'my' // Burmese
        • 'mk' // Macedonian*
        • 'nl' // Dutch
        • 'pl' // Polish
        • 'pt' // Portuguese
        • 'ro' // Romanian
        • 'ru' // Russian
        • 'sv' // Swedish
        • 'sk' // Slovak
        • 'sr' // Serbian*
        • 'tr' // Turkish
        • 'uk' // Ukranian
        • 'vn' // Vietnamese
    • symbols {boolean} default: true
      • false -> don't convert symbols
      • true -> convert symbols according to the 'lang' setting
    • maintainCase {boolean} default: false
      • true -> maintain case chars
      • false -> convert all chars to lower case
    • titleCase {boolean|array} default: false
      • true -> convert input string to title-case
      • array -> titlecase = true, but omit the words from in the array
    • truncate {number} default: 0
      • 0 -> don't trim length
      • >= 1 -> trim to max length while not breaking any words
    • uric {boolean} default: false
      • true -> additionally allow chars: ";", "?", ":", "@", "&", "=", "+", "$", ",", "/"
      • false
    • uricNoSlash {boolean} default: false
      • true -> additionally allow chars: ";", "?", ":", "@", "&", "=", "+", "$", ","
    • mark {boolean} default: false
      • true -> additionally allow chars: "-", "_", ".", "!", "~", "*", "'", "(", ")"
    • custom {object|array} default: {}
      • object -> custom map for translation, overwrites all i.e. { '&': '#', '*': ' star ' }
      • array -> add chars to allowed charMap (see example)
  • options {string} separator

notes: default only Base64 chars are allowed (/A-Za-z0-9_-/), setting uric, uricNoSlash or/and mark to true will add the specified chars to the list of allowed characters. The separator-character is always allowed.

Node.js
var getSlug = require('speakingurl');
Browser
<script src="bower_components/speakingurl/speakingurl.min.js"></script>

Ruby on Rails

# Add to application.js
//= require speakingurl

Examples

var slug;

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !");
console.log(slug); // Output: schoener-titel-laesst-gruessen-bel-ete

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !", '*');
console.log(slug); // Output: schoener*titel*laesst*gruessen*bel*ete

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !", {
        separator: '_'
	});
console.log(slug); // Output: schoener_titel_laesst_gruessen_bel_ete

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !", {
        uric: true
	});
console.log(slug); // Output: schoener-titel-laesst-gruessen?-bel-ete

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !", {
    	uricNoSlash: true
	});
console.log(slug); // Output: schoener-titel-laesst-gruessen?-bel-ete

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !", {
    	mark: true
	});
console.log(slug); // Output: schoener-titel-laesst-gruessen!-bel-ete-!

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !", {
    	truncate: 20
	});
console.log(slug); // Output: schoener-titel

slug = getSlug("Schöner Titel läßt grüßen!? Bel été !", {
	    maintainCase: true
	});
console.log(slug); // Output: Schoener-Titel-laesst-gruessen-Bel-ete

slug = getSlug("Äpfel & Birnen!", {
	    lang: 'de'
	});
console.log(slug); // Output: aepfel-und-birnen

slug = getSlug("မြန်မာ သာဓက", {
	    lang: 'my'
	});
console.log(slug); // Output: myanma-thadak

slug = getSlug('މިއަދަކީ ހދ ރީތި ދވހކވ', {
        lang: 'dv'
    });
console.log(slug); // Output: miadhakee hd reethi dvhkv

slug = getSlug("Apple & Pear!", {
	    lang: 'en' // lang: "en" is default, just to clarify
	});
console.log(slug); // Output: apple-and-pear

slug = getSlug('Foo & Bar * Baz', {
	    custom: {
	        '&': ' doo '
	    },
	    uric:true
	});
console.log(slug); // Output: foo-doo-bar-baz

slug = getSlug('Foo ♥ Bar');
console.log(slug); // Output: foo-love-bar

slug = getSlug('Foo & Bar | (Baz) * Doo', {
	    custom: {
	        '*': 'Boo'
	    },
	    mark:true
	});
console.log(slug); // Output: foo-and-bar-or-(baz)-boo-doo

slug = getSlug('Foo and Bar or Baz', {
	    custom: {
	        'and': 'und',
	        'or': ''
	    }
	});
console.log(slug); // Output: foo-und-bar-baz

slug = getSlug('[Knöpfe]', {
		custom: [
			'[',
			']'
		]
	});
console.log(slug); // Output: [knoepfe]

slug = getSlug('NEXUS4 only $299');
console.log(slug); // Output: nexus-4-only-usd299

slug = getSlug('NEXUS4 only €299', {
	    maintainCase: true
	});
console.log(slug); // Output: NEXUS-4-only-EUR299

slug = getSlug('Don\'t drink and drive', {
	    titleCase: true
	});
console.log(slug); // Output: Don-t-Drink-And-Drive

slug = getSlug('Don\'t drink and drive', {
	    titleCase: ['and']
	});
console.log(slug); // Output: Don-t-Drink-and-Drive

slug = getSlug('Foo & Bar ♥ Foo < Bar', {
	    lang: false
	});
console.log(slug); // Output: foo-bar-foo-bar

slug = getSlug('Foo & Bar ♥ Foo < Bar', {
	    symbols: false
	});
console.log(slug); // Output: foo-bar-foo-bar

slug = getSlug('ä♥ä', {
		lang: 'tr',
	    symbols: false
	});
console.log(slug); // Output: a

createSlug([options])

options: {object|string} config object or separator string (see above)

Create your own specially configured function.

var options = {
	    maintainCase: true,
	    separator: '_'
	};

var mySlug = require('speakingurl').createSlug(options);
// in browser:
// var mySlug = createSlug(options);

var slug = mySlug("Schöner Titel läßt grüßen!? Bel été !");
console.log(slug); // Output: Schoener_Titel_laesst_gruessen_Bel_ete

Create your own specially configured function with title-case feature.

var options = {
	    titleCase: [
	        "a","an","and","as","at","but",
	        "by","en","for","if","in","nor",
	        "of","on","or","per","the","to","vs"
	    ]
	};

var mySlug = require('speakingurl').createSlug(options);
// in browser:
// var mySlug = createSlug(options);

var slug = mySlug('welcome to the jungle');
console.log(slug); // Output: Welcome-to-the-Jungle

Changelog

see CHANGELOG.md

Tests

Build Status

npm test

Contribution

# fork pid/speakingurl on Github
$ git clone [email protected]:<YOUR_USER>/speakingurl.git
$ cd speakingurl
$ npm install
# add your stuff
# add tests
# add example for new feature
# add release info to CHANGELOG.md
# add description/example to README.md
$ gulp
$ commit files (speakingurl.min.js,...)
# if everything works fine, commit, push to your repository
# create pull request

Release

$ gulp bumpup --patch  # --minor # --major
$ gulp
$ gulp release

Release to RubyGems.org

$ gulp
$ gem build speakingurl-rails.gemspec
$ gem push speakingurl-rails-x.x.x.gem

References

Use in other environments

Ports

Credits

License

The BSD 3-Clause License (BSD3)

Copyright (c) 2013-2017 Sascha Droste [email protected] All rights reserved.

Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:

  • Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
  • Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
  • Neither the name of the author nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.

THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

Comments
  • Russian/Bulgarian letter not interpreted!

    Russian/Bulgarian letter not interpreted!

    Hello. I would like to ask what is the reason for the following interpretation:

    'ъ': '',

    This can be interpreted with the latin equivalent of 'a' or 'u'. Both would be understandable.

    enhancement in progress 
    opened by tsvetann 16
  • russian example - speaking url is translating to english...

    russian example - speaking url is translating to english...

    Hi,

    I am looking to "slugify" the following: ревущий фьорд

    I am hoping to get: ревущии-фьорд

    This is what speakingurl currently does:

    slug=require("speakingurl")
    [Function: getSlug]
    > slug("ревущий фьорд")
    'revushij-ford'
    > slug("ревущий фьорд",{lang:'ru'})
    'revushij-ford'
    

    Is there an option keep the original characters, but simplified (as I am hoping)?

    For background, these are slugs that the World of Warcraft api uses - so I am trying to mimic what it does.. so, perhaps not the best way round of doing this...

    Thanks, Chris

    question 
    opened by kimptoc 7
  • Add Swedish language

    Add Swedish language

    • Swedish alphabet: The 29 letters of this alphabet are the modern 26-letter basic Latin alphabet ('A' through 'Z') plus 'Å', 'Ä', and 'Ö', in that order.
    • ISO 639-1 for Swedish is sv
    opened by simison 6
  • Turkish translation needed

    Turkish translation needed

    'en': {
       '∆': 'delta',
       '∞': 'infinity',
       '♥': 'love',
       '&': 'and',
       '|': 'or',
       '<': 'less than',
       '>': 'greater than',
       '∑': 'sum',
       '¤': 'currency'
    },
    
    enhancement 
    opened by pid 6
  • complete Romanian characters; move to main table

    complete Romanian characters; move to main table

    • some uppercase characters were missing (Ă, Â, Î, Ș)
    • there is no ambiguity in converting to ascii, so we might as well include everything in the main table
    opened by mgax 5
  • Add support for

    Add support for "black-listed" words

    Hello,

    The lib would be wonderful if we could add a list of black listed words. This would be super useful for short words for instance, like "the", "a", "and". Whatever the language by the way.

    enhancement 
    opened by DjebbZ 5
  • Add option to remove underscores

    Add option to remove underscores

    Today I learned underscores aren't allowed in domain hostnames! Whoops. As such, I'd like an option to get rid of underscores, and replace them with hyphens.

    question 
    opened by n-rook 4
  • Translation needed: Ukranian

    Translation needed: Ukranian

               'uk': {
                    '∆': 'delta',
                    '∞': 'infinity',
                    '♥': 'love',
                    '&': 'and',
                    '|': 'or',
                    '<': 'less than',
                    '>': 'greater than',
                    '∑': 'sum',
                    '¤': 'currency'
                },
    

    !!! Translation must be already transliterated !!!

    enhancement 
    opened by pid 4
  • German umlaut not correct replaced...

    German umlaut not correct replaced...

    i have "datenschurtzerklärung" as slug, but it will not be "datenschutzerklaerung" it gets "datenschutzerla_rung" with option {lang:'de',seperator:'_'}

    Additional: Running on MacOS High Sierra and Linux Ubuntu 18.04 same problem

    opened by Dexus 3
  • Expand contractions before slugging

    Expand contractions before slugging

    Related to #105, but a different approach. Instead of omitting apostrophes and creating possibly-confusing words like wont or well, instead expand the contractions (opt-in?), thus creating do-not, will-not, we-will, etc.

    From the readme, this example:

    slug = getSlug('Don\'t drink and drive', {
    	    titleCase: true
    	});
    console.log(slug); // Output: Don-t-Drink-And-Drive
    

    would instead be:

    slug = getSlug('Don\'t drink and drive', {
    	    titleCase: true,
            expandContractions: true
    	});
    console.log(slug); // Output: Do-Not-Drink-And-Drive
    

    The package contractions can be used for English.

    I think there might be some use for this in French as well, but not as useful nor common. I'm not familiar enough with other languages.

    opened by passcod 3
  • please mention breaking changes in releases

    please mention breaking changes in releases

    Our app broke recently.

    I tracked it down to speakingurl removing special characters like "!", "?". This caused conflicts in document titles in our case.

    I have no idea when this change was introduced. I think it must have been introduced recently because documents only began to disappear in the last few months (judging from what users tell me).

    I made it a habit to check the release messages when updating a dependency that indicates a breaking change with it's version number.

    Unfortunately speakingurl does not mention what could break (for instance: https://github.com/pid/speakingurl/releases/tag/v14.0.0).

    Or is there a different way to see what could break?

    opened by barbalex 3
  • Trying to get in touch regarding a security issue

    Trying to get in touch regarding a security issue

    Hey there!

    I'd like to report a security issue but cannot find contact instructions on your repository.

    If not a hassle, might you kindly add a SECURITY.md file with an email, or another contact method? GitHub recommends this best practice to ensure security issues are responsibly disclosed, and it would serve as a simple instruction for security researchers in the future.

    Thank you for your consideration, and I look forward to hearing from you!

    (cc @huntr-helper)

    opened by JamieSlome 0
  • Add an option to disable currencies

    Add an option to disable currencies

    Hello, I'm trying to make speakingurl remove $ from strings instead of replacing it with usd. Options.symbols doesn't seem to change anything.

    speakingurl("test 123 $123", {
      symbols: false
    }); // => 'test-123-usd123'
    
    bug 
    opened by pcktm 1
Owner
Sascha
:w devfoobar_since_1982.txt Mostly Harmless.
Sascha
CSS is powerful, you can do a lot of things without JS.

You Don't Need JavaScript Please note these demos should be considered as CSS "Proofs of Concepts". They may have serious issues from accessibility po

You Don't Need 17.9k Jan 4, 2023
FakeCommitter is a tool for those who want to be a GITHUB POPSTAR WITH A LOT OF CONTRIBUTIONS DAILY

FakeCommitter is a tool for those who want to be a GITHUB POPSTAR WITH A LOT OF CONTRIBUTIONS DAILY! Or maybe you just want to sync your contribution number across accounts (like me).

Gustavo Henrique 16 Nov 10, 2022
An ingame overlay with a lot of enhancements for your daily gameplay

LostArkOverlay This project was generated using Nx. ?? Smart, Extensible Build Framework Quick Start & Documentation Nx Documentation 10-minute video

Pascal M 7 Sep 24, 2022
Most of my pride is here. I put a lot of love into this.

Develop Please use yarn npm i -g yarn for dependencies. Npm is really terrible for CI/CD. To start developing, you need to run two commands simulateno

Tivoli Cloud VR, Inc. 0 Sep 4, 2022
CSS Generator has a lot of tools 😉 🎉 👀

Css Generator ?? Packages used in Project : React Router Dom Framer Motion react-color react-icons react-awesome-button Preview Tools ?? Background to

Mohammad 19 Dec 31, 2022
"Pizza Party!" - A Jovo V4 master template supporting a lot of features

"Pizza Party!" - Yet another Jovo V4 master template supporting a lot of features There are a lot of Jovo examples around but I did not find any proje

Frank Börncke 8 Aug 2, 2022
Happy Birthday is a web-based party live background generated by CANVAS powered by JavaScript. This show a lot of random colorize particles in the background.

Happy BirthDay JS Happy Birthday is a web-based party live background generated by CANVAS powered by JavaScript. This show a lot of random colorize pa

Max Base 9 Oct 29, 2022
jQuery Tabs Plugin. CSS Tabs with Accessible and Responsive Design. Lot of Tab Themes with Vertical and Horizontal Orientation.

Macaw Tabs Macaw Tabs is jQuery tabs plugin. It helps you to create accessible and responsive jQuery tabs by implementing the W3 design patterns for t

HTMLCSSFreebies 6 Dec 8, 2022
jQuery easy ticker is a news ticker like plugin, which scrolls the list infinitely. It is highly customizable, flexible with lot of features and works in all browsers.

jQuery Easy Ticker plugin jQuery easy ticker is a news ticker like plugin which scrolls a list infinitely. It is highly customizable, flexible with lo

Aakash Chakravarthy 208 Dec 20, 2022
A highly customizable platform ready to be a portfolio website, and become a lot more with some of your own components

Vextra Elegant and animated portfolio website. Demo: vextra.vercel.app Vextra is a portfolio template, packed with animations with a satisfying flow t

null 3 Sep 19, 2022
URL Shortener API in NodeJS supporting pagination, sort params and lot more

node-url-shortener Built with ❤️ in NodeJS A simple URL Shortner REST API that uses shortid npm package to generate short endpoints for your long URL.

Dhairya Ostwal 3 Sep 22, 2022
Math Calc is a simple algebra calculator with options for basic addition, subtraction, multiplication, and division as well as many more mathematical properties.

Math-Calc Math Calc is a simple algebra calculator with options for basic addition, subtraction, multiplication, and division as well as many more mat

CoderX07 1 Dec 25, 2021
A fixed-width file format toolset with streaming support and flexible options.

fixed-width A fixed-width file format toolset with streaming support and flexible options. Features Flexible: lot of options Zero dependencies: small

Evologi Srl 6 Jul 14, 2022
A dashboard to display options-related data around PsyOptions markets and Serum orderbooks.

PsyOptions Data Dashboard Digestible data around options activity on Solana is pretty inaccessible at the moment. PsyViz provides a clean and user-fri

sanny 3 May 13, 2022
A non-overflowing `console.table` alternative with customization options.

nice-table A non-overflowing console.table alternative with customization options. Usage import { createTable } from 'nice-table'; type Person = {

Tim van Dam 5 Aug 4, 2022
Superlight vanilla javascript plugin, for modern web dropdowns. Supporting multi-options, search and images. Designed to be seamlessly themed

Superlight vanilla javascript dropdowns by LCweb Need to jump off of jQuery (or any other) dependency? Other packages are too heavy to just tweak sele

Luca 10 Dec 26, 2022
Simple quick javascript dropdown plugin with search, that able to work with thousands of options

fstdropdown fstdropdown - simple quick javascript dropdown plugin with bootstrap design and search, that able to work with thousands of options. Now w

Vladyslav Andrieiev 15 Nov 12, 2022
Kuldeep 2 Jun 21, 2022
Exposes theming options available in Joy UI by providing color palette and typography controls.

Joy Theme Creator Note: Joy UI is currently in alpha - some things may not be finished or working as expected. This project exposes the theming option

Oliver Benns 10 Dec 28, 2022