public static void HandleDrop(Store store, string filename) { if (store == null || filename == null) { return; } try { StatusDisplay.Show($"Reading {filename}"); AssemblyProcessor assemblyProcessor = new AssemblyProcessor(store); TextFileProcessor textFileProcessor = new TextFileProcessor(store); textFileProcessor.LoadCache(filename); Process(store, filename, assemblyProcessor, textFileProcessor); } catch (Exception e) { ErrorDisplay.Show(e.Message); } finally { StatusDisplay.Show(string.Empty); } }
public static IEnumerable <ModelElement> HandleMultiDrop(Store store, IEnumerable <string> filenames) { List <ModelElement> newElements = new List <ModelElement>(); List <string> filenameList = filenames?.ToList(); if (store == null || filenameList == null) { return(newElements); } try { StatusDisplay.Show($"Processing {filenameList.Count} files"); AssemblyProcessor assemblyProcessor = new AssemblyProcessor(store); TextFileProcessor textFileProcessor = new TextFileProcessor(store); try { // may not work. Might not be a text file textFileProcessor.LoadCache(filenameList); } catch { // if not, no big deal. Either it's not a text file, or we'll just process suboptimally } foreach (string filename in filenameList) { newElements.AddRange(Process(store, filename, assemblyProcessor, textFileProcessor)); } } catch (Exception e) { ErrorDisplay.Show(store, e.Message); } finally { StatusDisplay.Show("Ready"); } return(newElements); }
private static void Process(Store store, string filename, AssemblyProcessor assemblyProcessor, TextFileProcessor textFileProcessor) { try { Cursor.Current = Cursors.WaitCursor; ModelRoot.BatchUpdating = true; if (IsAssembly(filename)) { using (Transaction tx = store.TransactionManager.BeginTransaction("Process dropped assembly")) { if (assemblyProcessor.Process(filename)) { StatusDisplay.Show("Creating diagram elements. This might take a while..."); tx.Commit(); ModelDisplay.LayoutDiagram(store.ModelRoot().GetActiveDiagram() as EFModelDiagram); } } } else { using (Transaction tx = store.TransactionManager.BeginTransaction("Process dropped class")) { if (textFileProcessor.Process(filename)) { StatusDisplay.Show("Creating diagram elements. This might take a while..."); tx.Commit(); } } } } finally { Cursor.Current = Cursors.Default; ModelRoot.BatchUpdating = false; StatusDisplay.Show(""); } }
public bool Process(string inputFile, out List <ModelElement> newElements) { if (string.IsNullOrEmpty(inputFile)) { throw new ArgumentNullException(nameof(inputFile)); } newElements = new List <ModelElement>(); // did the user drop an intermediate file (one created by one of the parsers)? If so, process it and return the results AssemblyProcessor assemblyProcessor = new AssemblyProcessor(Store); if (assemblyProcessor.TryProcessIntermediateFile(inputFile, newElements)) { return(true); } try { // read the file string fileContents = File.ReadAllText(inputFile); // parse the contents SyntaxTree tree = CSharpSyntaxTree.ParseText(fileContents); if (tree.GetRoot() is CompilationUnitSyntax root) { List <ClassDeclarationSyntax> classDecls = root.DescendantNodes().OfType <ClassDeclarationSyntax>().Where(classDecl => classDecl.BaseList == null || classDecl.BaseList.Types.FirstOrDefault()?.ToString() != "DbContext").ToList(); List <EnumDeclarationSyntax> enumDecls = root.DescendantNodes().OfType <EnumDeclarationSyntax>().ToList(); if (!classDecls.Any() && !enumDecls.Any()) { WarningDisplay.Show($"Couldn't find any classes or enums to add to the model in {inputFile}"); return(false); } // keep this order: enums, classes, class properties newElements.AddRange(enumDecls.Select(d => ProcessEnum(d)).Where(e => e != null)); List <ModelClass> processedClasses = new List <ModelClass>(); List <ClassDeclarationSyntax> badClasses = new List <ClassDeclarationSyntax>(); foreach (ClassDeclarationSyntax classDecl in classDecls) { ModelClass modelClass = ProcessClass(classDecl, newElements); if (modelClass == null) { badClasses.Add(classDecl); } else { processedClasses.Add(modelClass); } } // process last so all classes and enums are already in the model foreach (ClassDeclarationSyntax classDecl in classDecls.Except(badClasses)) { ProcessProperties(classDecl); } // now that all the properties are in, go through the classes again and ensure identities are present based on convention // ReSharper disable once LoopCanBePartlyConvertedToQuery foreach (ModelClass modelClass in processedClasses.Where(c => !c.AllIdentityAttributes.Any())) { // no identity attribute. Only look in current class for attributes that could be identity by convention List <ModelAttribute> identitiesByConvention = modelClass.Attributes.Where(a => a.Name == "Id" || a.Name == $"{modelClass.Name}Id").ToList(); // if both 'Id' and '[ClassName]Id' are present, don't do anything since we don't know which to make the identity if (identitiesByConvention.Count == 1) { using (Transaction transaction = Store.TransactionManager.BeginTransaction("Add identity")) { identitiesByConvention[0].IsIdentity = true; transaction.Commit(); } } } } } catch { ErrorDisplay.Show(Store, "Error interpreting " + inputFile); return(false); } return(true); }
private static IEnumerable <ModelElement> Process(Store store, string filename, AssemblyProcessor assemblyProcessor, TextFileProcessor textFileProcessor) { List <ModelElement> newElements; Cursor prev = Cursor.Current; try { Cursor.Current = Cursors.WaitCursor; ModelRoot.BatchUpdating = true; using (Transaction tx = store.TransactionManager.BeginTransaction("Process drop")) { bool processingResult = IsAssembly(filename) ? assemblyProcessor.Process(filename, out newElements) : textFileProcessor.Process(filename, out newElements); if (processingResult) { StatusDisplay.Show("Creating diagram elements. This might take a while..."); tx.Commit(); } else { newElements = new List <ModelElement>(); } } } finally { Cursor.Current = prev; ModelRoot.BatchUpdating = false; StatusDisplay.Show("Ready"); } return(newElements); }