<commit_before>import React from "react";
import Moment from "moment";
import PropTypes from "prop-types";
import { forEach, includes } from "lodash-es";

window.relativeTimeCallbacks = [];

window.setInterval(1000, () => {
    forEach(window.relativeTimeCallbacks, callback => callback());
});

/**
 * Shows the passed time prop relative to the current time (eg. 3 days ago). The relative time string is updates
 * automatically as time passes.
 */
export class RelativeTime extends React.Component {

    constructor (props) {
        super(props);
        this.state = {
            timeString: this.getTimeString()
        };
    }

    static propTypes = {
        time: PropTypes.string.isRequired
    };

    componentWillMount () {
        window.relativeTimeCallbacks.push(this.update);
    }

    componentWillReceiveProps (nextProps) {
        this.setState({time: nextProps.time});
    }

    shouldComponentUpdate (nextProps, nextState) {
        // Check if the time string changed. Only re-render if it has.
        return nextState !== this.state || nextProps !== this.props;
    }

    componentDidUpdate (prevProps) {
        // If the component gets a new timestamp, the time string must be immediately updated. When the component
        // updates, check the old and new props to see if the timestamp changes. Force a time string update, if props
        // did change.
        if (prevProps !== this.props) {
            this.update();
        }
    }

    componentWillUnmount () {
        const index = window.relativeTimeCallbacks.indexOf(this.update);

        if (index !== -1) {
            window.relativeTimeCallbacks.splice(index, 1);
        }
    }

    getTimeString = () => {
        // Make the time string using Moment.js
        const timeString = Moment(this.props.time).fromNow();

        // It is possible that the relative time could be in the future if the browser time lags behind the server time.
        // If this is the case the string will contain the substring 'in a'. If this substring is present, return the
        // alternative time string 'just now'.
        return includes(timeString, "in a") || includes(timeString, "a few") ? "just now" : timeString;
    };<commit_msg>Use per-component interval to update RelativeTime<commit_after>import React from "react";
import Moment from "moment";
import PropTypes from "prop-types";
import { includes } from "lodash-es";

/**
 * Shows the passed time prop relative to the current time (eg. 3 days ago). The relative time string is updated
 * automatically as time passes.
 */
export class RelativeTime extends React.Component {

    constructor (props) {
        super(props);
        this.state = {
            timeString: this.getTimeString()
        };
    }

    static propTypes = {
        time: PropTypes.string.isRequired
    };

    componentDidMount () {
        this.interval = window.setInterval(this.update, 8000);
    }

    componentWillReceiveProps (nextProps) {
        this.setState({time: nextProps.time});
    }

    shouldComponentUpdate (nextProps, nextState) {
        // Check if the time string changed. Only re-render if it has.
        return nextState !== this.state || nextProps !== this.props;
    }

    componentDidUpdate (prevProps) {
        // If the component gets a new timestamp, the time string must be immediately updated. When the component
        // updates, check the old and new props to see if the timestamp changes. Force a time string update, if props
        // did change.
        if (prevProps !== this.props) {
            this.update();
        }
    }

    componentWillUnmount () {
        window.clearInterval(this.interval);
    }

    getTimeString = () => {
        // Make the time string using Moment.js
        const timeString = Moment(this.props.time).fromNow();

        // It is possible that the relative time could be in the future if the browser time lags behind the server time.
        // If this is the case the string will contain the substring 'in a'. If this substring is present, return the
        // alternative time string 'just now'.
        return includes(timeString, "in a") || includes(timeString, "a few") ? "just now" : timeString;
    };
{'fraction_non_alphanumeric': 0.0991481306199716, 'fraction_numerical': 0.002839564600094652, 'mean_word_length': 2.564080944350759, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 7, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1191985', 'n_tokens_mistral': 1122, 'n_tokens_neox': 1084, 'n_words': 406}