<div class="match-score">
    <div class="match-score__goalscorers-left">
        <div class="goal-scorers " data-behaviour="home-team">
            <div class="goal-scorers__group player-scored">
                <ul>
                    <li>
                        <span class="scorer-firstname">Kane</span>Kane
                        <span class="goal-time">(4&prime;)</span>
                        <span class="goal-time">(63&prime;)</span>
                    </li>
                    <li>
                        <span class="scorer-firstname">Rashford</span>Rashford
                        <span class="goal-time">(23&prime; PEN)</span>
                    </li>
                </ul>
            </div>
            <div class="goal-scorers__group player-sent-off">
                <ul>
                    <li>
                        <span class="scorer-firstname">Mings</span>Mings
                        <span class="goal-time">(76&prime;)</span>
                    </li>
                </ul>
            </div>
            <div class="goal-scorers__group missed-a-penalty">
                <ul>
                    <li>
                        <span class="scorer-firstname">Mings</span>Mings
                        <span class="goal-time">(41&prime; MISSED PEN)</span>
                    </li>
                </ul>
            </div>
        </div>

    </div>
    <div class="match-score__scoreline">
        <div class="scoreline">
            <div class="scoreline__title">Full time</div>
            <div class="scoreline__tournament-name">National league group stage</div>
            <div class="scoreline__location"><span>Sat 31 March, 3pm</span> <span>Wembley stadium, England</span></div>
            <div class="scoreline__results">
                <div class="scoreline__team-crests">
                    <img src="/assets/example-content/team-badge-eng.png" alt="England" />
                </div>
                <div class="scoreline__team-goals" data-behaviour="team-goals-scored">
                    <div class="scoreline__team-goals--scored ">
                        <span>4</span>
                        <span>2</span>
                    </div>
                    <div class="scoreline__team-goals--time">
                        <span class="scoreline__team-goals--ht">HT: 2-2</span>
                        <span class="scoreline__team-goals--ft">FT: 2-3</span>
                    </div>
                </div>
                <div class="scoreline__team-crests">
                    <img src="/assets/example-content/team-badge-isl.png" alt="Iceland" />
                </div>
            </div>
            <div class="scoreline__final-result">England win 4 - 3 on penalties</div>
        </div>

    </div>
    <div class="match-score__goalscorers-right">
        <div class="goal-scorers  goal-scorers--invert " data-behaviour="away-team">
            <div class="goal-scorers__group player-scored">
                <ul>
                    <li>
                        <span class="scorer-firstname">Sterling</span>Sterling
                        <span class="goal-time">(19&prime;)</span>
                    </li>
                    <li>
                        <span class="scorer-firstname">Sterling</span>Sterling
                        <span class="goal-time">(46&prime;)</span>
                    </li>
                </ul>
            </div>
            <div class="goal-scorers__group player-sent-off">
                <ul>
                    <li>
                        <span class="scorer-firstname">Sterling</span>Sterling
                        <span class="goal-time">(65&prime;)</span>
                    </li>
                    <li class="yellowcard">
                        <span class="scorer-firstname">Sterling</span>Sterling
                        <span class="goal-time">(64&prime;)</span>
                    </li>
                    <li class="yellowredcard">
                        <span class="scorer-firstname">Sterling</span>Sterling
                        <span class="goal-time">(64&prime;)</span>
                    </li>
                </ul>
            </div>
        </div>

    </div>
</div>

No notes defined.

/* No context defined. */
  • Content:
    /* eslint-disable prettier/prettier */
    /* eslint-disable no-param-reassign */
    const headers = {
      'Ocp-Apim-Subscription-Key': '8279c7fab35f432daf1a0bd395a9ae48',
    };
    const POLL_TIMING = 1000 * 60; // per 1min.
    
    // utility to check empty object
    const isEmptyObject = obj => Object.keys(obj).length === 0 && obj.constructor === Object;
    
    // utility to group by for provided `key` on `array`
    const groupBy = (array, key) => {
      return array.reduce((objectsByKeyValue, obj) => {
        const value = obj[key];
    
        objectsByKeyValue[value] = (objectsByKeyValue[value] || []).concat(obj);
        return objectsByKeyValue;
      }, {});
    };
    
    async function fetchLiveScore(matchId) {
      // replace url with `/livescore/` in development to see results
      const url = `${window.location.origin}/LiveMatch/LiveMatchDetails?matchid=${matchId}`;
      // eslint-disable-next-line compat/compat
      const response = await fetch(url, {
        headers,
      });
    
      return response.json();
    };
    
    // will update home team scores (left section)
    const renderGoalScorerHomeTeam = ({
      goal,
      missedPen,
      card
    }, { home }) => {
      let markup = '';
    
      const homeGoals = groupBy(goal.filter(g => g.contestantId === home), 'scorerId');
      const homeCards = groupBy(card.filter(c => c.contestantId === home), 'playerId');
      const homeMissedPens = groupBy(missedPen.filter(p => p.contestantId === home && p.type === 'PM'), 'playerId');
    
      if (!isEmptyObject(homeGoals)) {
        markup += `<div class="goal-scorers__group player-scored">
          <ul>
            ${Object.keys(homeGoals)
              .map(scorerId => {
                return `
                <li>
                  <span class="scorer-firstname"></span>${homeGoals[scorerId][0].scorerName}
                  <span class="goal-time">
                    ${homeGoals[scorerId].map(hgScorer => {
                      const type = hgScorer.type !== 'G' ? hgScorer.type : '';
    
                      return `(${hgScorer.timeMin}&prime;${type})`;
                    }).join('\n')}
                  </span>
    
                </li>`;
              })
              .join('\n')}
          </ul>
        </div>`;
      }
    
      if (!isEmptyObject(homeCards)) {
        markup += `<div class="goal-scorers__group player-sent-off">
          <ul>
            ${Object.keys(homeCards)
              .map(playerId => {
                return homeCards[playerId].map((hcPlayer, index) => {
                  let clsName;
    
                  if (index === 0 && homeCards[playerId][index].type === 'YC') {
                    clsName = 'yellowcard';
                  } else if (index === 1 && homeCards[playerId][index].type === 'YC') {
                    clsName = 'yellowredcard';
                  } else {
                    clsName = '';
                  }
                return `
                <li class="${clsName}">
                  <span class="scorer-firstname"></span>${homeCards[playerId][0].playerName}
                  <span class="goal-time">
                    (${hcPlayer.timeMin}&prime;)                
                  </span>
                </li>`;
              }).join('\n')
              })
              .join('\n')}
          </ul>
        </div>`;
      }
    
      if(!isEmptyObject(homeMissedPens)) {
        markup += `<div class="goal-scorers__group missed-a-penalty">
          <ul>
          ${Object.keys(homeMissedPens)
            .map(playerId => {
              return `<li>
              <span class="scorer-firstname"></span>${homeMissedPens[playerId][0].playerName}
              <span class="goal-time">
                ${homeMissedPens[playerId].map(player => {
                  return `(${player.timeMin}&prime; MISSED PEN)`;
                }).join('\n')}
              </span>
            </li>`;
            })
            .join('\n')}
          </ul>
        </div>`;
      }
    
      return markup;
    };
    
    // will update away team scores (right section)
    const renderGoalScorerAwayTeam = ({
      goal,
      missedPen,
      card
    }, { away }) => {
      let markup = '';
    
      const awayGoals = groupBy(goal.filter(g => g.contestantId === away), 'scorerId');
      const awayCards = groupBy(card.filter(c => c.contestantId === away), 'playerId');
      const awayMissedPens = groupBy(missedPen.filter(p => p.contestantId === away && p.type === 'PM'), 'playerId');
    
      if (!isEmptyObject(awayGoals)) {
        markup += `<div class="goal-scorers__group player-scored">
          <ul>
            ${Object.keys(awayGoals)
            .map(scorerId => {
              return `
                <li>
                  <span class="scorer-firstname"></span>${awayGoals[scorerId][0].scorerName}
                  <span class="goal-time">
                    ${awayGoals[scorerId].map(hgScorer => {
                      const type = hgScorer.type !== 'G' ? hgScorer.type : '';
    
                      return `(${hgScorer.timeMin}&prime;${type})`
                    }).join('\n')}
                  </span>
    
                </li>`;
            })
            .join('\n')}
          </ul>
        </div>`;
      }
    
      if (!isEmptyObject(awayCards)) {
        markup += `<div class="goal-scorers__group player-sent-off">
          <ul>
            ${Object.keys(awayCards)
            .map(playerId => {          
              return awayCards[playerId].map((hcPlayer, index) => {
                let clsName;
    
                if (index === 0 && awayCards[playerId][index].type === 'YC') {
                  clsName = 'yellowcard';
                } else if (index === 1 && awayCards[playerId][index].type === 'YC') {
                  clsName = 'yellowredcard';
                } else {
                  clsName = '';
                }
    
              return `
                <li class="${clsName}">
                  <span class="scorer-firstname"></span>${awayCards[playerId][0].playerName}
                  <span class="goal-time">
                  (${hcPlayer.timeMin}&prime;)                
                  </span>
                </li>`;
              }).join('\n')
            })
            .join('\n')}
          </ul>
        </div>`;
      }
    
      if (!isEmptyObject(awayMissedPens)) {
        markup += `<div class="goal-scorers__group missed-a-penalty">
          <ul>
          ${Object.keys(awayMissedPens)
            .map(playerId => {
              return `<li>
              <span class="scorer-firstname"></span>${awayMissedPens[playerId][0].playerName}
              <span class="goal-time">
                ${awayMissedPens[playerId].map(player => {
                  return `(${player.timeMin}&prime; MISSED PEN)`;
                }).join('\n')}
              </span>
            </li>`;
            })
            .join('\n')}
          </ul>
        </div>`;
      }
    
      return markup;
    };
    
    // will update middle section
    const renderScoreLineTeamGoals = ({
      matchDetails: {scores}
    }) => {
      const {ft, ht, et } = scores;
      const markup = `
        <div class="scoreline__team-goals--scored scoreline__team-goals--live-score">
          ${ft && !isEmptyObject(ft) ? `<span>${scores.ft.home}</span><span>${scores.ft.away}</span>` : ``}
        </div>
        <div class="scoreline__team-goals--time">
          ${ht && !isEmptyObject(ht) ? `<span class='scoreline__team-goals--ht'> HT: ${ht.home}-${ht.away} </span>` : ``}
          ${et && !isEmptyObject(et) ? `<span class='scoreline__team-goals--ft'> FT: ${et.home}-${et.away} </span>` : ``}
        </div>
      `;
    
      return markup;
    };
    
    // entry point for content update
    const updateContent = (parentEl, liveData, contestantIds) => {
      const {
        matchDetails: {matchLengthMin},
      } = liveData;
    
      // 1. update minutes / match length
      parentEl.querySelector(
        '[data-behaviour="match-length"]'
      ).innerHTML = matchLengthMin;
    
      // 2. updates the current score and half time/ full time score
      parentEl.querySelector(
        '[data-behaviour="team-goals-scored"]'
      ).innerHTML = renderScoreLineTeamGoals(liveData);
    
      // 3. update home team goal score
      parentEl.querySelector(
        '[data-behaviour=home-team]'
      ).innerHTML = renderGoalScorerHomeTeam(liveData, contestantIds);
    
      // 4. update away team goal score
      parentEl.querySelector(
        '[data-behaviour=away-team]'
      ).innerHTML = renderGoalScorerAwayTeam(liveData, contestantIds);
    };
    
    // forms an object with key as `team` and value as `contestant id`
    const getContestandIdsByTeam = contestants => {
      const result = {};
    
      contestants.forEach(contestant => {
        result[contestant.position] = contestant.id;
      });
    
      return result;
    }
    
    export default parentEl => {
      const { matchId } = parentEl.dataset;
    
      if (!matchId) {
        throw new Error('invalid match id');
      }
    
      try {
        const intervalId = setInterval(() => {
          fetchLiveScore(matchId).then(response => {
            if (!Object.keys(response).length) {
              // stop if there is no response
              // do we need a refresh?
    
              clearInterval(intervalId);
              return;
            }
            const { matchInfo: { contestant }, liveData } = response;
            const contestantIds = getContestandIdsByTeam(contestant);
    
            updateContent(parentEl, liveData, contestantIds);
          });
        }, POLL_TIMING);
      } catch (e) {
        throw new Error('Uable to retrive match score ::', e);
      }
    };
    
  • URL: /components/raw/match-score/match-score.js
  • Filesystem Path: src/library/modules/match-score/match-score.js
  • Size: 8.7 KB
  • Content:
    .match-score {
      display: grid;
      grid-gap: 2rem;
      margin-bottom: 3rem;
      transform: translateY(-3rem);
      position: relative;
      &__scoreline {
        background: $white;
        border-radius: 0.8rem;
        padding-top: 1.6rem;
      }
    
      @media (max-width: $mq-medium) {
        grid-template-areas:
          'middle middle'
          'left right';
        &__goalscorers-left {
          grid-area: left;
        }
        &__scoreline {
          grid-row: 1;
          grid-area: middle;
          margin: 0 0.8rem;
        }
        &__goalscorers-right {
          grid-area: right;
        }
      }
    
      @media (min-width: $mq-medium) {
        display: grid;
        grid-template-columns: 1fr 1.5fr 1fr;
        margin: 0 auto;
        margin-bottom: 3rem;
    
        &__goalscorers-left {
          margin-top: 3rem;
          padding-top: 2rem;
        }
        &__goalscorers-right {
          margin-top: 3rem;
          padding-top: 2rem;
        }
      }
    
      @media (min-width: $mq-large) {
        grid-template-columns: 1fr 2fr 1fr;
      }
    }
    
  • URL: /components/raw/match-score/match-score.scss
  • Filesystem Path: src/library/modules/match-score/match-score.scss
  • Size: 927 Bytes
<div class="match-score" {{#if liveScore}} data-behaviour='match-score-live' data-match-id="{{matchId}}" {{/if}}>
    <div class="match-score__goalscorers-left">
      {{render '@goal-scorers'}}
    </div>
    <div class="match-score__scoreline">
      {{#unless liveScore}}
        {{render '@scoreline'}}
      {{else}}
        {{render '@scoreline--live-score' this merge="true"}}
      {{/unless}}
    </div>
    <div class="match-score__goalscorers-right">
      {{render '@goal-scorers--invert'}}
    </div>
</div>