public bool HandleFor(ForStatement node)
        {
            var iterable = Eval.GetValueFromExpression(node.List);
            var iterator = (iterable as IPythonIterable)?.GetIterator();
            var value    = iterator?.Next ?? Eval.UnknownType;

            switch (node.Left)
            {
            case NameExpression nex:
                // for x in y:
                if (!string.IsNullOrEmpty(nex.Name))
                {
                    Eval.DeclareVariable(nex.Name, value, VariableSource.Declaration, Eval.GetLoc(nex));
                }
                break;

            case TupleExpression tex:
                // x = [('abc', 42, True), ('abc', 23, False)]
                // for some_str, (some_int, some_bool) in x:
                var h = new TupleExpressionHandler(Walker);
                h.HandleTupleAssignment(tex, node.List, value);
                break;
            }

            node.Body?.Walk(Walker);
            return(false);
        }
        public async Task HandleAssignmentAsync(AssignmentStatement node, CancellationToken cancellationToken = default)
        {
            cancellationToken.ThrowIfCancellationRequested();
            var value = await Eval.GetValueFromExpressionAsync(node.Right, cancellationToken);

            if (value.IsUnknown())
            {
                Log?.Log(TraceEventType.Verbose, $"Undefined value: {node.Right.ToCodeString(Ast).Trim()}");
            }

            if (value?.GetPythonType().TypeId == BuiltinTypeId.Ellipsis)
            {
                value = Eval.UnknownType;
            }

            if (node.Left.FirstOrDefault() is TupleExpression lhs)
            {
                // Tuple = Tuple. Transfer values.
                var texHandler = new TupleExpressionHandler(Walker);
                await texHandler.HandleTupleAssignmentAsync(lhs, node.Right, value, cancellationToken);

                return;
            }
            foreach (var expr in node.Left.OfType <ExpressionWithAnnotation>())
            {
                // x: List[str] = [...]
                await HandleAnnotatedExpressionAsync(expr, value, cancellationToken);
            }

            foreach (var ne in node.Left.OfType <NameExpression>())
            {
                if (Eval.CurrentScope.NonLocals[ne.Name] != null)
                {
                    Eval.LookupNameInScopes(ne.Name, out var scope, LookupOptions.Nonlocal);
                    if (scope != null)
                    {
                        scope.Variables[ne.Name].Value = value;
                    }
                    else
                    {
                        // TODO: report variable is not declared in outer scopes.
                    }
                    continue;
                }

                if (Eval.CurrentScope.Globals[ne.Name] != null)
                {
                    Eval.LookupNameInScopes(ne.Name, out var scope, LookupOptions.Global);
                    if (scope != null)
                    {
                        scope.Variables[ne.Name].Value = value;
                    }
                    else
                    {
                        // TODO: report variable is not declared in global scope.
                    }
                    continue;
                }

                Eval.DeclareVariable(ne.Name, value, Eval.GetLoc(ne));
            }
        }
        public void HandleAssignment(AssignmentStatement node)
        {
            if (node.Right is ErrorExpression)
            {
                return;
            }

            var value = Eval.GetValueFromExpression(node.Right) ?? Eval.UnknownType;
            // Check PEP hint first
            var valueType = Eval.GetTypeFromPepHint(node.Right);

            if (valueType != null)
            {
                HandleTypedVariable(valueType, value, node.Left.FirstOrDefault());
                return;
            }

            if (value.IsUnknown())
            {
                Log?.Log(TraceEventType.Verbose, $"Undefined value: {node.Right.ToCodeString(Ast).Trim()}");
            }
            if (value?.GetPythonType().TypeId == BuiltinTypeId.Ellipsis)
            {
                value = Eval.UnknownType;
            }

            if (node.Left.FirstOrDefault() is TupleExpression lhs)
            {
                // Tuple = Tuple. Transfer values.
                var texHandler = new TupleExpressionHandler(Walker);
                texHandler.HandleTupleAssignment(lhs, node.Right, value);
                return;
            }

            // Process annotations, if any.
            foreach (var expr in node.Left.OfType <ExpressionWithAnnotation>())
            {
                // x: List[str] = [...]
                HandleAnnotatedExpression(expr, value);
            }

            foreach (var ne in node.Left.OfType <NameExpression>())
            {
                if (Eval.CurrentScope.NonLocals[ne.Name] != null)
                {
                    Eval.LookupNameInScopes(ne.Name, out var scope, LookupOptions.Nonlocal);
                    if (scope != null)
                    {
                        scope.Variables[ne.Name].Assign(value, Eval.GetLoc(ne));
                    }
                    else
                    {
                        // TODO: report variable is not declared in outer scopes.
                    }
                    continue;
                }

                if (Eval.CurrentScope.Globals[ne.Name] != null)
                {
                    Eval.LookupNameInScopes(ne.Name, out var scope, LookupOptions.Global);
                    if (scope != null)
                    {
                        scope.Variables[ne.Name].Assign(value, Eval.GetLoc(ne));
                    }
                    else
                    {
                        // TODO: report variable is not declared in global scope.
                    }
                    continue;
                }

                var source = value.IsGeneric() ? VariableSource.Generic : VariableSource.Declaration;
                Eval.DeclareVariable(ne.Name, value ?? Module.Interpreter.UnknownType, source, Eval.GetLoc(ne));
            }

            TryHandleClassVariable(node, value);
        }