Skip to content

Instantly share code, notes, and snippets.

@octaviogb
Created December 5, 2019 17:17
Show Gist options
  • Save octaviogb/cce79723fc2fe11fd452e9e5d694f971 to your computer and use it in GitHub Desktop.
Save octaviogb/cce79723fc2fe11fd452e9e5d694f971 to your computer and use it in GitHub Desktop.
Código para transformar html para blocos de propriedades, em swift
// Criado por Octávio Turra em 05/12/2019
import Foundation
// Função que peguei para fazer o match
// e devolver o que bateu com a regex
func matches(for regex: String, in text: String) -> [String] {
// referência: https://stackoverflow.com/questions/27880650/swift-extract-regex-matches
do {
let regex = try NSRegularExpression(pattern: regex)
let results = regex.matches(in: text,
range: NSRange(text.startIndex..., in: text))
return results.map {
String(text[Range($0.range, in: text)!])
}
} catch let error {
print("invalid regex: \(error.localizedDescription)")
return []
}
}
// Executo aqui e retorno os groups
// Essa regex é a chave, pois ela quebra o que está em tag
// e separa o que não está
let split_tag_text = "(?<word>(<\\w+>)+.+?(<\\/\\w+>)+|\\w+)+"
var grs = matches(for: split_tag_text, in:"eu <b><i>quero</i></b> quero ir <i>embora agora</i>")
// O block é uma estrutura que vai guardar o nosso pedaço de texto
// e os seus atributos, que são o conteúdo das tags
// Eu só trabalho tags simples, sem atributos
struct Block {
var text: String = ""
var attributes: Array<String> = []
}
// Essa função que vai extrair os blocos
func handle(tag: String) -> Block {
// Preciso desse tags para poder pegar a quantidade de
// tags, ou seja, atributos que vamos ter
let tags = matches(for: "(<\\w+>)", in: tag)
// aqui vou fazer um outro matchh da tag e seu conteudo
// para poder indexar todos os atributos
var attributes = matches(for: "((<\\w+>)+|\\w+)", in: tag)
// vou pegar somente os atributos
let attrs = attributes[(attributes.count - tags.count) ..< attributes.count]
// vou pegar somente os conteudos
let s = attributes[1 ..< (attributes.count - tags.count)].joined(separator: " ")
return Block(text: s, attributes: attrs.dropLast(0))
}
// Aqui eu vou pegar e trabalhar as tags
// e separar dos textos puros
var groups = grs.map { (matchee: String) -> Block in
if matchee.starts(with: "<") { return handle(tag: matchee) }
else { return Block(text: matchee, attributes: []) }
}
// Vou criar um array para os atributos
var attribute_blocks: Array<(attribute: String, from: Int, to: Int)> = []
// Vou criar o texto limp
let text = groups.reduce("") {(acc: String, cur: Block) -> String in
var out = acc
let from = out.count
out += cur.text + " "
let to = out.count
cur.attributes.forEach { attr in
attribute_blocks.append((attribute: attr, from: from, to: to))
}
return out
}
// Aqui, printo os resultados
print(text)
print(attribute_blocks)
// Você pode consultar o resultado em
// https://tio.run/##hVZNb9tGED2Lv2Iq9EBBMmUbTZsKioK0dYAAQVM0RS@2YKzIlbQJxWX2Q3aS@scEPQTNtbde9cPcN7uURClFyoO9Ws7Ox5s3b2lv1Nx9c38/HNKPRolCU60Nvcjd5sNaafrNGyNIruj0wfDsfHh@evZ9kqgVbBw91b4qhFO6ShIcf@qrzcfNn5reeEm1XHipqBY4PRfvpCFNK@HyJVtKKuRal@uwy9Yz4aSnXK9IkJELeZvMfZXHA9Kmc2QUtkf00hlVLQakKnLy1m03enQyocu4ntL7hPAgkJFzaTafqlyJES2dq@1oOLRO5K81gs9LfZMh6BApWC7DDs@/e/jw9NsHp0PLsJwgghG5OwnBT5p0gnPgFKPwU0oX86NH5Mxb@vnlryi/FObitjbSWrhOa@GcNNUoGvaOzlpfOovT4WW2rVvBnKsc7Ky/9BhRLeSIg/Mi5YMZajXuWVXAaZYxatFhbx/fSOdNtU0BoetWYfxEUIO7y@j569MsxGr5@2q693gXVneUcxWhPmkMOrh3W8OjS7uqWotSFdvWXqXBLit1ju13svhJ2tyomjvT636W8eU0xknuAvsubmXunSbxxisQDEbaVJq0pYXRvrbBxtqGX7T5C1TLl2KNKmqtLMlSMBVn4GvkJCix@cDMd2IRSWtloHN8XTHTg03CJdq6VO4apteMBzrZTR@Pb7QpJun46uqmP@n1s/5jXg@bn3/w/16/m6yFQY7c/RbfR0ceA9ZdDMl4NhmrCTIwejxUk/FwNqHwi5QhvJGrmUaSYoG/bADgOPsXNAOur7luvxKcuPGAMdRMa6Fo4YUpBA9kpa2FCshCbD5qTGrosI4QAE4rvSUBUswAtx0EB5bB0BjgysnNP5iNQljGLaLu8f5vDIaYiXKpwz5ZaEgpcdwC4Z23hNPKHf0QcmXCMDjtQWdku80@Jiqck3ZETyBTb8fRZgIjsKPhBfd83pYmrjYMNgBDPYwLIgfBWYqqKDE6YnEgLPt04PAXI3NlGRhrZSwm0KLWBfQMuseZIZConCpEwVpH8STbDkgDDvlKDPZVN1mtsIJEJB3mU/B7xIjulkrdZvLEgqciOg@8X8N5VFu/QiBnGtFdoiFsHkjsY598oePJVvaKlYIR1wWS0a0@J51DxD/PbcfzSOx2jjEOJxfhsXolkcFRAC6bA7DvfaDLdL@GWPvK0UlAJ/7oUZaN6dhk@qWQ2@qbkEfhzoLD/wk6zV5pVckijZLgAgKEUesknUaeAmfSSF07OOBqKDIrjK6fC@vSU6hx5OqToF2@lbbcjg2Dvx@prRYZKgJpbplFtTeoKaoJKx7qgqxERac0dkv@B69VlXTUvGmnjFeGTW@UW6KocbeH001N7fFozHsQ4I4sMQk7q3bljdVh/ZfTXpRtLuV31AqVF4Gygqc4EvKAGwfcuw5Ktpv5fav2Xwdzo1cjelZBNp0Oi14jCochdcSOSqhRkPFGvCOAmZGFz2XaZQxSkef7ALlHx0OhAchGm/BREucEo8esyvODa56zwjZeRhrtXrJ5/xE7zUICfSbTwVHk2D6YdNi2xVHM4IXAbfs@wBRa2jkGLBN1LasibQPGyy1c/Dfi5TQo2UGDtmRG5BZFB/ECD5dr/G4QPE3xVg@fA836OINeA3@@@RQEh0cxHOdO7DzhzmWz5P7@Xw
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment