# Scores

### What does the include do?

The `scores` include allows you to retrieve detailed information about the scores within a football match from both participants (home and away teams). Including scores in your API requests provides comprehensive scoring data including 1st half, 2nd half, extra time, penalty shootout results, and current match score.

### Why use scores?

The scores include is essential for:

* **Live match tracking**: Display real-time score updates during matches
* **Historical score analysis**: Analyse how teams performed across different match periods
* **Comeback patterns**: Identify teams that score more in second halves
* **Extra time performance**: Track team performance in high-pressure situations
* **Statistical analysis**: Build datasets for scoring pattern analysis

### Requesting scores

To retrieve scores for a fixture, use the following include:

```http
https://api.sportmonks.com/v3/football/fixtures/{fixture_id}
?api_token=YOUR_TOKEN&include=scores
```

**Example:** Get scores for Napoli vs Atalanta (fixture ID: 19424997)

```http
https://api.sportmonks.com/v3/football/fixtures/19424997
?api_token=YOUR_TOKEN&include=scores
```

### Response structure

When you include `scores` in your request, you'll receive an array of score objects for each match period:

```json
{
  "data": {
    "id": 19424997,
    "sport_id": 1,
    "league_id": 384,
    "season_id": 25533,
    "stage_id": 77476851,
    "group_id": null,
    "aggregate_id": null,
    "round_id": 371860,
    "state_id": 5,
    "venue_id": 134,
    "name": "Napoli vs Atalanta",
    "starting_at": "2025-11-22 19:45:00",
    "result_info": "Napoli won after full-time.",
    "leg": "1\/1",
    "details": null,
    "length": 90,
    "placeholder": false,
    "has_odds": true,
    "has_premium_odds": true,
    "starting_at_timestamp": 1763840700,
    "scores": [
      {
        "id": 17490807,
        "fixture_id": 19424997,
        "type_id": 48996,
        "participant_id": 708,
        "score": {
          "goals": 1,
          "participant": "away"
        },
        "description": "2ND_HALF_ONLY"
      },
      {
        "id": 17490806,
        "fixture_id": 19424997,
        "type_id": 48996,
        "participant_id": 597,
        "score": {
          "goals": 0,
          "participant": "home"
        },
        "description": "2ND_HALF_ONLY"
      },
      {
        "id": 17490045,
        "fixture_id": 19424997,
        "type_id": 1525,
        "participant_id": 597,
        "score": {
          "goals": 3,
          "participant": "home"
        },
        "description": "CURRENT"
      },
      {
        "id": 17490044,
        "fixture_id": 19424997,
        "type_id": 1525,
        "participant_id": 708,
        "score": {
          "goals": 1,
          "participant": "away"
        },
        "description": "CURRENT"
      },
      {
        "id": 17490047,
        "fixture_id": 19424997,
        "type_id": 1,
        "participant_id": 597,
        "score": {
          "goals": 3,
          "participant": "home"
        },
        "description": "1ST_HALF"
      },
      {
        "id": 17490048,
        "fixture_id": 19424997,
        "type_id": 2,
        "participant_id": 708,
        "score": {
          "goals": 1,
          "participant": "away"
        },
        "description": "2ND_HALF"
      },
      {
        "id": 17490049,
        "fixture_id": 19424997,
        "type_id": 2,
        "participant_id": 597,
        "score": {
          "goals": 3,
          "participant": "home"
        },
        "description": "2ND_HALF"
      },
      {
        "id": 17490046,
        "fixture_id": 19424997,
        "type_id": 1,
        "participant_id": 708,
        "score": {
          "goals": 0,
          "participant": "away"
        },
        "description": "1ST_HALF"
      }
    ]
  }
}
```

### Field descriptions

| Field               | Type    | Description                                                         |
| ------------------- | ------- | ------------------------------------------------------------------- |
| `id`                | integer | Unique identifier for this score entry                              |
| `fixture_id`        | integer | ID of the fixture this score belongs to                             |
| `type_id`           | integer | Type identifier indicating the score period (see Score Types below) |
| `participant_id`    | integer | ID of the team (participant) this score belongs to                  |
| `score`             | object  | Score object containing goals and participant location              |
| `score.goals`       | integer | Number of goals scored by this participant in this period           |
| `score.participant` | string  | Team location: "home" or "away"                                     |
| `description`       | string  | Human-readable description of the score type                        |

### Score types and descriptions

When you use the scores include for a regular match, you'll get different types of scores based on the match state:

#### Regular Match (90 minutes)

| Description     | Explanation                                                     |
| --------------- | --------------------------------------------------------------- |
| `1ST_HALF`      | Goals scored during the first 45 minutes                        |
| `2ND_HALF_ONLY` | Goals scored during the second 45 minutes only (not cumulative) |
| `2ND_HALF`      | Cumulative score after both halves (1st half + 2nd half)        |
| `CURRENT`       | The current/final score of the match                            |

#### Extended match (Extra Time)

If the match goes into extra time, you'll see additional score types:

| Description       | Explanation                                                  |
| ----------------- | ------------------------------------------------------------ |
| `EXTRA_TIME`      | Goals scored during extra time (both periods combined)       |
| `EXTRA_TIME_ONLY` | Goals scored in extra time only (not including regular time) |
| `CURRENT`         | The updated current score including extra time               |

#### Penalty Shootout

If the match goes to penalties, you'll see:

| Description | Explanation                                        |
| ----------- | -------------------------------------------------- |
| `PENALTIES` | Number of successful penalty kicks in the shootout |
| `CURRENT`   | Final score (FT or ET), excluding penalties        |

**A few examples (not all scores) from the Euro 2024 quarter-final (Spain vs Germany):**

```json
"scores": [
  {
    "description": "1ST_HALF",
    "score": {
      "goals": 0,
      "participant": "home"
    }
  },
  {
    "description": "2ND_HALF",
    "score": [
      {
        "goals": 1,
        "participant": "home"
      },
      {
        "goals": 1,
        "participant": "away"
      }
    ]
  },
  {
    "description": "EXTRA_TIME",
    "score": {
      "goals": 1,
      "participant": "home"
    }
  },
  {
    "description": "CURRENT",
    "score": {
      "goals": 2,
      "participant": "home"
    }
  }
]
```

### Displaying current score

To display the latest scores for a game, **always use the `CURRENT` indicator**. This ensures you show the most up-to-date score regardless of whether the match concluded after full-time or extra time.

```python
def get_current_score(scores_data):
    """Extract current score for both teams"""
    current_scores = {}
    
    for score in scores_data:
        if score['description'] == 'CURRENT':
            participant = score['score']['participant']
            goals = score['score']['goals']
            current_scores[participant] = goals
    
    return current_scores

# Usage
current = get_current_score(fixture_scores)
print(f"Home: {current['home']} - Away: {current['away']}")
```

### Nested includes

The scores include supports the following nested includes for additional information:

#### scores.type

Get detailed information about the score type:

```http
https://api.sportmonks.com/v3/football/fixtures/{fixture_id}
?api_token=YOUR_TOKEN&include=scores.type
```

This returns the type object with details about the score period.

#### scores.participant

Get detailed information about the team (participant):

```http
https://api.sportmonks.com/v3/football/fixtures/{fixture_id}
?api_token=YOUR_TOKEN&include=scores.participant
```

This returns team information including name, logo, and other details.

**Example with nested includes:**

```json
{
  "scores": [
    {
      "id": 19424997,
      "fixture_id": 19424997,
      "type_id": 48996,
      "participant_id": 708,
      "score": {
        "goals": 1,
        "participant": "away"
      },
      "description": "2ND_HALF_ONLY",
      "participant": {
        "id": 708,
        "sport_id": 1,
        "country_id": 251,
        "venue_id": 193,
        "gender": "male",
        "name": "Atalanta",
        "short_code": "ATA",
        "image_path": "https://cdn.sportmonks.com/images/soccer/teams/4/708.png",
        "founded": 1907,
        "type": "domestic",
        "placeholder": false,
        "last_played_at": "2025-11-26 20:00:00"
      }
    },
    {
      "id": 17490806,
      "fixture_id": 19424997,
      "type_id": 48996,
      "participant_id": 597,
      "score": {
        "goals": 0,
        "participant": "home"
      },
      "description": "2ND_HALF_ONLY",
      "participant": {
        "id": 597,
        "sport_id": 1,
        "country_id": 251,
        "venue_id": 134,
        "gender": "male",
        "name": "Napoli",
        "short_code": "NAP",
        "image_path": "https://cdn.sportmonks.com/images/soccer/teams/21/597.png",
        "founded": 1926,
        "type": "domestic",
        "placeholder": false,
        "last_played_at": "2025-11-25 20:00:00"
      }
    }
  ]
}
```

### Code examples

#### Python Example

```python
import requests

# API configuration
API_TOKEN = "YOUR_TOKEN"
FIXTURE_ID = 19424997

# Request scores with nested includes
url = f"https://api.sportmonks.com/v3/football/fixtures/{FIXTURE_ID}"
params = {
    "api_token": API_TOKEN,
    "include": "scores.participant"
}

response = requests.get(url, params=params)
data = response.json()

# Extract scores
scores = data['data'].get('scores', [])

# Parse scores by description type
score_by_type = {}
for score in scores:
    description = score['description']
    if description not in score_by_type:
        score_by_type[description] = {'home': None, 'away': None}
    
    participant_type = score['score']['participant']
    score_by_type[description][participant_type] = {
        'goals': score['score']['goals'],
        'team': score.get('participant', {}).get('name', 'Unknown')
    }

# Display current score
if 'CURRENT' in score_by_type:
    current = score_by_type['CURRENT']
    print(f"Final Score: {current['home']['team']} {current['home']['goals']} - "
          f"{current['away']['goals']} {current['away']['team']}")

# Display half-time scores
if '1ST_HALF' in score_by_type:
    ht = score_by_type['1ST_HALF']
    print(f"Half Time: {ht['home']['goals']} - {ht['away']['goals']}")

# Display second half goals only
if '2ND_HALF_ONLY' in score_by_type:
    sh = score_by_type['2ND_HALF_ONLY']
    print(f"Second Half Goals: {sh['home']['goals']} - {sh['away']['goals']}")

# Analyze scoring patterns
def analyze_scoring_patterns(scores):
    """Analyze when goals were scored"""
    first_half = {'home': 0, 'away': 0}
    second_half = {'home': 0, 'away': 0}
    
    for score in scores:
        goals = score['score']['goals']
        participant = score['score']['participant']
        
        if score['description'] == '1ST_HALF':
            first_half[participant] = goals
        elif score['description'] == '2ND_HALF_ONLY':
            second_half[participant] = goals
    
    print("\nScoring Pattern Analysis:")
    print(f"Home team - 1st half: {first_half['home']}, 2nd half: {second_half['home']}")
    print(f"Away team - 1st half: {first_half['away']}, 2nd half: {second_half['away']}")

analyze_scoring_patterns(scores)
```

#### JavaScript example

```javascript
// API configuration
const API_TOKEN = "YOUR_TOKEN";
const FIXTURE_ID = 19424997;

// Request scores with nested includes
async function getFixtureScores() {
    const url = `https://api.sportmonks.com/v3/football/fixtures/${FIXTURE_ID}`;
    const params = new URLSearchParams({
        api_token: API_TOKEN,
        include: "scores.participant"
    });

    try {
        const response = await fetch(`${url}?${params}`);
        const data = await response.json();
        
        const scores = data.data.scores || [];
        
        // Parse scores by description type
        const scoreByType = {};
        scores.forEach(score => {
            const description = score.description;
            if (!scoreByType[description]) {
                scoreByType[description] = { home: null, away: null };
            }
            
            const participantType = score.score.participant;
            scoreByType[description][participantType] = {
                goals: score.score.goals,
                team: score.participant?.name || 'Unknown'
            };
        });
        
        // Display current score
        if (scoreByType['CURRENT']) {
            const current = scoreByType['CURRENT'];
            console.log(`Final Score: ${current.home.team} ${current.home.goals} - ${current.away.goals} ${current.away.team}`);
        }
        
        // Display half-time scores
        if (scoreByType['1ST_HALF']) {
            const ht = scoreByType['1ST_HALF'];
            console.log(`Half Time: ${ht.home.goals} - ${ht.away.goals}`);
        }
        
        // Display second half goals only
        if (scoreByType['2ND_HALF_ONLY']) {
            const sh = scoreByType['2ND_HALF_ONLY'];
            console.log(`Second Half Goals: ${sh.home.goals} - ${sh.away.goals}`);
        }
        
        // Analyze scoring patterns
        analyzeScoringPatterns(scores);
        
    } catch (error) {
        console.error("Error fetching scores:", error);
    }
}

function analyzeScoringPatterns(scores) {
    const firstHalf = { home: 0, away: 0 };
    const secondHalf = { home: 0, away: 0 };
    
    scores.forEach(score => {
        const goals = score.score.goals;
        const participant = score.score.participant;
        
        if (score.description === '1ST_HALF') {
            firstHalf[participant] = goals;
        } else if (score.description === '2ND_HALF_ONLY') {
            secondHalf[participant] = goals;
        }
    });
    
    console.log("\nScoring Pattern Analysis:");
    console.log(`Home team - 1st half: ${firstHalf.home}, 2nd half: ${secondHalf.home}`);
    console.log(`Away team - 1st half: ${firstHalf.away}, 2nd half: ${secondHalf.away}`);
}

// Display scores in a table format
function displayScoresTable(scores) {
    const table = document.createElement('table');
    table.innerHTML = `
        <thead>
            <tr>
                <th>Period</th>
                <th>Home</th>
                <th>Away</th>
            </tr>
        </thead>
        <tbody>
        </tbody>
    `;
    
    const tbody = table.querySelector('tbody');
    const scoreTypes = ['1ST_HALF', '2ND_HALF_ONLY', 'EXTRA_TIME', 'CURRENT'];
    
    scoreTypes.forEach(type => {
        const homeScore = scores.find(s => s.description === type && s.score.participant === 'home');
        const awayScore = scores.find(s => s.description === type && s.score.participant === 'away');
        
        if (homeScore && awayScore) {
            const row = tbody.insertRow();
            row.innerHTML = `
                <td>${type.replace(/_/g, ' ')}</td>
                <td>${homeScore.score.goals}</td>
                <td>${awayScore.score.goals}</td>
            `;
        }
    });
    
    document.body.appendChild(table);
}

// Run the example
getFixtureScores();
```

### Common use cases

#### 1. Live Score Display

Display live scores that automatically update with the most current match state:

```python
def format_live_score(scores):
    current = next((s for s in scores if s['description'] == 'CURRENT'), None)
    if not current:
        return "Score not available"
    
    home_score = next(s for s in scores if s['description'] == 'CURRENT' and s['score']['participant'] == 'home')
    away_score = next(s for s in scores if s['description'] == 'CURRENT' and s['score']['participant'] == 'away')
    
    return f"{home_score['score']['goals']} - {away_score['score']['goals']}"
```

#### 2. Half-time vs Full-time analysis

Compare first half and full-time scores to identify second-half comebacks:

```python
def check_comeback(scores):
    ht_home = next((s['score']['goals'] for s in scores if s['description'] == '1ST_HALF' and s['score']['participant'] == 'home'), 0)
    ht_away = next((s['score']['goals'] for s in scores if s['description'] == '1ST_HALF' and s['score']['participant'] == 'away'), 0)
    
    ft_home = next((s['score']['goals'] for s in scores if s['description'] == 'CURRENT' and s['score']['participant'] == 'home'), 0)
    ft_away = next((s['score']['goals'] for s in scores if s['description'] == 'CURRENT' and s['score']['participant'] == 'away'), 0)
    
    if ht_home > ht_away and ft_home < ft_away:
        return "Away team made a comeback!"
    elif ht_away > ht_home and ft_away < ft_home:
        return "Home team made a comeback!"
    else:
        return "No comeback occurred"
```

#### 3. Statistical analysis

Build datasets for machine learning or statistical analysis:

```python
def build_scoring_dataset(fixtures_with_scores):
    dataset = []
    for fixture in fixtures_with_scores:
        scores = fixture.get('scores', [])
        
        record = {
            'fixture_id': fixture['id'],
            'home_1st_half': 0,
            'away_1st_half': 0,
            'home_2nd_half': 0,
            'away_2nd_half': 0,
            'home_final': 0,
            'away_final': 0
        }
        
        for score in scores:
            desc = score['description']
            part = score['score']['participant']
            goals = score['score']['goals']
            
            if desc == '1ST_HALF':
                record[f'{part}_1st_half'] = goals
            elif desc == '2ND_HALF_ONLY':
                record[f'{part}_2nd_half'] = goals
            elif desc == 'CURRENT':
                record[f'{part}_final'] = goals
        
        dataset.append(record)
    
    return dataset
```

### Best practices

1. **Always use CURRENT for live updates**: Don't rely on calculating 1ST\_HALF + 2ND\_HALF, as extra time and penalties will make this incorrect.
2. **Check for extra time and penalties**: Before displaying results, check if `EXTRA_TIME` or `PENALTIES` descriptions exist.
3. **Use nested includes for complete data**: Include `scores.participant` to get team names and logos without additional API calls.
4. **Cache historical data**: Scores don't change after a match ends. Cache completed matches to reduce API calls.
5. **Handle missing data gracefully**: Not all matches have all score types immediately available during live matches.

### Related includes

* [**Participants**](https://docs.sportmonks.com/football/tutorials-and-guides/tutorials/includes/participants) - Get team information for the scoring teams
* [**Events**](https://docs.sportmonks.com/football/tutorials-and-guides/tutorials/includes/events) - See individual goal events with scorers
* [**Statistics**](https://docs.sportmonks.com/football/definitions/types/statistics) - Combine scores with match statistics for analysis
* [**Periods**](https://docs.sportmonks.com/football/tutorials-and-guides/tutorials/includes/periods) - Get timing information for when goals were scored

### Summary

The `scores` include provides comprehensive scoring data for all match periods including regular time, extra time, and penalties. With support for nested includes and clear score type descriptions, it enables accurate live score displays, statistical analysis, and historical score tracking. Always use the `CURRENT` description to display the most up-to-date score.
