Scrapping

Description :

Ce script en Python scrape les jeux vidéo depuis le PlayStation Store et met à jour un fichier JSON contenant la liste des jeux. Voici un résumé de son fonctionnement :

1. Initialisation des variables et chargement du fichier JSON

  • MIN_PAGE et MAX_PAGE définissent la plage des pages à scraper (1 à 260).
  • dict_game charge les données existantes du fichier games_list.json.
  • id_exist récupère le dernier identifiant (id) enregistré pour éviter les doublons.
  • ID est défini comme le prochain identifiant disponible.

2. Scraping des pages du PlayStation Store

  • Pour chaque page de MIN_PAGE à MAX_PAGE :
  • Le script récupère le HTML de la page via une requête requests.get(url).
  • Si le code de réponse HTTP est 200 (succès), il analyse le HTML avec BeautifulSoup.
  • Il récupère les blocs contenant les jeux (a class="psw-content-link").

3. Extraction des informations sur les jeux

  • Titre du jeu (name_game).
  • Prix du jeu (price_game), avec vérification des valeurs particulières :
  • “Gratuit” si le prix commence par “g”.
  • “Inclus, PS Extra” si le prix commence par “i”.
  • Image du jeu (img_game), en s’assurant de récupérer la bonne image.
  • Plateforme (platform_game), qui peut être PS4, PS5 ou les deux.
  • Lien vers la page du jeu (url_game).

4. Ajout des jeux à la liste JSON

  • Vérification si le jeu est déjà présent en comparant les noms avec any().
  • Si le jeu est nouveau, il est ajouté au dictionnaire dict_game avec un nouvel ID.

5. Mise à jour du fichier JSON

  • À la fin de la boucle, le script enregistre la liste mise à jour dans games_list.json.
  • Il affiche le nombre de nouveaux jeux ajoutés.

6. Gestion des erreurs

  • Si une page ne répond pas (status_code ≠ 200), un message d’erreur est affiché.
  • Affichage d’un message de fin pour indiquer la complétion du programme.

Conclusion

Ce script permet d’extraire automatiquement des jeux du PlayStation Store et de les stocker dans un fichier JSON, en évitant les doublons et en mettant à jour les identifiants des nouveaux jeux.


Code source

from bs4 import BeautifulSoup
import requests
import json

# Nombre de pages que l'on souhaite extraire avec notre boucle
MIN_PAGE = 1
MAX_PAGE = 260

# Ouverture du fichier JSON
with open("./games_list.json", "r") as f:
dict_game = json.load(f)

# Notre variable 'name_exist' ci-dessous nous sert plus bas dans le code pour vérifier si le jeu est déjà dans le fichier JSON
name_exist = ""

id_exist = 0
# On vérifie le dernier ID dans la liste pour continuer et ne pas repartir à 1 à chaque lancement du code
for d in dict_game:
id_exist = d["id"]
# On vérifie si on a bien un ID dans notre liste
if id_exist:
id_exist = d["id"]

ID = 1 id_exist

for i in range(MIN_PAGE, MAX_PAGE):

# URL de la page
url = f"https://store.playstation.com/fr-fr/category/4cbf39e2-5749-4970-ba81-93a489e4570c/{i}"
response = requests.get(url)

# Vérification que la réponse est bien égale à 200 avant de commencer notre boucle
if response.status_code == 200:
html = response.text

# Lecture des données HTML
soup = BeautifulSoup(html, "html5lib")

# Ciblage de la div parente pour récupérer les enfants
bloc_game = soup.find_all('a', class_="psw-content-link")

for b in bloc_game:

# Récupération du titre
name_game = b.find('span', class_="psw-m-b-2")

# Récupération du prix
price_game = b.find('span', class_="psw-m-r-3")

# Vérification de la donnée du prix, si c'est un nombre ou un texte
if price_game:
if price_game.text[0].lower() == "g":
price_game = "Gratuit"
elif price_game.text[0].lower() == "i":
price_game = "Inclus, PS Extra"
else:
price_game = price_game.text[1::]
else:
price_game = ""

# Récupération de l'image (on vient chercher dans notre balise 'span' s'il existe plusieurs images à l'intérieur)
img_game = b.find('span', class_="psw-media-frame").find_all('img')
# Vérification qu'il existe bien 2 balises <img>
if len(img_game) > 1:
img_game = img_game[1]
else:
img_game = img_game[0]

# Récupération des plateformes multiples (PS5 & PS4)
platform_game = b.find('div', class_="psw-l-cluster").find_all('span', class_="psw-platform-tag")
# Vérification qu'il existe bien 2 balises <div>
if len(platform_game) > 1:
platform_game = platform_game[0].text, platform_game[1].text
else:
platform_game = platform_game[0].text

# Récupération du lien de la page du jeu
link_game = b.get('href')
url_game = f"https://store.playstation.com{link_game}"

# Création de la liste avant importation
list_game = {
'id': ID,
'name': name_game.text,
'platform': platform_game,
'image': img_game["src"],
'link': url_game,
'price': price_game
}

# Vérification avec 'any' pour savoir si le jeu existe déjà dans notre fichier JSON
name_any = any([True if name_game.text in d["name"] else False for d in dict_game])
# S'il n'existe pas, on l'ajoute à notre fichier JSON
if not name_any:
dict_game.append(list_game)
ID = 1

# On incrémente notre variable i pour changer de page
print('page :', i)
i = 1
else:
print(f"ERREUR: {response.status_code}")

# Une fois la boucle terminée, on envoie notre liste au fichier JSON
with open('games_list.json', 'w') as fichier:
json.dump(dict_game, fichier, indent=4)

total_add_game = int(ID) - int(id_exist)
if total_add_game != 1:
print(total_add_game, "fichiers viennent d'être ajoutés !")
else:
print("Aucun nouveau fichier n'a été ajouté !")
print("FIN DU PROGRAMME.")

Fichier JSON

[
{
"id": 1,
"name": "DoubleDragon Revive",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202407/0111/9e88a794181445e441f6c9f1c0d6e8cc64748f66ab144f45.png",
"link": "https://store.playstation.com/fr-fr/product/JP0036-PPSA23000_00-DDRAGONREVIVE000",
"price": "34,99"
},
{
"id": 2,
"name": "Double Dragon Revive \u00c9dition Deluxe",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202411/2109/b02e9891ee936cfbf73763879f874a82ae0975f002a57bb6.png",
"link": "https://store.playstation.com/fr-fr/product/JP0036-PPSA23000_00-DDREVIVEDXEDI000",
"price": "49,99"
},
{
"id": 3,
"name": "Hell is Us",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202502/0416/4ca7b6e306b177339c1792b17e8539bd4e0f561b97ccd172.png",
"link": "https://store.playstation.com/fr-fr/product/EP6665-PPSA09259_00-HIU0000000000000",
"price": "59,99"
},
{
"id": 4,
"name": "Hell is Us - Deluxe Edition",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202502/1208/e5cdd3846747654d3b855bb944b5306b255fadaa0a5743f9.png",
"link": "https://store.playstation.com/fr-fr/product/EP6665-PPSA09259_00-HIU00DELUXE00001",
"price": "79,99"
},
{
"id": 5,
"name": "SHINOBI: Art of Vengeance PS4 et PS5",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202501/2001/ef5de71af75b004bb6870ee2e041ad8a3d7b1867b463e17d.png",
"link": "https://store.playstation.com/fr-fr/product/UP0177-PPSA19461_00-SHINOBIAOV000001",
"price": "29,99"
},
{
"id": 6,
"name": "METAL GEAR SOLID \u0394: SNAKE EATER",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202406/0513/d35b305652ee922a72b4020bd5d6ef36675cf526dd4945d1.png",
"link": "https://store.playstation.com/fr-fr/product/JP0101-PPSA15304_00-MGSDELTAMAINGAME",
"price": "79,99"
},
{
"id": 7,
"name": "METAL GEAR SOLID \u0394: SNAKE EATER Digital Deluxe Edition",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202501/2904/555d1ee5094c3c06e59a70ae95388b8114bcb2fadd2f0a35.png",
"link": "https://store.playstation.com/fr-fr/product/JP0101-PPSA15304_00-SNAKEEATERDELUXE",
"price": "89,99"
},
{
"id": 8,
"name": "SHINOBI: Art of Vengeance \u00c9dition Deluxe num\u00e9rique PS4 et PS5",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202501/2401/39c4d012f1b93fa8278a7ab254dba52db4dfd3b773dfb11d.png",
"link": "https://store.playstation.com/fr-fr/product/UP0177-PPSA19461_00-SHINOBIAOVDX0001",
"price": "39,99"
},
{
"id": 9,
"name": "GRADIUS ORIGINS",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202502/1808/4f588810bee68b1bcb2c38a8ddf345544fa93cd989b61164.png",
"link": "https://store.playstation.com/fr-fr/product/JP0101-PPSA19724_00-GRADIUSORIGINCOL",
"price": "39,99"
},
{
"id": 10,
"name": "\u00c9dition Standard PS4 & PS5 - Demon Slayer -Kimetsu no Yaiba- The Hinokami Chronicles\u00a02",
"platform": "PS5",
"image": "https://image.api.playstation.com/vulcan/ap/rnd/202502/0606/4f087ea8042a30b984552cbc5df2b2c4d540a7f039d1292a.png",
"link": "https://store.playstation.com/fr-fr/product/HP0177-PPSA25427_00-HINOKAMI20000000",
"price": "59,99"
}
]

Prochainement :

Programmation Orientée Objet en python sur la manipulation des objets dans le fichier JSON.