• Not Exported

    Detects patterns where users consistently skip specific artists

    Analyzes artists with high skip ratios to identify potential artist aversion patterns. This algorithm identifies artists that the user consistently avoids or dislikes based on their skip behavior across multiple tracks by the same artist.

    The detection process involves:

    1. Filtering artists with sufficient data points (minimum tracks and skips)
    2. Identifying artists with skip ratios exceeding thresholds
    3. Calculating confidence scores based on consistency and frequency
    4. Generating human-readable pattern descriptions

    Artist aversion patterns are particularly valuable for:

    • Improving personalized recommendations by avoiding disliked artists
    • Identifying taste changes over time
    • Understanding explicit vs. implicit preferences

    Parameters

    • artistMetrics: Record<string, ArtistMetricsData>

      Object mapping artist IDs to their skip metrics data

    Returns DetectedPattern[]

    Array of detected artist aversion patterns that meet confidence thresholds

    // Detection of artist aversion patterns
    const artistMetrics = await aggregateArtistSkipMetrics();
    const aversionPatterns = detectArtistAversionPatterns(artistMetrics);

    // Example pattern result:
    // {
    // type: "artist_aversion",
    // confidence: 0.85,
    // description: "Frequently skips tracks by Artist Name",
    // ...additional pattern data
    // }
    function detectArtistAversionPatterns(
    artistMetrics: Record<string, ArtistMetricsData>,
    ): DetectedPattern[] {
    const patterns: DetectedPattern[] = [];

    // Find artists with high skip ratios
    Object.entries(artistMetrics).forEach(([, metrics]) => {
    // Only consider artists with enough data
    if (
    metrics.uniqueTracksSkipped.length < 3 ||
    metrics.totalSkips < PATTERN_THRESHOLDS.MIN_OCCURRENCES
    ) {
    return;
    }

    // Check if skip ratio is high enough to indicate aversion
    if (metrics.skipRatio > 0.7) {
    // Calculate confidence based on data points and skip ratio
    const confidence = calculateConfidence(
    metrics.skipRatio,
    metrics.uniqueTracksSkipped.length,
    metrics.totalSkips,
    );

    if (confidence >= PATTERN_THRESHOLDS.CONFIDENCE_THRESHOLD) {
    patterns.push({
    type: PatternType.ARTIST_AVERSION,
    confidence,
    description: `Frequently skips tracks by ${metrics.artistName}`,
    occurrences: metrics.totalSkips,
    relatedItems: [metrics.artistName],
    details: {
    skipRatio: metrics.skipRatio,
    uniqueTracksSkipped: metrics.uniqueTracksSkipped.length,
    averagePlayPercentage: metrics.averagePlayPercentage,
    },
    firstDetected: new Date().toISOString(),
    lastDetected: new Date().toISOString(),
    });
    }
    }
    });

    return patterns;
    }