internal static IDisposable SetupSearchModelEventsObserver(NodeSearchModel model, IEventController controller, ILibraryViewCustomization customization, int throttleTime = 200) { customization.SpecificationUpdated += (o, e) => controller.RaiseEvent("libraryDataUpdated"); var observer = new EventObserver <NodeSearchElement, IEnumerable <NodeSearchElement> >( elements => NotifySearchModelUpdate(customization, elements), CollectToList ).Throttle(TimeSpan.FromMilliseconds(throttleTime)); Action <NodeSearchElement> handler = (searchElement) => { var libraryViewController = (controller as LibraryViewController); if ((libraryViewController != null) && (libraryViewController.disableObserver)) { return; } observer.OnEvent(searchElement); }; Action <NodeSearchElement> onRemove = e => handler(null); //Set up the event callback model.EntryAdded += handler; model.EntryRemoved += onRemove; model.EntryUpdated += handler; //Set up the dispose event handler observer.Disposed += () => { model.EntryAdded -= handler; model.EntryRemoved -= onRemove; model.EntryUpdated -= handler; }; return(observer); }
/// <summary> /// As we rely on search when generating markdown files and matching them with content from the DynamoDictionary /// we need to add all NodeModel nodes to the SearchModel. /// </summary> /// <param name="asm"></param> /// <param name="nodeModelType"></param> /// <param name="searchModel"></param> private static void AddNodeModelsToSearchModel(Assembly asm, NodeSearchModel searchModel) { System.Type[] typesInAsm = null; try { typesInAsm = asm.GetTypes(); } // see https://docs.microsoft.com/en-us/dotnet/api/system.reflection.assembly.gettypes?view=netframework-4.8#remarks catch (ReflectionTypeLoadException ex) { Program.VerboseControlLog(ex.Message); typesInAsm = ex.Types; } var nodeTypes = typesInAsm .Where(x => NodeModelAssemblyLoader.IsNodeSubType(x)) .Select(t => new TypeLoadData(t)) .Where(type => type != null && !type.IsDeprecated && !type.IsHidden) .ToList(); foreach (var type in nodeTypes) { Program.VerboseControlLog($"adding nodeModelSearchElement for {type.Category} {type.Name}"); searchModel.Add(new NodeModelSearchElement(type)); } }
internal SearchViewModel(DynamoViewModel dynamoViewModel, NodeSearchModel model) { Model = model; this.dynamoViewModel = dynamoViewModel; MaxNumSearchResults = 15; InitializeCore(); }
/// <summary> /// As we rely on search when generating markdown files and matching them with content from the DynamoDictionary /// we need to add all ZT nodes to the SearchModel. /// </summary> /// <param name="funcGroup"></param> /// <param name="nodeSearchModel"></param> private static void AddFunctionGroupToSearch(FunctionGroup funcGroup, NodeSearchModel nodeSearchModel) { foreach (var functionDescriptor in funcGroup.Functions) { if (functionDescriptor.IsVisibleInLibrary) { nodeSearchModel.Add(new ZeroTouchSearchElement(functionDescriptor)); } } }
private static List <MdFileInfo> FileInfosFromSearchModel(NodeSearchModel nodeSearchModel) { var fileInfos = new List <MdFileInfo>(); foreach (var entry in nodeSearchModel.SearchEntries) { if (MdFileInfo.TryGetMdFileInfoFromSearchEntry(entry, out MdFileInfo info)) { fileInfos.Add(info); } } return(fileInfos); }
public void LibraryDataUpdatedEventRaised() { const string libraryDataUpdated = "libraryDataUpdated"; var timeout = 50; //50 milliseconds var resetevent = new AutoResetEvent(false); var model = new NodeSearchModel(); var controller = new Mock <IEventController>(); controller.Setup(c => c.RaiseEvent(It.IsAny <string>(), It.IsAny <object[]>())).Callback(() => resetevent.Set()); var customization = new LibraryViewCustomization(); var disposable = LibraryViewController.SetupSearchModelEventsObserver(model, controller.Object, customization, timeout); controller.Verify(c => c.RaiseEvent(libraryDataUpdated, It.IsAny <object[]>()), Times.Never); var d1 = MockNodeSearchElement("A", "B"); var d2 = MockNodeSearchElement("C", "D"); var d3 = MockNodeSearchElement("E", "F"); model.Add(d1.Object); model.Add(d2.Object); model.Add(d3.Object); Assert.AreEqual(3, model.NumElements); Assert.IsTrue(resetevent.WaitOne(timeout * 200)); resetevent.Dispose(); controller.Verify(c => c.RaiseEvent(libraryDataUpdated), Times.Once); var spec = customization.GetSpecification(); var section = spec.sections.FirstOrDefault(); Assert.AreEqual(1, spec.sections.Count); //There must be a section named "Add-ons" now. Assert.AreEqual("Add-ons", section.text); Assert.AreEqual(3, section.include.Count); Assert.AreEqual("A, C, E", string.Join(", ", section.include.Select(i => i.path))); //Dispose disposable.Dispose(); d1 = MockNodeSearchElement("G", "B"); d2 = MockNodeSearchElement("H", "D"); d3 = MockNodeSearchElement("I", "F"); model.Add(d1.Object); model.Add(d2.Object); model.Add(d3.Object); Assert.AreEqual(6, model.NumElements); controller.Verify(c => c.RaiseEvent(libraryDataUpdated, It.IsAny <object[]>()), Times.Once); }
internal SearchViewModel(DynamoViewModel dynamoViewModel) { Model = dynamoViewModel.Model.SearchModel; this.dynamoViewModel = dynamoViewModel; IPathManager pathManager = null; if (dynamoViewModel != null && (dynamoViewModel.Model != null)) { pathManager = dynamoViewModel.Model.PathManager; } iconServices = new IconServices(pathManager); InitializeCore(); }
private void ButtonClick(object sender, RoutedEventArgs e) { Button but = e.Source as Button; string content = but.Content.ToString().ToUpper(); FrameworkElement fe = sender as FrameworkElement; FavouriteNodesViewModel dc = fe.DataContext as FavouriteNodesViewModel; ReadyParams rp = dc.ReadyParamType; var vlp = rp as ViewLoadedParams; var dynViewModel = vlp.DynamoWindow.DataContext as DynamoViewModel; var dm = dynViewModel.Model as DynamoModel; NodeSearchModel nsm = dm.SearchModel; List <Dynamo.Search.SearchElements.NodeSearchElement> nodes = nsm.SearchEntries.ToList(); List <int> nodePosition = new List <int>(); List <string> nodeNames = new List <string>(); for (int i = 0; i < nodes.Count; i++) { nodeNames.Add(nodes[i].FullName); if (nodes[i].FullName.ToUpper().Contains(content)) { nodePosition.Add(i); } } if (nodePosition.Count != 0) { MethodInfo dynMethod = nodes[(nodePosition[0])].GetType().GetMethod("ConstructNewNodeModel", BindingFlags.NonPublic | BindingFlags.Instance); object obj = dynMethod.Invoke(nodes[(nodePosition[0])], new object[] { }); NodeModel nM = obj as NodeModel; try { dm.ExecuteCommand(new DynamoModel.CreateNodeCommand(nM, 0, 0, true, false)); } catch (Exception) { } } }
/// <summary> /// Helper method for custom node adding and removing /// </summary> public static void AssertAddAndRemoveCustomNode( NodeSearchModel searchModel, string nodeName, string catName, string descr = "Bla", string path = "Bla") { var dummyInfo = new CustomNodeInfo(Guid.NewGuid(), nodeName, catName, descr, path); var dummySearch = new CustomNodeSearchElement(null, dummyInfo); searchModel.Add(dummySearch); var res = searchModel.Search(nodeName).ToList(); Assert.AreNotEqual(0, res.Count()); Assert.AreEqual(res[0].Name, nodeName); searchModel.Remove(dummySearch); res = searchModel.Search(nodeName).ToList(); Assert.AreEqual(0, res.Count()); }
internal SearchViewModel(DynamoViewModel dynamoViewModel) { Model = dynamoViewModel.Model.SearchModel; this.dynamoViewModel = dynamoViewModel; IPathManager pathManager = null; if (dynamoViewModel != null && (dynamoViewModel.Model != null)) { pathManager = dynamoViewModel.Model.PathManager; } iconServices = new IconServices(pathManager); MaxNumSearchResults = 15; selectionNavigator = new SelectionNavigator(SearchRootCategories); InitializeCore(); }
public void SearchHighlightMarginConverterTest() { var converter = new SearchHighlightMarginConverter(); var textBlock = new TextBlock { Width = 50, Height = 10 }; # region dynamoViewModel and searchModel DynamoViewModel dynamoViewModel = DynamoViewModel.Start(); var searchModel = new NodeSearchModel(); # endregion var searhViewModel = new SearchViewModel(dynamoViewModel); object[] array = { textBlock, searhViewModel }; var thickness = new Thickness(0, 0, textBlock.ActualWidth, textBlock.ActualHeight); object result; //1. Array is null. //2. TextBlock.Text is empty. //3. TextBlock contains highlighted phrase. // 1 case Assert.Throws<NullReferenceException>(() => converter.Convert(null, null, null, null)); // 2 case textBlock.Text = ""; array[0] = textBlock; result = converter.Convert(array, null, null, null); Assert.AreEqual(thickness, result); // 3 case // This case we can't check properly, because TextBlock.ActualWidth and TextBlock.ActualHeight equals 0. textBlock.Text = "abcd"; array[0] = textBlock; searhViewModel.SearchText = "a"; thickness = new Thickness(0, 0, -6.6733333333333338, 0); result = converter.Convert(array, null, null, null); Assert.AreEqual(thickness, result); var shutdownParams = new DynamoViewModel.ShutdownParams(shutdownHost: false, allowCancellation: false); dynamoViewModel.PerformShutdownSequence(shutdownParams); }
// Just for tests. internal SearchViewModel(NodeSearchModel model) { Model = model; selectionNavigator = new SelectionNavigator(SearchRootCategories); InitializeCore(); }
internal SearchViewModel(DynamoViewModel dynamoViewModel) { Model = dynamoViewModel.Model.SearchModel; this.dynamoViewModel = dynamoViewModel; IPathManager pathManager = null; if (dynamoViewModel != null && (dynamoViewModel.Model != null)) pathManager = dynamoViewModel.Model.PathManager; iconServices = new IconServices(pathManager); MaxNumSearchResults = 15; selectionNavigator = new SelectionNavigator(SearchRootCategories); InitializeCore(); }
public void Init() { search = new NodeSearchModel(); }
// Just for tests. internal SearchViewModel(NodeSearchModel model) { Model = model; InitializeCore(); }
private static List <MdFileInfo> Scan(IEnumerable <string> assemblyPaths) { var fileInfos = new List <MdFileInfo>(); var nodeSearchModel = new NodeSearchModel(); var pathManager = new PathManager(new PathManagerParams()); Console.WriteLine($"Starting scan of following assemblies: {string.Join(", ", assemblyPaths)}"); var functionGroups = new Dictionary <string, Dictionary <string, FunctionGroup> >(new LibraryPathComparer()); foreach (var path in assemblyPaths) { try { var functionDescriptors = new List <FunctionDescriptor>(); if (new FileInfo(path).Extension == ".ds") { var dsDescriptors = GetFunctionDescriptorsFromDsFile(pathManager, path); if (dsDescriptors != null) { functionDescriptors.AddRange(dsDescriptors); } } else { //load the assembly. Assembly asm = Assembly.LoadFrom(path); AssemblyName name = asm.GetName(); if (NodeModelAssemblyLoader.ContainsNodeModelSubType(asm)) { AddNodeModelsToSearchModel(asm, nodeSearchModel); continue; } var dllDescriptors = GetFunctionDescriptorsFromDll(pathManager, asm); if (dllDescriptors != null) { functionDescriptors.AddRange(dllDescriptors); } } foreach (var descriptor in functionDescriptors) { Dictionary <string, FunctionGroup> functionGroupDict; if (!functionGroups.TryGetValue(descriptor.Assembly, out functionGroupDict)) { functionGroupDict = new Dictionary <string, FunctionGroup>(); functionGroups[descriptor.Assembly] = functionGroupDict; } var qualifiedName = descriptor.QualifiedName; FunctionGroup functionGroup; if (!functionGroupDict.TryGetValue(qualifiedName, out functionGroup)) { functionGroup = new FunctionGroup(qualifiedName); functionGroupDict[qualifiedName] = functionGroup; } functionGroup.AddFunctionDescriptor(descriptor); } } catch (Exception e) { CommandHandler.LogExceptionToConsole(e); continue; } } if (functionGroups.Any()) { AddFunctionGroupsToSearch(functionGroups.Values.SelectMany(x => x.Values.Select(g => g)), nodeSearchModel); } fileInfos.AddRange(FileInfosFromSearchModel(nodeSearchModel)); Console.WriteLine($"{fileInfos.Count()} nodes found during scan"); return(fileInfos); }
public void Init() { model = new NodeSearchModel(); viewModel = new SearchViewModel(null, model); }
/// <summary> /// Constructor /// </summary> /// <param name="items"></param> public SearchResultDataProvider(NodeSearchModel model, IconResourceProvider iconProvider) : base(model, iconProvider) { }
public void Init() { model = new NodeSearchModel(); viewModel = new SearchViewModel(model); }
// Just for tests. internal SearchViewModel(NodeSearchModel model) { Model = model; selectionNavigator = new SelectionNavigator(SearchRootCategories); InitializeCore(); }
protected DynamoModel(IStartConfiguration config) { ClipBoard = new ObservableCollection<ModelBase>(); pathManager = new PathManager(new PathManagerParams { CorePath = config.DynamoCorePath, PathResolver = config.PathResolver }); // Ensure we have all directories in place. pathManager.EnsureDirectoryExistence(); Context = config.Context; IsTestMode = config.StartInTestMode; DebugSettings = new DebugSettings(); Logger = new DynamoLogger(DebugSettings, pathManager.LogDirectory); MigrationManager = new MigrationManager(DisplayFutureFileMessage, DisplayObsoleteFileMessage); MigrationManager.MessageLogged += LogMessage; MigrationManager.MigrationTargets.Add(typeof(WorkspaceMigrations)); var thread = config.SchedulerThread ?? new DynamoSchedulerThread(); Scheduler = new DynamoScheduler(thread, IsTestMode); Scheduler.TaskStateChanged += OnAsyncTaskStateChanged; geometryFactoryPath = config.GeometryFactoryPath; IPreferences preferences = CreateOrLoadPreferences(config.Preferences); var settings = preferences as PreferenceSettings; if (settings != null) { PreferenceSettings = settings; PreferenceSettings.PropertyChanged += PreferenceSettings_PropertyChanged; } InitializePreferences(preferences); InitializeInstrumentationLogger(); if (!isTestMode && this.PreferenceSettings.IsFirstRun) { DynamoMigratorBase migrator = null; try { migrator = DynamoMigratorBase.MigrateBetweenDynamoVersions(pathManager, config.PathResolver); } catch (Exception e) { Logger.Log(e.Message); } if (migrator != null) { var isFirstRun = this.PreferenceSettings.IsFirstRun; this.PreferenceSettings = migrator.PreferenceSettings; // Preserve the preference settings for IsFirstRun as this needs to be set // only by UsageReportingManager this.PreferenceSettings.IsFirstRun = isFirstRun; } } SearchModel = new NodeSearchModel(); SearchModel.ItemProduced += node => ExecuteCommand(new CreateNodeCommand(node, 0, 0, true, true)); NodeFactory = new NodeFactory(); NodeFactory.MessageLogged += LogMessage; CustomNodeManager = new CustomNodeManager(NodeFactory, MigrationManager); InitializeCustomNodeManager(); extensionManager = new ExtensionManager(); extensionManager.MessageLogged += LogMessage; var extensions = config.Extensions ?? ExtensionManager.ExtensionLoader.LoadDirectory(pathManager.ExtensionsDirectory); if (extensions.Any()) { var startupParams = new StartupParams(config.AuthProvider, pathManager, CustomNodeManager); foreach (var ext in extensions) { ext.Startup(startupParams); ext.Load(preferences, pathManager); ext.RequestLoadNodeLibrary += LoadNodeLibrary; ExtensionManager.Add(ext); } } Loader = new NodeModelAssemblyLoader(); Loader.MessageLogged += LogMessage; DisposeLogic.IsShuttingDown = false; // Create a core which is used for parsing code and loading libraries var libraryCore = new ProtoCore.Core(new Options { RootCustomPropertyFilterPathName = string.Empty }); libraryCore.Compilers.Add(Language.kAssociative, new Compiler(libraryCore)); libraryCore.Compilers.Add(Language.kImperative, new ProtoImperative.Compiler(libraryCore)); libraryCore.ParsingMode = ParseMode.AllowNonAssignment; LibraryServices = new LibraryServices(libraryCore, pathManager); LibraryServices.MessageLogged += LogMessage; LibraryServices.LibraryLoaded += LibraryLoaded; ResetEngineInternal(); AddHomeWorkspace(); AuthenticationManager = new AuthenticationManager(config.AuthProvider); UpdateManager = config.UpdateManager ?? new DefaultUpdateManager(null); UpdateManager.Log += UpdateManager_Log; if (!IsTestMode) { DefaultUpdateManager.CheckForProductUpdate(UpdateManager); } Logger.Log(string.Format("Dynamo -- Build {0}", Assembly.GetExecutingAssembly().GetName().Version)); InitializeNodeLibrary(preferences); LogWarningMessageEvents.LogWarningMessage += LogWarningMessage; StartBackupFilesTimer(); TraceReconciliationProcessor = this; foreach (var ext in ExtensionManager.Extensions) { try { ext.Ready(new ReadyParams()); } catch (Exception ex) { Logger.Log(ex.Message); } } }
/// <summary> /// Constructor /// </summary> /// <param name="items"></param> public NodeItemDataProvider(NodeSearchModel model) : base(false) { this.model = model; }
public NodeItemDataProvider(NodeSearchModel model, IconResourceProvider iconProvider) { this.model = model; this.iconProvider = iconProvider; }
/// <summary> /// Constructor /// </summary> /// <param name="items"></param> public SearchResultDataProvider(NodeSearchModel model) : base(model) { }
internal SearchViewModel(DynamoViewModel dynamoViewModel) { Model = dynamoViewModel.Model.SearchModel; this.dynamoViewModel = dynamoViewModel; IPathManager pathManager = null; if (dynamoViewModel != null && (dynamoViewModel.Model != null)) pathManager = dynamoViewModel.Model.PathManager; iconServices = new IconServices(pathManager); InitializeCore(); }
private static void AddFunctionGroupsToSearch(IEnumerable <FunctionGroup> functionGroups, NodeSearchModel nodeSearchModel) { foreach (var funcGroup in functionGroups) { AddFunctionGroupToSearch(funcGroup, nodeSearchModel); } }
/// <summary> /// Default constructor for DynamoModel /// </summary> /// <param name="config">Start configuration</param> protected DynamoModel(IStartConfiguration config) { ClipBoard = new ObservableCollection<ModelBase>(); pathManager = new PathManager(new PathManagerParams { CorePath = config.DynamoCorePath, HostPath = config.DynamoHostPath, PathResolver = config.PathResolver }); // Ensure we have all directories in place. var exceptions = new List<Exception>(); pathManager.EnsureDirectoryExistence(exceptions); Context = config.Context; IsTestMode = config.StartInTestMode; var config2 = config as IStartConfiguration2; IsHeadless = (config2 != null) ? config2.IsHeadless : false; DebugSettings = new DebugSettings(); Logger = new DynamoLogger(DebugSettings, pathManager.LogDirectory); foreach (var exception in exceptions) { Logger.Log(exception); // Log all exceptions. } MigrationManager = new MigrationManager(DisplayFutureFileMessage, DisplayObsoleteFileMessage); MigrationManager.MessageLogged += LogMessage; MigrationManager.MigrationTargets.Add(typeof(WorkspaceMigrations)); var thread = config.SchedulerThread ?? new DynamoSchedulerThread(); Scheduler = new DynamoScheduler(thread, config.ProcessMode); Scheduler.TaskStateChanged += OnAsyncTaskStateChanged; geometryFactoryPath = config.GeometryFactoryPath; IPreferences preferences = CreateOrLoadPreferences(config.Preferences); var settings = preferences as PreferenceSettings; if (settings != null) { PreferenceSettings = settings; PreferenceSettings.PropertyChanged += PreferenceSettings_PropertyChanged; } InitializeInstrumentationLogger(); if (!IsTestMode && PreferenceSettings.IsFirstRun) { DynamoMigratorBase migrator = null; try { var dynamoLookup = config.UpdateManager != null && config.UpdateManager.Configuration != null ? config.UpdateManager.Configuration.DynamoLookUp : null; migrator = DynamoMigratorBase.MigrateBetweenDynamoVersions(pathManager, dynamoLookup); } catch (Exception e) { Logger.Log(e.Message); } if (migrator != null) { var isFirstRun = PreferenceSettings.IsFirstRun; PreferenceSettings = migrator.PreferenceSettings; // Preserve the preference settings for IsFirstRun as this needs to be set // only by UsageReportingManager PreferenceSettings.IsFirstRun = isFirstRun; } } InitializePreferences(PreferenceSettings); // At this point, pathManager.PackageDirectories only has 1 element which is the directory // in AppData. If list of PackageFolders is empty, add the folder in AppData to the list since there // is no additional location specified. Otherwise, update pathManager.PackageDirectories to include // PackageFolders if (PreferenceSettings.CustomPackageFolders.Count == 0) PreferenceSettings.CustomPackageFolders = new List<string> {pathManager.UserDataDirectory}; //Make sure that the default package folder is added in the list if custom packages folder. var userDataFolder = pathManager.GetUserDataFolder(); //Get the default user data path if (Directory.Exists(userDataFolder) && !PreferenceSettings.CustomPackageFolders.Contains(userDataFolder)) { PreferenceSettings.CustomPackageFolders.Add(userDataFolder); } pathManager.Preferences = PreferenceSettings; SearchModel = new NodeSearchModel(); SearchModel.ItemProduced += node => ExecuteCommand(new CreateNodeCommand(node, 0, 0, true, true)); NodeFactory = new NodeFactory(); NodeFactory.MessageLogged += LogMessage; CustomNodeManager = new CustomNodeManager(NodeFactory, MigrationManager); InitializeCustomNodeManager(); extensionManager = new ExtensionManager(); extensionManager.MessageLogged += LogMessage; var extensions = config.Extensions ?? LoadExtensions(); Loader = new NodeModelAssemblyLoader(); Loader.MessageLogged += LogMessage; // Create a core which is used for parsing code and loading libraries var libraryCore = new ProtoCore.Core(new Options()); libraryCore.Compilers.Add(Language.Associative, new Compiler(libraryCore)); libraryCore.Compilers.Add(Language.Imperative, new ProtoImperative.Compiler(libraryCore)); libraryCore.ParsingMode = ParseMode.AllowNonAssignment; LibraryServices = new LibraryServices(libraryCore, pathManager, PreferenceSettings); LibraryServices.MessageLogged += LogMessage; LibraryServices.LibraryLoaded += LibraryLoaded; ResetEngineInternal(); AddHomeWorkspace(); AuthenticationManager = new AuthenticationManager(config.AuthProvider); UpdateManager = config.UpdateManager ?? new DefaultUpdateManager(null); // config.UpdateManager has to be cast to IHostUpdateManager in order to extract the HostVersion and HostName // see IHostUpdateManager summary for more details var hostUpdateManager = config.UpdateManager as IHostUpdateManager; if (hostUpdateManager != null) { HostName = hostUpdateManager.HostName; HostVersion = hostUpdateManager.HostVersion == null ? null : hostUpdateManager.HostVersion.ToString(); } else { HostName = string.Empty; HostVersion = null; } UpdateManager.Log += UpdateManager_Log; if (!IsTestMode && !IsHeadless) { DefaultUpdateManager.CheckForProductUpdate(UpdateManager); } Logger.Log(string.Format("Dynamo -- Build {0}", Assembly.GetExecutingAssembly().GetName().Version)); InitializeNodeLibrary(PreferenceSettings); if (extensions.Any()) { var startupParams = new StartupParams(config.AuthProvider, pathManager, new ExtensionLibraryLoader(this), CustomNodeManager, GetType().Assembly.GetName().Version, PreferenceSettings); foreach (var ext in extensions) { var logSource = ext as ILogSource; if (logSource != null) logSource.MessageLogged += LogMessage; try { ext.Startup(startupParams); } catch (Exception ex) { Logger.Log(ex.Message); } ExtensionManager.Add(ext); } } LogWarningMessageEvents.LogWarningMessage += LogWarningMessage; StartBackupFilesTimer(); TraceReconciliationProcessor = this; foreach (var ext in ExtensionManager.Extensions) { try { ext.Ready(new ReadyParams(this)); } catch (Exception ex) { Logger.Log(ex.Message); } } }
public void Init() { search = new NodeSearchModel(); }
// Just for tests. internal SearchViewModel(NodeSearchModel model) { Model = model; InitializeCore(); }
/// <summary> /// Helper method for custom node adding and removing /// </summary> public static void AssertAddAndRemoveCustomNode( NodeSearchModel searchModel, string nodeName, string catName, string descr = "Bla", string path = "Bla") { var dummyInfo = new CustomNodeInfo(Guid.NewGuid(), nodeName, catName, descr, path); var dummySearch = new CustomNodeSearchElement(null, dummyInfo); searchModel.Add(dummySearch); var res = searchModel.Search(nodeName).ToList(); Assert.AreNotEqual(0, res.Count()); Assert.AreEqual(res[0].Name, nodeName); searchModel.Remove(dummySearch); res = searchModel.Search(nodeName).ToList(); Assert.AreEqual(0, res.Count()); }