Skip to content

Italian #11

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 13 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions EseguiScript.bat
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
@echo off
streamlit run ddqbscript\main.py
pause
108 changes: 97 additions & 11 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,16 +1,102 @@
# AI-Web-Scraper
An AI web scraper using ollama, brightdata, selenium and other libraries.
# AI Web Scraper con Ollama

Questo progetto ti permette di fare il scraping dei siti web e analizzare il loro contenuto utilizzando il modello Llama3 di Ollama. Il programma estrae e processa i dati dai siti web, permettendoti di fare domande sul contenuto DOM estratto e di scaricare i risultati.

# 💻 Launch Your Software Development Career Today!
Se preferisci la versione in inglese di questo progetto, puoi trovarla [qui](https://github.com/dddevid/AI-Web-Scraper-Ollama).

🎓 **No degree? No problem!** My program equips you with everything you need to break into tech and land an entry-level software development role.
## Requisiti

🚀 **Why Join?**
- 💼 **$70k+ starting salary potential**
- 🕐 **Self-paced:** Complete on your own time
- 🤑 **Affordable:** Low risk compared to expensive bootcamps or degrees
- 🎯 **45,000+ job openings** in the market
Prima di cominciare, assicurati di avere installato:

👉 **[Start your journey today!](https://techwithtim.net/dev)**
No experience needed—just your determination. Future-proof your career and unlock six-figure potential like many of our students have!
- Python 3.8 o superiore
- `pip` (gestore di pacchetti Python)

### Passaggio 1: Installa Ollama e Llama3

1. **Scarica Ollama**:
- Ollama è una piattaforma che esegue modelli di intelligenza artificiale come Llama3. Puoi scaricare Ollama per il tuo sistema dal sito ufficiale:
[Download Ollama](https://ollama.com/download)

2. **Installa il modello Llama3**:
- Dopo aver scaricato Ollama, devi installare il modello Llama3. Apri un terminale o prompt dei comandi e esegui il seguente comando per installare il modello Llama3:
```
ollama install llama3
```

### Passaggio 2: Clona il Repository

1. **Clona il repository**:
- Per prima cosa, clona il repository GitHub sulla tua macchina locale eseguendo il seguente comando, specificando il branch italiano:
```
git clone --branch Italian https://github.com/dddevid/AI-Web-Scraper-Ollama.git
```

2. **Naviga nella cartella del progetto**:
- Cambia nella cartella del progetto eseguendo:
```
cd AI-Web-Scraper-Ollama
```

### Passaggio 3: Configura l'Ambiente Python

1. **Crea un ambiente virtuale (opzionale ma consigliato)**:
- Crea un ambiente virtuale per gestire le dipendenze del progetto:
```
python -m venv venv
```

2. **Attiva l'ambiente virtuale**:
- Su Windows:
```
venv\Scripts\activate
```
- Su macOS/Linux:
```
source venv/bin/activate
```

3. **Installa le dipendenze richieste**:
- Il file `requirements.txt` si trova nella cartella `ddbqscript`. Installa le librerie Python necessarie eseguendo:
```
pip install -r ddbqscript/requirements.txt
```

### Passaggio 4: Esegui l'Applicazione

#### Su Windows:

- **Esegui lo script utilizzando il file batch**:
- Usa il file `Executethescript.bat` per avviare l'applicazione:
```
Executethescript.bat
```

#### Su macOS/Linux:

- **Esegui lo script utilizzando Streamlit**:
- Avvia l'app Streamlit eseguendo il seguente comando:
```
streamlit run ddbqscript/main.py
```

2. **Accedi all'app**:
- L'interfaccia Streamlit si aprirà nel tuo browser. Ora puoi inserire un URL di un sito web, fare scraping del suo contenuto e analizzarlo usando Llama3.

### Passaggio 5: Utilizzo

- **Fare scraping di un sito web**: Inserisci un URL e clicca su "Scrape the website" per fare scraping del contenuto del sito.
- **Analizzare il contenuto**: Dopo aver fatto lo scraping, puoi inserire una descrizione di cosa vuoi analizzare, e l'IA processerà il contenuto.
- **Scaricare i risultati**: Una volta completata l'analisi, puoi scaricare i risultati nei formati JSON e TXT.

### Risoluzione dei Problemi

- **Ollama non trovato**: Se ricevi un errore relativo a Ollama, assicurati che sia correttamente installato e che sia aggiunto al PATH del sistema.
- **Dipendenze mancanti**: Assicurati di aver installato tutte le librerie Python necessarie eseguendo `pip install -r ddbqscript/requirements.txt`.

---

### Se ti è piaciuto questo progetto, puoi offirmi un caffè! ☕

[![Buy me a coffee](https://cdn.buymeacoffee.com/buttons/v2/default-yellow.png)](https://buymeacoffee.com/devidd)

Cliccando sul link, puoi scegliere di donarmi quanto vuoi o iscriverti per 30€ al mese per supportare lo sviluppo continuo di questo progetto.
Binary file removed chromedriver
Binary file not shown.
76 changes: 76 additions & 0 deletions ddqbscript/main.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
import streamlit as st
import json
import os
import zipfile
import io

from scrape import (
scrape_website,
extract_body_content,
clean_body_content,
split_dom_content,
)
from parse import parse_with_ollama

# Interfaccia utente Streamlit
st.title("Scraper Web con IA")
url = st.text_input("Inserisci URL del sito web")

# Passaggio 1: Scraping del sito web
if st.button("Scrapa sito web"):
if url:
st.write("Scraping del sito web in corso...")

# Scraping del sito web
dom_content = scrape_website(url)
body_content = extract_body_content(dom_content)
cleaned_content = clean_body_content(body_content)

# Salvataggio del contenuto DOM nello stato della sessione di Streamlit
st.session_state.dom_content = cleaned_content

# Visualizzazione del contenuto DOM in una casella espandibile
with st.expander("Visualizza contenuto DOM"):
st.text_area("Contenuto DOM", cleaned_content, height=300)

# Passaggio 2: Fare domande sul contenuto DOM
if "dom_content" in st.session_state:
parse_description = st.text_area("Descrivi cosa vuoi analizzare")

if st.button("Analizza contenuto"):
if parse_description:
st.write("Analisi del contenuto in corso...")

# Analisi del contenuto con Ollama
dom_chunks = split_dom_content(st.session_state.dom_content)
parsed_result = parse_with_ollama(dom_chunks, parse_description)
st.session_state.parsed_result = parsed_result
st.write(parsed_result)

# Tasto per scaricare i risultati
if "parsed_result" in st.session_state:
if st.button("Scarica risultati"):
# Crea un file JSON
json_data = {
"url": url,
"parse_description": parse_description,
"parsed_result": st.session_state.parsed_result
}

# Crea un file ZIP in memoria
zip_buffer = io.BytesIO()
with zipfile.ZipFile(zip_buffer, 'w', zipfile.ZIP_DEFLATED) as zip_file:
# Aggiunge risultato.json
zip_file.writestr('risultato.json', json.dumps(json_data, indent=2, ensure_ascii=False))

# Aggiunge risultato.txt
zip_file.writestr('risultato.txt', st.session_state.parsed_result)

# Prepara il download
zip_buffer.seek(0)
st.download_button(
label="Scarica risultati (JSON + TXT)",
data=zip_buffer,
file_name="risultati_scraping.zip",
mime="application/zip"
)
31 changes: 31 additions & 0 deletions ddqbscript/parse.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
#parse.py

from langchain_ollama import OllamaLLM
from langchain_core.prompts import ChatPromptTemplate

template = (
"Sei incaricato di estrarre informazioni specifiche dal seguente contenuto testuale: {dom_content}. "
"Segui attentamente queste istruzioni: \n\n"
"1. **Estrazione Informazioni:** Estrai solo le informazioni che corrispondono direttamente alla descrizione fornita: {parse_description}. "
"2. **Nessun Contenuto Aggiuntivo:** Non includere testo, commenti o spiegazioni aggiuntive nella tua risposta. "
"3. **Risposta Vuota:** Se nessuna informazione corrisponde alla descrizione, restituisci una stringa vuota ('')."
"4. **Solo Dati Diretti:** L'output deve contenere solo i dati esplicitamente richiesti, senza altro testo."
)

model = OllamaLLM(model="llama3")


def parse_with_ollama(dom_chunks, parse_description):
prompt = ChatPromptTemplate.from_template(template)
chain = prompt | model

parsed_results = []

for i, chunk in enumerate(dom_chunks, start=1):
response = chain.invoke(
{"dom_content": chunk, "parse_description": parse_description}
)
print(f"Batch analizzato: {i} di {len(dom_chunks)}")
parsed_results.append(response)

return "\n".join(parsed_results)
17 changes: 9 additions & 8 deletions requirements.txt → ddqbscript/requirements.txt
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
streamlit
langchain
langchain_ollama
selenium
beautifulsoup4
lxml
html5lib
python-dotenv
streamlit
langchain
langchain_ollama
selenium
beautifulsoup4
lxml
html5lib
python-dotenv
webdriver-manager
103 changes: 46 additions & 57 deletions scrape.py → ddqbscript/scrape.py
Original file line number Diff line number Diff line change
@@ -1,57 +1,46 @@
from selenium.webdriver import Remote, ChromeOptions
from selenium.webdriver.chromium.remote_connection import ChromiumRemoteConnection
from bs4 import BeautifulSoup
from dotenv import load_dotenv
import os

load_dotenv()

SBR_WEBDRIVER = os.getenv("SBR_WEBDRIVER")


def scrape_website(website):
print("Connecting to Scraping Browser...")
sbr_connection = ChromiumRemoteConnection(SBR_WEBDRIVER, "goog", "chrome")
with Remote(sbr_connection, options=ChromeOptions()) as driver:
driver.get(website)
print("Waiting captcha to solve...")
solve_res = driver.execute(
"executeCdpCommand",
{
"cmd": "Captcha.waitForSolve",
"params": {"detectTimeout": 10000},
},
)
print("Captcha solve status:", solve_res["value"]["status"])
print("Navigated! Scraping page content...")
html = driver.page_source
return html


def extract_body_content(html_content):
soup = BeautifulSoup(html_content, "html.parser")
body_content = soup.body
if body_content:
return str(body_content)
return ""


def clean_body_content(body_content):
soup = BeautifulSoup(body_content, "html.parser")

for script_or_style in soup(["script", "style"]):
script_or_style.extract()

# Get text or further process the content
cleaned_content = soup.get_text(separator="\n")
cleaned_content = "\n".join(
line.strip() for line in cleaned_content.splitlines() if line.strip()
)

return cleaned_content


def split_dom_content(dom_content, max_length=6000):
return [
dom_content[i : i + max_length] for i in range(0, len(dom_content), max_length)
]
from selenium import webdriver
from selenium.webdriver.chrome.service import Service
from webdriver_manager.chrome import ChromeDriverManager
from bs4 import BeautifulSoup

def scrape_website(website):
service = Service(ChromeDriverManager().install())
options = webdriver.ChromeOptions()

options.add_argument("--no-sandbox")
options.add_argument("--disable-dev-shm-usage")

driver = webdriver.Chrome(service=service, options=options)

try:
driver.get(website)
print("Navigazione completata! Scraping del contenuto della pagina...")
html = driver.page_source
return html
finally:
driver.quit()

def extract_body_content(html_content):
soup = BeautifulSoup(html_content, "html.parser")
body_content = soup.body
if body_content:
return str(body_content)
return ""

def clean_body_content(body_content):
soup = BeautifulSoup(body_content, "html.parser")

for script_or_style in soup(["script", "style"]):
script_or_style.extract()

cleaned_content = soup.get_text(separator="\n")
cleaned_content = "\n".join(
line.strip() for line in cleaned_content.splitlines() if line.strip()
)

return cleaned_content

def split_dom_content(dom_content, max_length=6000):
return [
dom_content[i : i + max_length] for i in range(0, len(dom_content), max_length)
]
43 changes: 0 additions & 43 deletions main.py

This file was deleted.

Loading