lib/rules/no-loop-func.js
function isSafe(loopNode, reference) {
    const variable = reference.resolved;
    const definition = variable && variable.defs[0];
    const declaration = definition && definition.parent;
    const kind = (declaration && declaration.type === "VariableDeclaration")
        ? declaration.kind
        : "";

    // Variables which are declared by `const` is safe.
    if (kind === "const") {
        return true;
    }

    /*
     * Variables which are declared by `let` in the loop is safe.
     * It's a different instance from the next loop step's.
     */
    if (kind === "let" &&
        declaration.range[0] > loopNode.range[0] &&
        declaration.range[1] < loopNode.range[1]
    ) {
        return true;
    }

    /*
     * WriteReferences which exist after this border are unsafe because those
     * can modify the variable.
     */
    const border = getTopLoopNode(
        loopNode,
        (kind === "let") ? declaration : null
    ).range[0];

    /**
     * Checks whether a given reference is safe or not.
     * The reference is every reference of the upper scope's variable we are
     * looking now.
     *
     * It's safeafe if the reference matches one of the following condition.
     * - is readonly.
     * - doesn't exist inside a local function and after the border.
     *
     * @param {eslint-scope.Reference} upperRef - A reference to check.
     * @returns {boolean} `true` if the reference is safe.
     */
    function isSafeReference(upperRef) {
        const id = upperRef.identifier;

        return (
            !upperRef.isWrite() ||
            variable.scope.variableScope === upperRef.from.variableScope &&
            id.range[0] < border
        );
    }

    return Boolean(variable) && variable.references.every(isSafeReference);
}
function isSafe(loopNode, reference) {
    const variable = reference.resolved;
    const definition = variable && variable.defs[0];
    const declaration = definition && definition.parent;
    const kind = (declaration && declaration.type === "VariableDeclaration")
        ? declaration.kind
        : "";

    // Variables which are declared by `const` is safe.
    if (kind === "const") {
        return true;
    }

    /*
     * Variables which are declared by `let` in the loop is safe.
     * It's a different instance from the next loop step's.
     */
    if (kind === "let" &&
        declaration.range[0] > loopNode.range[0] &&
        declaration.range[1] < loopNode.range[1]
    ) {
        return true;
    }

    /*
     * WriteReferences which exist after this border are unsafe because those
     * can modify the variable.
     */
    const border = getTopLoopNode(
        loopNode,
        (kind === "let") ? declaration : null
    ).range[0];

    /**
     * Checks whether a given reference is safe or not.
     * The reference is every reference of the upper scope's variable we are
     * looking now.
     *
     * It's safeafe if the reference matches one of the following condition.
     * - is readonly.
     * - doesn't exist inside a local function and after the border.
     *
     * @param {eslint-scope.Reference} upperRef - A reference to check.
     * @returns {boolean} `true` if the reference is safe.
     */
    function isSafeReference(upperRef) {
        const id = upperRef.identifier;

        return (
            !upperRef.isWrite() ||
            variable.scope.variableScope === upperRef.from.variableScope &&
            id.range[0] < border
        );
    }

    return Boolean(variable) && variable.references.every(isSafeReference);
}
function isSafe ( loopNode , reference ) { const variable = reference . resolved ; const definition = variable && variable . defs [ 0 ] ; const declaration = definition && definition . parent ; const kind = ( declaration && declaration . type === "VariableDeclaration" ) ? declaration . kind : "" ; // Variables which are declared by `const` is safe. if ( kind === "const" ) { return true ; } /*
     * Variables which are declared by `let` in the loop is safe.
     * It's a different instance from the next loop step's.
     */ if ( kind === "let" && declaration . range [ 0 ] > loopNode . range [ 0 ] && declaration . range [ 1 ] < loopNode . range [ 1 ] ) { return true ; } /*
     * WriteReferences which exist after this border are unsafe because those
     * can modify the variable.
     */ const border = getTopLoopNode ( loopNode , ( kind === "let" ) ? declaration : null ) . range [ 0 ] ; /**
     * Checks whether a given reference is safe or not.
     * The reference is every reference of the upper scope's variable we are
     * looking now.
     *
     * It's safeafe if the reference matches one of the following condition.
     * - is readonly.
     * - doesn't exist inside a local function and after the border.
     *
     * @param {eslint-scope.Reference} upperRef - A reference to check.
     * @returns {boolean} `true` if the reference is safe.
     */ function isSafeReference ( upperRef ) { const id = upperRef . identifier ; return ( ! upperRef . isWrite ( ) || variable . scope . variableScope === upperRef . from . variableScope && id . range [ 0 ] < border ) ; } return Boolean ( variable ) && variable . references . every ( isSafeReference ) ; }
Checks whether a given reference which refers to an upper scope's variable is
safe or not.

@param {ASTNode} loopNode - A containing loop node.
@param {eslint-scope.Reference} reference - A reference to check.
@returns {boolean} `true` if the reference is safe or not.
Checks whether a given reference which refers to an upper scope s variable is safe or not .