Nivel: Iniciación | 15 minutos | Domina la recopilación de inteligencia multiplataforma y duplica tu eficiencia de investigación
TIP
last30days-Skill es actualmente el Skill de investigación con IA más completo en ClawHub. Admite la búsqueda paralela en más de 10 fuentes de señales, eliminación automática de duplicados, puntuación y generación de informes fácticos con citas.
GitHub: mvanhorn/last30days-skill
Perfil del lector objetivo
- Desarrolladores con 1 a 5 años de experiencia.
- Personas que necesitan realizar selección de herramientas de IA, investigación de competencia y seguimiento de tendencias tecnológicas a diario.
- Usuarios con conocimientos básicos de línea de comandos, familiarizados con Claude Code o Codex CLI.
- Quienes deseen abandonar el proceso fragmentado de "revisar Reddit/HN para encontrar información".
Dependencias principales y entorno
| Dependencia | Descripción | Obligatorio |
|---|---|---|
| Node.js 18+ | Entorno de ejecución del Skill | Sí |
| Python 3.10+ | Lenguaje principal del script | Sí |
| ScrapeCreators API Key | Reddit/TikTok/Instagram 3-en-1 | Sí |
| Claude Code o Codex CLI | Soporte de ejecución del Skill | Sí |
| X AUTH_TOKEN / CT0 | Autenticación de búsqueda en X (opcional) | No |
| Bluesky App Password | Búsqueda en Bluesky (opcional) | No |
| Polymarket Gamma API | Datos del mercado de predicción (gratis) | No |
Árbol de estructura completa del proyecto
last30days-skill/
├── SKILL.md # Archivo de definición del Skill (desplegar en ~/.claude/skills/)
├── SPEC.md # Documentación completa de especificaciones técnicas
├── CLAUDE.md # Guía de desarrollo para Claude Code
├── scripts/
│ ├── last30days.py # Entrada principal en Python (motor de investigación)
│ ├── sync.sh # Script de sincronización de despliegue
│ └── lib/
│ ├── __init__.py # Entrada del paquete (evita importaciones ansiosas)
│ ├── env.py # Carga de variables de entorno
│ ├── dates.py # Rango de fechas y cálculo de confianza
│ ├── cache.py # Caché con TTL de 24h
│ ├── http.py # Cliente HTTP de biblioteca estándar
│ ├── models.py # Selección automática de modelos OpenAI/xAI
│ ├── openai_reddit.py # Búsqueda en Reddit (OpenAI Responses API)
│ ├── xai_x.py # Búsqueda en X (xAI Responses API)
│ ├── reddit_enrich.py # Extracción de métricas profundas de hilos de Reddit
│ ├── hackernews.py # Hacker News (API gratuita de Algolia)
│ ├── polymarket.py # Mercados de predicción de Polymarket (Gamma API)
│ ├── bluesky.py # Búsqueda en Bluesky/AT Protocol
│ ├── truthsocial.py # Búsqueda en Truth Social
│ ├── normalize.py # Respuesta cruda → Esquema normalizado
│ ├── score.py # Modelo de puntuación multiseñal
│ ├── dedupe.py # Detección de duplicados aproximados
│ ├── render.py # Renderizado de informes en Markdown / JSON
│ └── schema.py # Definición y validación de tipos
├── skills/last30days/
│ └── last30days.sh # Envoltura Shell (Entrada del Skill para Claude Code)
└── fixtures/ # Datos de prueba (fixtures)
Paso 1: Instalación y configuración de autenticación
1.1 Instalación mediante plugin de Claude Code (Recomendado)
Si ya usas Claude Code, instálalo directamente con los comandos de plugin:
/plugin marketplace add mvanhorn/last30days-skill
/plugin install last30days@last30days-skill
O usa la herramienta oficial ClawHub:
clawhub install last30days-official
WARNING
El método de instalación por plugin requiere que tu versión de Claude Code admita el comando /plugin. Verifica primero que claude --version >= 1.0.
1.2 Instalación manual mediante Git Clone
¿No quieres usar plugins? Clónalo directamente de forma local:
# Clonar en el directorio de skills de Claude Code
git clone https://github.com/mvanhorn/last30days-skill.git \
~/.claude/skills/last30days
# Entrar al directorio y ver los archivos
cd ~/.claude/skills/last30days
ls -la scripts/
1.3 Configuración de ScrapeCreators API Key (Obligatorio)
Este es el punto de entrada unificado para Reddit, TikTok e Instagram. Una sola clave lo maneja todo:
- Visita scrapecreators.com, regístrate y obtén tu API Key.
- Crea el archivo de configuración:
mkdir -p ~/.config/last30days
cat > ~/.config/last30days/.env << 'EOF'
# Obligatorio: Clave 3-en-1 para Reddit + TikTok + Instagram
SCRAPECREATORS_API_KEY=sc_xxxxxxxxxxxxxxxxxxxx
# Opcional: OpenAI API (puede omitirse si ya iniciaste sesión en Codex)
OPENAI_API_KEY=sk-xxxxxxxxxxxxxxxxxxxx
EOF
chmod 600 ~/.config/last30days/.env # Protege archivos sensibles
1.4 Configuración opcional para X / Bluesky
Búsqueda en X (Método recomendado):
# 1. Inicia sesión en x.com, abre DevTools del navegador (F12)
# 2. Application → Cookies → Copia los valores de auth_token y ct0
# 3. Escríbelos en el .env
cat >> ~/.config/last30days/.env << 'EOF'
# Autenticación de búsqueda en X (vía cookies)
AUTH_TOKEN=xxxxxxxxxxxxxxxxxxxx
CT0=xxxxxxxxxxxxxxxxxxxx
# Alternativa para X: xAI API (no requiere cookies)
XAI_API_KEY=xai-xxxxxxxxxxxxxxxxxxxx
EOF
Búsqueda en Bluesky:
# 1. Ve a bsky.app/settings/app-passwords y crea una contraseña de aplicación
# 2. Escríbela en el .env
cat >> ~/.config/last30days/.env << 'EOF'
# Bluesky/AT Protocol
BSKY_HANDLE=tuusuario.bsky.social
BSKY_APP_PASSWORD=xxxx-xxxx-xxxx-xxxx
EOF
TIP
Las cookies de X y la contraseña de Bluesky son opcionales. Si no quieres complicarte, usar las opciones gratuitas de Polymarket, Hacker News y Reddit es suficiente para cubrir la mayoría de los escenarios.
1.5 Verificar que la instalación fue exitosa
# Ejecuta una prueba simple (--mock usa datos locales, no consume cuota de API)
python3 ~/.claude/skills/last30days/scripts/last30days.py "Claude Code tips" --mock --emit=compact
Si ves una salida similar, todo funciona correctamente:
=== last30days Report: Claude Code tips ===
Sources: reddit, hackernews | Time: 2026-03-25 | Mode: mock
[results...]
Paso 2: Uso básico
2.1 Línea de comandos /last30days
En Claude Code, escribe directamente el comando:
/last30days best Claude Code prompts
Mediante Codex CLI:
python3 ~/.claude/skills/last30days/scripts/last30days.py "best Claude Code prompts" --emit=compact
TIP
Por defecto, busca contenido popular de los últimos 30 días, cubriendo más de 10 fuentes como Reddit, X, YouTube, TikTok, Instagram, Hacker News, Polymarket, Bluesky, etc. Una búsqueda suele tardar de 2 a 8 minutos; los temas de nicho pueden tardar más.
2.2 Interpretación de la estructura del informe
Tras la ejecución, recibirás un informe estructurado con este aspecto:
# last30days Report: best Claude Code prompts
## Sources Searched (6 active)
reddit | x | hackernews | polymarket | youtube | reddit_threads
## Top Findings
...
## Best Practices (Métodos validados por la comunidad)
...
## Prompt Pack (Listo para copiar)
...
## Recent Developments
...
## References (Con enlaces a las fuentes)
...
El informe realizará automáticamente:
- Detección de convergencia: El contenido mencionado en múltiples plataformas recibe más peso.
- Eliminación de duplicados: Solo se conserva el mejor post entre publicaciones semánticamente similares.
- Decaimiento por tiempo: El contenido más reciente aparece primero.
- Citación: Cada conclusión incluye un enlace original.
2.3 Modo rápido --quick
¿Tienes prisa? Añade --quick para saltar algunas búsquedas profundas:
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"Cursor AI vs Windsurf" \
--quick \
--emit=compact
2.4 Ventana de tiempo personalizada --days=N
No tiene por qué ser 30 días, puedes personalizarlo:
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"OpenClaw latest news" \
--days=7 \
--emit=compact
2.5 Forzar actualización de caché --refresh
Los resultados se guardan en caché por 24 horas. Para buscar de nuevo:
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"AI code editors comparison" \
--refresh \
--emit=compact
Paso 3: Mecanismo de búsqueda paralela multifuente
3.1 Principios de búsqueda en Reddit
Reddit es la fuente de señales más importante. El Skill sigue dos pasos:
# scripts/lib/openai_reddit.py (versión simplificada)
def search_reddit(query: str, days: int = 30) -> list[dict]:
# Paso 1: Usar OpenAI Responses API + web_search para descubrimiento inicial
response = openai.responses.create(
model="gpt-4o",
input=f"Find active Reddit discussions about: {query}",
tools=[{"type": "web_search"}],
max_tokens=2000
)
# Paso 2: Extraer el JSON original del hilo para obtener votos y comentarios reales
enriched = reddit_enrich.fetch_threads(response.urls, days)
return enriched
TIP
A partir de la v2.9, Reddit utiliza ScrapeCreators por defecto. Una sola clave cubre Reddit, TikTok e Instagram, siendo más estable que las soluciones independientes anteriores.
3.2 Integración con Hacker News
Acceso gratuito, no requiere ninguna API Key:
# scripts/lib/hackernews.py
def search_hackernews(query: str, days: int = 30) -> list[dict]:
# La API de Algolia para HN es abierta y gratuita
url = "https://hn.algolia.com/api/v1/search"
params = {
"query": query,
"tags": "story",
"numericFilters": f"created_at_i>{cutoff_timestamp(days)}"
}
resp = requests.get(url, params=params)
items = resp.json()["hits"]
# Ordenar por combinación de puntos + número de comentarios
return sorted(items, key=lambda x: x["points"] + x["num_comments"] * 2, reverse=True)
3.3 Datos de mercados de predicción de Polymarket
Este es el punto diferenciador de last30days frente a otras herramientas: no solo mira "lo que dice la gente", sino también "cuánto dinero está apostando la gente":
# scripts/lib/polymarket.py
def search_polymarket(query: str) -> list[dict]:
# Acceso gratuito a Gamma API
url = "https://gamma-api.polymarket.com/markets"
resp = requests.get(url, params={"topic": query, "limit": 20})
markets = resp.json()
# Modelo de puntuación de cinco factores
for m in markets:
m["composite_score"] = (
m["text_relevance"] * 0.30 +
m["volume_24h"] * 0.30 +
m["liquidity"] * 0.15 +
m["price_velocity"] * 0.15 +
m["outcome_competitiveness"] * 0.10
)
return sorted(markets, key=lambda x: x["composite_score"], reverse=True)
Efecto real: Al buscar "OpenClaw", no solo verás posts de Reddit, sino también datos de Polymarket sobre el "número de usuarios activos mensuales de OpenClaw". Esas cuotas apostadas con dinero real suelen ser más convincentes que cualquier post.
3.4 Análisis del modelo de puntuación multiseñal
Los resultados de todas las fuentes fluyen hacia un canal de puntuación unificado:
# scripts/lib/score.py
def compute_composite_score(item: dict, query: str, days: int) -> float:
# 1. Relevancia de texto (similitud bidireccional + expansión de sinónimos)
text_score = bidirectional_similarity(item["text"], query)
# 2. Normalización de la velocidad de interacción
engagement_score = normalize_velocity(item["engagement"])
# 3. Ponderación por autoridad de la fuente (HN > Reddit > X > TikTok)
authority_score = SOURCE_WEIGHTS[item["source"]]
# 4. Bonus por convergencia multiplataforma (mencionado en varios sitios)
convergence_score = detect_convergence(item, all_results)
# 5. Decaimiento temporal (exponencial de 0.98 por día)
recency_score = 0.98 ** days_since_post(item["timestamp"])
return (
text_score * 0.35 +
engagement_score * 0.25 +
authority_score * 0.20 +
convergence_score * 0.10 +
recency_score * 0.10
)
La puntuación en pruebas ciegas de la v2.5 subió de 3.73/5.0 (v1) a 4.38/5.0, una mejora de aproximadamente el 17%.
Paso 4: Modo Comparativo (X vs Y)
4.1 Caso de estudio "Cursor vs Windsurf"
Una de las funciones más potentes de last30days: comparar dos herramientas directamente:
/last30days cursor vs windsurf
O vía línea de comandos:
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"cursor vs windsurf" \
--emit=compact
4.2 Mecanismo de investigación paralela de tres vías
El modo comparativo activa tres investigaciones independientes:
# scripts/lib/score.py (rama de modo comparativo)
def run_comparative_mode(query_a: str, query_b: str, base_query: str):
# Búsqueda paralela en tres vías
results_a = run_research(query_a) # Vía 1: Solo busca Cursor
results_b = run_research(query_b) # Vía 2: Solo busca Windsurf
results_base = run_research(base_query) # Vía 3: Busca discusiones comparativas entre ambos
# Generar informe de comparación lateral
return render_comparison(results_a, results_b, results_base)
4.3 Interpretación del informe comparativo
El formato del informe de salida es similar a este:
## Comparative Analysis: Cursor vs Windsurf
### Strengths
| Dimension | Cursor | Windsurf |
|---|---|---|
| Velocidad de autocompletado | ⭐⭐⭐⭐⭐ | ⭐⭐⭐ |
| Comprensión de contexto | ⭐⭐⭐⭐ | ⭐⭐⭐⭐⭐ |
| Edición multiactiva | ⭐⭐⭐⭐ | ⭐⭐⭐ |
| Ecosistema de comunidad | ⭐⭐⭐⭐⭐ | ⭐⭐⭐ |
### Weaknesses
| Dimension | Cursor | Windsurf |
|---|---|---|
| Uso de memoria | Alto | Medio |
| Soporte offline | Pobre | Bueno |
### Community Sentiment (30-day)
- Cursor: 78% positivo (1,240 discusiones)
- Windsurf: 65% positivo (890 discusiones)
### Data-Driven Verdict
Cursor lidera en compromiso comunitario y calidad de completado.
Windsurf destaca en comprensión contextual para refactorizaciones complejas.
**Recomendación**: Usa Cursor para codificación diaria; Windsurf para planificación de arquitectura.
Paso 5: Integración con otros Skills / Pipelines de CI
5.1 Inyección como contexto
Otros Skills pueden referenciar directamente los resultados de investigación de last30days:
## Recent Research Context
!python3 ~/.claude/skills/last30days/scripts/last30days.py \
"tu tema de investigación" \
--emit=context
5.2 Leer contexto desde archivo
## Research Context
!cat ~/.local/share/last30days/out/last30days.context.md
5.3 Integración de salida JSON en CI/CD
Inyecta resultados en flujos de automatización:
# Salida en formato JSON para uso programático
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"best LLM for code review 2026" \
--emit=json > research.json
# Verificar los 3 mejores modelos recomendados
python3 -c "
import json
data = json.load(open('research.json'))
for r in data['top_results'][:3]:
print(f\"- {r['title']} (score: {r['score']:.2f})\")
"
5.4 Sobrescritura de .env a nivel de proyecto
¿No quieres una configuración global? Coloca un archivo .claude/last30days.env en la raíz de tu proyecto para sobrescribir la configuración global:
mkdir -p .claude
cat > .claude/last30days.env << 'EOF'
# API Key específica para este proyecto
SCRAPECREATORS_API_KEY=sc_project_specific_key
OPENAI_API_KEY=sk-project-specific-key
EOF
TIP
Esto es extremadamente útil para el trabajo en equipo: cada persona usa su propia clave, pero el comportamiento del Skill se mantiene consistente.
5.5 Validación automática al iniciar sesión
La v2.9.5 añade una comprobación de configuración al iniciar la sesión. Claude Code verificará automáticamente si tu .env está completo al arrancar:
# Activar validación manualmente
python3 ~/.claude/skills/last30days/scripts/last30days.py \
--validate-config
Si faltan claves necesarias, verás advertencias claras:
❌ SCRAPECREATORS_API_KEY is missing (required)
✅ OPENAI_API_KEY found
⚠️ BSKY_HANDLE is missing (optional)
Solución de problemas comunes
Q1: Error SCRAPECREATORS_API_KEY is missing al ejecutar
Causa: Las variables de entorno no se cargaron correctamente.
Solución:
# Confirmar que la clave existe
cat ~/.config/last30days/.env | grep SCRAPECREATORS_API_KEY
# Si instalaste vía plugin, intenta sincronizar manualmente
bash ~/.claude/skills/last30days/scripts/sync.sh
Q2: La búsqueda en X siempre devuelve resultados vacíos
Causa: Las cookies AUTH_TOKEN / CT0 han expirado o son inválidas.
Solución:
# 1. Inicia sesión de nuevo en x.com
# 2. Copia los tokens actualizados
# 3. Actualiza el .env
# O usa la alternativa de xAI API (no requiere cookies)
echo "XAI_API_KEY=xai-tullave" >> ~/.config/last30days/.env
Q3: La búsqueda es muy lenta (más de 10 minutos)
Causa: Se buscan hasta 10 fuentes en paralelo por defecto; temas muy específicos requieren más reintentos de API.
Solución:
# 1. Usa --quick para saltar búsquedas profundas
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"niche topic" \
--quick
# 2. Verifica si alguna fuente da timeout constantemente
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"topic" \
--sources=reddit # Busca solo en Reddit para depuración rápida
Q4: Polymarket devuelve mercados irrelevantes
Causa: La coincidencia en Polymarket se basa en palabras clave y algunos temas no tienen mercados activos.
Solución:
# Especificar manualmente etiquetas de expansión
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"AI coding assistant" \
--polymarket-tags="artificial intelligence,llm,gpt" \
--emit=compact
Q5: Claude Code muestra Permission denied en los scripts
Causa: Los scripts shell no tienen permisos de ejecución.
Solución:
chmod +x ~/.claude/skills/last30days/skills/last30days.sh
chmod +x ~/.claude/skills/last30days/scripts/last30days.py
Q6: Hay pocos posts de Reddit en el informe, pero hay mucha discusión en la web
Causa: A partir de la v2.9 se usa ScrapeCreators por defecto. La clave está configurada pero el formato podría ser incorrecto.
Solución:
# Validar si la clave de ScrapeCreators es funcional
curl -H "x-api-key: sc_tullave" \
https://api.scrapecreators.com/v1/reddit/search?q=test
# Si la clave funciona pero sigues sin datos, intenta forzar ScrapeCreators en el .env
echo "FORCE_SCRAPECREATORS=1" >> ~/.config/last30days/.env
Lectura adicional / Direcciones avanzadas
1. Ajuste del modelo de puntuación
Los pesos en scripts/lib/score.py están predefinidos. Si prefieres una fuente específica, puedes hacer un fork y modificarlos:
# Subir el peso de autoridad de Hacker News de 0.20 a 0.35
SOURCE_WEIGHTS = {
"hackernews": 0.35, # ↑ Cambiado desde 0.20
"reddit": 0.25,
"x": 0.15,
"polymarket": 0.15,
"youtube": 0.10,
}
2. Acceso a fuentes personalizadas
¿Quieres añadir GitHub Issues o LinkedIn? Consulta la especificación de interfaz en hackernews.py, crea un nuevo módulo en scripts/lib/ y regístralo en last30days.py. SPEC.md contiene la definición completa de la interfaz.
3. Automatización de investigaciones periódicas
Usa cron para ejecutar investigaciones regulares y actualizar tu base de conocimientos:
# Ejecutar investigación semanal de herramientas de IA cada mañana a las 8:00
0 8 * * * python3 ~/.claude/skills/last30days/scripts/last30days.py \
"AI developer tools weekly" \
--days=7 \
--emit=md \
--output ~/Documents/Last30Days/ai-tools-weekly-$(date +\%Y-\%m-\%d).md
4. Vinculación con bases de conocimiento
Inyecta resultados directamente en tu base de conocimientos personal (pipeline RAG):
# Generar contexto con citas y enviarlo a otro Skill
python3 ~/.claude/skills/last30days/scripts/last30days.py \
"Claude Code advanced techniques" \
--emit=context > ~/.knowledge/last30_context.md
Recursos relacionados
- GitHub: mvanhorn/last30days-skill
- ClawHub: last30days-official
- ScrapeCreators API: scrapecreators.com
- Sitio oficial de OpenClaw: openclaw.ai
- Hacker News Algolia API: hn.algolia.com/api
- Polymarket Gamma API: gamma-api.polymarket.com