Dans cet article, je vais vous guider à travers la configuration et l’utilisation du modèle de transcription Whisper d’OpenAI sur un système Windows 11. Vous découvrirez comment j’ai automatisé la transcription de fichiers audio et de vidéos YouTube via un serveur domestique Nextcloud, avec une gestion simple et fluide des fichiers à partir d’un smartphone. Ce guide couvre toutes les étapes, de l’installation des dépendances à l’automatisation complète de la transcription, en incluant une solution pour contourner les restrictions YouTube.
Exemple d’utilisation
J’enregistre les parties importantes des cours de fac et prends des notes écrites pour le reste. Sur le trajet, je relis mes notes et en fais un fichier audio. Toujours sur mon smartphone, je déplace les fichiers audio dont je veux une retranscription dans un répertoire qui est sur mon cloud privé Nextcloud. Je prends soin de nommer les fichiers explicitement.
Nextcloud, l’application sur mon smartphone, synchronise le dossier et fait une copie des fichiers audio sur mon serveur. Si je veux une retranscription d’un documentaire ou d’une conférence sur YouTube, je copie l’adresse de la vidéo dans un fichier .txt que je déplace dans un autre répertoire de mon cloud prévu uniquement pour ça. Je nomme également bien ces fichiers.
Mon serveur scanne les deux répertoires. Si le script détecte des fichiers, il les transcrit et dépose la transcription sous forme de fichiers .txt et .docx dans un troisième répertoire, également dans le cloud. Je peux ainsi récupérer facilement les textes de retranscription.
Suite à cela je peu retravailler mes cours de façon automatisé avec une autre IA tel que ChatGPT, mais choisissez Français « MISTRAL » c’est bien mieux que le voleur de Bill Gates.
Configuration matérielle utilisée :
- Système d’exploitation : Windows 11
- GPU : Nvidia 4060 Ti 16 Go VRAM
- CPU : AMD Ryzen 7
- RAM : 64 Go DDR4 3600 MHz
- Stockage : SSD NVMe
1. Préparation de l’environnement
1.1. Installation de Python
Si vous ne l’avez pas déjà fait, installez Python sur votre machine. Lors de l’installation, veillez à cocher l’option « Add Python to PATH ».
1.2. Création d’un environnement virtuel
Créez un environnement virtuel Python pour isoler les dépendances de votre projet. Voici la commande pour créer un environnement :
python -m venv whisper_envBashActivez l’environnement virtuel :
whisper_env\Scripts\activateBash1.3. Installation des dépendances
Pour que le script fonctionne, installez les bibliothèques suivantes dans votre environnement virtuel :
- Whisper : Le modèle de transcription d’OpenAI.
pip install git+https://github.com/openai/whisper.gitBash- PyTorch (avec CUDA pour l’accélération GPU)
pip install torch torchvision torchaudio --index-url https://download.pytorch.org/whl/cu118Bash- python-docx : Pour convertir les fichiers
.txten.docx.
pip install python-docxBash- yt-dlp : Pour télécharger des vidéos YouTube et en extraire l’audio.
pip install yt-dlpBash- ffmpeg-python : Une interface Python pour manipuler les fichiers audio et vidéo via FFmpeg.
pip install ffmpeg-pythonBash- pydub : Une bibliothèque pour manipuler des fichiers audio. Ici pour les transcrire en plusieurs parties si la durée est longue afin de ne pas surcharger le processus.
pip install pydubBash1.4. Installation de FFmpeg
FFmpeg est requis pour la manipulation des fichiers audio et vidéo. Il doit être installé en dehors de Python. Voici comment procéder :
- Téléchargez FFmpeg depuis le site officiel.
- Décompressez l’archive.
- Ajoutez FFmpeg au PATH de votre système pour qu’il soit accessible partout.
2. Contourner les restrictions YouTube avec les cookies
Certaines vidéos YouTube nécessitent une authentification ou imposent des restrictions. Pour contourner cela, nous allons utiliser un fichier de cookies. Cette solution à une faiblesse c’est qu’il faut régulièrement rafraichir le fichier en réenregistrant les cookies.
2.1. Exporter les cookies depuis votre navigateur
- Installez une extension comme cookies.txt.
- Connectez vous à votre compte YouTube dans votre navigateur.
- Exportez les cookies et sauvegardez le fichier sous le nom
cookies.txt.
2.2. Où sauvegarder le fichier cookies.txt ?
Placez le fichier cookies.txt :
- Dans le même répertoire que votre script Python.
- Vérifiez que le chemin dans le script correspond bien à l’emplacement du fichier :pythonCopier le code
ydl_opts = {
'cookiefile': 'cookies.txt', # Chemin vers le fichier cookies.txt
}Python3. Démarrage automatique de Whisper au lancement de Windows
Pour rendre le processus encore plus simple et transparent, j’ai configuré le démarrage automatique de Whisper au lancement de mon PC. Cela me permet de lancer Whisper et mon script de transcription sans intervention manuelle dès que mon ordinateur démarre.
3.1. Contenu du fichier .bat
@echo off
timeout /t 30
REM Activer l'environnement virtuel
echo Activating virtual environment >> F:\IA\whisper\start_log.txt
call F:\IA\whisper\venv\Scripts\activate.bat >> F:\IA\whisper\start_log.txt 2>&1
REM Se déplacer dans le répertoire du script
echo Changing directory to F:\IA\whisper >> F:\IA\whisper\start_log.txt
cd /d F:\IA\whisper >> F:\IA\whisper\start_log.txt 2>&1
REM Lancer le script Python
echo Starting transcription script >> F:\IA\whisper\start_log.txt
start /B python transcription_script.py >> F:\IA\whisper\script_log.txt 2>&1
REM Désactiver l'environnement virtuel
echo Deactivating virtual environment >> F:\IA\whisper\start_log.txt
deactivateBash3.2. Ajouter le fichier .bat au démarrage de Windows
- Sauvegardez le fichier sous le nom
start_whisper.bat. - Placez un raccourci vers ce fichier dans le dossier Démarrage de Windows :
- Appuyez sur
Win + R, tapezshell:startup, validez. - Collez un raccourci vers votre fichier
.bat.
- Appuyez sur
4. Automatisation de la transcription avec Nextcloud
4.1. Gestion des fichiers via Nextcloud
J’ai mis en place un serveur Nextcloud à domicile avec un nom de domaine et un reverse proxy. Cette configuration me permet de gérer mes fichiers à distance via l’application Nextcloud sur mon smartphone.
- Pour les fichiers audio :
- J’enregistre des fichiers audio sur mon smartphone et je les copie dans un répertoire Nextcloud dédié à la transcription.
- Une fois le fichier synchronisé avec mon serveur, un script Python effectue la transcription.
- Pour les vidéos YouTube :
- Je crée un fichier texte contenant l’URL de la vidéo que je souhaite transcrire. Ce fichier
.txtest nommé en fonction du contenu de la vidéo. - Une fois ce fichier synchronisé, le script télécharge la vidéo, en extrait l’audio et génère la transcription.
- Je crée un fichier texte contenant l’URL de la vidéo que je souhaite transcrire. Ce fichier
5. script de transcription
Le script de transcription est au cœur de ce processus d’automatisation. Il gère la détection des fichiers audio ou des liens YouTube dans les répertoires surveillés, effectue la transcription via Whisper, et enregistre les résultats.
import os
import time
import whisper
import torch
from docx import Document
import yt_dlp
from datetime import datetime
import threading
from pydub import AudioSegment
# Configuration des chemins et verrou
audio_folder = r"\\OMV\whisper\trans_audio"
text_folder = r"\\OMV\whisper\trans_texte"
video_folder = r"\\OMV\whisper\trans_video"
lock_file = os.path.join(audio_folder, "transcription.lock")
log_file = "F:\\IA\\whisper\\script_log.txt"
# Extensions audio supportées
audio_extensions = [".m4a", ".mp3", ".wav", ".flac"]
# Modèle Whisper
model_name = "large" # Utiliser le modèle le plus précis
device = "cuda" if torch.cuda.is_available() else "cpu"
model = whisper.load_model(model_name, device=device)
# Verrou global pour la gestion des logs
log_lock = threading.Lock()
# Déclaration du fichier de log pour start_log
start_log_file = "F:\\IA\\whisper\\start_log.txt"
def log_with_timestamp(message, log_file):
"""Ajoute un message avec date et heure dans un fichier de log."""
try:
# Vérifie si le message est une chaîne valide
if not isinstance(message, str):
raise ValueError("Le message à journaliser doit être une chaîne de caractères.")
# Vérifie si le dossier contenant le fichier log existe, sinon le crée
log_dir = os.path.dirname(log_file)
if log_dir and not os.path.exists(log_dir):
os.makedirs(log_dir, exist_ok=True) # Création récursive du dossier
# Génère l'horodatage et écrit dans le fichier log
timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
with open(log_file, "a", encoding="utf-8") as f:
f.write(f"[{timestamp}] {message}\n")
except PermissionError:
# Si les permissions posent problème
print(f"Erreur : Impossible d'écrire dans le fichier de log : {log_file}. Vérifiez les permissions.")
except Exception as e:
# Si une autre erreur survient
print(f"Erreur inattendue lors de l'écriture dans le fichier de log : {e}")
# Exemple de fonction principale où vous écrivez dans les deux fichiers de log
if __name__ == "__main__":
# Écrit dans script_log.txt
log_with_timestamp("Ce message va dans script_log.txt", log_file)
# Écrit dans start_log.txt
log_with_timestamp("Ce message va dans start_log.txt", start_log_file)
# Un autre exemple
log_with_timestamp("Démarrage du processus...", start_log_file)
log_with_timestamp("Fin du script.", log_file)
# Fonction pour segmenter l'audio en parties plus courtes
def segment_audio(file_path, segment_length=60000):
audio = AudioSegment.from_file(file_path)
segments = []
start = 0
end = segment_length
while start < len(audio):
segment = audio[start:end]
segments.append(segment)
start = end
end += segment_length
return segments
# Fonction pour transcrire un fichier audio
def transcribe_audio(file_path):
log_with_timestamp(f"Transcribing {file_path}...", log_file)
segments = segment_audio(file_path)
transcription = ""
for i, segment in enumerate(segments):
segment_path = f"{file_path}_segment_{i}.wav"
segment.export(segment_path, format="wav")
result = model.transcribe(segment_path, language='fr', task='transcribe', beam_size=5, best_of=5)
transcription += result["text"] + " "
os.remove(segment_path) # Supprimer le segment temporaire
log_with_timestamp(f"Transcription result: {transcription}", log_file)
return transcription
# Fonction pour convertir un fichier texte en fichier docx
def txt_to_docx(txt_path, docx_path):
log_with_timestamp(f"Converting {txt_path} to {docx_path}...", log_file)
doc = Document()
with open(txt_path, "r", encoding="utf-8") as f:
doc.add_paragraph(f.read())
doc.save(docx_path)
# Fonction pour télécharger une vidéo YouTube
def download_youtube_video(video_url, output_dir, output_file_base):
ydl_opts = {
'format': 'bestaudio/best',
'outtmpl': os.path.join(output_dir, output_file_base + '.webm'),
'postprocessors': [{
'key': 'FFmpegExtractAudio',
'preferredcodec': 'mp3',
'preferredquality': '192',
}],
'cookiefile': 'cookies.txt', # Utilisation des cookies pour éviter les restrictions
'age_restricted': True, # Gérer les vidéos avec restrictions d'âge
'retries': 10, # Nombre de tentatives de téléchargement
'retry_sleep_functions': {
'sleep': lambda x: time.sleep(x),
'sleep_time': 30, # Temps d'attente entre les tentatives
},
# 'proxy': 'http://your_proxy_here:port', # Utilisation d'un proxy (facultatif)
}
try:
with yt_dlp.YoutubeDL(ydl_opts) as ydl:
info_dict = ydl.extract_info(video_url, download=True)
audio_file = os.path.join(output_dir, output_file_base + '.mp3')
video_title = info_dict.get("title", "Untitled")
log_with_timestamp(f"Downloaded and converted: {audio_file}", log_file)
return audio_file, video_title
except Exception as e:
log_with_timestamp(f"Error downloading video {video_url}: {e}", log_file)
return None, None
# Fonction principale pour scanner les dossiers et traiter les fichiers
def scan_and_process():
log_with_timestamp("Starting the process...", log_file)
while True:
# Vérification et création du fichier de verrouillage
if os.path.exists(lock_file):
log_with_timestamp("Transcription en cours. Attente de 5 minutes avant de scanner à nouveau...", log_file)
time.sleep(300)
continue
# Vérifier si un fichier d'arrêt existe
stop_file = os.path.join(audio_folder, "stop.txt")
if os.path.exists(stop_file):
log_with_timestamp("Arrêt détecté. Sortie du script...", log_file)
os.rename(stop_file, os.path.join(audio_folder, "no_stop.txt"))
break
# Création du fichier de verrouillage
try:
with open(lock_file, "w") as lock:
lock.write("locked")
log_with_timestamp("Lock file created. Starting processing.", log_file)
except Exception as e:
log_with_timestamp(f"Erreur : Impossible de créer le fichier de verrouillage. {e}", log_file)
return
try:
# Scanner et traiter les fichiers audio
for file_name in os.listdir(audio_folder):
if any(file_name.endswith(ext) for ext in audio_extensions):
audio_path = os.path.join(audio_folder, file_name)
txt_file_name = os.path.splitext(file_name)[0] + ".txt"
txt_path = os.path.join(text_folder, txt_file_name)
# Vérifier si la transcription existe déjà
if not os.path.exists(txt_path):
text = transcribe_audio(audio_path)
with open(txt_path, "w", encoding="utf-8") as txt_file:
txt_file.write(text)
log_with_timestamp(f"Saved transcription to {txt_path}", log_file)
# Convertir en .docx
docx_file_name = txt_file_name.replace(".txt", ".docx")
docx_path = os.path.join(text_folder, docx_file_name)
txt_to_docx(txt_path, docx_path)
# Scanner et traiter les fichiers texte contenant des liens YouTube
log_with_timestamp(f"Scanning folder: {video_folder}", log_file)
try:
for file_name in os.listdir(video_folder):
log_with_timestamp(f"Found file: {file_name}", log_file)
if file_name.endswith(".txt"):
link_path = os.path.join(video_folder, file_name)
with open(link_path, "r") as link_file:
video_url = link_file.readline().strip()
log_with_timestamp(f"Read video URL: {video_url}", log_file)
base_name = os.path.splitext(file_name)[0]
txt_file_name = base_name + ".txt"
txt_path = os.path.join(text_folder, txt_file_name)
if not os.path.exists(txt_path):
audio_path, video_title = download_youtube_video(video_url, audio_folder, base_name)
if audio_path:
text = transcribe_audio(audio_path)
transcription_with_metadata = f"{video_title}\n{video_url}\n\n{text}"
with open(txt_path, "w", encoding="utf-8") as txt_file:
txt_file.write(transcription_with_metadata)
log_with_timestamp(f"Saved transcription to {txt_path}", log_file)
# Convertir en .docx
docx_file_name = txt_file_name.replace(".txt", ".docx")
docx_path = os.path.join(text_folder, docx_file_name)
txt_to_docx(txt_path, docx_path)
except Exception as e:
log_with_timestamp(f"Erreur : {e}. Nouvelle tentative dans 2 minutes...", log_file)
time.sleep(120)
finally:
if os.path.exists(lock_file):
os.remove(lock_file)
log_with_timestamp("Lock file removed. Waiting for next scan.", log_file)
else:
log_with_timestamp("Lock file does not exist. Waiting for next scan.", log_file)
# Pause avant le prochain scan
log_with_timestamp("Attente de 5 minutes avant le prochain scan...", log_file)
time.sleep(300)
# Point d'entrée du script
if __name__ == "__main__":
scan_and_process()Python5.1. Étapes clés du script :
Le script de transcription est au cœur de ce processus d’automatisation. Voici les étapes clés mises à jour avec la gestion des restrictions YouTube :
- Surveillance des répertoires Nextcloud :
- Le script surveille en continu deux répertoires spécifiques sur votre Nextcloud :
- Un répertoire pour les fichiers audio à transcrire.
- Un répertoire pour les fichiers
.txtcontenant des URL YouTube.
- Le script surveille en continu deux répertoires spécifiques sur votre Nextcloud :
- Téléchargement des vidéos YouTube avec
yt-dlpcorrigé :- Si un fichier
.txtcontenant une URL est détecté, le script :- Télécharge la vidéo via yt-dlp.
- Extrait uniquement l’audio au format
.mp3pour économiser du stockage. - Contourne les restrictions YouTube grâce à l’utilisation d’un fichier de cookies (
cookies.txt).
- Si un fichier
- Transcription automatique des fichiers audio avec Whisper :
- Une fois l’audio récupéré (depuis une vidéo YouTube ou directement depuis un fichier audio), le script :
- Transcrit le contenu en texte brut grâce au modèle Whisper.
- Sauvegarde la transcription au format
.txt.
- Une fois l’audio récupéré (depuis une vidéo YouTube ou directement depuis un fichier audio), le script :
- Conversion du texte en
.docx:- Le script convertit chaque fichier
.txten un fichier Word.docxpour une meilleure lisibilité et compatibilité.
- Le script convertit chaque fichier
- Gestion des logs et des erreurs :
- Chaque étape est consignée dans un fichier de log.
- Les erreurs comme les restrictions YouTube (par exemple : « Sign in to confirm you’re not a bot ») sont gérées de manière robuste pour éviter que le script ne plante.
- Nettoyage des fichiers temporaires :
- Les fichiers audio ou vidéos temporaires (comme les
.webmissus de YouTube) sont supprimés automatiquement après transcription.
- Les fichiers audio ou vidéos temporaires (comme les
- Stockage des résultats :
- Les fichiers
.txtet.docxfinaux sont déplacés dans un troisième répertoire Nextcloud, prêt à être synchronisé sur votre smartphone ou autre appareil.
- Les fichiers

