Skip to content

Historique d'annotation

Potato enregistre chaque action d'annotation avec horodatage, identifiant d'annotateur et historique des versions, ce qui donne une piste d'audit complète, la possibilité d'annuler et la détection des changements.

Potato enregistre chaque action d'annotation avec des métadonnées d'horodatage fines. De quoi analyser les performances, assurer la qualité et constituer une piste d'audit détaillée.

Vue d'ensemble

Le système d'historique d'annotation enregistre :

  • Chaque action d'annotation : choix d'étiquettes, annotations d'empans, saisies de texte
  • Des horodatages précis : côté serveur et côté client
  • Les métadonnées de l'action : utilisateur, instance, schéma, ancienne et nouvelle valeur
  • Des métriques de performance : temps de traitement, cadence des actions
  • L'activité suspecte : actions anormalement rapides ou en rafale

Suivi des actions

Chaque modification d'annotation est consignée sous forme d'AnnotationAction, avec les champs suivants :

ChampDescription
action_idUUID unique de l'action
timestampHorodatage côté serveur
client_timestampHorodatage côté navigateur (s'il est disponible)
user_idUtilisateur à l'origine de l'action
instance_idInstance en cours d'annotation
action_typeType d'action effectuée
schema_nameNom du schéma d'annotation
label_nameÉtiquette précise au sein du schéma
old_valueValeur précédente (mises à jour et suppressions)
new_valueNouvelle valeur (ajouts et mises à jour)
span_dataDétails de l'empan pour les annotations d'empans
server_processing_time_msTemps de traitement côté serveur

Types d'action

Les types d'action suivis sont les suivants :

  • add_label - Nouveau choix d'étiquette
  • update_label - Valeur d'étiquette modifiée
  • delete_label - Étiquette retirée
  • add_span - Nouvelle annotation d'empan
  • update_span - Annotation d'empan modifiée
  • delete_span - Annotation d'empan supprimée

Configuration

Le suivi de l'historique d'annotation est actif par défaut. Aucune configuration supplémentaire n'est nécessaire.

Métriques de performance

Le système calcule des métriques de performance à partir de l'historique des actions :

python
from potato.annotation_history import AnnotationHistoryManager
 
metrics = AnnotationHistoryManager.calculate_performance_metrics(actions)
 
# Returns:
{
    'total_actions': 150,
    'average_action_time_ms': 45.2,
    'fastest_action_time_ms': 12,
    'slowest_action_time_ms': 234,
    'actions_per_minute': 8.5,
    'total_processing_time_ms': 6780
}

Détection d'activité suspecte

Le système repère les schémas d'annotation potentiellement problématiques :

python
from potato.annotation_history import AnnotationHistoryManager
 
analysis = AnnotationHistoryManager.detect_suspicious_activity(
    actions,
    fast_threshold_ms=500,      # Actions faster than this are flagged
    burst_threshold_seconds=2   # Actions closer than this are flagged
)
 
# Returns:
{
    'suspicious_actions': [...],
    'fast_actions_count': 5,
    'burst_actions_count': 12,
    'fast_actions_percentage': 3.3,
    'burst_actions_percentage': 8.0,
    'suspicious_score': 15.2,
    'suspicious_level': 'Low'
}

Niveaux de suspicion

ScoreNiveauInterprétation
0-10NormalComportement d'annotation habituel
10-30LowQuelques actions rapides, sans doute acceptable
30-60MediumTendance notable, à examiner éventuellement
60-80HighTendance préoccupante, examen conseillé
80-100Very HighProblème de qualité probable, examen immédiat

Référence de l'API

AnnotationAction

python
from potato.annotation_history import AnnotationAction
 
action = AnnotationAction(
    action_id="uuid-here",
    timestamp=datetime.now(),
    user_id="annotator1",
    instance_id="doc_001",
    action_type="add_label",
    schema_name="sentiment",
    label_name="positive",
    old_value=None,
    new_value=True
)
 
# Serialize to dictionary
data = action.to_dict()
 
# Deserialize from dictionary
action = AnnotationAction.from_dict(data)

AnnotationHistoryManager

python
from potato.annotation_history import AnnotationHistoryManager
 
# Create a new action with current timestamp
action = AnnotationHistoryManager.create_action(
    user_id="annotator1",
    instance_id="doc_001",
    action_type="add_label",
    schema_name="sentiment",
    label_name="positive",
    old_value=None,
    new_value=True
)
 
# Filter actions by time range
filtered = AnnotationHistoryManager.get_actions_by_time_range(
    actions,
    start_time=datetime(2024, 1, 1),
    end_time=datetime(2024, 1, 31)
)
 
# Filter actions by instance
instance_actions = AnnotationHistoryManager.get_actions_by_instance(
    actions, instance_id="doc_001"
)
 
# Calculate performance metrics
metrics = AnnotationHistoryManager.calculate_performance_metrics(actions)
 
# Detect suspicious activity
analysis = AnnotationHistoryManager.detect_suspicious_activity(actions)

Cas d'usage

Assurance qualité

Surveiller le comportement des annotateurs pour repérer les problèmes de qualité :

python
for user_id in get_all_users():
    user_actions = get_user_actions(user_id)
    analysis = AnnotationHistoryManager.detect_suspicious_activity(user_actions)
 
    if analysis['suspicious_level'] in ['High', 'Very High']:
        flag_for_review(user_id, analysis)

Piste d'audit

Suivre les modifications à des fins de conformité réglementaire :

python
instance_actions = AnnotationHistoryManager.get_actions_by_instance(
    all_actions, "doc_001"
)
 
audit_log = [action.to_dict() for action in instance_actions]
with open("audit_doc_001.json", "w") as f:
    json.dump(audit_log, f, indent=2)

Analyse temporelle

Comprendre les rythmes d'annotation :

python
from collections import Counter
 
hours = Counter(action.timestamp.hour for action in all_actions)
print("Peak annotation hours:", hours.most_common(5))

Stockage des données

L'historique d'annotation est conservé dans les fichiers d'état des utilisateurs :

text
output/
  annotations/
    user_state_annotator1.json  # Includes action history
    user_state_annotator2.json

Format d'export

Les actions sont sérialisées avec des horodatages ISO 8601 :

json
{
  "action_id": "550e8400-e29b-41d4-a716-446655440000",
  "timestamp": "2024-01-15T10:30:45.123456",
  "user_id": "annotator1",
  "instance_id": "doc_001",
  "action_type": "add_label",
  "schema_name": "sentiment",
  "label_name": "positive",
  "old_value": null,
  "new_value": true,
  "server_processing_time_ms": 23
}

Bonnes pratiques

  1. Surveillance régulière : consultez périodiquement les rapports d'activité suspecte
  2. Réglage des seuils : ajustez les seuils de détection à la complexité de la tâche
  3. Sauvegardes : exportez régulièrement l'historique pour la conservation à long terme
  4. Conformité et vie privée : prévoyez une politique de rétention pour les horodatages

Pour aller plus loin

Pour les détails d'implémentation, consultez la documentation source.