/// <summary>
        /// Calls an internal function or external function.
        /// </summary>
        /// <param name="ctx">The context of the runtime.</param>
        /// <param name="fexpr">The function call expression</param>
        /// <param name="functionName">The name of the function. if not supplied, gets from the fexpr</param>
        /// <param name="pushCallStack"></param>
        /// <returns></returns>
        public static object CallFunction(Context ctx, FunctionCallExpr fexpr, string functionName, bool pushCallStack)
        {
            if (string.IsNullOrEmpty(functionName))
            {
                functionName = fexpr.NameExp.ToQualifiedName();
            }

            if (!FunctionHelper.IsInternalOrExternalFunction(ctx, functionName, null))
            {
                throw ExceptionHelper.BuildRunTimeException(fexpr, "Function does not exist : '" + functionName + "'");
            }

            // 1. Push the name of the function on teh call stack
            if (pushCallStack)
            {
                ctx.State.Stack.Push(functionName, fexpr);
            }

            // 2. Call the function.
            object result = null;

            // Case 1: Custom C# function blog.create blog.*
            if (ctx.ExternalFunctions.Contains(functionName))
            {
                result = ctx.ExternalFunctions.Call(functionName, fexpr);
            }

            // Case 2: Script functions "createUser('john');"
            else
            {
                result = FunctionHelper.CallFunctionInScript(ctx, functionName, fexpr.ParamListExpressions, fexpr.ParamList, true);
            }

            // 3. Finnaly pop the call stact.
            if (pushCallStack)
            {
                ctx.State.Stack.Pop();
            }

            result = CheckConvert(result);
            return(result);
        }
Example #2
0
        /// <summary>
        /// Call a fluent script function from c#.
        /// </summary>
        /// <param name="context">The context of the call.</param>
        /// <param name="expr">The lambda function</param>
        /// <param name="convertApplicableTypes">Whether or not to convert applicable c# types to fluentscript types, eg. ints and longs to double, List(object) to LArrayType and Dictionary(string, object) to LMapType</param>
        /// <param name="args"></param>
        public static object CallFunctionViaCSharpUsingLambda(Context context, FunctionExpr expr, bool convertApplicableTypes, params object[] args)
        {
            var argsList = args.ToList <object>();

            if (convertApplicableTypes)
            {
                LangTypeHelper.ConvertToLangTypeValues(argsList);
            }
            var execution = new Execution();

            execution.Ctx = context;
            if (EvalHelper.Ctx == null)
            {
                EvalHelper.Ctx = context;
            }

            var result = FunctionHelper.CallFunctionInScript(context, execution, expr.Meta.Name, expr, null, argsList, false);

            return(result);
        }
        /// <summary>
        /// Execute a member call.
        /// </summary>
        /// <param name="ctx">The context of the script</param>
        /// <param name="memberAccess">Object to hold all the relevant information required for the member call.</param>
        /// <param name="paramListExpressions">The expressions to resolve as parameters</param>
        /// <param name="paramList">The list of parameters.</param>
        /// <returns></returns>
        public static object CallMemberOnClass(Context ctx, AstNode node, MemberAccess memberAccess, List <Expr> paramListExpressions, List <object> paramList)
        {
            object result = LObjects.Null;
            var    obj    = memberAccess.Instance;
            var    type   = memberAccess.DataType;

            // Case 1: Property access
            if (memberAccess.Property != null)
            {
                var prop = type.GetProperty(memberAccess.MemberName);
                if (prop != null)
                {
                    result = prop.GetValue(obj, null);
                }
            }
            // Case 2: Method call.
            else if (memberAccess.Method != null)
            {
                result = FunctionHelper.MethodCall(ctx, obj, type, memberAccess.Method, paramListExpressions, paramList, true);
            }
            result = CheckConvert(result);
            return(result);
        }
Example #4
0
        /// <summary>
        /// Gets a member access object representing the a member access.
        /// </summary>
        /// <param name="node"></param>
        /// <param name="ctx"></param>
        /// <param name="varExp"></param>
        /// <param name="memberName"></param>
        /// <returns></returns>
        public static MemberAccess GetMemberAccess(AstNode node, Context ctx, Expr varExp, string memberName, IAstVisitor visitor)
        {
            var isVariableExp = varExp.IsNodeType(NodeTypes.SysVariable);
            var variableName  = isVariableExp ? ((VariableExpr)varExp).Name : string.Empty;

            // CASE 1: External function call "user.create"
            if (isVariableExp && FunctionHelper.IsExternalFunction(ctx.ExternalFunctions, variableName, memberName))
            {
                return new MemberAccess(MemberMode.FunctionExternal)
                       {
                           Name = variableName, MemberName = memberName
                       }
            }
            ;

            // CASE 2. Static method call: "Person.Create"
            if (isVariableExp)
            {
                var result = MemberHelper.IsExternalTypeName(ctx.Memory, ctx.Types, variableName);

                if (result.Success)
                {
                    return(MemberHelper.GetExternalTypeMember(node, (Type)result.Item, variableName, null, memberName, true));
                }
            }

            // CASE 3: Module
            if (varExp.IsNodeType(NodeTypes.SysVariable))
            {
                var name = varExp.ToQualifiedName();
                if (!ctx.Memory.Contains(name))
                {
                    var modresult = ResolveSymbol(varExp.SymScope, name);
                    if (modresult != null)
                    {
                        return(modresult);
                    }
                }
            }

            // CASE 4: Nested member.
            var res = varExp.Visit(visitor);

            if (res is MemberAccess)
            {
                return(res as MemberAccess);
            }

            var obj = res as LObject;

            // Check for empty objects.
            ExceptionHelper.NotNull(node, obj, "member access");

            var type = obj.Type;

            // Case 3: Method / Property on FluentScript type
            var isCoreType = obj.Type.IsBuiltInType();

            if (isCoreType)
            {
                var result = MemberHelper.GetLangBasicTypeMember(node, ctx.Methods, obj, memberName);
                return(result);
            }

            // CASE 4: Method / Property on External/Host language type (C#)
            var lclass     = obj as LClass;
            var lclassType = lclass.Type as LClassType;
            var member     = MemberHelper.GetExternalTypeMember(node, lclassType.DataType, variableName, lclass.Value, memberName, false);

            return(member);
        }