尚未检测到更新。GitHub 发布版本后会显示在这里。
个人 GitHub 账号下公开仓库的所有者可以登录并验证所有权,自行管理介绍,无需管理员批准。
登录并生成验证文件,在 30 分钟内将其提交到此仓库的默认分支。其他分支或分叉仓库中的文件无效。然后在下方检查文件,即可无需管理员批准直接管理项目。请保留文件以维持管理权限。
如需登录,将前往登录页面。登录后请回到此处,再次点击所选的验证按钮。
在项目文件夹中运行 /nomorevibe verify,即可验证所有权并自行管理介绍。
一分钟完成验证制作者的介绍仅有上面的一句话。 更多详情请阅读仓库 README。 仓库 README ↗
正在加载完整 README。
查看完整 README ↗Releva la cartelera semanal de las salas de CABA del padrón data/salas.json y
publica una web con tres vistas: Películas, Por cine y Calendario.
Salas hoy (17): Cinemark Caballito, Hoyts Abasto, Hoyts DOT, Cinemark Palermo, Cinemark Puerto Madero,
Cinemark Parque Brown, Atlas Caballito, Cine Gaumont (Espacio INCAA Km 0), Multiplex Belgrano, Multiplex Lavalle,
Showcase Belgrano, Cine Cosmos UBA, Atlas Flores, Atlas Liniers, Atlas Alcorta, Atlas Patio Bullrich y
Cinépolis Recoleta. Cada sala tiene id, barrio, comuna, coordenadas, cadena
(define el color), fuente (módulo de carteleras/sources/), cfg (parámetros
para ese módulo), alcance (semana: la fuente publica varios días; dia: solo el día de la corrida) y
cobertura (completa o parcial: la fuente lista solo parte de la cartelera). activa: false saca una sala de la
corrida sin borrarla. carteleras/salas.py valida el padrón (incluye alcance y cobertura) y run.py aborta si es
inválido. Para agregar una sala de una fuente existente alcanza con una entrada nueva en el JSON.
Sólo biblioteca estándar de Python 3. Sin dependencias. Una credencial opcional: TMDB_TOKEN (ver «TMDb por API»).
python3 run.py # releva todo y genera salida/cartelera.html + salida/datos.json
python3 run.py --salida salida/cartelera-caba.html --json salida/datos-caba.json # para probar sin pisar lo de la rutina
python3 run.py --sin-puntajes # más rápido, sin consultar TMDb
python3 -m unittest discover -s tests -t .
node --test tests/js/*.test.js # funciones puras de filtros (bloque al principio de templates/app.js)
node scripts/contar_watchlist.mjs <export.zip|watchlist.csv> salida/datos-caba.json # conteo local de matches de una watchlist (no imprime títulos que no cruzan)
Ventana y fechas. La ventana es la fecha de Buenos Aires de la corrida + 4 días (no depende de Cinemark). Las fuentes «solo hoy»
(unica diario, Showcase) se asignan siempre a esa fecha; los días siguientes de esas salas se muestran con la leyenda «Esta sala publica
su programación día a día» (nunca se copian horarios a otros días). El dataset trae por sala alcance, cobertura y dias_con_datos.
La rutina diaria tiene que correr a las 11:00 ART (no antes de las 10).
Tests (ninguno sale a la red): test_fuentes_nuevas.py (unica semanal/diario, Multiplex, Showcase y su cruce, con muestras reales en tests/fixtures/fuentes/), test_run_fuentes.py (corrida completa con fuentes falsas), test_tmdb.py (matching, caché, 401/429, corrida completa y anti-fuga del token, con respuestas guardadas en tests/fixtures/tmdb/), test_parsers.py (parsers frágiles),
test_salas.py (padrón), test_unify_salas.py (cruce por sala y no regresión
contra tests/legacy_unify.py, el construir de main con 4 salas fijas),
test_cinemark_fixture.py (JSON-LD real recortado en tests/fixtures/).
run.py imprime un resumen al final (películas por sala, cuántas con puntaje,
pedidos HTTP y duración) y escribe en stderr ATENCION sin_datos=<ids de sala>
si alguna quedó en cero, o ATENCION sin_puntajes=<tmdb|rt> si un proveedor de
puntajes no devolvió ninguno.
| Sala | Fuente | Cómo |
|---|---|---|
| Cinemark y Hoyts (6 salas) | cinemark.com.ar | JSON-LD renderizado del lado del servidor en /cartelera/<slug> (una página por sala, en serie); la ficha en el payload de Next.js de /pelicula/<slug> (máx. 4 en paralelo). La sinopsis se descarta si tiene menos de 40 caracteres o empieza con $ (a veces el payload trae un precio) |
| Atlas Caballito | atlascines.com | API interna sin auth (GetFechasDisponibles, GetCacheFuncionesComplejoPeliculaFecha), complejo 191 (cfg.complejo). Si la API viene vacía (503 de Cloudflare) cae a unica diario: la sala pasa a dia/parcial en esa corrida (cfg.respaldo en el padrón) |
| Gaumont y Cosmos UBA | www.unica-cartelera.com.ar | Programación semanal en prosa (unica.semanal, expandir_semana). Se reparte solo dentro de la semana del encabezado «SEMANA DEL JUEVES dd AL MIÉRCOLES dd DE »; sin encabezado legible, hasta el miércoles siguiente a la fecha de corrida |
| Atlas Flores, Liniers, Alcorta, Patio Bullrich y Cinépolis Recoleta | www.unica-cartelera.com.ar | Una tarjeta por película con los horarios del día de la consulta e idioma (Cast. = D, Subt. = S) (unica.diario). Cobertura parcial (observado: lista 2 películas donde la web oficial de Cinépolis lista más de 25). «(Martes y miércoles cerrado)»: si la corrida cae en ese día, la sala queda sin datos |
| Multiplex Belgrano y Lavalle | multiplex.com.ar | Un solo pedido a la home: JSON en data-funciones (~55 días). Complejo por la etiqueta de <input name="complejo">, título del <h4>, noche de cine (dia, no dia_real), deduplicado por id de función; se recorta a la ventana |
| Showcase Belgrano | todoshowcase.com/cartelera/belgrano | HTML del lado del servidor, solo el día actual, formato e idioma por función (un <p> puede traer una línea por idioma) |
| TMDb (id, títulos, puntaje) | api.themoviedb.org | API oficial v3 con TMDB_TOKEN: 1 búsqueda + 1 ficha por película nueva, verificando el director. Caché en |
carteleras/tmdb.py)Da por película: tmdb_id, titulo_original, titulo_local (es-AR, si falta es-MX, es-ES),
titulo_en, anio_tmdb y el puntaje (score, sólo con vote_count >= 20). Con tmdb_id la
tarjeta muestra «Ver en Letterboxd» (letterboxd.com/tmdb/<id>/) y «TMDb»; sin id no hay enlaces.
TMDB_TOKEN; viaja en el header
Authorization: Bearer, nunca en URLs. No se imprime ni se guarda en el HTML, el JSON, la caché ni el log.ATENCION sin_clave=tmdb. Con token inválido (401): ATENCION clave_invalida=tmdb. 429: espera Retry-After, máx. 2 reintentos.data/tmdb-cache.json (se commitea; sin puntajes ni credenciales). Se invalida si cambian el director o el año
del cine. Para corregir un match equivocado, editar la entrada a mano: poner el tmdb_id correcto y "verif": "manual";
la corrida la respeta siempre.tmdb=<con puntaje> tmdb_id=<n>/<total> verificadas=<n> cache=<hits> sin_score_votos=<n> pedidos_tmdb=<n>
y la lista sin_tmdb_id=... para revisar a mano.export TMDB_TOKEN='...' y scripts/probar_tmdb.sh (o sin exportar: lo pide sin mostrarlo).
Corre run.py, informa el porcentaje con id, las que quedaron sin match y 5 enlaces de Letterboxd para abrir, y hace el
grep anti-fuga del token en el HTML, el JSON, la caché y el log. Nunca pegar el token en el chat.TMDB_TOKEN va como variable del entorno remoto. El prompt debe prohibir env, printenv, set -x
y cualquier echo de variables TMDB_*.*.cinemark.com.ar
*.atlascines.com
*.multiplex.com.ar
*.todoshowcase.com
*.unica-cartelera.com.ar <- con www; el dominio pelado devuelve 403
*.themoviedb.org <- hoy alcanza con api.themoviedb.org (themoviedb.org web da 403)
api.themoviedb.org
*.rottentomatoes.com
*.frame.claudeusercontent.com <- para releer el artifact antes de republicarlo
IMDb y Letterboxd no se pueden usar aunque el dominio esté permitido. No es
un problema de lista blanca sino de los sitios: imdb.com responde 202 con un
cuerpo de ~2 KB (desafío de bots) y letterboxd.com responde 403. Habría que
usar una API con clave, y hoy el proyecto no usa ninguna. Las películas
argentinas del Gaumont además casi no figuran en Rotten Tomatoes, así que para
ésas TMDb era la única fuente.
Desde la corrida del 06/10/2026 el scraping de themoviedb.org cayó en la misma bolsa (reemplazado por la API, ver arriba).
themoviedb.org empezó a responder 403 con el interstitial de Cloudflare
("Just a moment..."), tanto en la búsqueda como en la ficha, y no alcanza con
mandar headers completos de navegador como en Rotten Tomatoes: se probó y
sigue dando 403. api.themoviedb.org responde 401 porque pide clave. Mientras
dure, la web sale sólo con los puntajes de Rotten Tomatoes y las películas
argentinas del Gaumont quedan sin ninguno. Se salió con la API oficial.
WebFetch está bloqueado aunque el tráfico directo pase. Por eso todo el
código usa urllib y no WebFetch.
Una película aparece duplicada. Cada cine la nombra distinto y la
normalización no alcanzó. Agregar una entrada a ALIAS en
carteleras/unify.py. Ya están cargados los dos casos conocidos: Harry
Potter 25° Aniversario y La noche del demonio 6.
Una sala aparece en cero. Casi nunca es que no haya funciones: o cambió la
estructura del sitio, o el dominio se cayó de la lista blanca. run.py lo
avisa por stderr.
Un proveedor de puntajes queda en cero. Mismo síntoma y misma causa: el
sitio cambió o empezó a servir un desafío de bots. run.py avisa con
ATENCION sin_puntajes=<proveedor>. Conviene verificarlo a mano antes de tocar
los parsers: si urllib ya recibe un 403 o un cuerpo de "Just a moment...",
el problema no está en las expresiones regulares.
Los horarios del Gaumont o Cosmos salen mal. Es la fuente más frágil porque viene en
prosa. Los tests de tests/test_parsers.py cubren los tres casos que ya
fallaron una vez; agregar el nuevo caso ahí antes de tocar el parser.
Otras rarezas conocidas, ya contempladas:
startDate con zona horaria malformada (...Z-03:00). La Z
es un bug del sitio: la hora de pared ya es local de Buenos Aires.un librosobre); Atlas se come el
espacio tras las comas. Se prefiere el texto de Atlas y se corrige sólo lo
que se puede corregir sin adivinar.Actualizar la cartelera semanal de cuatro cines de Buenos Aires.
1. Ejecutar en el repo clonado:
python3 run.py
Usa urllib, NO WebFetch (WebFetch está bloqueado en este entorno).
Leer el resumen que imprime al final.
2. Si el resumen trae "ATENCION sin_datos=<sala>", NO abortar: publicar
igual con las salas que sí se relevaron y decir cuáles faltaron y por qué.
Nunca inventar horarios ni reutilizar los de la semana pasada.
3. Publicar salida/cartelera.html en el artifact YA EXISTENTE, sin crear
uno nuevo:
- primero leerlo con action "read" y esta url:
https://claude.ai/code/artifact/48264826-0395-45e1-a12b-3c4d86dd2d8d
- después republicar sobre esa MISMA url pasándola como `url`.
4. Avisar con PushNotification dentro de <routine_summary>. Primera oración:
cuántas películas hay y si hubo estrenos. Después: el link a la página,
los títulos mejor puntuados y cualquier sala que haya quedado sin datos.
El paso 3 no es opcional: si se publica sin pasar url, se crea una página
nueva con otra dirección y el link anclado queda congelado en la versión vieja.
«Conectar Letterboxd» lee en el navegador el .zip del export (solo watchlist.csv, por partes con Blob.slice; nunca profile.csv) o el CSV suelto,
y marca las películas en cartel cuyo tmdb_id coincide por título + año TMDb (±1). Sin red, sin logs; «Recordar» guarda solo tmdb_id en
cartelera-caba-watchlist-v1. Lógica pura en el bloque WL de templates/app.js; tests en tests/js/watchlist.test.js con zips/CSV sintéticos.
data/tmdb-cache.json| Puntajes | rottentomatoes.com | Tomatómetro y público; requiere headers de navegador completos |