Cómo aprendí a dejar de preocuparme y amar la herramienta de capitalización

Visión general

Escribo muchos tutoriales para Envato Tuts +. Estos tutoriales tienen encabezados que deben seguir ciertas reglas de uso de mayúsculas. Tuts + nos proporciona a los autores una herramienta basada en la web que toma el texto de un encabezado y devuelve un encabezado debidamente capitalizado. Cuando escribo mis tutoriales, estoy tratando de entrar en el flujo y cambiar a la herramienta de capitalización interrumpe mi flujo. Yo solo lo usaba para hacer mayúsculas.. 

Resulta que a menudo cometí errores, lo que causó un trabajo adicional a los editores de Tuts + que tuvieron que corregirlos. Siendo programador, decidí programar mi salida del problema. Todavía escribo mis propios encabezados, pero cuando termino, ejecuto un pequeño programa Python que analiza mi artículo, detecta todos los encabezados y luego los ejecuta a través de la herramienta de capitalización Tuts + y capitaliza correctamente todos los encabezados.. 

Como la herramienta de uso de mayúsculas es una aplicación basada en web y no una API, tuve que automatizar el navegador para poder invocarlo y extraer los encabezados en mayúsculas. En este tutorial, aprenderá cómo controlar el navegador en Python a través de Selenium y hacer que haga su oferta. 

Cómo capitalizar encabezados

Capitalizar encabezados no es ciencia espacial, pero tampoco es trivial. Hay varios estilos, con algunas superposiciones y algunas variaciones. Esto es más o menos el consenso:

  • Poner en mayúscula todas las palabras con cuatro o más letras.
  • Siempre capitalice las primeras y últimas palabras.
  • No capitalice artículos: a, an, the.
  • No use mayúsculas en conjunciones cortas: y, o, ni, para, pero, todavía.

Luego hay un montón de excepciones y situaciones especiales (por ejemplo, los encabezados fluyen a la línea siguiente) Pero todo esto es discutible. Incluso si decidiera escribir mi propio código de mayúsculas, Tuts + ya escogió su sabor y necesito ajustarme al estilo elegido..

El convertidor de casos en línea

La herramienta de mayúsculas Tuts + es una herramienta interna destinada a ser utilizada solo por los instructores de Tuts +, por lo que no puedo usarla como una demostración. Sin embargo, encontré una herramienta similar llamada Title Case Converter. Es una aplicación web con un área de texto grande donde puede escribir su encabezado (o título), un botón de conversión en el que hace clic para enviar el formulario, un área de salida que aparece con un encabezado correctamente en mayúscula, y finalmente un botón de copia que copia el encabezado convertido al portapapeles.

Un plan para automatizar la herramienta de capitalización

DE ACUERDO. Voy a usar el convertidor de casos en línea, pero no hay API. Esto no es un gran problema. Puedo automatizar el navegador y simular que un usuario escriba el encabezado en el campo de entrada, haga clic en el botón de conversión, espere a que aparezca la salida, haga clic en el botón de copia y finalmente pegue el encabezado correctamente en mayúsculas del portapapeles.

El primer paso es elegir una automatización del navegador. Elegí Selenium WebDriver, que he usado con éxito antes. El resto del plan es:

  • Lanzar un navegador.
  • Vaya a la URL del convertidor de casos en línea.
  • Encuentra todos los elementos necesarios..
  • Rellenar el campo de entrada.
  • Enviar el formulario.
  • Espera la salida.
  • Haga clic en el botón Copiar.
  • Lee el encabezado en mayúsculas del portapapeles..

El código fuente completo se puede encontrar en GitLab.

Introducción al selenio

Selenium ha automatizado los navegadores desde 2004. En 2008 se fusionó con el proyecto WebDriver, que aborda algunas de las limitaciones del Selenium original (por ejemplo, ejecutándose en el recinto de seguridad de JavaScript). 

Selenium aún ofrece el sabor original de Selenium llamado Selenium RC (Control Remoto). También tiene un IDE para escribir suites de pruebas automatizadas y una herramienta llamada Selenium Grid que escala Selenium RC para grandes suites de pruebas que deben ejecutarse en múltiples entornos. Nos limitaremos al acceso programático al navegador a través de la API WebDriver (a.k.a. Selenium 2).

Instalación de Selenium y un controlador web

Instalar Selenium es tan simple como pipenv selenio. Si no está familiarizado con Pipenv, visite Revisiting Python Packaging With Pipenv. También necesita un controlador web específico. Hay drivers web para diferentes navegadores y back-ups. Puedes encontrar la lista completa en el sitio web de Selenium.

Elegí el controlador web de Chrome para este tutorial. Aquí está la última versión.

Es un archivo zip único que contiene un solo ejecutable (hay versiones de Windows, macOS y Linux). Una vez que lo hayas descargado, descomprímelo y colócalo en tu camino..

¡Felicidades! Ya está listo para usar Selenium WebDriver de Python.

Lanzar el navegador

Selenium hace que sea muy fácil lanzar un navegador. Siempre que tenga el controlador web correcto en su camino, simplemente importe el Selenio.webdriver Módulo y llame al método adecuado para iniciar su navegador de elección:

desde Selenio importar controlador de webdriver = webdriver.Chrome ()

Navegando a una URL

Una vez que tenga un objeto controlador, puede llamar al obtener() Método para navegar a cualquier página web. Aquí es cómo navegar al convertidor de títulos de títulos: 

driver.get ('https://titlecaseconverter.com')

Encontrar elementos

Necesitamos una forma de ubicar los elementos en la página con la que desea interactuar. La forma más sencilla es inspeccionar la página web en el navegador y encontrar los identificadores de los elementos de destino. En la siguiente captura de pantalla, puede ver que el campo de entrada tiene el id "título":

El botón de conversión no tiene identificación, pero eso no es un problema, como verá pronto. Aquí está el código para ubicar el formulario y los campos de texto por ID:

input_field = driver.find_element_by_id ('title')

Si un elemento con el que desea interactuar no tiene un ID, puede encontrarlo utilizando otros métodos, como el nombre, el nombre de la clase o el selector de CSS. Consulta todas las opciones en esta guía de Selenium..  

Por ejemplo, para localizar el botón de conversión, usé su nombre de clase:

convertButton = \ driver.find_element_by_class_name ('convertButton')

Campos de texto de población

Para rellenar el campo de entrada, podemos utilizar el send_keys () Método de nuestro elemento de campo de entrada. Pero asegúrese de borrarlo primero. De lo contrario, simplemente añadirá al texto existente..

input_field.clear () input_field.send_keys (encabezado) 

Eso fue bastante facil.

Haciendo clic en los botones y enviando formularios

Ahora es el momento de enviar el formulario. Puedes hacerlo de dos maneras:

  • Encuentre el elemento de formulario en la página y llame a su enviar() método.
  • Encuentra el botón de convertir y haz clic en él..

Inicialmente envié el formulario directamente:

form = driver.find_element_by_css_selector ('body> form') form.submit () 

Por alguna razón, no funciona. No hay error, pero no pasa nada. No dediqué mucho tiempo a investigar porque el objetivo principal de Selenium y este tutorial es simular a una persona. Así que utilicé el otro método y simplemente hice clic en el botón que encontré anteriormente:

convertButton.click ()

A la espera de la presentación del formulario

El convertidor de casos en línea es algo elegante. El campo de salida no existe inicialmente. Después de hacer clic en el botón Convertir y se envía el formulario, se muestra la salida junto con el botón Copiar. Eso significa que debemos esperar hasta que se complete el envío del formulario antes de que aparezca el botón de copia y podemos hacer clic en él para copiar la salida en el portapapeles.

El selenio te tiene cubierto. Tiene soporte para la espera de condiciones arbitrarias y el tiempo de espera si no se materializan. Aquí está el código que espera al botón de copia. Crea un WebDriverWait Objeto con un tiempo de espera de cinco segundos. Luego crea una condición para la presencia de un elemento con el nombre de clase botón de copia, y luego llama al objeto de espera hasta() método con la condición.

wait = WebDriverWait (controlador, 5) buttonPresent = presence_of_element_located ((By.CLASS_NAME, 'copyButton')) copyButton = wait.until (buttonPresent) 

El resultado es que después de hacer clic en el botón de conversión, esperará hasta que el botón de copia aparezca o se agote después de cinco segundos. Si todo está bien, devolverá el botón de copia elemento.

Leyendo el encabezado en mayúscula

Puedes leer el contenido de los campos de texto con field.get_attribute ('valor'). Pero, como mencioné antes, el convertidor de casos en línea es algo sofisticado. Su salida es una estructura anidada de divisiones y divs, y cuando se desplaza sobre cada parte de la salida, le indica por qué está en mayúsculas o no.. 

Podría profundizar este laberinto y analizar el rumbo real, pero hay una forma más fácil. El botón Copiar copia el encabezado en mayúsculas al portapapeles. Podemos simplemente hacer clic en el botón y leer el encabezado del portapapeles. Usé el módulo portapapeles, que puedes instalar con pipenv instalar portapapeles. El siguiente código borra el portapapeles al copiar una cadena vacía en él, hace clic en el botón de copia y lee repetidamente el portapapeles hasta que no esté vacío..

clipboard.copy (") copyButton.click () result = clipboard.paste () mientras que no es el resultado: time.sleep (0.1) result = clipboard.paste ()

Capitalizando todo un documento de rebajas

DE ACUERDO. Podemos capitalizar una sola partida. Pongo todo este código en una sola función:

def capitalize_heading (encabezado): input_field = driver.find_element_by_id ('title') input_field.clear () input_field.send_keys (encabezado) # form = driver.find_element_by_css_selector ('body> form') # form.submit () convertButton = \ driver .find_element_by_class_name ('convertButton') convertButton.click () # Espera a que aparezca el botón de copia wait = WebDriverWait (driver, 5) buttonPresent = presence_of_el_tement_located (tab. .copy (") copyButton.click () result = clipboard.paste () mientras que no es el resultado: time.sleep (0.1) result = clipboard.paste () devuelve el resultado

Ahora, armados con esta capacidad, podemos analizar un artículo completo y capitalizar todos los encabezados. Escribo mis tutoriales en Markdown. Todos mis encabezados comienzan con uno o más hashes (#). 

Definí una función auxiliar que toma una línea y, si contiene un encabezado, la capitaliza correctamente usando el capitalize_heading () Función y devuelve el resultado. Lo principal es eliminar todos los hashes y espacios principales y restaurarlos más tarde. No podemos alimentar un encabezado con espacios iniciales porque confunde el convertidor de casos en línea: 

def capitalize_line (line): tokens = line.split ('#') header = tokens [-1] space_count = len (heading) - len (heading.lstrip ()) spacing = heading [: space_count] tokens [-1] = espacio + capitalize_heading (heading.lstrip ()) resultado = '#'. join (tokens) resultado de retorno

En este punto, podemos capitalizar un encabezado de Markdown. Es hora de capitalizar todo un documento de Markdown. Este código es bastante simple: repasa todas las líneas, escribe en mayúsculas todas las líneas que comiencen con un hash y devuelve el texto correctamente en mayúsculas:

def capitalize_all_headings (markdown):
 mayúscula = [] líneas = markdown.split ('\ n') para las líneas: if line.startswith ('#'): line = capitalize_line (line) print (line) capitalized.append (line) return '\ n '.join (en mayúsculas)

La función principal toma un documento Markdown de entrada, lo capitaliza y guarda el resultado como "capitalized.md", que puede verificar y usar. Lo único que debe tener cuidado es si su documento de Markdown contiene líneas sin encabezado que comienzan con un hash. Esto puede suceder si encabeza bloques de código que contienen comentarios de Python o bash.

Dato curioso: el tutorial que está leyendo en este momento se capitalizó con este programa.

Conclusión

La automatización del navegador le permite tomar control de las aplicaciones web que no proporcionan una API mediante programación. Esto es útil principalmente para rellenar formularios y otras actividades web interactivas (haciendo clic en "¿Siguiente" en EULA largos?). 

Selenium se diseñó principalmente para probar aplicaciones web, pero es excelente para automatizar cualquier interacción basada en el navegador. Si piensa un poco, probablemente puede encontrar muchas aplicaciones web que puede automatizar y hacer su vida más fácil..