Skip to content

Instantly share code, notes, and snippets.

What would you like to do?
Mapping URL (Deep linking) on iOS.
import Foundation
extension String {
//Know if self is only composed by numbers
var isNumber: Bool {
return !self.isEmpty && CharacterSet.decimalDigits.isSuperset(of: CharacterSet(charactersIn: self))
//Struct to check Regular Expresions
struct Regex {
let pattern: String
let options: NSRegularExpression.Options!
private var matcher: NSRegularExpression {
return try! NSRegularExpression(pattern: self.pattern, options: self.options)
init(_ pattern: String, options: NSRegularExpression.Options = [.caseInsensitive]) {
self.pattern = pattern
self.options = options
//Devuelve el array de grupos
func match(_ string: String, options: NSRegularExpression.MatchingOptions = []) -> [NSTextCheckingResult] {
return self.matcher.matches(in: string, options: [], range: NSMakeRange(0, string.characters.count))
//Implement this in whatever type you want to check with regular expresions
protocol RegexMatchable {
func match(regex: Regex) -> Bool
//Wrap the comparing string and the groups to extract ids
final class Matcher: RegexMatchable {
let comparing: String
var groups: [NSTextCheckingResult]?
var matchingGroups: [String] {
var matches = [String]()
if let groups = groups {
let string = comparing as NSString
for group in groups {
for index in 1..<group.numberOfRanges {
matches.append(string.substring(with: group.rangeAt(index)))
return matches
var intGroups: [Int] {
return self.matchingGroups.flatMap { Int($0) }
init(_ matching: String) {
self.matching = matching
func match(regex: Regex) -> Bool {
let matches = regex.match(self.matching)
if !matches.isEmpty {
self.groups = matches
return true
return false
extension String: RegexMatchable {
func match(regex: Regex) -> Bool {
return !regex.match(self).isEmpty
//Overload patter matching operator
func ~=<T>(pattern: Regex, matchable: T) -> Bool where T: RegexMatchable {
return matchable.match(regex: pattern)
//Routing with enums its easy
enum DeepLinking {
case helado(id: Int)
func linking(_ path: String) -> DeepLinking? {
let matching = Matcher(path)
switch matching {
case Regex("^(\\/helado\\/([0-9]+)\\/*)"):
guard let id = matching.intGroups.first else { return nil }
//Here you have your id, typed.
return .helado(id: id)
//No matches
return nil
let link = linking("/helado/43") //.helado(43)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.