text:
using ClosedXML.Excel.CalcEngine.Exceptions;
using Irony.Ast;
using Irony.Parsing;
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using XLParser;

namespace ClosedXML.Excel.CalcEngine
{
    /// <summary>
    /// A parser that takes a string and parses it into concrete syntax tree through XLParser and then
    /// to abstract syntax tree that is used to evaluate the formula.
    /// </summary>
    internal class FormulaParser
    {
        /// <summary>
        /// A prefix is that is used for functions that are present in a version of Excel, but aren't present in older versions.
        /// </summary>
        /// <example>
        /// If you write <c>CONCAT(A1,B1)</c> in Excel 2021 (not present in Excel 2013), it is saved to the worksheet file as
        /// <c>_xlfn.CONCAT(A1,B1)</c>, but the Excel GUI will show only <c>CONCAT(A1,B1)</c>, without the <c>_xlfn</c>.
        /// </example>
        private const string DefaultFunctionNameSpace = "_xlfn";

        // Names for unary/binary op terms don't have a const names in the grammar
        private static readonly Dictionary<string, UnaryOp> PrefixOpMap = new(StringComparer.Ordinal)
        {
            {  "+", UnaryOp.Add },
            {  "-", UnaryOp.Subtract },
            {  "@", UnaryOp.ImplicitIntersection }
        };

        private static readonly Dictionary<string, BinaryOp> BinaryOpMap = new(StringComparer.Ordinal)
        {
            { "^", BinaryOp.Exp },
            { "*", BinaryOp.Mult },
            { "/", BinaryOp.Div },
            { "+", BinaryOp.Add },
            { "-", BinaryOp.Sub },
            { "&", BinaryOp.Concat },
            { ">", BinaryOp.Gt },
            { "=", BinaryOp.Eq },
            { "<", BinaryOp.Lt },
            { "<>", BinaryOp.Neq },
            { ">=", BinaryOp.Gte },
            { "<=", BinaryOp.Lte },
        };

        private static readonly Dictionary<string, XLError> ErrorMap = new(StringComparer.OrdinalIgnoreCase)
        {
            ["#REF!"] = XLError.CellReference,
            ["#VALUE!"] = XLError.IncompatibleValue,
            ["#DIV/0!"] = XLError.DivisionByZero,
            ["#NAME?"] = XLError.NameNotRecognized,
            ["#N/A"] = XLError.NoValueAvailable,
            ["#NULL!"] = XLError.NullValue,
            ["#NUM!"] = XLError.NumberInvalid
        };

        private static readonly Dictionary<string, ReferenceItemType> RangeTermMap = new(StringComparer.Ordinal)
        {
            { GrammarNames.Cell, ReferenceItemType.Cell },
            { GrammarNames.VerticalRange, ReferenceItemType.VRange },
            { GrammarNames.HorizontalRange, ReferenceItemType.HRange }
        };

        private static readonly Func<AstNode, bool> IsErrorNode = static node => node is ScalarNode scalarNode && scalarNode.Value.TryPickError(out _);

        private readonly Parser _parser;
        private readonly FunctionRegistry _fnTbl;

        public FormulaParser(FunctionRegistry functionRegistry)
        {
            _parser = new Parser(GetGrammar());
            _fnTbl = functionRegistry;
        }

        internal ParseTree ParseCst(string formulaText)
        {
            try
            {
                return _parser.Parse(formulaText);
            }
            catch (NullReferenceException ex) when (ex.StackTrace.StartsWith("   at Irony.Ast.AstBuilder.BuildAst(ParseTreeNode parseNode)"))
            {
                throw new InvalidOperationException($"Unable to parse formula '{formulaText}'. Some Irony grammar term is missing AST configuration.");
            }
        }

        /// <summary>
        /// Parse a tree into a CSt that also has AST.
        /// </summary>
        public Formula ConvertToAst(ParseTree cst)
        {
            var astContext = new AstContext(_parser.Language);
            if (cst.HasErrors())
                throw new ExpressionParseException($"Unable to parse formula '{cst.SourceText}':\n" + string.Join("\n", cst.ParserMessages.Select(c => $"Location {c.Location.Line}:{c.Location.Column} - {c.Message}")));

            var astBuilder = new AstBuilder(astContext);
            astBuilder.BuildAst(cst);
            var root = (ValueNode)cst.Root.AstNode ?? throw new InvalidOperationException("Formula doesn't have AST root.");

            var flags = astContext.Values.ContainsKey(FormulaFlags.HasSubtotal)
                ? FormulaFlags.HasSubtotal
                : FormulaFlags.None;
            return new Formula(cst.SourceText, root, flags);
        }

        private ExcelFormulaGrammar GetGrammar()
        {
            var grammar = new ExcelFormulaGrammar();
            grammar.FormulaWithEq.AstConfig.NodeCreator = CreateCopyNode(1);
            grammar.Formula.AstConfig.NodeCreator = CreateCopyNode(0);
            grammar.ArrayFormula.AstConfig.NodeCreator = CreateNotImplementedNode("array formula");
            grammar.ArrayFormula.SetFlag(TermFlags.AstDelayChildren);
            grammar.ReservedName.AstConfig.NodeCreator = CreateNotImplementedNode("reserved name");
            grammar.ReservedName.SetFlag(TermFlags.AstDelayChildren);

            grammar.MultiRangeFormula.AstConfig.NodeCreator = CreateCopyNode(1);
            grammar.Union.AstConfig.NodeCreator = CreateUnionNode;
            grammar.intersectop.SetFlag(TermFlags.NoAstNode);

            grammar.Constant.AstConfig.NodeCreator = CreateCopyNode(0);
            grammar.Number.AstConfig.NodeCreator = CreateNumberNode;
            grammar.Number.SetFlag(TermFlags.AstDelayChildren);
            grammar.Bool.AstConfig.NodeCreator = CreateBoolNode;
            grammar.Bool.SetFlag(TermFlags.AstDelayChildren);
            grammar.Text.AstConfig.NodeCreator = CreateTextNode;
            grammar.Text.SetFlag(TermFlags.AstDelayChildren);
            grammar.Error.AstConfig.NodeCreator = CreateErrorNode;
            grammar.Error.SetFlag(TermFlags.AstDelayChildren);
            grammar.RefError.AstConfig.NodeCreator = CreateErrorNode;
            grammar.RefError.SetFlag(TermFlags.AstDelayChildren);
            grammar.ConstantArray.AstConfig.NodeCreator = CreateNotImplementedNode("constant array");
            grammar.ConstantArray.SetFlag(TermFlags.AstDelayChildren);

            grammar.FunctionCall.AstConfig.NodeCreator = GetFunctionCallNodeFactory();
            grammar.FunctionName.SetFlag(TermFlags.NoAstNode);
            grammar.Arguments.AstConfig.NodeCreator = (_, _) => { }; // Irony shouldn't throw if no factory exist, but it does = use empty factory.
            grammar.Argument.AstConfig.NodeCreator = CreateCopyNode(0);
            grammar.EmptyArgument.AstConfig.NodeCreator = CreateEmptyArgumentNode;
            grammar.EmptyArgument.SetFlag(TermFlags.AstDelayChildren);

            grammar.Reference.AstConfig.NodeCreator = CreateReferenceNodeFactory();

            // ReferenceItem term is transient - ReferenceNode will create AST nodes for Cell..HRange.
            grammar.Cell.SetFlag(TermFlags.NoAstNode);
            grammar.NamedRange.SetFlag(TermFlags.NoAstNode);
            grammar.VRange.SetFlag(TermFlags.NoAstNode);
            grammar.HRange.SetFlag(TermFlags.NoAstNode);
            grammar.UDFunctionCall.AstConfig.NodeCreator = CreateUDFunctionNode;
            grammar.UDFName.SetFlag(TermFlags.NoAstNode);
            grammar.StructuredReference.AstConfig.NodeCreator = CreateStructuredReferenceNode;
            grammar.StructuredReference.SetFlag(TermFlags.AstDelayChildren);

            grammar.ReferenceFunctionCall.AstConfig.NodeCreator = CreateReferenceFunctionCallNodeFactory();
            grammar.RefFunctionName.SetFlag(TermFlags.NoAstNode);

            // DDE formula parsing in XLParser seems to be buggy. It can't parse any 'in-the-wild' examples I have found.
            grammar.DynamicDataExchange.AstConfig.NodeCreator = CreateNotImplementedNode("dynamic data exchange");
            grammar.DynamicDataExchange.SetFlag(TermFlags.AstDelayChildren);

            grammar.Prefix.AstConfig.NodeCreator = GetPrefixNodeCreator();
            grammar.SheetToken.SetFlag(TermFlags.NoAstNode);
            grammar.SheetQuotedToken.SetFlag(TermFlags.NoAstNode);
            grammar.MultipleSheetsToken.SetFlag(TermFlags.NoAstNode);
            grammar.MultipleSheetsQuotedToken.SetFlag(TermFlags.NoAstNode);

            grammar.File.AstConfig.NodeCreator = CreateFileNodeFactory();
            grammar.File.SetFlag(TermFlags.AstDelayChildren);

            return grammar;
        }

        private void CreateNumberNode(AstContext context, ParseTreeNode parseNode)
        {
            var value = parseNode.ChildNodes.Single().Token.Value;
            parseNode.AstNode = new ScalarNode(value is int intValue ? (double)intValue : (double)value);
        }

        private void CreateBoolNode(AstContext context, ParseTreeNode parseNode)
        {
            var boolValue = string.Equals(parseNode.ChildNodes.Single().Token.Text, "TRUE", StringComparison.OrdinalIgnoreCase);
            parseNode.AstNode = new ScalarNode(boolValue);
        }

        private void CreateTextNode(AstContext context, ParseTreeNode parseNode)
        {
            parseNode.AstNode = new ScalarNode(parseNode.ChildNodes.Single().Token.ValueString);
        }

        private void CreateErrorNode(AstContext context, ParseTreeNode parseNode)
        {
            var errorType = ErrorMap[parseNode.ChildNodes.Single().Token.Text];
            parseNode.AstNode = new ScalarNode(errorType);
        }

        private AstNodeFactory GetFunctionCallNodeFactory()
        {
            return new()
            {
                {
                    For(PrefixOpMap.Keys.ToArray(), GrammarNames.Formula),
                    node => new UnaryNode(PrefixOpMap[node.ChildNodes[0].Term.Name], (ValueNode)node.ChildNodes[1].AstNode)
                },
                {
                    For(GrammarNames.Formula, "%"),
                    node => new UnaryNode(UnaryOp.Percentage, (ValueNode)node.ChildNodes[0].AstNode)
                },
                {
                    For(GrammarNames.FunctionName, GrammarNames.Arguments),
                    (node, ctx) => CreateExcelFunctionCallExpression(ctx, node.ChildNodes[0], node.ChildNodes[1])
                },
                {
                    For(GrammarNames.Formula, BinaryOpMap.Keys.ToArray(), GrammarNames.Formula),
                    node => new BinaryNode(BinaryOpMap[node.ChildNodes[1].Term.Name], (ValueNode)node.ChildNodes[0].AstNode, (ValueNode)node.ChildNodes[2].AstNode)
                }
            };
        }

        /// <summary>
        /// Reference AST node is significantly different from CST node. It takes Reference, ReferenceFunctionCall and ReferenceItem terms into a reference value
        /// that represent an area of a workbook (ReferenceNode, StructuredReferenceNode) and operations over these areas (BinaryOperation, UnaryOperation, FunctionExpression).
        /// </summary>
        private AstNodeFactory CreateReferenceNodeFactory()
        {
            return new()
            {
                {
                    // ReferenceItem is transient, so its rules are basically merged with Reference - Cell, NamedRange, VRange, HRange
                    For(new[] { GrammarNames.Cell, GrammarNames.VerticalRange, GrammarNames.HorizontalRange }),
                    node => new ReferenceNode(null, RangeTermMap[node.ChildNodes[0].Term.Name], node.ChildNodes[0].ChildNodes.Single().Token.Text)
                },
                {
                    // Named range can be NameToken or NamedRangeCombinationToken. The combination token is there only to detect names like A1A1.
                    For(GrammarNames.NamedRange),
                    node => new NameNode(null, node.ChildNodes[0].ChildNodes.Single().Token.Text)
                },
                {
                    // ReferenceItem:RefError. #REF! error is not grouped with other errors, but is a part of Reference term.
                    For(IsErrorNode),
                    node => (ScalarNode)node.ChildNodes[0].AstNode
                },
                {
                    // ReferenceItem:UDFunctionCall
                    For(GrammarNames.UDFunctionCall),
                    node =>
                    {
                        var fn = (FunctionNode)node.ChildNodes[0].AstNode;
                        return new FunctionNode(null, fn.Name, fn.Parameters);
                    }
                },
                {
                    // ReferenceItem:StructuredReference. TODO: Copy structured reference once implemented
                    For(GrammarNames.StructuredReference),
                    node => new StructuredReferenceNode(null)
                },
                {
                    // ReferenceFunctionCall - Reference + colon + Reference
                    // ReferenceFunctionCall - Reference + intersectop + Reference
                    // ReferenceFunctionCall - Reference + Union + Reference
                    For(typeof(BinaryNode)),
                    node => (BinaryNode)node.ChildNodes[0].AstNode
                },
                {
                    // ReferenceFunctionCall - RefFunctionName + Arguments + CloseParen
                    For(typeof(FunctionNode)),
                    node => (FunctionNode)node.ChildNodes[0].AstNode
                },
                {
                    // ReferenceFunctionCall - Reference + hash
                    For(typeof(UnaryNode)),
                    node => (UnaryNode)node.ChildNodes[0].AstNode
                },
                {
                    // OpenParen + Reference + CloseParen
                    For(typeof(ReferenceNode)),
                    node => (ReferenceNode)node.ChildNodes[0].AstNode
                },
                {
                    // Prefix + ReferenceItem:Cell|NamedRange|VRange|HRange
                    // Split into two branches, because named range is not actually range, but an alias for a formula
                    For(typeof(PrefixNode), new[] { GrammarNames.Cell, GrammarNames.VerticalRange, GrammarNames.HorizontalRange }),
                    node => new ReferenceNode((PrefixNode)node.ChildNodes[0].AstNode, RangeTermMap[node.ChildNodes[1].Term.Name], node.ChildNodes[1].ChildNodes.Single().Token.Text)
                },
                {
                    // Prefix + ReferenceItem:Cell|NamedRange|VRange|HRange
                    For(typeof(PrefixNode), GrammarNames.NamedRange),
                    node => new NameNode((PrefixNode)node.ChildNodes[0].AstNode, node.ChildNodes[1].ChildNodes.Single().Token.Text)
                },
                {
                    // Prefix + ReferenceItem:RefError
                    For(typeof(PrefixNode), IsErrorNode),
                    node =>
                    {
                        // I think =#REF!#REF! was evaluated to #REF! in Excel 2021.
                        return (ScalarNode)node.ChildNodes[1].AstNode;
                    }
                },
                {
                    // Prefix + ReferenceItem:UDFunctionCall
                    For(typeof(PrefixNode), GrammarNames.UDFunctionCall),
                    node =>
                    {
                        var prefix = (PrefixNode)node.ChildNodes[0].AstNode;
                        var fn = (FunctionNode)node.ChildNodes[1].AstNode;
                        return new FunctionNode(prefix, fn.Name, fn.Parameters);
                    }
                },
                {
                    // Prefix + ReferenceItem:StructuredReference. TODO: Copy structured reference once implemented
                    For(typeof(PrefixNode), GrammarNames.StructuredReference),
                    node => new StructuredReferenceNode(null)
                },
                {
                    For(GrammarNames.DynamicDataExchange),
                    node => new NotSupportedNode("dynamic data exchange")
                }
            };
        }

        // AST node created by this factory is mostly just copied upwards in the ReferenceNode factory.
        private AstNodeFactory CreateReferenceFunctionCallNodeFactory()
        {
            return new()
            {
                {
                    For(GrammarNames.Reference, ":", GrammarNames.Reference),
                    node => new BinaryNode(BinaryOp.Range, (ValueNode)node.ChildNodes[0].AstNode, (ValueNode)node.ChildNodes[2].AstNode)
                },
                {
                    For(GrammarNames.Reference, GrammarNames.TokenIntersect, GrammarNames.Reference),
                    node => new BinaryNode(BinaryOp.Intersection, (ValueNode)node.ChildNodes[0].AstNode, (ValueNode)node.ChildNodes[2].AstNode)
                },
                {
                    For(GrammarNames.Union),
                    node => (ValueNode)node.ChildNodes.Single().AstNode
                },
                {
                    For(GrammarNames.RefFunctionName, GrammarNames.Arguments),
                    (node, ctx) => CreateExcelFunctionCallExpression(ctx, node.ChildNodes[0], node.ChildNodes[1])
                },
                {
                    For(GrammarNames.Reference, "#"),
                    node => new UnaryNode(UnaryOp.SpillRange, (ValueNode)node.ChildNodes[0].AstNode)
                }
            };
        }

        private AstNodeFactory GetPrefixNodeCreator()
        {
            return new()
            {
                {
                    For(GrammarNames.TokenSheet),
                    node =>
                    {
                        var sheetName = RemoveExclamationMark(node.ChildNodes[0].Token.Text);
                        return new PrefixNode(null, sheetName, null, null);
                    }
                },
                {
                    For("'", GrammarNames.TokenSheetQuoted),
                    node =>
                    {
                        var quotedSheetName = RemoveExclamationMark("'" + node.ChildNodes[1].Token.Text);
                        return new PrefixNode(null, quotedSheetName.UnescapeSheetName(), null, null);
                    }
                },
                {
                    For(typeof(FileNode), GrammarNames.TokenSheet),
                    node =>
                    {
                        var fileNode = (FileNode)node.ChildNodes[0].AstNode;
                        var sheetName = RemoveExclamationMark(node.ChildNodes[1].Token.Text);
                        return new PrefixNode(fileNode, sheetName, null, null);
                    }
                },
                {
                    For("'", typeof(FileNode), GrammarNames.TokenSheetQuoted),
                    node =>
                    {
                        var fileNode = (FileNode)node.ChildNodes[1].AstNode;
                        var quotedSheetName = RemoveExclamationMark("'" + node.ChildNodes[2].Token.Text);
                        return new PrefixNode(fileNode, quotedSheetName.UnescapeSheetName(), null, null);
                    }
                },
                {
                    For(typeof(FileNode), "!"),
                    node =>
                    {
                        var fileNode = (FileNode)node.ChildNodes[0].AstNode;
                        return new PrefixNode(fileNode, null, null, null);
                    }
                },
                {
                    For(GrammarNames.TokenMultipleSheets),
                    node =>
                    {
                        var normalSheets = RemoveExclamationMark(node.ChildNodes[0].Token.Text).Split(':');
                        return new PrefixNode(null, null, normalSheets[0], normalSheets[1]);
                    }
                },
                {
                    For("'", GrammarNames.TokenMultipleSheetsQuoted),
                    node =>
                    {
                        var quotedSheets = RemoveExclamationMark(("'" + node.ChildNodes[1].Token.Text).UnescapeSheetName()).Split(':');
                        return new PrefixNode(null, null, quotedSheets[0], quotedSheets[1]);
                    }
                },
                {
                    For(typeof(FileNode), GrammarNames.TokenMultipleSheets),
                    node =>
                    {
                        var fileNode = (FileNode)node.ChildNodes[0].AstNode;
                        var normalSheets = RemoveExclamationMark(node.ChildNodes[1].Token.Text).Split(':');
                        return new PrefixNode(fileNode, null, normalSheets[0], normalSheets[1]);
                    }
                },
                {
                    For("'", typeof(FileNode), GrammarNames.TokenMultipleSheetsQuoted),
                    node =>
                    {
                        var fileNode = (FileNode)node.ChildNodes[1].AstNode;
                        var quotedSheets = RemoveExclamationMark(("'" + node.ChildNodes[2].Token.Text).UnescapeSheetName()).Split(':');
                        return new PrefixNode(fileNode, null, quotedSheets[0], quotedSheets[1]);
                    }
                },
                {
                    For(GrammarNames.TokenRefError),
                    node =>
                    {
                        // #REF! is a valid sheet name, Token.ValueString is lower case for some reason.
                        return new PrefixNode(null, RemoveExclamationMark(node.ChildNodes[0].Token.Text), null, null);
                    }
                }
            };
        }

        private AstNodeFactory CreateFileNodeFactory()
        {
            return new()
            {
                {
                    For(GrammarNames.TokenFileNameNumeric),
                    node =>
                    {
                        var numberInBrackets = node.ChildNodes[0].Token.Text;
                        var fileNumericIndex = int.Parse(StripBrackets(numberInBrackets), NumberStyles.None);
                        return new FileNode(fileNumericIndex);
                    }
                },
                {
                    For(GrammarNames.TokenFileNameEnclosedInBrackets),
                    node => new FileNode(node.ChildNodes[0].Token.Text)
                },
                {
                    For(GrammarNames.TokenFilePath, GrammarNames.TokenFileNameEnclosedInBrackets),
                    node =>
                    {
                        var filePath = node.ChildNodes[0].Token.Text;
                        var fileName = node.ChildNodes[1].Token.Text;
                        return new FileNode(System.IO.Path.Combine(filePath, StripBrackets(fileName)));
                    }
                },
                {
                    For(GrammarNames.TokenFilePath, GrammarNames.TokenFileName),
                    node =>
                    {
                        var filePath = node.ChildNodes[0].Token.Text;
                        var fileName = node.ChildNodes[1].Token.Text;
                        return new FileNode(System.IO.Path.Combine(filePath, fileName));
                    }
                }
            };
        }

        private void CreateUDFunctionNode(AstContext context, ParseTreeNode parseNode)
        {
            var functionName = parseNode.ChildNodes[0].ChildNodes.Single().Token.Text.WithoutLast(1);

            if (functionName.StartsWith($"{DefaultFunctionNameSpace}."))
            {
                parseNode.AstNode = CreateExcelFunctionCallExpression(context, parseNode.ChildNodes[0], parseNode.ChildNodes[1]);
                return;
            }

            var arguments = parseNode.ChildNodes[1].ChildNodes.Select(treeNode => treeNode.AstNode).Cast<ValueNode>().ToList();
            parseNode.AstNode = new FunctionNode(functionName, arguments); ;
        }

        private FunctionNode CreateExcelFunctionCallExpression(AstContext ctx, ParseTreeNode nameNode, ParseTreeNode argumentsNode)
        {
            var functionName = nameNode.ChildNodes.Single().Token.Text.WithoutLast(1);
            var foundFunction = _fnTbl.TryGetFunc(functionName, out var parmMin, out var parmMax);
            if (!foundFunction && functionName.StartsWith($"{DefaultFunctionNameSpace}."))
            {
                functionName = functionName.Substring(DefaultFunctionNameSpace.Length + 1);
                foundFunction = _fnTbl.TryGetFunc(functionName, out parmMin, out parmMax);
            }

            if (!foundFunction)
                throw new NameNotRecognizedException($"The function `{functionName}` was not recognised.");

            var arguments = argumentsNode.ChildNodes.Select(treeNode => treeNode.AstNode).Cast<ValueNode>().ToList();
            if (parmMin != -1 && arguments.Count < parmMin)
                throw new ExpressionParseException($"Too few parameters for function '{functionName}'. Expected a minimum of {parmMin} and a maximum of {parmMax}.");

            if (parmMax != -1 && arguments.Count > parmMax)
                throw new ExpressionParseException($"Too many parameters for function '{functionName}'.Expected a minimum of {parmMin} and a maximum of {parmMax}.");

            if (string.Equals(functionName, @"SUBTOTAL", StringComparison.OrdinalIgnoreCase))
                ctx.Values[FormulaFlags.HasSubtotal] = true;

            return new FunctionNode(functionName, arguments);
        }

        private static AstNodeCreator CreateCopyNode(int childIndex)
        {
            return (context, parseNode) =>
            {
                var copyNode = parseNode.ChildNodes[childIndex];
                parseNode.AstNode = copyNode.AstNode;
            };
        }

        private static AstNodeCreator CreateNotImplementedNode(string featureText)
        {
            return (_, parseNode) => parseNode.AstNode = new NotSupportedNode(featureText);
        }

        private void CreateUnionNode(AstContext context, ParseTreeNode parseNode)
        {
            var unionRangeNode = (ValueNode)parseNode.ChildNodes[0].AstNode;
            foreach (var referenceNode in parseNode.ChildNodes.Skip(1))
                unionRangeNode = new BinaryNode(BinaryOp.Union, unionRangeNode, (ValueNode)referenceNode.AstNode);
            parseNode.AstNode = unionRangeNode;
        }

        private void CreateEmptyArgumentNode(AstContext context, ParseTreeNode parseNode)
        {
            parseNode.AstNode = new ScalarNode(ScalarValue.Blank);
        }

        public void CreateStructuredReferenceNode(AstContext context, ParseTreeNode parseNode)
        {
            parseNode.AstNode = new StructuredReferenceNode(null);
        }

        private static string RemoveExclamationMark(string sheetName)
        {
            if (!sheetName.EndsWith("!"))
                throw new ArgumentException($"'{sheetName}' doesn't end with !", nameof(sheetName));

            return sheetName.Substring(0, sheetName.Length - 1);
        }

        private string StripBrackets(string fileName)
        {
            if (!fileName.StartsWith("[") || !fileName.EndsWith("]"))
                throw new ArgumentException($"'{fileName}' isn't a text in []", nameof(fileName));

            return fileName.Substring(1, fileName.Length - 2);
        }

        private static NodePredicate[] For(params NodePredicate[] conditions) => conditions;

        private class AstNodeFactory : System.Collections.IEnumerable
        {
            private readonly List<KeyValuePair<NodePredicate[], Func<ParseTreeNode, AstContext, AstNode>>> _factories = new();

            public void Add(NodePredicate[] cstNodeConditions, Func<ParseTreeNode, AstNode> astNodeFactory)
                => _factories.Add(new KeyValuePair<NodePredicate[], Func<ParseTreeNode, AstContext, AstNode>>(cstNodeConditions, (node, _) => astNodeFactory(node)));

            public void Add(NodePredicate[] cstNodeConditions, Func<ParseTreeNode, AstContext, AstNode> astNodeFactory)
                => _factories.Add(new KeyValuePair<NodePredicate[], Func<ParseTreeNode, AstContext, AstNode>>(cstNodeConditions, astNodeFactory));

            public System.Collections.IEnumerator GetEnumerator() => throw new NotSupportedException();

            public static implicit operator AstNodeCreator(AstNodeFactory factory) => factory.CreateNode;

            private void CreateNode(AstContext context, ParseTreeNode parseNode)
            {
                // Sequential conditions are slower than binary switch, but it is readable.
                foreach (var factory in _factories)
                {
                    var conditions = factory.Key;
                    var conditionsSatisfied = parseNode.ChildNodes.Count == conditions.Length
                        && parseNode.ChildNodes.Zip(conditions, (n, c) => c.Func(n)).All(x => x);
                    if (conditionsSatisfied)
                    {
                        parseNode.AstNode = factory.Value(parseNode, context);
                        return;
                    }
                }

                throw new InvalidOperationException($"Failed to convert CST to AST for term {parseNode.Term.Name}.");
            }
        }

        private class NodePredicate
        {
            private NodePredicate(Func<ParseTreeNode, bool> func) => Func = func;

            public Func<ParseTreeNode, bool> Func { get; }

            public static implicit operator NodePredicate(string termName) => new(x => x.Term.Name == termName);
            public static implicit operator NodePredicate(string[] termNames) => new(x => termNames.Contains(x.Term.Name));
            public static implicit operator NodePredicate(Type astNodeType) => new(x => x.AstNode?.GetType() == astNodeType);
            public static implicit operator NodePredicate(Func<AstNode, bool> cond) => new(x => x.AstNode is ValueNode astNode && cond(astNode));
        }
    }
}


text:
module Travis::API::V3
  class BillingClient
    class ConfigurationError < StandardError; end

    ALLOWANCE_TIMEOUT = 1 # second
    EXECUTIONS_TIMEOUT = 60 # seconds

    def initialize(user_id)
      @user_id = user_id
    end

    def allowance(owner_type, owner_id)
      response = connection(timeout: ALLOWANCE_TIMEOUT).get("/usage/#{owner_type.downcase}s/#{owner_id}/allowance")
      return BillingClient.default_allowance_response unless response.status == 200

      Travis::API::V3::Models::Allowance.new(2, owner_id, response.body)
    end

    def authorize_build(repo, sender_id, jobs)
      response = connection.post("/#{repo.owner.class.name.downcase.pluralize}/#{repo.owner.id}/authorize_build", { repository: { private: repo.private? }, sender_id: sender_id, jobs: jobs })
      handle_errors_and_respond(response)
    end

    def self.default_allowance_response(id = 0)
      Travis::API::V3::Models::Allowance.new(1, id, {
        "public_repos" => true,
        "private_repos" => false,
        "concurrency_limit" => 1,
        "user_usage" => false,
        "pending_user_licenses" => false
      }.freeze)
    end

    def self.minimal_allowance_response(id = 0)
      Travis::API::V3::Models::Allowance.new(2, id, {})
    end

    def executions(owner_type, owner_id, page, per_page, from, to)
      response = connection(timeout: EXECUTIONS_TIMEOUT).get("/usage/#{owner_type.downcase}s/#{owner_id}/executions?page=#{page}&per_page=#{per_page}&from=#{from}&to=#{to}")
      executions = response.body.map do |execution_data|
        Travis::API::V3::Models::Execution.new(execution_data)
      end
      executions
    end

    def calculate_credits(users, executions)
      response = connection.post("/usage/credits_calculator", users: users, executions: executions)
      response.body.map do |calculator_data|
        Travis::API::V3::Models::CreditsResult.new(calculator_data)
      end
    end

    def credits_calculator_default_config
      response = connection.get('/usage/credits_calculator/default_config')

      Travis::API::V3::Models::CreditsCalculatorConfig.new(response.body)
    end

    def all
      data = connection.get('/subscriptions').body
      subscriptions = data.fetch('subscriptions').map do |subscription_data|
        Travis::API::V3::Models::Subscription.new(subscription_data)
      end
      permissions = data.fetch('permissions')

      Travis::API::V3::Models::SubscriptionsCollection.new(subscriptions, permissions)
    end

    def all_v2
      data = connection.get('/v2/subscriptions').body
      subscriptions = data.fetch('plans').map do |subscription_data|
        Travis::API::V3::Models::V2Subscription.new(subscription_data)
      end
      permissions = data.fetch('permissions')

      Travis::API::V3::Models::SubscriptionsCollection.new(subscriptions, permissions)
    end

    def get_subscription(id)
      response = connection.get("/subscriptions/#{id}")
      handle_subscription_response(response)
    end

    def get_v2_subscription(id)
      response = connection.get("/v2/subscriptions/#{id}")
      handle_v2_subscription_response(response)
    end

    def get_invoices_for_subscription(id)
      connection.get("/subscriptions/#{id}/invoices").body.map do |invoice_data|
        Travis::API::V3::Models::Invoice.new(invoice_data)
      end
    end

    def get_invoices_for_v2_subscription(id)
      connection.get("/v2/subscriptions/#{id}/invoices").body.map do |invoice_data|
        Travis::API::V3::Models::Invoice.new(invoice_data)
      end
    end

    def trials
      connection.get('/trials').body.map do | trial_data |
        Travis::API::V3::Models::Trial.new(trial_data)
      end
    end

    def create_trial(type, id)
      response = connection.post("/trials/#{type}/#{id}")
      handle_errors_and_respond(response)
    end

    def update_address(subscription_id, address_data)
      response = connection.patch("/subscriptions/#{subscription_id}/address", address_data)
      handle_subscription_response(response)
    end

    def update_v2_address(subscription_id, address_data)
      response = connection.patch("/v2/subscriptions/#{subscription_id}/address", address_data)
      handle_v2_subscription_response(response)
    end

    def update_creditcard(subscription_id, creditcard_token)
      response = connection.patch("/subscriptions/#{subscription_id}/creditcard", token: creditcard_token)
      handle_subscription_response(response)
    end

    def update_v2_creditcard(subscription_id, creditcard_token)
      response = connection.patch("/v2/subscriptions/#{subscription_id}/creditcard", token: creditcard_token)
      handle_v2_subscription_response(response)
    end

    def update_plan(subscription_id, plan_data)
      response = connection.patch("/subscriptions/#{subscription_id}/plan", plan_data)
      handle_subscription_response(response)
    end

    def create_subscription(subscription_data)
      response = connection.post('/subscriptions', subscription_data)
      handle_subscription_response(response)
    end

    def create_v2_subscription(subscription_data)
      response = connection.post('/v2/subscriptions', subscription_data)
      handle_v2_subscription_response(response)
    end

    def changetofree_v2_subscription(subscription_id, data)
      response = connection.patch("/v2/subscriptions/#{subscription_id}/changetofree", data)
      handle_v2_subscription_response(response)
    end

    def update_v2_subscription(subscription_id, plan_data)
      response = connection.patch("/v2/subscriptions/#{subscription_id}/plan", plan_data)
      handle_v2_subscription_response(response)
    end

    def purchase_addon(subscription_id, addon_config_id)
      response = connection.patch("/v2/subscriptions/#{subscription_id}/addon", { addon: addon_config_id })
      handle_v2_subscription_response(response)
    end

    def v2_subscription_user_usages(subscription_id)
      connection.get("/v2/subscriptions/#{subscription_id}/user_usage").body.map do |usage_data|
        Travis::API::V3::Models::V2AddonUsage.new(usage_data)
      end
    end

    def v2_plans_for_organization(organization_id)
      connection.get("/v2/plans_for/organization/#{organization_id}").body.map do |plan_data|
        Travis::API::V3::Models::V2PlanConfig.new(plan_data)
      end
    end

    def v2_plans_for_user
      connection.get('/v2/plans_for/user').body.map do |plan_data|
        Travis::API::V3::Models::V2PlanConfig.new(plan_data)
      end
    end

    def cancel_subscription(id, reason_data)
      response = connection.post("/subscriptions/#{id}/cancel", reason_data)
      handle_subscription_response(response)
    end

    def plans_for_organization(organization_id)
      connection.get("/plans_for/organization/#{organization_id}").body.map do |plan_data|
        Travis::API::V3::Models::Plan.new(plan_data)
      end
    end

    def plans_for_user
      connection.get('/plans_for/user').body.map do |plan_data|
        Travis::API::V3::Models::Plan.new(plan_data)
      end
    end

    def resubscribe(id)
      response = connection.patch("/subscriptions/#{id}/resubscribe")
      handle_subscription_response(response)
    end

    def pay(id)
      response = connection.post("/subscriptions/#{id}/pay")
      handle_subscription_response(response)
    end

    def pay_v2(id)
      response = connection.post("/v2/subscriptions/#{id}/pay")
      handle_v2_subscription_response(response)
    end

    def get_coupon(code)
      response = connection.get("/coupons/#{code}")
      handle_coupon_response(response)
    end

    def update_organization_billing_permission(organization_id, billing_admin_only)
      response = connection.patch("/organization/permission_update/#{organization_id}", billing_admin_only)
      handle_subscription_response(response)
    end

    def create_auto_refill(plan_id, is_enabled)
      response = connection.post('/auto_refill', {plan: plan_id, enabled: is_enabled})
      handle_errors_and_respond(response)
    end

    def update_auto_refill(addon_id, threshold, amount)
      response = connection.patch('/auto_refill', {id: addon_id, threshold: threshold, amount: amount})
      handle_errors_and_respond(response)
    end

    def get_auto_refill(plan_id)
      response = connection.get("/auto_refill?plan_id=#{plan_id}")
      handle_errors_and_respond(response) { |r| Travis::API::V3::Models::AutoRefill.new(r) }
    end

    def cancel_v2_subscription(id, reason_data)
      response = connection.post("/v2/subscriptions/#{id}/cancel", reason_data)
      handle_subscription_response(response)
    end

    private

    def handle_subscription_response(response)
      handle_errors_and_respond(response) { |r| Travis::API::V3::Models::Subscription.new(r) }
    end

    def handle_v2_subscription_response(response)
      handle_errors_and_respond(response) { |r| Travis::API::V3::Models::V2Subscription.new(r) }
    end

    def handle_coupon_response(response)
      handle_errors_and_respond(response) { |r| Travis::API::V3::Models::Coupon.new(r) }
    end

    def handle_errors_and_respond(response)
      case response.status
      when 200, 201
        yield(response.body) if block_given?
      when 202
        true
      when 204
        true
      when 400
        raise Travis::API::V3::ClientError, response.body['error']
      when 403
        raise Travis::API::V3::InsufficientAccess, response.body['rejection_code']
      when 404
        raise Travis::API::V3::NotFound, response.body['error']
      when 422
        raise Travis::API::V3::UnprocessableEntity, response.body['error']
      else
        raise Travis::API::V3::ServerError, 'Billing system failed'
      end
    end

    def connection(timeout: 10)
      @connection ||= Faraday.new(url: billing_url, ssl: { ca_path: '/usr/lib/ssl/certs' }) do |conn|
        conn.basic_auth '_', billing_auth_key
        conn.headers['X-Travis-User-Id'] = @user_id.to_s
        conn.headers['Content-Type'] = 'application/json'
        conn.request :json
        conn.response :json
        conn.options[:open_timeout] = timeout
        conn.options[:timeout] = timeout
        conn.use OpenCensus::Trace::Integrations::FaradayMiddleware if Travis::Api::App::Middleware::OpenCensus.enabled?
        conn.adapter :net_http
      end
    end

    def billing_url
      Travis.config.billing.url || raise(ConfigurationError, 'No billing url configured')
    end

    def billing_auth_key
      Travis.config.billing.auth_key || raise(ConfigurationError, 'No billing auth key configured')
    end
  end
end

redpajama_set_name: RedPajamaGithub


text:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using System.Windows.Documents;

namespace MathEasy.src.LMD.Core
{
    public class LMD_Plaintext: LMD_Object
    {
        public String Text { get; set; }
        public String HTML { get; set; }

        public LMD_Plaintext(String Text)
        {
            this.Text = Text;
            this.HTML = "";
        }

        public bool isEqualTo(LMD_Object cmpObj)
        {
            LMD_Plaintext cmpPt = cmpObj as LMD_Plaintext;
            return cmpPt != null && Text == cmpPt.Text;
        }

        public void build()
        {
            HTML = HTMLizer.prepareForHTML(Text);
        }
    }
}


text:
struct MovableButNonCopyable {
#if ! defined BOOST_NO_DELETED_FUNCTIONS
      MovableButNonCopyable(MovableButNonCopyable const&) = delete;
      MovableButNonCopyable& operator=(MovableButNonCopyable const&) = delete;
#else
private:
    MovableButNonCopyable(MovableButNonCopyable const&);
    MovableButNonCopyable& operator=(MovableButNonCopyable const&);
#endif
public:
    MovableButNonCopyable() {};
    MovableButNonCopyable(MovableButNonCopyable&&) {};
    MovableButNonCopyable& operator=(MovableButNonCopyable&&) {
      return *this;
    };
};
int main()
{
    boost::packaged_task<MovableButNonCopyable>(MovableButNonCopyable());
    return 0;
}
#else
int main()
{
    return 0;
}
#endif


text:
{% extends 'base.html' %}

{% block head %}

<link href="/static/css/django-admin-widgets.css" rel="stylesheet" type="text/css">
{{ form.media }}
{% endblock %}

{% block content %}

Add a Student

<form method='POST' action=''>
	{% csrf_token %}
	{{form.as_p}}
	<input type='submit' value="Save Student", action="">
	<input type="submit" value="Save and add another", name="_add_another">
</form>

{% endblock %}


text:
package com.petremoto.utils;

import android.app.Activity;
import android.content.Context;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.view.Gravity;
import android.widget.Toast;

import com.petremoto.R;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.HttpURLConnection;
import java.net.URL;
import java.text.DecimalFormat;

import org.joda.time.format.DateTimeFormat;
import org.joda.time.format.DateTimeFormatter;

public final class PetRemotoUtils {

    private PetRemotoUtils() {
    }

    private static final String URL = "http://thiner.herokuapp.com/api/user";
    // private static final String URL = "http://192.168.1.244:5000/api/ti";

    /**
     * The Constant mFormat.
     */
    private static final String FORMAT_SHORT = "HH:mm";
    private static final String FORMAT_LONG = "HH:mm dd/MM/YYYY";

    public static void showToast(final Context context, final String message) {
        final Toast makeText = Toast.makeText(context, message,
                Toast.LENGTH_LONG);
        makeText.setGravity(Gravity.TOP, 0, 0);
        makeText.show();
    }

    public static String getServerURL() {
        return URL;
    }

    // Given a URL, establishes an HttpUrlConnection and retrieves
    // the web page content as a InputStream, which it returns as
    // a string.
    public static String downloadUrl(final String myurl) {
        InputStream is = null;
        InputStreamReader isr = null;
        BufferedReader br = null;
        try {
            final URL url = new URL(myurl);
            final HttpURLConnection conn = (HttpURLConnection) url
                    .openConnection();
            conn.setReadTimeout(10000 /* milliseconds */);
            conn.setConnectTimeout(15000 /* milliseconds */);
            conn.setRequestMethod("GET");
            conn.setDoInput(true);
            conn.connect();

            is = conn.getInputStream();
            isr = new InputStreamReader(is, "UTF-8");
            br = new BufferedReader(isr);

            String line;
            final StringBuffer buf = new StringBuffer();

            while ((line = br.readLine()) != null) {
                buf.append(line);
            }

            is.close();
            isr.close();
            br.close();

            return buf.toString();

        } catch (final IOException e) {
            MyLog.error("Error when downloading url", e);
        } finally {
            try {
                if (br != null) {
                    br.close();
                }
            } catch (final IOException e) {
                MyLog.error("Error when downloading url", e);
            }
        }

        return null;
    }

    public static String sendPOST(final String myurl, final String paramns)
            throws IOException {

        final URL url = new URL(myurl);
        final HttpURLConnection conn = (HttpURLConnection) url.openConnection();
        conn.setReadTimeout(10000);
        conn.setConnectTimeout(15000);
        conn.setRequestMethod("POST");
        conn.setDoInput(true);
        conn.setDoOutput(true);

        final OutputStreamWriter osw = new OutputStreamWriter(
                conn.getOutputStream(), "UTF-8");
        osw.write(paramns);
        osw.flush();

        final BufferedReader br = new BufferedReader(new InputStreamReader(
                conn.getInputStream(),
                "UTF-8"));

        final StringBuffer contentAsString = new StringBuffer();
        String line;

        while ((line = br.readLine()) != null) {
            contentAsString.append(line);
        }

        osw.close();
        br.close();

        return contentAsString.toString();
    }

    public static boolean isConnected(final Activity act) {
        final ConnectivityManager connMgr = (ConnectivityManager) act
                .getSystemService(Context.CONNECTIVITY_SERVICE);
        final NetworkInfo networkInfo = connMgr.getActiveNetworkInfo();

        if (networkInfo != null && networkInfo.isConnected()) {
            return true;
        }

        return false;
    }

    public static void showNotConnected(final Context context) {
        Toast.makeText(context,
                context.getString(R.string.connection_unavailable),
                Toast.LENGTH_LONG).show();
    }

    public static void showCantWithoutConnection(final Context context) {
        Toast.makeText(context,
                context.getString(R.string.cant_without_connection),
                Toast.LENGTH_SHORT).show();
    }

    /**
     * Gets the date time format.
     *
     * @return the date time format
     */
    public static DateTimeFormatter getDateTimeFormat() {
        return DateTimeFormat.forPattern(FORMAT_LONG);

    }

    public static String formatDouble(final double num) {
        final DecimalFormat df = new DecimalFormat("#,###.00");

        boolean hasFloating = false;

        if (num - (int) num != 0) {
            hasFloating = true;
        }

        if (hasFloating) {
            return df.format(num);
        } else {
            return String.valueOf((int) num);
        }

    }

}


text:
package com.udacity.github.oauth.test

import com.udacity.github.oauth.GitHubUser
import com.udacity.github.oauth.AuthKey
import com.udacity.github.oauth.GitHubOauthServlet
import org.eclipse.jetty.server.Server
import org.eclipse.jetty.server.ServerConnector
import org.eclipse.jetty.servlet.ServletContextHandler
import org.eclipse.jetty.webapp.WebAppContext
import org.scalatest.BeforeAndAfterAll
import org.scalatest.FunSuite
import java.net.URLEncoder
import Http.get

object GitHubOauthServletServer {

  val port = 11111
  val server = new Server(port)

  val host = s"http://localhost:${port}"

  val context = new ServletContextHandler(ServletContextHandler.SESSIONS)
  context.setContextPath("/")
  context.addServlet(classOf[GitHubOauthServlet], "/*")
  server.setHandler(context)

  def start(): Unit = {
    server.start()
  }

  def stop(): Unit = {
    server.stop()
  }

}

class GitHubOauthServletTests extends FunSuite with BeforeAndAfterAll {

  override def beforeAll(): Unit = {
    GitHubServer.start()
    GitHubOauthServletServer.start()
  }

  override def afterAll(): Unit = {
    GitHubOauthServletServer.stop()
    GitHubServer.stop()
  }

  test("get 'missing system properties' page") {
    System.clearProperty("GH_CLIENT_ID")
    System.clearProperty("GH_CLIENT_SECRET")
    System.clearProperty("GH_OAUTH_URL")
    System.clearProperty("GH_API_URL")
    System.clearProperty("GH_ORG")

    get(GitHubOauthServletServer.host) match { case Response(status, headers, body) =>
        assert(500 === status)
        assert(body.contains("Missing environment configuration:"))
        assert(body.contains("GH_CLIENT_ID"))
        assert(body.contains("GH_CLIENT_SECRET"))
        assert(body.contains("GH_OAUTH_URL"))
        assert(body.contains("GH_API_URL"))
        assert(body.contains("GH_ORG"))
    }

    System.setProperty("GH_CLIENT_ID", "42")
    System.setProperty("GH_CLIENT_SECRET", "42")
    System.setProperty("GH_OAUTH_URL", s"${GitHubServer.host}/oauth")
    System.setProperty("GH_API_URL", s"${GitHubServer.host}/api")
    System.setProperty("GH_ORG", "megacorp")
  }

  val continueUrl = "http://example.com/"
  var redirectUrl: String = ""

  test("redirect to github to initiate oauth") {
    val continue = URLEncoder.encode(continueUrl)
    get(GitHubOauthServletServer.host + "/" + continue) match {
      case Response(status, headers, body) =>
        assert(302 === status)
        assert(headers.get("Location").isDefined)
        redirectUrl = headers("Location")
        assert(redirectUrl.startsWith(GitHubServer.host + "/oauth/authorize"))
    }
  }

  test("authenticate via github oauth") {
    get(redirectUrl) match {
      case Response(status, headers, body) =>
        assert(302 === status)
        assert(headers.get("Location").isDefined)
        redirectUrl = headers("Location")
        assert(redirectUrl.startsWith(GitHubOauthServletServer.host + "/"))
    }
  }

  test("fail to sign-in without access_token") {
    get(redirectUrl) match {
      case Response(status, headers, body) =>
        assert(401 === status)
    }
  }

  test("enable access_token") {
    get(GitHubServer.host + "/enable-access-token") match {
      case Response(status, headers, body) =>
        assert(200 === status)
    }
  }

  test("fail to sign-in with non-org user") {
    get(redirectUrl) match {
      case Response(status, headers, body) =>
        assert(403 === status)
    }
  }

  test("add user to the udacity org") {
    get(GitHubServer.host + "/add-user-to-org") match {
      case Response(status, headers, body) =>
        assert(200 === status)
    }
  }

  test("complete sign-in") {
    get(redirectUrl) match {
      case Response(status, headers, body) =>
        assert(302 === status)
        assert(headers.get("Location") === Some(continueUrl))
        val userO: Option[GitHubUser] =
          for {
            setCookie <- headers.get("Set-Cookie")
            values    <- setCookie.split("=").lift(1)
            value     <- values.split(";").lift(0)
            user      <- GitHubOauthServlet.get(AuthKey(value))
          } yield user
        assert(Some(GitHubUser("bob")) === userO)
    }
  }

}


text:
The Magento_Weee module enables the application of fees/fixed product taxes (FPT) on certain types of products, usually related to electronic devices and recycling.
Fixed product taxes can be used to setup a WEEE tax that is a fixed amount, rather than a percentage of the product price. FPT can be configured to be displayed at various places in Magento. Rules, amounts, and display options can be configured in the backend. This module extends the existing functionality of Magento_Tax.

The Magento_Wee module includes the following:

* ability to add different number of fixed product taxes to product. They are treated as a product attribute;
* configuration of where Weee appears (on category, product, sales, invoice, or credit memo pages) and whether FPT should be taxed;
* a new line item in the totals section.

# System requirements
The Magento_Weee module does not have any specific system requirements.

## Install
Magento_Weee module can be installed automatically (using native Magento install mechanism) without any additional actions

## Uninstall
Magento installation with existing products with FPT:
* Disable FPT on the backend
* Remove all products with FPT
* Remove all FPT attributes from attribute sets
* Delete all FPT attributes
* Remove module directory from the code base
* New Magento installation:
* Can be removed without additional actions


text:
package io.reinert.requestor.core;

/**
 * An extension interface implemented by request filters.
 * Request filters are intended to manipulate the request before it is sent to the server.
 *
 * @author Danilo Reinert
 */
public interface RequestFilter {

    interface Provider extends io.reinert.requestor.core.Provider<RequestFilter> { }

    /**
     * Filter method called before a request has been dispatched to a client transport layer.
     *
     * @param request   The request to be dispatched.
     */
    void filter(RequestInProcess request);
}


text:
SYNONYM

#### According to
Index Fungorum

#### Published in
null

#### Original name
Peniophora fibuligera K.S. Thind & S.S. Rattan

### Remarks
null


text:
<link rel="import" href="../polymer/polymer.html">
<link rel="import" href="../marked-element/marked-element.html">
<link rel="import" href="../prism-element/prism-highlighter.html">
<link rel="import" href="../prism-element/prism-theme-default.html">

<link rel="import" href="iron-doc-api.html">
<link rel="import" href="iron-doc-viewer-behavior.html">
<link rel="import" href="iron-doc-viewer-styles.html">

<dom-module id="iron-doc-mixin">
  <template>

    <prism-highlighter></prism-highlighter>

[[title]]

[[descriptor.summary]]

Path: [[descriptor.path]]

Mixins:

        <template is="dom-repeat" items="[[descriptor.mixins]]" sort="_compareDescriptors">,
          [[item]]</template>

        Description

      <marked-element sanitize markdown="[[descriptor.description]]">

      </marked-element>

    <iron-doc-api
        descriptor="[[descriptor]]"
        fragment-prefix="[[fragmentPrefix]]">
    </iron-doc-api>

  </template>

</dom-module>


text:
export { BigNumber } from "./bignumber";
export { formatFixed, FixedFormat, FixedNumber, parseFixed } from "./fixednumber";
// Internal methods used by address
export { _base16To36, _base36To16 } from "./bignumber";
//# sourceMappingURL=index.js.map


text:
{% extends 'administration/base_admin.html' %}
{% block content %}
{% load admin_filters %}

Create new Category

                    {% if messages %}
    					{% for message in messages %}
							{% if message.message == 'categorie_exists' %}

This category already exists!

							{% endif %}
    					{% endfor %}
					{% endif %}
                    {% if messages %}
                        {% for message in messages %}
                            {% if message.message == 'empty_category' %}

Type in an name!

                            {% endif %}
                        {% endfor %}
                    {% endif %}
				    <form class="form" role="form" method="post" accept-charset="UTF-8">
					{%csrf_token%}

		  				    <input type="name" class="form-control input-lg" placeholder="Category Name" name="name" maxlength="50" required/>

						    <input name="create_category" id="standard-grey-button-bold" type="submit" class="btn btn-block btn-lg btn-primary" value="Create"/>

				    </form>

Search Category

                    {% if messages %}
                        {% for message in messages %}
                            {% if message.message == 'category_not_exists' %}

This category doesn't exist!

                            {% endif %}
                        {% endfor %}
                    {% endif %}
                    <form class="form" role="form" method="POST" accept-charset="UTF-8">
                    {%csrf_token%}

                            <input type="name" class="form-control input-lg" placeholder="Category Name" name="name" maxlength="50" required/>

                            <input name="search_category" id="standard-grey-button-bold" type="submit" class="btn btn-block btn-lg btn-primary" value="Search"/>

                    </form>

                    {% if categ %}

Categories

                                 Show All

                    {% else %}

Categories

                    {% endif %}

                    {% if messages %}
    					{% for message in messages %}
							{% if message.message == 'categorie_sonst' %}

Cannot delete Other!

							{% elif message.message == 'categorie_gone' %}

Another admin has already deleted this categorie

                            {% endif%}
    					{% endfor %}
					{% endif %}

                        {% if categ %}

{{ categ.name }}

Number of members: {{ categ|filter_cats|length }}

                                         Delete

                        {% else %}
                            {% for categorie in categories %}

{{ categorie.name }}

Number of needs: {{ categorie|filter_cats|length }}

                                             Delete

                            {% empty %}

No categories available. Create some.

                            {% endfor %}
                        {% endif %}

	            <button type="button" class="close" data-dismiss="modal">×</button>

Delete This Category

If you delete This Category, the data will be permanently lost.

Would you like to rethink your decision?

	            <button id="standard-grey-button-light" type="button" class="btn btn-default" data-dismiss="modal">Rethink</button>

	                 Delete

{% endblock %}


text:
package nest.sparkle.util

import org.scalatest.{FunSuite, Matchers}

import org.joda.time.{DateTimeZone, DateTime, DurationFieldType}
import nest.sparkle.util.StringToMillis._

class TestPeriod extends FunSuite with Matchers {

  DateTimeZone.setDefault(DateTimeZone.UTC)

  test("10 days") {
    Period.parse("10 days") shouldBe Some(Period(10, DurationFieldType.days))
  }

  test("3 years") {
    Period.parse("3 years") shouldBe Some(Period(3, DurationFieldType.years))
  }

   test("1500 microseconds") {
    Period.parse("1500 microseconds") shouldBe Some(Period(1, DurationFieldType.millis))
  }

  test("zero length periods should be ok") {
    Period.parse("0 weeks") shouldBe Some(Period(0, DurationFieldType.weeks))
  }

  test("negative length periods should be illegal") {
    Period.parse("-1 days") shouldBe None
  }

  test("round date down by millis") {
    val date = new DateTime("2014-07-06T04:33:01.326".toMillis)
    val period = Period.parse("25 milliseconds").get
    val rounded = period.roundDate(date)
    rounded shouldBe new DateTime("2014-07-06T04:33:01.325".toMillis)
  }

  test("round date down by seconds (date seconds on period boundary)") {
    val date = new DateTime("2014-07-06T04:01:10.000".toMillis)
    val period = Period.parse("10 seconds").get
    val rounded = period.roundDate(date)
    rounded shouldBe new DateTime("2014-07-06T04:01:10.000".toMillis)
  }

  test("round date down by seconds (date seconds > period boundary)") {
    val date = new DateTime("2014-07-06T04:01:42.000".toMillis)
    val period = Period.parse("10 seconds").get
    val rounded = period.roundDate(date)
    rounded shouldBe new DateTime("2014-07-06T04:01:40.000".toMillis)
  }

  test("round date down by seconds (date seconds < period boundary)") {
    val date = new DateTime("2014-07-06T04:01:09.000".toMillis)
    val period = Period.parse("10 seconds").get
    val rounded = period.roundDate(date)
    rounded shouldBe new DateTime("2014-07-06T04:01:00.000".toMillis)
  }

  test("round date down by minutes") {
    val date = new DateTime("2014-07-06T04:33:01.000".toMillis)
    val period = Period.parse("15 minutes").get
    val rounded = period.roundDate(date)
    rounded shouldBe new DateTime("2014-07-06T04:30:00.000".toMillis)
  }

  test("round date down by hours") {
    val date = new DateTime("2014-07-06T05:01:00.000".toMillis)
    val period = Period.parse("2 hours").get
    val rounded = period.roundDate(date)
    rounded shouldBe new DateTime("2014-07-06T04:00:00.000".toMillis)
  }

  test("round date down by months") {
    val date = new DateTime("2014-07-06T05:01:00.000".toMillis)
    val period = Period.parse("3 months").get
    val rounded = period.roundDate(date)
    rounded shouldBe new DateTime("2014-06-01T00:00:00.000".toMillis)
  }

}


text:
import {
  Component,
  OnInit
} from '@angular/core';

<% if (pageservice) { %>
import { <%= pagename %>Service } from './<%= pagename %>.service';
<% } else { %>
<% } %>

@Component({
  /**
   * The selector is what angular internally uses
   * for `document.querySelectorAll(selector)` in our index.html
   * where, in this case, selector is the string 'header'
   */
  selector: 'ng<%= pagename %>',

  /**
   * Our list of styles in our component. We may add more to compose many styles together
   */
  // styles and styleUrls both will inject style tag in head for component view is general i.e encapsulation: ViewEncapsulation.None
  // styleUrls not working for absoluate url - for node_modules

  //styleUrls: [ './<%= pagename %>.component.css' ],
  styles: [
    require('./<%= pagename %>.component.css')
  ],

  /**
   * Every Angular template is first compiled by the browser before Angular runs it's compiler
   */
  templateUrl: './<%= pagename %>.component.html'<% if (pageservice) { %>,
  providers: [<%= pagename %>Service]
  <% } else { %>
<% } %>
})
export class <%= pagename %>Component implements OnInit {

  constructor(<% if (pageservice) { %>  private <%= pagename %>Service : <%= pagename %>Service  <% } else { %> <% } %>) {}

  public ngOnInit() {
    console.log('hello `<%= pagename %>` component');
  }
}


text:
package ol.style;

import ol.GwtOLBaseTestCase;

/**
 * Test for {@link ol.style.IconImageCache}.
 *
 * @author Tino Desjardins
 */
public class IconImageCacheTest extends GwtOLBaseTestCase {

    public void testIconImageCache() {

        injectUrlAndTest(() -> {

            IconImageCache iconImageCache = IconImageCache.get();
            assertNotNull(iconImageCache);
            assertEquals(iconImageCache, IconImageCache.get());
            iconImageCache.setSize(128);

        });

    }
}


text:
package com.peak.salut;

import android.net.wifi.p2p.WifiP2pDevice;

import com.bluelinelabs.logansquare.annotation.JsonField;
import com.bluelinelabs.logansquare.annotation.JsonObject;

import java.util.HashMap;
import java.util.Map;

@JsonObject
public class SalutDevice {

    @JsonField
    public Map<String, String> txtRecord;
    @JsonField
    public String deviceName;
    @JsonField
    public String serviceName;
    @JsonField
    public String instanceName;
    @JsonField
    public String readableName;
    @JsonField
    public boolean isRegistered;
    @JsonField
    protected int servicePort;
    @JsonField
    protected String TTP = "._tcp.";
    @JsonField
    protected String macAddress;
    @JsonField
    protected String serviceAddress;

    public SalutDevice() {
    }

    public SalutDevice(SalutDevice device) {
        this.serviceName = device.serviceName;
        this.readableName = device.readableName;
        this.instanceName = device.instanceName;
        this.deviceName = device.deviceName;
        this.macAddress = device.macAddress;
        this.txtRecord = new HashMap(device.txtRecord.size());
        for(Map.Entry<String, String> entry : txtRecord.entrySet()) {
            this.txtRecord.put(entry.getKey(), entry.getValue());
        }
    }

    public SalutDevice(WifiP2pDevice device, Map<String, String> txtRecord) {
        this.serviceName = txtRecord.get("SERVICE_NAME");
        this.readableName = txtRecord.get("INSTANCE_NAME");
        this.instanceName = txtRecord.get("INSTANCE_NAME");
        this.deviceName = device.deviceName;
        this.macAddress = device.deviceAddress;
        this.txtRecord = txtRecord;

    }

    public int getServicePort() {
        return servicePort;
    }

    public String getMacAddress() {
        return macAddress;
    }

    public String getServiceAddress() {
        return serviceAddress;
    }

    @Override
    public String toString() {
        return String.format("Salut Device | Service Name: %s TTP: %s Human-Readable Name: %s", instanceName, TTP, readableName);
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        SalutDevice device = (SalutDevice) o;

        if (!deviceName.equals(device.deviceName)) return false;
        return macAddress != null ? macAddress.equals(device.macAddress) : device.macAddress == null;

    }

    @Override
    public int hashCode() {
        int result = deviceName.hashCode();
        result = 31 * result + (macAddress != null ? macAddress.hashCode() : 0);
        return result;
    }
}


text:
export { Method } from './method.enum';
export { Status } from './status-codes.object';


text:
// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "content/browser/background_fetch/background_fetch_service_impl.h"

#include <memory>

#include "base/bind.h"
#include "base/bind_helpers.h"
#include "base/guid.h"
#include "base/optional.h"
#include "base/task/post_task.h"
#include "content/browser/background_fetch/background_fetch_context.h"
#include "content/browser/background_fetch/background_fetch_metrics.h"
#include "content/browser/background_fetch/background_fetch_registration_id.h"
#include "content/browser/background_fetch/background_fetch_registration_notifier.h"
#include "content/browser/background_fetch/background_fetch_request_match_params.h"
#include "content/browser/bad_message.h"
#include "content/browser/service_worker/service_worker_info.h"
#include "content/browser/storage_partition_impl.h"
#include "content/public/browser/browser_task_traits.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/render_process_host.h"
#include "content/public/browser/web_contents.h"
#include "mojo/public/cpp/bindings/self_owned_receiver.h"
#include "third_party/blink/public/mojom/fetch/fetch_api_request.mojom.h"

namespace content {

namespace {
// Maximum length of a developer-provided |developer_id| for a Background Fetch.
constexpr size_t kMaxDeveloperIdLength = 1024 * 1024;
}  // namespace

// static
void BackgroundFetchServiceImpl::CreateForWorker(
    const ServiceWorkerVersionInfo& info,
    mojo::PendingReceiver<blink::mojom::BackgroundFetchService> receiver) {
  DCHECK_CURRENTLY_ON(BrowserThread::UI);
  RenderProcessHost* render_process_host =
      RenderProcessHost::FromID(info.process_id);

  if (!render_process_host)
    return;

  RunOrPostTaskOnThread(
      FROM_HERE, ServiceWorkerContext::GetCoreThreadId(),
      base::BindOnce(
          BackgroundFetchServiceImpl::CreateOnCoreThread,
          WrapRefCounted(static_cast<StoragePartitionImpl*>(
                             render_process_host->GetStoragePartition())
                             ->GetBackgroundFetchContext()),
          info.script_origin,
          /* render_frame_tree_node_id= */ 0,
          /* wc_getter= */ base::NullCallback(), std::move(receiver)));
}

// static
void BackgroundFetchServiceImpl::CreateForFrame(
    RenderFrameHost* render_frame_host,
    mojo::PendingReceiver<blink::mojom::BackgroundFetchService> receiver) {
  DCHECK_CURRENTLY_ON(BrowserThread::UI);
  DCHECK(render_frame_host);
  RenderProcessHost* render_process_host = render_frame_host->GetProcess();
  DCHECK(render_process_host);

  WebContents::Getter wc_getter = base::NullCallback();

  // Permissions need to go through the DownloadRequestLimiter if the fetch
  // is started from a top-level frame.
  if (!render_frame_host->GetParent()) {
    wc_getter = base::BindRepeating(&WebContents::FromFrameTreeNodeId,
                                    render_frame_host->GetFrameTreeNodeId());
  }

  RunOrPostTaskOnThread(
      FROM_HERE, ServiceWorkerContext::GetCoreThreadId(),
      base::BindOnce(
          BackgroundFetchServiceImpl::CreateOnCoreThread,
          WrapRefCounted(static_cast<StoragePartitionImpl*>(
                             render_process_host->GetStoragePartition())
                             ->GetBackgroundFetchContext()),
          render_frame_host->GetLastCommittedOrigin(),
          render_frame_host->GetFrameTreeNodeId(), std::move(wc_getter),
          std::move(receiver)));
}

// static
void BackgroundFetchServiceImpl::CreateOnCoreThread(
    scoped_refptr<BackgroundFetchContext> background_fetch_context,
    url::Origin origin,
    int render_frame_tree_node_id,
    WebContents::Getter wc_getter,
    mojo::PendingReceiver<blink::mojom::BackgroundFetchService> receiver) {
  DCHECK_CURRENTLY_ON(ServiceWorkerContext::GetCoreThreadId());

  mojo::MakeSelfOwnedReceiver(
      std::make_unique<BackgroundFetchServiceImpl>(
          std::move(background_fetch_context), std::move(origin),
          render_frame_tree_node_id, std::move(wc_getter)),
      std::move(receiver));
}

BackgroundFetchServiceImpl::BackgroundFetchServiceImpl(
    scoped_refptr<BackgroundFetchContext> background_fetch_context,
    url::Origin origin,
    int render_frame_tree_node_id,
    WebContents::Getter wc_getter)
    : background_fetch_context_(std::move(background_fetch_context)),
      origin_(std::move(origin)),
      render_frame_tree_node_id_(render_frame_tree_node_id),
      wc_getter_(std::move(wc_getter)) {
  DCHECK(background_fetch_context_);
}

BackgroundFetchServiceImpl::~BackgroundFetchServiceImpl() {
  DCHECK_CURRENTLY_ON(ServiceWorkerContext::GetCoreThreadId());
}

void BackgroundFetchServiceImpl::Fetch(
    int64_t service_worker_registration_id,
    const std::string& developer_id,
    std::vector<blink::mojom::FetchAPIRequestPtr> requests,
    blink::mojom::BackgroundFetchOptionsPtr options,
    const SkBitmap& icon,
    blink::mojom::BackgroundFetchUkmDataPtr ukm_data,
    FetchCallback callback) {
  DCHECK_CURRENTLY_ON(ServiceWorkerContext::GetCoreThreadId());

  if (!ValidateDeveloperId(developer_id) || !ValidateRequests(requests)) {
    std::move(callback).Run(
        blink::mojom::BackgroundFetchError::INVALID_ARGUMENT,
        /* registration= */ nullptr);
    return;
  }

  // New |unique_id|, since this is a new Background Fetch registration. This is
  // the only place new |unique_id|s should be created outside of tests.
  BackgroundFetchRegistrationId registration_id(service_worker_registration_id,
                                                origin_, developer_id,
                                                base::GenerateGUID());

  background_fetch_context_->StartFetch(
      registration_id, std::move(requests), std::move(options), icon,
      std::move(ukm_data), render_frame_tree_node_id_, wc_getter_,
      std::move(callback));
}

void BackgroundFetchServiceImpl::GetIconDisplaySize(
    blink::mojom::BackgroundFetchService::GetIconDisplaySizeCallback callback) {
  DCHECK_CURRENTLY_ON(ServiceWorkerContext::GetCoreThreadId());
  background_fetch_context_->GetIconDisplaySize(std::move(callback));
}

void BackgroundFetchServiceImpl::GetRegistration(
    int64_t service_worker_registration_id,
    const std::string& developer_id,
    GetRegistrationCallback callback) {
  DCHECK_CURRENTLY_ON(ServiceWorkerContext::GetCoreThreadId());
  if (!ValidateDeveloperId(developer_id)) {
    std::move(callback).Run(
        blink::mojom::BackgroundFetchError::INVALID_ARGUMENT,
        /* registration= */ nullptr);
    return;
  }

  background_fetch_context_->GetRegistration(service_worker_registration_id,
                                             origin_, developer_id,
                                             std::move(callback));
}

void BackgroundFetchServiceImpl::GetDeveloperIds(
    int64_t service_worker_registration_id,
    GetDeveloperIdsCallback callback) {
  DCHECK_CURRENTLY_ON(ServiceWorkerContext::GetCoreThreadId());
  background_fetch_context_->GetDeveloperIdsForServiceWorker(
      service_worker_registration_id, origin_, std::move(callback));
}

bool BackgroundFetchServiceImpl::ValidateDeveloperId(
    const std::string& developer_id) {
  if (developer_id.empty() || developer_id.size() > kMaxDeveloperIdLength) {
    mojo::ReportBadMessage("Invalid developer_id");
    return false;
  }

  return true;
}

bool BackgroundFetchServiceImpl::ValidateUniqueId(
    const std::string& unique_id) {
  if (!base::IsValidGUIDOutputString(unique_id)) {
    mojo::ReportBadMessage("Invalid unique_id");
    return false;
  }

  return true;
}

bool BackgroundFetchServiceImpl::ValidateRequests(
    const std::vector<blink::mojom::FetchAPIRequestPtr>& requests) {
  if (requests.empty()) {
    mojo::ReportBadMessage("Invalid requests");
    return false;
  }

  return true;
}

}  // namespace content