Résumé des Questions d'Entretien en Développement Python et Web

Python Basics

1. Les trois caractéristiques fondamentales de la programmation orientée objet

**Encapsulation:**L'encapsulation consiste à regrouper des données et des méthodes au sein d'un objet unique. L'objet peut ensuite accéder à ses attributs et méthodes via la notation ".".

**Héritage:**L'héritage permet à une classe enfant de hériter des attributs et méthodes d'une classe parente, tout en ayant la possibilité de les modifier ou de les réutiliser.

**Polymorphisme:**En Python, le polymorphisme consiste à standardiser les noms des méthodes et attributs entre différentes classes similaires. Cela améliore la cohérence du code et facilite sa compréhension.

2. Qu'est-ce que le modèle "Canard" (Duck Typing)?

Python n'impose pas de conventions strictes de codage. Si un objet possède les méthodes attendues, il peut être utilisé comme prévu, peu importe sa classe exacte. C'est ce qu'on appelle le modèle "Canard" : "si ça ressemble à un canard, ça marche comme un canard".

3. Quel est le rôle de super()?

La fonction super() permet d'appeler des méthodes ou attributs de la classe parente depuis une classe enfant. Elle est particulièrement utile lorsque la classe enfant redéfinit une méthode existante dans la classe parente et qu'on souhaite exécuter les deux versions.

4. Qu'est-ce que la réflexion et ses méthodes courantes?

La réflexion consiste à manipuler les attributs d'un objet via des chaînes de caractères. Quatre fonctions intégrées sont utilisées :

  • hasattr: vérifie si un attribut existe dans une classe
  • getattr: récupère l'adresse mémoire d'une méthode d'un objet via son nom
  • setattr: lie une fonction externe à une instance
  • delattr: supprime une méthode d'une instance ou d'une classe

5. Qu'est-ce que la gestion de contexte?

La gestion de contexte permet d'exécuter du code avant et après un bloc d'opérations, souvent pour la gestion de ressources. Pour utiliser l'instruction with, un objet doit implémenter les méthodes __enter__ et __exit__.

class GestionnaireFichier:
    def __init__(self, nom_fichier):
        self.nom_fichier = nom_fichier
    
    def __enter__(self):
        print("Début du bloc with")
        return self
    
    def __exit__(self, type_exception, valeur_exception, traceback):
        print("Fin du bloc with")

with GestionnaireFichier('document.txt') as gestionnaire:
    print("Traitement du fichier")

6. Différences entre import et from...import...

Points communs:

  • Les deux exécutent le fichier du module
  • Les deux créent un espace de noms pour le module
  • Les deux recherchent les fonctionnalités dans l'espace de noms de définition

Différences:

  • import nécessite un préfixe pour accéder aux éléments
  • from...import... permet d'utiliser directement les éléments sans préfixe

7. Parcours en profondeur et en largeur en Python 3

Classes nouvelles (Python 3): parcours en largeur - recherche de gauche à droite jusqu'au sommet du losange (exclu) Classes classiques (Python 2): parcours en profondeur - recherche de gauche à droite jusqu'au sommet du losange (inclus), puis poursuite avec la classe parente suivante

8. Avantages et inconvénients de la programmation orientée objet

Avantages:

  • Simplification des problèmes complexes par décomposition en étapes simples
  • Modularisation et réutilisation du code

Inconvénients:

  • Une solution optimisée pour un problème peut être inadaptée à un autre
  • Modification d'un élément peut impacter l'ensemble du système

9. Qu'est-ce qu'un itérable et un itérateur?

Un itérable est tout objet possédant une méthode __iter__(). L'appel de cette méthode renvoie un itérateur. Un itérateur possède une méthode __next__() pour obtenir l'élément suivant et une méthode __iter__() renvoyant l'itérateur lui-même.

10. Méthodes d'un métaclasse personnalisé

__call__: appelé lors de l'instanciation d'une classe __new__: appelé lors de la création d'un objet classe __init__: appelé lors de l'initialisation d'une classe

Ordre d'exécution: __call__, puis __new__, puis __init__

11. Comment voir toutes les classes parentes d'une classe?

La méthode classe.mro() renvoie la liste des classes parentes dans l'ordre d'héritage.

12. Parcours en profondeur et en largeur en POO

Le parcours en profondeur concerne les classes classiques avec un héritage en losange. Le parcours en largeur concerne les classes nouvelles avec un héritage en losange.

13. Quelques méthodes spéciales (magic methods)

__init__: initialisation d'un objet __new__: création d'un objet (utilisé dans les singletons) __str__: représentation en chaîne de caractères pour print() __del__: appelé lors de la suppression d'un objet

14. Mécanisme de comptage de références en Python

Le garbage collector de Python utilise principalement le comptage de références, avec le marquage-élimination et le nettoyage par génération comme solutions aux références cycliques.

15. Différence entre copy et deepcopy

Pour les types immuables (nombres, chaînes, tuples), copy et deepcopy renvoient la même adresse. Pour les types mutables (listes, dictionnaires):

  • copy crée une nouvelle copie superficielle (les objets imbriqués partagent la même référence)
  • deepcopy crée une copie complète et indépendante, y compris pour les objets imbriqués

16. Différences entre Python 2 et Python 3

  1. print() en Python 3 vs print sans parenthèses en Python 2
  2. range() renvoie un itérateur en Python 3 vs une liste en Python 2
  3. Encodage par défaut: UTF-8 en Python 3 vs ASCII en Python 2
  4. Types de chaînes: str pour les chaînes Unicode en Python 3 vs unicode en Python 2
  5. Pas besoin de déclaration d'encodage en Python 3
  6. input() en Python 3 vs raw_input() en Python 2

17. Itérateurs et générateurs

Un itérateur implémente __iter__ et __next__. Un générateur est une fonction utilisant yield au lieu de return. Les générateurs sont plus compacts et efficaces que les itérateurs manuels.

18. Qu'est-ce que le déballage de séquence?

Le déballage de séquence consiste à extraire des éléments de conteneurs (listes, tuples, chaînes, etc.) dans des variables distinctes.

19. Qu'est-ce qu'une constante en Python?

Python n'a pas de véritable constante. Par convention, les noms de constantes sont en majuscules. On peut simuler des constantes avec une classe personnalisée:

class Constantes:
    def __setattr__(self, nom, valeur):
        if hasattr(self, nom):
            raise f"Impossible de modifier la constante {nom}"
        self.__dict__[nom] = valeur

constantes = Constantes()
constantes.PI = 3.14

20. Qu'est-ce que la récursion?

La récursion est une fonction qui s'appelle elle-même directement ou indirectement. La limite maximale de récursion en Python est environ 1000.

21. Gestion des exceptions en Python

Une exception est un signal indiquant une erreur lors de l'exécution. Quelques exceptions courantes:

  • NameError: variable non définie
  • TypeError: opération non valide pour le type
  • ValueError: argument de bonne type mais valeur incorrecte
  • IndexError: index hors de la plage
  • KeyError: clé de dictionnaire inexistante
  • AttributeError: attribut inexistant

22. Qu'est-ce que assert?

assert vérifie qu'une condition est vraie. Si elle est fausse, lève une exception AssertionError. Utile pour les tests.

23. Exécuter des commandes système depuis Python

# Méthode 1: os.system()
import os
os.system('ls -l')

# Méthode 2: os.popen()
import os
resultat = os.popen('ls -l')
print(resultat.read())

# Méthode 3: subprocess
import subprocess
processus = subprocess.Popen('ls -l', shell=True, stdout=subprocess.PIPE)
sortie, erreur = processus.communicate()
print(sortie)

# Méthode 4: commands
import commands
status, sortie = commands.getstatusoutput('ls -l')
print(sortie)

Django Interview Questions

1. Qu'est-ce que WSGI, uWSGI?

WSGI: Interface de passerelle entre serveur web et framework web. uWSGI: Protocole de communication et serveur web implémentant WSGI. uWSGI: Serveur web implémentant WSGI et uWSGI.

2. Optimisations de données dans Django

  • Limiter les clés étrangères
  • Utiliser le cache
  • Préférer VARCHAR à TEXT quand possible
  • Créer des indexes pour les champs fréquemment recherchés
  • Utiliser le cache des QuerySets
  • Récupérer toutes les données nécessaires en une seule requête
  • Utiliser values() ou values_list() quand seuls certains champs sont nécessaires
  • Utiliser le tag with dans les templates pour mettre en cache les résultats

3. Rôle des middlewares dans Django

Les middlewares traitent les requêtes et réponses à un niveau global. Ils permettent d'effectuer des opérations avant et après l'exécution des vues.

Exemples:

  • Protection CSRF
  • Authentification des utilisateurs
  • Contrôle d'accès (liste blanche/noire)

4. Méthodes des middlewares Django

  • process_request: traitement au début de la requête
  • process_view: après le routage, avant la vue
  • process_exception: en cas d'exception
  • process_template_response: pendant le rendu du template
  • process_response: avant l'envoi de la réponse

5. Fichiers statiques dans Django

Placer les fichiers statiques (CSS, JS, images) dans un dossier static. Configurer dans settings.py:

STATIC_URL = '/static/'
STATICFILES_DIRS = [
    os.path.join(BASE_DIR, 'static'),
]

Utiliser dans les templates:

{% load static %}
<link rel="stylesheet" href="{% static 'css/style.css' %}">

6. request.POST et request.GET

request.POST: récupère les données des requêtes POST request.GET: récupère les données des requêtes GET

Les méthodes sont sensibles à la casse. Pour récupérer toutes les valeurs d'une liste, utiliser getlist().

7. Différences entre versions Django

  • path vs re_path (nouveau format d'URL sans regex)
  • Améliorations du cache
  • Améliorations de l'ORM
  • Améliorations de l'administration

8. Récupérer un objet pour édition

Utiliser une requête GET avec l'ID de l'objet en paramètre:

objet = MonModele.objects.get(id=id_objet)

9. Différence entre select_related et prefetch_related

select_related: effectue une jointure pour récupérer les objets liés en une seule requête SQL prefetch_related: effectue des requêtes séparées puis assemble les résultats

10. Paramètre on_delete dans les ForeignKey

Définit le comportement lors de la suppression de l'objet référencé. Obligatoire depuis Django 2.0.

11. Paramètres des champs Django ORM

  • null: autorise les valeurs NULL
  • unique: valeur unique dans la table
  • db_index: crée un index
  • default: valeur par défaut
  • auto_now_add: date de création automatique
  • auto_now: date de modification automatique

12. Méthodes des QuerySet

  • all(): tous les objets
  • filter(): objets correspondant aux critères
  • get(): un objet spécifique
  • exclude(): objets ne correspondant pas aux critères
  • order_by(): tri des résultats
  • reverse(): inversion de l'ordre
  • count(): nombre d'objets
  • first(): premier objet
  • last(): dernier objet
  • exists(): vérifie l'existence d'objets
  • values(): dictionnaires au lieu d'objets
  • values_list(): tuples au lieu d'objets
  • distinct(): élimine les doublons

13. Commandes Django

# Créer un projet
django-admin startproject nom_projet

# Créer une app
python manage.py startapp nom_app

# Démarrer le serveur
python manage.py runserver

14. Cycle de vie d'une requête Django

  1. WSGI: encapsulation de la requête
  2. Middlewares: traitement avant les vues
  3. Routage: correspondance URL → vue
  4. Vue: traitement de la logique métier
  5. Middlewares: traitement après les vues
  6. WSGI: envoi de la réponse

15. FBV vs CBV

FBV (Function-Based Views): traitement des requêtes par des fonctions CBV (Class-Based Views): traitement des requêtes par des classes

Avantages du CBV:

  • Réutilisation du code
  • Utilisation de l'orienté objet (héritage, mixins)
  • Meilleure organisation du code

16. Composants intégrés de Django

  • Admin: interface d'administration des modèles
  • Model: interaction avec la base de données
  • Form: validation et génération de formulaires HTML
  • ModelForm: combinaison de modèle et formulaire

17. Différence entre values et values_list

values(): renvoie une liste de dictionnaires values_list(): renvoie une liste de tuples

18. Mécanisme de cache intégré à Django

Django met en cache les données (variables ou pages entières) selon une stratégie définie. Lors d'une nouvelle requête, Django vérifie si le cache est encore valide.

19. Pourquoi runserver n'est pas adapté au déploiement?

runserver est un serveur de développement mono-processus. Pour le déploiement, utiliser uWSGI ou Gunicorn avec Nginx pour un meilleur rendement, une meilleure gestion des processus et une plus grande stabilité.

DRF (Django REST Framework) Interview Questions

1. Vue DRF

APIView: encapsule HttpRequest en Request, gère authentification/permissions/limites GenericAPIView: ajoute des méthodes pour les sérialiseurs et les données, souvent avec des mixins

2. Cinq mixins d'extension

ListModelMixin: méthode list() pour renvoyer une liste d'objets CreateModelMixin: méthode create() pour créer un objet RetrieveModelMixin: méthode retrieve() pour obtenir un objet UpdateModelMixin: méthode update() pour mettre à jour un objet DestroyModelMixin: méthode destroy() pour supprimer un objet

3. Sous-classes de vues DRF

ListAPIView: liste d'objets CreateAPIView: création d'objet RetrieveAPIView: obtention d'un objet UpdateAPIView: mise à jour d'objet DestroyAPIView: suppression d'objet ListCreateAPIView: combinaison liste/création RetrieveUpdateAPIView: combinaison obtention/mise à jour RetrieveUpdateDestroyAPIView: combinaison complète

4. ViewSet DRF

ViewSet hérite de ViewSetMixin et APIView. Il ne définit pas de méthodes HTTP mais des actions:

  • list(): liste de données
  • retrieve(): donnée unique
  • create(): création
  • update(): mise à jour
  • destroy(): suppression

5. Configuration des analyseurs

Les analyseurs déterminent quels formats de données sont acceptés. On peut configurer globalement ou localement:

# Configuration globale
REST_FRAMEWORK = {
    'DEFAULT_PARSER_CLASSES': [
        'rest_framework.parsers.JSONParser',
        'rest_framework.parsers.MultiPartParser',
    ]
}

# Configuration locale
class MaVue(APIView):
    parser_classes = [JSONParser]

6. Gestion des exceptions personnalisées

DRF fournit une gestion des exceptions de base. On peut étendre cette gestion pour gérer des cas spécifiques et renvoyer des informations cohérentes aux clients.

7. Frontend et Backend séparés

Le frontend (navigateur) gère l'affichage et les interactions, le backend fournit des API. Les technologies peuvent varier (React, Angular, Vue.js pour le frontend; Django, Flask, Node.js pour le backend).

8. Qu'est-ce que DRF?

DRF est un framework pour construire des API RESTful avec Django. Il fournit des outils pour la sérialisation, l'authentification, la limitation de débit, etc.

9. Paramètre many=True vs many=False

many=True: sérialisation de plusieurs objets many=False: sérialisation d'un seul objet

10. Qu'est-ce que JWT?

JWT (JSON Web Token) est un standard pour l'authentification via des tokens. Avantages:

  • Stocké côté client
  • Intégration d'une durée de vie
  • Signature cryptographique pour l'intégrité

11. Les trois authentifications DRF

  • Authentification: vérifie l'identité de l'utilisateur
  • Autorisation: vérifie les permissions de l'utilisateur
  • Limitation de débit: contrôle le nombre de requêtes

12. Créer une classe de limitation personnalisée

  1. Hériter de SimpleRateThrottle
  2. Définir un attribut scope
  3. Configurer les taux dans settings
  4. Implémenter get_cache_key

13. Vérification JWT

Le token est envoyé avec un préfixe (ex: "Bearer"). Le serveur vérifie la signature et le payload pour valider l'authentification.

14. ModelSerializer vs Serializer

ModelSerializer:

  • Génère automatiquement les champs à partir du modèle
  • Génère automatiquement les validateurs
  • Fournit des méthodes create() et update()

Serializer:

  • Définition manuelle des champs
  • Validation personnalisée

15. Traitement des données dans DRF

La classe Request de DRF étend la requête Django. Elle met en cache les données pour les requêtes POST/PUT/PATCH et fournit query_params pour les paramètres d'URL.

16. Filtres pour les vues de liste

  • Filtre de tri: OrderingFilter
  • Filtre de recherche: SearchFilter
  • Filtre de champ: DjangoFilterBackend
  • Pagination: PageNumberPagination, LimitOffsetPagination, CursorPagination

17. Avantages de JWT

  • Stocké côté client
  • Durée de vie intégrée
  • Signature cryptographique

18. FBV vs CBV

FBV: fonctions pour gérer les requêtes CBV: classes pour gérer les requêtes

Avantages du CBV:

  • Réutilisation du code
  • Meilleure organisation
  • Gestion différente des méthodes HTTP

19. RESTful API

Conventions pour les API:

  • HTTPS pour la sécurité
  • URL avec version et identifiant API
  • Ressources nommées (noms au pluriel)
  • Méthodes HTTP pour les actions
  • Codes de statut HTTP appropriés
  • Gestion des erreurs

20. Processus d'authentification DRF

  1. as_view() est exécuté
  2. dispatch() dans APIView
  3. _authenticate() dans APIView
  4. authenticate() dans la classe personnalisée
  5. Affectation de request.user et request.auth

21. Création et vérification JWT

Création:

  1. Obtenir l'utilisateur avec identifiant/mot de passe
  2. Générer le payload avec les informations utilisateur
  3. Créer le token à partir du payload

Vérification:

  1. Extraire le token de la requête
  2. Vérifier la signature et la validité
  3. Extraire les informations utilisateur

MySQL Interview Questions

1. Qu'est-ce qu'une transaction?

Une transaction est une séquence d'opérations qui forment une unité logique de travail. Les transactions respectent les propriétés ACID.

2. Qu'est-ce que ACID?

A (Atomicité): toutes les opérations réussissent ou échouent ensemble C (Cohérence): la base de données reste dans un état cohérent I (Isolation): les transactions s'exécutent de manière isolée D (Durabilité): les résultats persist même en cas de panne

3. Problèmes de concurrence

  • Lecture sale: lecture de données non validées par une autre transaction
  • Lecture non reproductible: résultats différents lors de lectures répétées
  • Fantôme: apparition de nouveaux enregistrements lors de requêtes répétées

4. Niveaux d'isolation

  • Non validé: peut lire des données non validées
  • Validé: ne lit que des données validées
  • Répétable: garantit la cohérence des lectures multiples
  • Sérieux: séquence les transactions pour éviter les problèmes

5. Verrous dans MySQL

  • Verrous partagés: lecture simultanée possible
  • Verrous exclusifs: écriture exclusive
  • Verrous à ligne/grappe/table: selon le moteur

6. Optimisation SQL

  • Éviter les opérateurs != ou <> dans WHERE
  • Éviter les tests NULL dans WHERE
  • Utiliser EXISTS au lieu de IN quand possible
  • Remplacer HAVING par WHERE quand possible

7. Optimisation d'index

Les indexes accélèrent les requêtes mais ralentissent les insertions/mises à jour. Types:

  • Index normaux
  • Index uniques
  • Index primaires
  • Index de clés étrangères
  • Index composites
  • Index全文

8. Trois formes normales

1NF: pas de colonnes répétitives, toutes les valeurs atomiques 2NF: dépendance fonctionnelle complète de la clé primaire 3NF: pas de dépendance transitive

9. Moteurs de stockage

InnoDB:

  • Transactions
  • Verrous à ligne
  • Clés étrangères
  • Index B-tree

MyISAM:

  • Plus rapide pour les lectures
  • Verrous à table
  • Index B-tree
  • Compteurs intégrés

10. Encodages de caractères

utf8_bin: sensible à la casse utf8_general_ci: insensible à la casse, rapide utf8_unicode_ci: insensible à la casse, précis

Pour les emojis, utiliser utf8mb4.

11. Autres commandes SQL

  • TRUNCATE: supprime les données mais pas la structure
  • ORDER BY: tri des résultats
  • GROUP BY: regroupement des résultats
  • Opérateur +: addition ou concaténation selon les types

Étiquettes: Python Django MySQL Programmation orientée objet API REST

Publié le 24 juin à 23h52