123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266 |
- # -*- coding: utf-8 -*-
- """
- Copyright (C) 2017, Rodrigo Garcia.
- <strysg@riseup.net>
- This program is free software: you can redistribute it and/or modify
- it under the terms of the GNU Affero Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU Affero General Public License
- along with this program. If not, see <http://www.gnu.org/licenses/>.
- """
- # Utilidades en General
- import random
- import os
- import json
- import datetime as dt
- def titulo_legible(titulo):
- '''
- Retorna la cadena `titulo' como una cadena legible, ej:
- red-indestructible-12
- Red indestructible 12
- '''
- titulo = titulo.split('posts/')[-1]
- titulo = titulo.split('Posts/')[-1]
- titulo = titulo.split('.md')[0]
- titulo = titulo[0].upper() + titulo[1:]
- return titulo.replace('-'," ")
- def captcha_pregunta_opciones_random():
- '''
- Retorna una tupla con la pregunta y opciones del
- archivo captchas.txt siguiendo el formato del archivo.
- (pregunta,[opciones])
- Devuelve None en caso de error
- '''
- with open("monomotapa/captchas.txt", "r") as fil:
- contenido = fil.read()
- lista = contenido.split("###")[1:]
- total = len(lista)
- indice = int(random.random()*(total))
- captcha = lista[indice]
- pregunta = "Letra con la que empieza hola"
- opciones = ['h','f','Z','N']
- random.shuffle(opciones)
- respuestas = ['h']
- try:
- pregunta = captcha.split("\n")[1]
- opciones = captcha.split("\n")[2].split(",")
- random.shuffle(opciones)
- return (pregunta, opciones)
- except:
- print ("Captcha Error en:"+captcha+"\n indice:"+str(indice))
- return ("Letra con la que empieza hola",['h','e','z'])
- return None
- def captcha_comprobar_respuesta(pregunta, respuesta):
- '''
- Comprueba si la respuesta a la pregunta dada es la correcta
- buscando en el archivo captchas.txt, devuelve True o False
- TODO: En caso de exito marcar el captcha como usado y rehabilitarlo luego
- de digamos 1 minuto.
- '''
- correcto = False
- if pregunta is None or respuesta is None:
- return False
- with open("monomotapa/captchas.txt", "r") as fil:
- contenido = fil.read()
- indice = contenido.find(pregunta)
- if indice != -1:
- aux = contenido[indice:]
- respuesta_correcta = aux.split("\n")[2]
- if respuesta_correcta == respuesta:
- correcto = True
- if correcto:
- return True
- return False
- def pregunta_captcha_random():
- '''
- Retorna una tupla con una pregunta al azar del archivo
- captchas.txt siguiendo el formato del archivo.
-
- El formato de la tupla es:
- (pregunta,[opciones],[respuestas])
- Devuelve None en caso de error
- '''
- with open("monomotapa/captchas.txt", "r") as fil:
- contenido = fil.read()
- lista = contenido.split("###")[1:]
- total = len(lista)
- indice = int(random.random()*(total))
- captcha = lista[indice]
-
- pregunta = "Letra con la que empieza hola"
- opciones = ['h','f','Z']
- respuestas = ['h']
- try:
- pregunta = captcha.split("\n")[1]
- opciones = captcha.split("\n")[2].split(",")
- respuestas = captcha.split("\n")[3].split(",")
- return (pregunta, opciones, respuestas)
- except:
- print ("Error en:"+captcha+"\n indice:"+str(indice))
- return ("Letra con la que empieza hola",['h','e','z'],['h'])
- return None
- def categorias_de_post(nombre=None):
- ''' Devuelve una lista con los nombres de las categorias a las
- que pertenece un post con nombre `nombre' '''
- categorias = []
- with open("monomotapa/src/posts/"+nombre, 'r') as fil:
- c = fil.readline() # primera linea con las categorias
- lc = c.split("[#")[1:]
- for cad in lc:
- cat = cad.split("]")[0]
- categorias.append(cat)
- return categorias
- return None
- def categoriasDePost(nombre=None):
- ''' Retorna la lista con los nombres de las categorias a las que
- pertenece un post de nombre `nombre'.
- Este metodo lee el archivo pages.json'''
- nombre = nombre.split('.md')[0]
- with open(os.path.join('monomotapa', 'pages.json'), 'r') as pagefile:
- json_pattrs = json.load(pagefile)
- if json_pattrs.get('posts/' + nombre, None) is not None:
- return json_pattrs['posts/' + nombre]['categorias']
- else:
- return []
- def categoriasList(categoria=None):
- ''' Retorna una lista con los nombres de posts y el numero de posts
- que pertenecen a la categoria dada o cada categoria
- Las categorias se obtienen del archivo pages.json.
- Si no se especifica `categoria' cada elemento de la lista devuelta es:
- (nombre_categoria, numero_posts, [nombres_posts])
- Si se especifica `categoria' cada elemento de la lista devuelta es:
- (numero_posts, [nombres_posts]
- '''
- json_pattrs = {}
- dict = {}
- with open(os.path.join('monomotapa', 'pages.json'), 'r') as pagefile:
- json_pattrs = json.load(pagefile)
- for key,value in json_pattrs.items():
- nombre = key.split('posts/')[-1]
- if value.get('categorias', None) is None:
- continue
- for cat in value['categorias']:
- if dict.get(cat, None) is None:
- dict[cat] = {
- 'contador': 1,
- 'posts': [nombre]
- }
- else:
- dict[cat]['contador'] += 1 # contador de post en categoria
- dict[cat]['posts'].append(nombre)
- lista = []
- for key, value in dict.items():
- if categoria is None:
- lista.append((key, value['contador'], value['posts']))
- elif key == categoria:
- lista = [value['contador'], value['posts']]
- return lista
- def cabezaPost(archivo , max_caracteres=250, categorias=True):
- """ Devuelve las primeras lineas de un archivo de post (en formato markdown)
- con un maximo numero de caracteres excluyendo titulos en la cabeza devuelta.
- Si se especifica `categorias' en True
- Se devuelve una lista de la forma:
- (cabeza_post, categorias)
- donde categorias son cadenas con los nombres de las categorias a la que
- pertenece el post
- """
- cabeza_post = ""
- cats = []
- with open(os.path.join("monomotapa/src/posts",archivo)) as file:
- cats = categoriasDePost(archivo)
- # analizando si hay titulos al principio
- for linea in file.readlines():
- # evitando h1, h2
- if linea.startswith("##") or linea.startswith("#"):
- cabeza_post += " "
- else:
- cabeza_post += linea
- if len(cabeza_post) >= max_caracteres:
- break
- cabeza_post = cabeza_post[0:max_caracteres-1]
- if categorias:
- return (cabeza_post, cats)
- return cabeza_post
- def metaTagsAutomaticos(nombreArchivo, atributos):
- ''' Extrae información básica de los atributos del post y los agrega en
- el atributo `meta'.
- -- return lista meta con las propiedades llenadas
- '''
- meta = []
- title = ''
- summary = ''
- if not isinstance(atributos.get('attributes', ''), dict):
- atributos['attributes'] = {}
- summary = atributos['attributes'].get('summary', atributos.get('heading', 'otro post de Rodrigo Garcia Saenz'))
- title = atributos['attributes'].get('heading', atributos.get('title', 'otro post de Rodrigo Garcia Saenz'))
- meta.append({"tag": "name", "name":"description", "content":summary})
- meta.append({"tag": "property","name":"og:description", "content":summary})
- meta.append({"tag": "property","name":"og:title", "content":title})
- meta.append({"tag": "property","name":"og:type", "content":"web"})
- meta.append({"tag": "name","name":"twitter:card", "content":"summary"})
- meta.append({"tag": "name","name":"twitter:description", "content":summary})
- meta.append({"tag": "name","name":"twitter:title", "content":title})
- meta.append({"tag": "name","name":"twitter:site", "content": atributos['url_base']})
- meta.append({"tag": "name","name":"twitter:autor", "content": "@strymsg"})
-
- # keywords
- keywords = atributos.get('keywords', '')
- for categoria in atributos.get('categorias', []):
- keywords += ', ' + categoria
- meta.append({"tag": "name", "name":"keywords", "content":keywords})
- for keyword in keywords.split(','):
- meta.append({"tag":"property", "name": "article:tag", "content":keyword})
- meta.append({"tag":"name","name":"news_keywords", "content":keywords})
- # fechas
- date = ''
- date = atributos['attributes'].get('date', str(dt.datetime.now()))
- # imagenes
- imgCard = atributos['attributes'].get('image-card', '/static/imgs/cabecera1.png')
- meta.append({"tag":"itemprop", "name": "image", "content": imgCard})
- meta.append({"tag":"property", "name": "og:image", "content": imgCard})
- meta.append({"tag":"name", "name": "twitter:image:src", "content": atributos['url_base'] + imgCard})
-
- return meta
|