public CompileRequest( ICollection <CompilableClass> classes, ModuleCompileTimeServices moduleCompileTimeServices) { _classes = classes; _moduleCompileTimeServices = moduleCompileTimeServices; }
public Type CompileStandInClass( CodegenClassType classType, string classNameSimple, ModuleCompileTimeServices services) { var namespaceScope = new CodegenNamespaceScope(services.Namespace, null, false); var classScope = new CodegenClassScope(true, namespaceScope, null); var clazz = new CodegenClass( classType, null, classNameSimple, classScope, EmptyList<CodegenTypedParam>.Instance, null, new CodegenClassMethods(), new CodegenClassProperties(), EmptyList<CodegenInnerClass>.Instance); // This is a bit hacky... basically, Esper has to generate a "Type" that can be returned and // included as the "Underlying" type for the JsonEventType. This method is called during the // portion of the sequence where we are attempting to build the forgeables, so the real type // doesnt exist yet. Esper builds the stand-in but expects that the real type will be used // at runtime. In Java, type erasure allows this to happen because there is no real type in // backing arrays and collections. In .NET we need the types to match. // // We are creating a "capsule" class which will act as a placeholder. When we detect that // the type is a capsule type in the JsonEventType, we will attempt to "resolve" and replace // it. var classNameFull = namespaceScope.Namespace + '.' + classNameSimple; var capsuleClass = CapsuleEmitter.CreateCapsule(classNameFull); return capsuleClass.TargetType; }
protected internal static EPCompiled Compile( IList<Compilable> compilables, string optionalModuleName, IDictionary<ModuleProperty, object> moduleProperties, ModuleCompileTimeServices compileTimeServices, CompilerOptions compilerOptions) { ICollection<Assembly> assemblies = new HashSet<Assembly>(); try { EPCompiledManifest manifest = CompileToModules( assemblies, compilables, optionalModuleName, moduleProperties, compileTimeServices, compilerOptions, out var assembly); return new EPCompiled(assemblies, manifest); } catch (EPCompileException) { throw; } catch (Exception ex) { throw new EPCompileException( "Unexpected exception compiling module: " + ex.Message, ex, new EmptyList<EPCompileExceptionItem>()); } }
private static EPCompiledManifest CompileToAssembly( FAFQueryMethodForge query, string classPostfix, CompilerOptions compilerOptions, ModuleCompileTimeServices compileTimeServices, out Assembly assembly) { string queryMethodProviderClassName; try { queryMethodProviderClassName = CompilerHelperFAFQuery.CompileQuery(query, classPostfix,compileTimeServices, out assembly); } catch (StatementSpecCompileException ex) { EPCompileExceptionItem first; if (ex is StatementSpecCompileSyntaxException) { first = new EPCompileExceptionSyntaxItem(ex.Message, ex.Expression, -1); } else { first = new EPCompileExceptionItem(ex.Message, ex.Expression, -1); } var items = Collections.SingletonList(first); throw new EPCompileException(ex.Message + " [" + ex.Expression + "]", ex, items); } // compile query provider var fafProviderClassName = MakeFAFProvider( queryMethodProviderClassName, classPostfix, compileTimeServices, out assembly); // create manifest return new EPCompiledManifest(COMPILER_VERSION, null, fafProviderClassName, false); }
public static ExprValidationContext Make( IContainer container, StreamTypeService streamTypeService) { var moduleServices = new ModuleCompileTimeServices(container); moduleServices.Configuration = new Configuration(); moduleServices.ImportServiceCompileTime = SupportClasspathImport.GetInstance(container); var services = new StatementCompileTimeServices(1, moduleServices); var raw = new StatementRawInfo(1, "abc", null, StatementType.SELECT, null, null, null, null); return new ExprValidationContextBuilder(streamTypeService, raw, services).Build(); }
CompileCallable( CompilableItem compilableItem, ModuleCompileTimeServices compileTimeServices, Semaphore semaphore, ICollection <Assembly> statementAssemblies) { _compilableItem = compilableItem; _compileTimeServices = compileTimeServices; _semaphore = semaphore; _statementAssemblies = statementAssemblies; }
private void AddModuleImports( ICollection<Import> imports, ModuleCompileTimeServices compileTimeServices) { if (imports != null) { foreach (var imported in imports) { try { compileTimeServices.ImportServiceCompileTime.AddImport(imported); } catch (ImportException e) { throw new EPCompileException("Invalid module import: " + e.Message, e); } } } }
public static string CompileQuery( FAFQueryMethodForge query, string classPostfix, ModuleCompileTimeServices compileTimeServices, out Assembly assembly) { var statementFieldsClassName = CodeGenerationIDGenerator.GenerateClassNameSimple( typeof(StatementFields), classPostfix); var packageScope = new CodegenNamespaceScope( compileTimeServices.Namespace, statementFieldsClassName, compileTimeServices.IsInstrumented()); var queryMethodProviderClassName = CodeGenerationIDGenerator.GenerateClassNameSimple( typeof(FAFQueryMethodProvider), classPostfix); var forgeablesQueryMethod = query.MakeForgeables(queryMethodProviderClassName, classPostfix, packageScope); IList<StmtClassForgeable> forgeables = new List<StmtClassForgeable>(forgeablesQueryMethod); forgeables.Add(new StmtClassForgeableStmtFields(statementFieldsClassName, packageScope, 0)); // forge with statement-fields last var classes = new List<CodegenClass>(forgeables.Count); foreach (var forgeable in forgeables) { var clazz = forgeable.Forge(true, true); classes.Add(clazz); } // assign the assembly (required for completeness) assembly = null; // compile with statement-field first classes = classes .OrderBy(c => c.ClassType.GetSortCode()) .ToList(); var container = compileTimeServices.Container; var compiler = container .RoslynCompiler() .WithCodeLogging(compileTimeServices.Configuration.Compiler.Logging.IsEnableCode) .WithCodeAuditDirectory(compileTimeServices.Configuration.Compiler.Logging.AuditDirectory) .WithCodegenClasses(classes); assembly = compiler.Compile(); return queryMethodProviderClassName; }
internal static CodegenMethod MakeInitEventTypes( CodegenClassScope classScope, ModuleCompileTimeServices compileTimeServices) { var symbolsEventTypeInit = new ModuleEventTypeInitializeSymbol(); var initializeEventTypesMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsEventTypeInit, classScope) .AddParam( typeof(EPModuleEventTypeInitServices), ModuleEventTypeInitializeSymbol.REF_INITSVC.Ref); foreach (var eventType in compileTimeServices.EventTypeCompileTimeRegistry.NewTypesAdded) { var addType = RegisterEventTypeCodegen( eventType, initializeEventTypesMethod, classScope, symbolsEventTypeInit); initializeEventTypesMethod.Block.Expression(LocalMethod(addType)); } return initializeEventTypesMethod; }
public static EPCompiled Compile( Compilable compilable, ModuleCompileTimeServices services, CompilerArguments args) { var compileTimeServices = new StatementCompileTimeServices(0, services); var walkResult = CompilerHelperSingleEPL.ParseCompileInlinedClassesWalk(compilable, compileTimeServices); var raw = walkResult.StatementSpecRaw; var statementType = StatementTypeUtil.GetStatementType(raw); if (statementType != StatementType.SELECT) { // the fire-and-forget spec is null for "select" and populated for I/U/D throw new StatementSpecCompileException( "Provided EPL expression is a continuous query expression (not an on-demand query)", compilable.ToEPL()); } var annotations = AnnotationUtil.CompileAnnotations( raw.Annotations, services.ImportServiceCompileTime, compilable); // walk subselects, alias expressions, declared expressions, dot-expressions var visitor = StatementSpecRawWalkerSubselectAndDeclaredDot.WalkSubselectAndDeclaredDotExpr(raw); // compile context descriptor ContextCompileTimeDescriptor contextDescriptor = null; var optionalContextName = raw.OptionalContextName; if (optionalContextName != null) { var detail = services.ContextCompileTimeResolver.GetContextInfo(optionalContextName); if (detail == null) { throw new StatementSpecCompileException( "Context by name '" + optionalContextName + "' could not be found", compilable.ToEPL()); } contextDescriptor = new ContextCompileTimeDescriptor( optionalContextName, detail.ContextModuleName, detail.ContextVisibility, new ContextPropertyRegistry(detail), detail.ValidationInfos); } var statementNameFromAnnotation = GetNameFromAnnotation(annotations); var statementName = statementNameFromAnnotation == null ? GetDefaultStatementName() : statementNameFromAnnotation.Trim(); var statementRawInfo = new StatementRawInfo( 0, statementName, annotations, statementType.Value, contextDescriptor, null, compilable, null); StatementSpecCompiledDesc compiledDesc = StatementRawCompiler.Compile( raw, compilable, false, true, annotations, visitor.Subselects, new List<ExprTableAccessNode>(raw.TableExpressions), statementRawInfo, compileTimeServices); StatementSpecCompiled specCompiled = compiledDesc.Compiled; var fafSpec = specCompiled.Raw.FireAndForgetSpec; //var @namespace = "generated"; var classPostfix = IdentifierUtil.GetIdentifierMayStartNumeric(statementName); EPCompiledManifest manifest; Assembly assembly; FAFQueryMethodForge query; if (specCompiled.Raw.InsertIntoDesc != null) { query = new FAFQueryMethodIUDInsertIntoForge( specCompiled, compilable, statementRawInfo, compileTimeServices); } else if (fafSpec == null) { // null indicates a select-statement, same as continuous query var desc = new FAFQueryMethodSelectDesc( specCompiled, compilable, statementRawInfo, compileTimeServices); var classNameResultSetProcessor = CodeGenerationIDGenerator.GenerateClassNameSimple( typeof(ResultSetProcessorFactoryProvider), classPostfix); query = new FAFQueryMethodSelectForge(desc, classNameResultSetProcessor, statementRawInfo); } else if (fafSpec is FireAndForgetSpecDelete) { query = new FAFQueryMethodIUDDeleteForge( specCompiled, compilable, statementRawInfo, compileTimeServices); } else if (fafSpec is FireAndForgetSpecUpdate) { query = new FAFQueryMethodIUDUpdateForge( specCompiled, compilable, statementRawInfo, compileTimeServices); } else { throw new IllegalStateException("Unrecognized FAF code " + fafSpec); } // verify substitution parameters VerifySubstitutionParams(raw.SubstitutionParameters); try { manifest = CompileToAssembly(query, classPostfix, args.Options, services, out assembly); } catch (EPCompileException) { throw; } catch (Exception ex) { throw new EPCompileException( "Unexpected exception compiling module: " + ex.Message, ex, new EmptyList<EPCompileExceptionItem>()); } return new EPCompiled(new [] { assembly }, manifest); }
private static string MakeFAFProvider( string queryMethodProviderClassName, string classPostfix, ModuleCompileTimeServices compileTimeServices, out Assembly assembly) { var statementFieldsClassName = CodeGenerationIDGenerator.GenerateClassNameSimple( typeof(StatementFields), classPostfix); var namespaceScope = new CodegenNamespaceScope( compileTimeServices.Namespace, statementFieldsClassName, compileTimeServices.IsInstrumented()); var fafProviderClassName = CodeGenerationIDGenerator.GenerateClassNameSimple(typeof(FAFProvider), classPostfix); var classScope = new CodegenClassScope(true, namespaceScope, fafProviderClassName); var methods = new CodegenClassMethods(); var properties = new CodegenClassProperties(); // -------------------------------------------------------------------------------- // Add statementFields // -------------------------------------------------------------------------------- var ctor = new CodegenCtor( typeof(CompilerHelperFAFProvider), classScope, new List<CodegenTypedParam>()); ctor.Block.AssignRef(Ref("statementFields"), NewInstanceInner(statementFieldsClassName)); // initialize-event-types var initializeEventTypesMethod = MakeInitEventTypes(classScope, compileTimeServices); // initialize-query var initializeQueryMethod = CodegenMethod .MakeMethod( typeof(void), typeof(EPCompilerImpl), CodegenSymbolProviderEmpty.INSTANCE, classScope) .AddParam( typeof(EPStatementInitServices), EPStatementInitServicesConstants.REF.Ref); initializeQueryMethod.Block.AssignMember( MEMBERNAME_QUERY_METHOD_PROVIDER, NewInstanceInner(queryMethodProviderClassName, EPStatementInitServicesConstants.REF, Ref("statementFields"))); // get-execute var queryMethodProviderProperty = CodegenProperty.MakePropertyNode( typeof(FAFQueryMethodProvider), typeof(EPCompilerImpl), CodegenSymbolProviderEmpty.INSTANCE, classScope); queryMethodProviderProperty.GetterBlock.BlockReturn(Ref(MEMBERNAME_QUERY_METHOD_PROVIDER)); // provide module dependencies var moduleDependenciesProperty = CodegenProperty.MakePropertyNode( typeof(ModuleDependenciesRuntime), typeof(EPCompilerImpl), CodegenSymbolProviderEmpty.INSTANCE, classScope); moduleDependenciesProperty.GetterBlock .BlockReturn(compileTimeServices.ModuleDependencies.Make( initializeQueryMethod, classScope)); // build stack CodegenStackGenerator.RecursiveBuildStack(moduleDependenciesProperty, "ModuleDependencies", methods, properties); CodegenStackGenerator.RecursiveBuildStack(initializeEventTypesMethod, "InitializeEventTypes", methods, properties); CodegenStackGenerator.RecursiveBuildStack(initializeQueryMethod, "InitializeQuery", methods, properties); CodegenStackGenerator.RecursiveBuildStack(queryMethodProviderProperty, "QueryMethodProvider", methods, properties); IList<CodegenTypedParam> members = new List<CodegenTypedParam>(); members.Add(new CodegenTypedParam(statementFieldsClassName, null, "statementFields")); var typedParam = new CodegenTypedParam(typeof(FAFQueryMethodProvider), MEMBERNAME_QUERY_METHOD_PROVIDER); typedParam.IsReadonly = false; members.Add(typedParam); var clazz = new CodegenClass( CodegenClassType.FAFPROVIDER, typeof(FAFProvider), fafProviderClassName, classScope, members, ctor, methods, properties, new EmptyList<CodegenInnerClass>()); var container = compileTimeServices.Container; var compiler = container .RoslynCompiler() .WithCodeLogging(compileTimeServices.Configuration.Compiler.Logging.IsEnableCode) .WithCodeAuditDirectory(compileTimeServices.Configuration.Compiler.Logging.AuditDirectory) .WithCodegenClasses(new List<CodegenClass>() { clazz }); assembly = compiler.Compile(); return CodeGenerationIDGenerator.GenerateClassNameWithNamespace( compileTimeServices.Namespace, typeof(FAFProvider), classPostfix); }
public EPCompilerSPIExpressionImpl(ModuleCompileTimeServices moduleServices) { this.moduleServices = moduleServices; }
public static CompilableItem CompileItem( Compilable compilable, string optionalModuleName, string moduleIdentPostfix, int statementNumber, ISet<string> statementNames, ModuleCompileTimeServices moduleCompileTimeServices, CompilerOptions compilerOptions, out Assembly assembly) { var compileTimeServices = new StatementCompileTimeServices(statementNumber, moduleCompileTimeServices); // Stage 0 - parse and compile-inline-classes and walk statement var walked = ParseCompileInlinedClassesWalk(compilable, compileTimeServices); var raw = walked.StatementSpecRaw; string classNameCreateClass = null; if (raw.CreateClassProvided != null) { classNameCreateClass = DetermineClassNameCreateClass(walked.ClassesInlined); } try { // Stage 2(a) - precompile: compile annotations var annotations = AnnotationUtil.CompileAnnotations( raw.Annotations, compileTimeServices.ImportServiceCompileTime, compilable); // Stage 2(b) - walk subselects, alias expressions, declared expressions, dot-expressions ExprNodeSubselectDeclaredDotVisitor visitor; try { visitor = StatementSpecRawWalkerSubselectAndDeclaredDot.WalkSubselectAndDeclaredDotExpr(raw); } catch (ExprValidationException ex) { throw new StatementSpecCompileException(ex.Message, compilable.ToEPL()); } var subselectNodes = visitor.Subselects; // Determine a statement name var statementNameProvided = GetNameFromAnnotation(annotations); if (compilerOptions.StatementName != null) { var assignedName = compilerOptions.StatementName.Invoke( new StatementNameContext( () => compilable.ToEPL(), statementNameProvided, optionalModuleName, annotations, statementNumber)); if (assignedName != null) { statementNameProvided = assignedName; } } var statementName = statementNameProvided ?? Convert.ToString(statementNumber); if (statementNames.Contains(statementName)) { var count = 1; var newStatementName = statementName + "-" + count; while (statementNames.Contains(newStatementName)) { count++; newStatementName = statementName + "-" + count; } statementName = newStatementName; } statementName = statementName.Trim(); statementNames.Add(statementName); // Determine table access nodes var tableAccessNodes = DetermineTableAccessNodes(raw.TableExpressions, visitor); // compile scripts once in this central place, may also compile later in expression ScriptValidationPrecompileUtil.ValidateScripts( raw.ScriptExpressions, raw.ExpressionDeclDesc, compileTimeServices); // Determine subselects for compilation, and lambda-expression shortcut syntax for named windows if (!visitor.ChainedExpressionsDot.IsEmpty()) { RewriteNamedWindowSubselect( visitor.ChainedExpressionsDot, subselectNodes, compileTimeServices.NamedWindowCompileTimeResolver); } // Stage 2(c) compile context descriptor ContextCompileTimeDescriptor contextDescriptor = null; var optionalContextName = raw.OptionalContextName; if (optionalContextName != null) { var detail = compileTimeServices.ContextCompileTimeResolver.GetContextInfo(optionalContextName); if (detail == null) { throw new StatementSpecCompileException( "Context by name '" + optionalContextName + "' could not be found", compilable.ToEPL()); } contextDescriptor = new ContextCompileTimeDescriptor( optionalContextName, detail.ContextModuleName, detail.ContextVisibility, new ContextPropertyRegistry(detail), detail.ValidationInfos); } // Stage 2(d) compile raw statement spec var statementType = StatementTypeUtil.GetStatementType(raw).Value; var statementRawInfo = new StatementRawInfo( statementNumber, statementName, annotations, statementType, contextDescriptor, raw.IntoTableSpec?.Name, compilable, optionalModuleName); var compiledDesc = StatementRawCompiler.Compile( raw, compilable, false, false, annotations, subselectNodes, tableAccessNodes, statementRawInfo, compileTimeServices); var specCompiled = compiledDesc.Compiled; var statementIdentPostfix = IdentifierUtil.GetIdentifierMayStartNumeric(statementName); // get compile-time user object object userObjectCompileTime = null; if (compilerOptions.StatementUserObject != null) { userObjectCompileTime = compilerOptions.StatementUserObject.Invoke( new StatementUserObjectContext( () => compilable.ToEPL(), statementName, optionalModuleName, annotations, statementNumber)); } // handle hooks HandleStatementCompileHook(annotations, compileTimeServices, specCompiled); // Stage 3(a) - statement-type-specific forge building var @base = new StatementBaseInfo( compilable, specCompiled, userObjectCompileTime, statementRawInfo, optionalModuleName); StmtForgeMethod forgeMethod; if (raw.UpdateDesc != null) { forgeMethod = new StmtForgeMethodUpdate(@base); } else if (raw.OnTriggerDesc != null) { forgeMethod = new StmtForgeMethodOnTrigger(@base); } else if (raw.CreateIndexDesc != null) { forgeMethod = new StmtForgeMethodCreateIndex(@base); } else if (raw.CreateVariableDesc != null) { forgeMethod = new StmtForgeMethodCreateVariable(@base); } else if (raw.CreateDataFlowDesc != null) { forgeMethod = new StmtForgeMethodCreateDataflow(@base); } else if (raw.CreateTableDesc != null) { forgeMethod = new StmtForgeMethodCreateTable(@base); } else if (raw.CreateExpressionDesc != null) { forgeMethod = new StmtForgeMethodCreateExpression(@base); } else if (raw.CreateClassProvided != null) { forgeMethod = new StmtForgeMethodCreateClass(@base, walked.ClassesInlined, classNameCreateClass); } else if (raw.CreateWindowDesc != null) { forgeMethod = new StmtForgeMethodCreateWindow(@base); } else if (raw.CreateContextDesc != null) { forgeMethod = new StmtForgeMethodCreateContext(@base); } else if (raw.CreateSchemaDesc != null) { forgeMethod = new StmtForgeMethodCreateSchema(@base); } else { forgeMethod = new StmtForgeMethodSelect(@base); } // check context-validity conditions for this statement if (contextDescriptor != null) { try { foreach (var validator in contextDescriptor.ValidationInfos) { validator.ValidateStatement( contextDescriptor.ContextName, specCompiled, compileTimeServices); } } catch (ExprValidationException ex) { throw new StatementSpecCompileException(ex.Message, ex, compilable.ToEPL()); } } // Stage 3(b) - forge-factory-to-forge var classPostfix = moduleIdentPostfix + "_" + statementIdentPostfix; var forgeables = new List<StmtClassForgeable>(); // add forgeables from filter-related processing i.e. multikeys foreach (var additional in compiledDesc.AdditionalForgeables) { var namespaceScope = new CodegenNamespaceScope(compileTimeServices.Namespace, null, false); forgeables.Add(additional.Make(namespaceScope, classPostfix)); } var filterSpecCompileds = new List<FilterSpecCompiled>(); var scheduleHandleCallbackProviders = new List<ScheduleHandleCallbackProvider>(); var namedWindowConsumers = new List<NamedWindowConsumerStreamSpec>(); var filterBooleanExpressions = new List<FilterSpecParamExprNodeForge>(); var result = forgeMethod.Make(compileTimeServices.Namespace, classPostfix, compileTimeServices); forgeables.AddAll(result.Forgeables); VerifyForgeables(forgeables); filterSpecCompileds.AddAll(result.Filtereds); scheduleHandleCallbackProviders.AddAll(result.Scheduleds); namedWindowConsumers.AddAll(result.NamedWindowConsumers); filterBooleanExpressions.AddAll(result.FilterBooleanExpressions); // Stage 3(c) - filter assignments: assign filter callback ids and filter-path-num for boolean expressions var filterId = -1; foreach (var provider in filterSpecCompileds) { var assigned = ++filterId; provider.FilterCallbackId = assigned; } // Stage 3(d) - schedule assignments: assign schedule callback ids var scheduleId = 0; foreach (var provider in scheduleHandleCallbackProviders) { provider.ScheduleCallbackId = scheduleId++; } // Stage 3(e) - named window consumers: assign consumer id var namedWindowConsumerId = 0; foreach (var provider in namedWindowConsumers) { provider.NamedWindowConsumerId = namedWindowConsumerId++; } // Stage 3(f) - filter boolean expression id assignment var filterBooleanExprNum = 0; foreach (var expr in filterBooleanExpressions) { expr.FilterBoolExprId = filterBooleanExprNum++; } // Stage 3(f) - verify substitution parameters VerifySubstitutionParams(raw.SubstitutionParameters); // Stage 4 - forge-to-class (forge with statement-fields last) var classes = forgeables .Select(forgeable => forgeable.Forge(true, false)) .ToList(); // Stage 5 - refactor methods to make sure the constant pool does not grow too large for any given class CompilerHelperRefactorToStaticMethods.RefactorMethods( classes, compileTimeServices.Configuration.Compiler.ByteCode.MaxMethodsPerClass); // Stage 6 - sort to make the "fields" class first and all the rest later var sorted = classes .OrderBy(c => c.ClassType.GetSortCode()) .ToList(); // We are making sure JsonEventType receives the underlying class itself CompilableItemPostCompileLatch postCompile = CompilableItemPostCompileLatchDefault.INSTANCE; foreach (var eventType in compileTimeServices.EventTypeCompileTimeRegistry.NewTypesAdded) { if (eventType is JsonEventType) { postCompile = new CompilableItemPostCompileLatchJson( compileTimeServices.EventTypeCompileTimeRegistry.NewTypesAdded, compileTimeServices.ParentClassLoader); break; } } var container = compileTimeServices.Container; var compiler = container .RoslynCompiler() .WithCodeLogging(compileTimeServices.Configuration.Compiler.Logging.IsEnableCode) .WithCodeAuditDirectory(compileTimeServices.Configuration.Compiler.Logging.AuditDirectory) .WithCodegenClasses(sorted); assembly = compiler.Compile(); string statementProviderClassName = CodeGenerationIDGenerator.GenerateClassNameWithNamespace( compileTimeServices.Namespace, typeof(StatementProvider), classPostfix); var additionalClasses = new HashSet<Type>(); additionalClasses.AddAll(walked.ClassesInlined.Classes); compileTimeServices.ClassProvidedCompileTimeResolver.AddTo(additionalClasses); compileTimeServices.ClassProvidedCompileTimeRegistry.AddTo(additionalClasses); return new CompilableItem( statementProviderClassName, classes, postCompile, additionalClasses); } catch (StatementSpecCompileException) { throw; } catch (ExprValidationException ex) { throw new StatementSpecCompileException(ex.Message, ex, compilable.ToEPL()); } catch (EPException ex) { throw new StatementSpecCompileException(ex.Message, ex, compilable.ToEPL()); } catch (Exception ex) { var text = ex.Message ?? ex.GetType().FullName; throw new StatementSpecCompileException(text, ex, compilable.ToEPL()); } }
private static EPCompiledManifest CompileToModules( ICollection<Assembly> assemblies, IList<Compilable> compilables, string optionalModuleName, IDictionary<ModuleProperty, object> moduleProperties, ModuleCompileTimeServices compileTimeServices, CompilerOptions compilerOptions, out Assembly assembly) { var moduleAssignedName = optionalModuleName ?? Guid.NewGuid().ToString(); var moduleIdentPostfix = IdentifierUtil.GetIdentifierMayStartNumeric(moduleAssignedName); // compile each statement var statementNumber = 0; IList<string> statementClassNames = new List<string>(); ISet<string> statementNames = new HashSet<string>(); IList<EPCompileExceptionItem> exceptions = new List<EPCompileExceptionItem>(); IList<EPCompileExceptionItem> postLatchExceptions = new List<EPCompileExceptionItem>(); foreach (var compilable in compilables) { string className = null; EPCompileExceptionItem exception = null; try { CompilableItem compilableItem = CompilerHelperStatementProvider.CompileItem( compilable, optionalModuleName, moduleIdentPostfix, statementNumber, statementNames, compileTimeServices, compilerOptions, out assembly); assemblies.Add(assembly); className = compilableItem.ProviderClassName; compilableItem.PostCompileLatch.Completed(assemblies); // there can be a post-compile step, which may block submitting further compilables try { compilableItem.PostCompileLatch.AwaitAndRun(); } catch (Exception e) { postLatchExceptions.Add( new EPCompileExceptionItem( e.Message, e, compilable.ToEPL(), -1)); } } catch (StatementSpecCompileException ex) { if (ex is StatementSpecCompileSyntaxException) { exception = new EPCompileExceptionSyntaxItem(ex.Message, ex.Expression, -1); } else { exception = new EPCompileExceptionItem( ex.Message, ex, ex.Expression, -1); } exceptions.Add(exception); } if (exception == null) { statementClassNames.Add(className); statementNumber++; } } exceptions.AddAll(postLatchExceptions); if (!exceptions.IsEmpty()) { var ex = exceptions[0]; throw new EPCompileException( "Error during compilation: " + ex.Message + " [" + ex.Expression + "]", ex, exceptions); } // compile module resource var moduleProviderClassName = CompileModule( optionalModuleName, moduleProperties, statementClassNames, moduleIdentPostfix, compileTimeServices, out assembly); #if TBD // revisit // remove path create-class class-provided byte code compileTimeServices.ClassProvidedCompileTimeResolver.RemoveFrom(moduleBytes); // add class-provided create-class classes to module bytes foreach (var entry in compileTimeServices.ClassProvidedCompileTimeRegistry.Classes) { moduleBytes.Put(entry.Value.Assembly); } #endif // create module XML return new EPCompiledManifest(COMPILER_VERSION, moduleProviderClassName, null, compileTimeServices.SerdeResolver.IsTargetHA); }
private static string CompileModule( string optionalModuleName, IDictionary<ModuleProperty, object> moduleProperties, IList<string> statementClassNames, string moduleIdentPostfix, ModuleCompileTimeServices compileTimeServices, out Assembly assembly) { // write code to create an implementation of StatementResource var statementFieldsClassName = CodeGenerationIDGenerator.GenerateClassNameSimple( typeof(StatementFields), moduleIdentPostfix); var namespaceScope = new CodegenNamespaceScope( compileTimeServices.Namespace, statementFieldsClassName, compileTimeServices.IsInstrumented()); var moduleClassName = CodeGenerationIDGenerator.GenerateClassNameSimple( typeof(ModuleProvider), moduleIdentPostfix); var classScope = new CodegenClassScope(true, namespaceScope, moduleClassName); var methods = new CodegenClassMethods(); var properties = new CodegenClassProperties(); // provide module name var moduleNameProp = CodegenProperty.MakePropertyNode( typeof(string), typeof(EPCompilerImpl), CodegenSymbolProviderEmpty.INSTANCE, classScope); moduleNameProp.GetterBlock.BlockReturn(Constant(optionalModuleName)); // provide module properties var modulePropertiesProp = CodegenProperty.MakePropertyNode( typeof(IDictionary<ModuleProperty, object>), typeof(EPCompilerImpl), CodegenSymbolProviderEmpty.INSTANCE, classScope); MakeModuleProperties(moduleProperties, modulePropertiesProp); // provide module dependencies var moduleDependenciesProp = CodegenProperty.MakePropertyNode( typeof(ModuleDependenciesRuntime), typeof(EPCompilerImpl), CodegenSymbolProviderEmpty.INSTANCE, classScope); compileTimeServices.ModuleDependencies.Inject(moduleDependenciesProp.GetterBlock); // register types var initializeEventTypesMethod = MakeInitEventTypes(classScope, compileTimeServices); // register named windows var symbolsNamedWindowInit = new ModuleNamedWindowInitializeSymbol(); var initializeNamedWindowsMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsNamedWindowInit, classScope) .AddParam( typeof(EPModuleNamedWindowInitServices), ModuleNamedWindowInitializeSymbol.REF_INITSVC.Ref); foreach (var namedWindow in compileTimeServices.NamedWindowCompileTimeRegistry.NamedWindows) { var addNamedWindow = RegisterNamedWindowCodegen( namedWindow, initializeNamedWindowsMethod, classScope, symbolsNamedWindowInit); initializeNamedWindowsMethod.Block.Expression(LocalMethod(addNamedWindow)); } // register tables var symbolsTableInit = new ModuleTableInitializeSymbol(); var initializeTablesMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsTableInit, classScope) .AddParam(typeof(EPModuleTableInitServices), ModuleTableInitializeSymbol.REF_INITSVC.Ref); foreach (var table in compileTimeServices.TableCompileTimeRegistry.Tables) { var addTable = RegisterTableCodegen(table, initializeTablesMethod, classScope, symbolsTableInit); initializeTablesMethod.Block.Expression(LocalMethod(addTable)); } // register indexes var symbolsIndexInit = new ModuleIndexesInitializeSymbol(); var initializeIndexesMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsIndexInit, classScope) .AddParam(typeof(EPModuleIndexInitServices), EPModuleIndexInitServicesConstants.REF.Ref); foreach (KeyValuePair<IndexCompileTimeKey, IndexDetailForge> index in compileTimeServices .IndexCompileTimeRegistry.Indexes) { var addIndex = RegisterIndexCodegen(index, initializeIndexesMethod, classScope, symbolsIndexInit); initializeIndexesMethod.Block.Expression(LocalMethod(addIndex)); } // register contexts var symbolsContextInit = new ModuleContextInitializeSymbol(); var initializeContextsMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsContextInit, classScope) .AddParam( typeof(EPModuleContextInitServices), ModuleContextInitializeSymbol.REF_INITSVC.Ref); foreach (var context in compileTimeServices.ContextCompileTimeRegistry.Contexts) { var addContext = RegisterContextCodegen( context, initializeContextsMethod, classScope, symbolsContextInit); initializeContextsMethod.Block.Expression(LocalMethod(addContext)); } // register variables var symbolsVariablesInit = new ModuleVariableInitializeSymbol(); var initializeVariablesMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsVariablesInit, classScope) .AddParam( typeof(EPModuleVariableInitServices), ModuleVariableInitializeSymbol.REF_INITSVC.Ref); foreach (var variable in compileTimeServices.VariableCompileTimeRegistry.Variables) { var addVariable = RegisterVariableCodegen( variable, initializeVariablesMethod, classScope, symbolsVariablesInit); initializeVariablesMethod.Block.Expression(LocalMethod(addVariable)); } // register expressions var symbolsExprDeclaredInit = new ModuleExpressionDeclaredInitializeSymbol(); var initializeExprDeclaredMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsExprDeclaredInit, classScope) .AddParam( typeof(EPModuleExprDeclaredInitServices), ModuleExpressionDeclaredInitializeSymbol.REF_INITSVC.Ref); foreach (var expression in compileTimeServices.ExprDeclaredCompileTimeRegistry.Expressions) { var addExpression = RegisterExprDeclaredCodegen( expression, initializeExprDeclaredMethod, classScope, symbolsExprDeclaredInit); initializeExprDeclaredMethod.Block.Expression(LocalMethod(addExpression)); } // register scripts var symbolsScriptInit = new ModuleScriptInitializeSymbol(); var initializeScriptsMethod = CodegenMethod .MakeMethod(typeof(void), typeof(EPCompilerImpl), symbolsScriptInit, classScope) .AddParam(typeof(EPModuleScriptInitServices), ModuleScriptInitializeSymbol.REF_INITSVC.Ref); foreach (var expression in compileTimeServices.ScriptCompileTimeRegistry.Scripts) { var addScript = RegisterScriptCodegen( expression, initializeScriptsMethod, classScope, symbolsScriptInit); initializeScriptsMethod.Block.Expression(LocalMethod(addScript)); } // register provided classes var symbolsClassProvidedInit = new ModuleClassProvidedInitializeSymbol(); var initializeClassProvidedMethod = CodegenMethod .MakeParentNode(typeof(void), typeof(EPCompilerImpl), symbolsClassProvidedInit, classScope) .AddParam(typeof(EPModuleClassProvidedInitServices), ModuleClassProvidedInitializeSymbol.REF_INITSVC.Ref); foreach (var currClazz in compileTimeServices.ClassProvidedCompileTimeRegistry.Classes) { var addClassProvided = RegisterClassProvidedCodegen( currClazz, initializeClassProvidedMethod, classScope, symbolsClassProvidedInit); initializeClassProvidedMethod.Block.Expression(LocalMethod(addClassProvided)); } // instantiate factories for statements var statementsProp = CodegenProperty.MakePropertyNode( typeof(IList<StatementProvider>), typeof(EPCompilerImpl), CodegenSymbolProviderEmpty.INSTANCE, classScope); statementsProp.GetterBlock.DeclareVar<IList<StatementProvider>>( "statements", NewInstance(typeof(List<StatementProvider>), Constant(statementClassNames.Count))); foreach (var statementClassName in statementClassNames) { statementsProp.GetterBlock.ExprDotMethod( Ref("statements"), "Add", NewInstanceInner(statementClassName)); } statementsProp.GetterBlock.BlockReturn(Ref("statements")); // build stack CodegenStackGenerator.RecursiveBuildStack( moduleNameProp, "ModuleName", methods, properties); CodegenStackGenerator.RecursiveBuildStack( modulePropertiesProp, "ModuleProperties", methods, properties); CodegenStackGenerator.RecursiveBuildStack( moduleDependenciesProp, "ModuleDependencies", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeEventTypesMethod, "InitializeEventTypes", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeNamedWindowsMethod, "InitializeNamedWindows", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeTablesMethod, "InitializeTables", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeIndexesMethod, "InitializeIndexes", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeContextsMethod, "InitializeContexts", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeVariablesMethod, "InitializeVariables", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeExprDeclaredMethod, "InitializeExprDeclareds", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeScriptsMethod, "InitializeScripts", methods, properties); CodegenStackGenerator.RecursiveBuildStack( initializeClassProvidedMethod, "InitializeClassProvided", methods, properties); CodegenStackGenerator.RecursiveBuildStack( statementsProp, "Statements", methods, properties); var clazz = new CodegenClass( CodegenClassType.MODULEPROVIDER, typeof(ModuleProvider), moduleClassName, classScope, new EmptyList<CodegenTypedParam>(), null, methods, properties, new EmptyList<CodegenInnerClass>()); var container = compileTimeServices.Container; var compiler = container .RoslynCompiler() .WithCodeLogging(compileTimeServices.Configuration.Compiler.Logging.IsEnableCode) .WithCodeAuditDirectory(compileTimeServices.Configuration.Compiler.Logging.AuditDirectory) .WithCodegenClasses(new[] {clazz}); assembly = compiler.Compile(); return CodeGenerationIDGenerator.GenerateClassNameWithNamespace( compileTimeServices.Namespace, typeof(ModuleProvider), moduleIdentPostfix); }