Added unit test for SearchApi, but couldn't get it to work per #447. Any help??

master
David Hall 2024-05-28 20:16:27 -06:00
parent a6b7eaa606
commit 2c8b89fdbf
5 changed files with 124 additions and 12 deletions

View File

@ -15,7 +15,7 @@
<NeutralLanguage>en-US</NeutralLanguage>
<Nullable>enable</Nullable>
<SignAssembly>true</SignAssembly>
<NoWarn>$(NoWarn);NETSDK1138;SYSLIB0003;SYSLIB0004;SYSLIB0011;IL2026;IL2050;IL2075;IL2067;IL2070;IL2072;IL2077;IL2080;IL2087;IL2090;CS0618;CA1401;CA2101;SYSLIB1054;</NoWarn>
<NoWarn>$(NoWarn);NETSDK1138;SYSLIB0003;SYSLIB0004;SYSLIB0011;IL2026;IL2050;IL2075;IL2067;IL2070;IL2072;IL2077;IL2080;IL2087;IL2090;CS0618;CA1041;CA1401;CA2101;SYSLIB1054;SYSLIB1096;</NoWarn>
<AccelerateBuildsInVisualStudio>true</AccelerateBuildsInVisualStudio>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)'=='Release'">

View File

@ -2863,7 +2863,8 @@ public static partial class SearchApi
// OnItemsChanged( DWORD dwNumberOfChanges, SEARCH_ITEM_CHANGE [] rgDataChangeEntries, DWORD [] rgdwDocIds, HRESULT []
// rghrCompletionCodes );
[PInvokeData("searchapi.h")]
void OnItemsChanged(uint dwNumberOfChanges, [In, MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 0)] SEARCH_ITEM_CHANGE[] rgDataChangeEntries, [Out, MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 0)] uint[] rgdwDocIds, [Out, MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 0)] HRESULT[] rghrCompletionCodes);
void OnItemsChanged(uint dwNumberOfChanges, [In, MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 0)] SEARCH_ITEM_CHANGE[] rgDataChangeEntries,
[Out, MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 0)] uint[] rgdwDocIds, [Out, MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 0)] HRESULT[] rghrCompletionCodes);
}
/// <summary>Provides methods for accessing thesaurus information.</summary>
@ -2929,7 +2930,7 @@ public static partial class SearchApi
// https://docs.microsoft.com/en-us/windows/desktop/api/searchapi/nf-searchapi-isearchlanguagesupport-loadwordbreaker HRESULT
// LoadWordBreaker( LCID lcid, REFIID riid, void **ppWordBreaker, LCID *pLcidUsed );
[PInvokeData("searchapi.h")]
void LoadWordBreaker(uint lcid, in Guid riid, [MarshalAs(UnmanagedType.IUnknown, IidParameterIndex = 1)] out object ppWordBreaker, out uint pLcidUsed);
void LoadWordBreaker(LCID lcid, in Guid riid, [MarshalAs(UnmanagedType.IUnknown, IidParameterIndex = 1)] out object ppWordBreaker, out LCID pLcidUsed);
/// <summary>Retrieves an interface to the word stemmer registered for the specified language code identifier (LCID).</summary>
/// <param name="lcid">
@ -2951,7 +2952,7 @@ public static partial class SearchApi
// https://docs.microsoft.com/en-us/windows/desktop/api/searchapi/nf-searchapi-isearchlanguagesupport-loadstemmer HRESULT
// LoadStemmer( LCID lcid, REFIID riid, void **ppStemmer, LCID *pLcidUsed );
[PInvokeData("searchapi.h")]
void LoadStemmer(uint lcid, in Guid riid, [MarshalAs(UnmanagedType.IUnknown, IidParameterIndex = 1)] out object ppStemmer, out uint pLcidUsed);
void LoadStemmer(LCID lcid, in Guid riid, [MarshalAs(UnmanagedType.IUnknown, IidParameterIndex = 1)] out object ppStemmer, out LCID pLcidUsed);
/// <summary>
/// Determines whether the query token is a prefix of the document token, disregarding case, width, and (optionally) diacritics.
@ -4086,7 +4087,7 @@ public static partial class SearchApi
// put_QueryContentLocale( LCID lcid );
[PInvokeData("searchapi.h")]
[DispId(0x60010001)]
uint QueryContentLocale { [param: In] set; get; }
LCID QueryContentLocale { [param: In] set; get; }
/// <summary>
/// Gets or sets the language code identifier (LCID) for the locale to use when parsing Advanced Query Syntax (AQS) keywords.
@ -4100,7 +4101,7 @@ public static partial class SearchApi
// put_QueryKeywordLocale( LCID lcid );
[PInvokeData("searchapi.h")]
[DispId(0x60010003)]
uint QueryKeywordLocale { [param: In] set; get; }
LCID QueryKeywordLocale { [param: In] set; get; }
/// <summary>Gets or sets a value that specifies how query terms are to be expanded.</summary>
/// <value>
@ -6065,6 +6066,26 @@ public static partial class SearchApi
HRESULT LoadIFilterWithPrivateComActivation(in FILTERED_DATA_SOURCES filteredSources, [In, MarshalAs(UnmanagedType.Bool)] bool useDefault, out Guid filterClsid, [MarshalAs(UnmanagedType.Bool)] out bool isFilterPrivateComActivated, out IFilter filterObj);
}
/// <summary>Gets the change notification sink interface.</summary>
/// <param name="mgr">The <see cref="ISearchCatalogManager"/> instance.</param>
/// <param name="pISearchNotifyInlineSite"><para>Type: <c>ISearchNotifyInlineSite*</c></para>
/// <para>A pointer to your ISearchNotifyInlineSite interface.</para></param>
/// <param name="pGUIDCatalogResetSignature"><para>Type: <c>GUID*</c></para>
/// <para>Receives a pointer to the GUID representing the catalog reset. If this GUID changes, all notifications must be resent.</para></param>
/// <param name="pGUIDCheckPointSignature"><para>Type: <c>GUID*</c></para>
/// <para>Receives a pointer to the GUID representing a checkpoint.</para></param>
/// <param name="pdwLastCheckPointNumber"><para>Type: <c>DWORD*</c></para>
/// <para>Receives a pointer to the number indicating the last checkpoint to be saved.</para></param>
/// <returns>Receives a pointer to the <see cref="ISearchItemsChangedSink"/> interface.</returns>
// https://docs.microsoft.com/en-us/windows/desktop/api/searchapi/nf-searchapi-isearchcatalogmanager-getitemschangedsink HRESULT
// GetItemsChangedSink( ISearchNotifyInlineSite *pISearchNotifyInlineSite, REFIID riid, void **ppv, GUID
// *pGUIDCatalogResetSignature, GUID *pGUIDCheckPointSignature, DWORD *pdwLastCheckPointNumber );
public static ISearchItemsChangedSink GetItemsChangedSink(this ISearchCatalogManager mgr, ISearchNotifyInlineSite pISearchNotifyInlineSite, out Guid pGUIDCatalogResetSignature, out Guid pGUIDCheckPointSignature, out uint pdwLastCheckPointNumber)
{
mgr.GetItemsChangedSink(pISearchNotifyInlineSite, typeof(ISearchItemsChangedSink).GUID, out var ppv, out pGUIDCatalogResetSignature, out pGUIDCheckPointSignature, out pdwLastCheckPointNumber);
return (ISearchItemsChangedSink)ppv;
}
/// <summary>Describes security authentication information for content access.</summary>
// https://docs.microsoft.com/en-us/windows/desktop/api/searchapi/ns-searchapi-authentication_info typedef struct
// _AUTHENTICATION_INFO { DWORD dwSize; AUTH_TYPE atAuthenticationType; LPCWSTR pcwszUser; LPCWSTR pcwszPassword; } AUTHENTICATION_INFO;
@ -6307,7 +6328,7 @@ public static partial class SearchApi
/// <para>Type: <c>LCID</c></para>
/// <para>The LCID of the column.</para>
/// </summary>
public uint lcid;
public LCID lcid;
}
/// <summary>Specifies the changes to an indexed item.</summary>
@ -6344,7 +6365,8 @@ public static partial class SearchApi
/// or SEARCH_CHANGE_MODIFY notification. In the case of a move, this member contains the new URL of the item.
/// </para>
/// </summary>
[MarshalAs(UnmanagedType.LPWStr)] public string lpwszURL;
[MarshalAs(UnmanagedType.LPWStr)]
public string? lpwszURL;
/// <summary>
/// <para>Type: <c>LPWSTR</c></para>
@ -6353,7 +6375,8 @@ public static partial class SearchApi
/// SEARCH_CHANGE_DELETE notification.
/// </para>
/// </summary>
[MarshalAs(UnmanagedType.LPWStr)] public string lpwszOldURL;
[MarshalAs(UnmanagedType.LPWStr)]
public string? lpwszOldURL;
}
/// <summary>Describes the status of a document to be indexed.</summary>
@ -6542,7 +6565,7 @@ public static partial class SearchApi
/// word breaking of text. If the chunk is neither text-type nor a value-type with data type VT_LPWSTR, VT_LPSTR or VT_BSTR, this
/// field is ignored.
/// </summary>
public uint locale;
public LCID locale;
/// <summary>
/// The property to be applied to the chunk. See FULLPROPSPEC. If a filter requires that the same text have more than one

View File

@ -0,0 +1,8 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<AssemblyName>UnitTest.PInvoke.SearchApi</AssemblyName>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\..\..\PInvoke\SearchApi\Vanara.PInvoke.SearchApi.csproj" />
</ItemGroup>
</Project>

View File

@ -0,0 +1,64 @@
using NUnit.Framework;
using NUnit.Framework.Internal;
using System.IO;
using static Vanara.PInvoke.SearchApi;
namespace Vanara.PInvoke.Tests;
[TestFixture]
public class SearchApiTests
{
ISearchCatalogManager? catalogManager;
[OneTimeSetUp]
public void _Setup()
{
ISearchManager searchManager = new();
catalogManager = searchManager.GetCatalog("SystemIndex");
}
[OneTimeTearDown]
public void _TearDown()
{
}
//[Test]
public void GetItemsChangedSinkTest()
{
TestInlineSite testInlineSite = new(TestContext.Out);
ISearchItemsChangedSink itemsChangedSink = catalogManager!.GetItemsChangedSink(testInlineSite, out _, out _, out _);
using TemporaryDirectory tempDir = new();
string f1 = tempDir.RandomTxtFileFullPath;
File.Copy(TestCaseSources.SmallFile, f1);
Assert.That(File.Exists(f1), Is.True);
string f2 = tempDir.RandomTxtFileFullPath;
SEARCH_ITEM_CHANGE itemChange = new()
{
Change = SEARCH_KIND_OF_CHANGE.SEARCH_CHANGE_MOVE_RENAME,
Priority = SEARCH_NOTIFICATION_PRIORITY.SEARCH_NORMAL_PRIORITY,
pUserData = default, //This is supposed to be a "Pointer to user information", but I have no idea what this means or what it wants
lpwszURL = new Uri(f2).AbsoluteUri,
lpwszOldURL = new Uri(f1).AbsoluteUri
};
File.Move(f1, f2);
Assert.That(File.Exists(f2), Is.True);
// I can't get this to work. I get an exception (DTS_E_OLEDBERROR) when trying to call OnItemsChanged.
SEARCH_ITEM_CHANGE[] itemsChangedArray = [itemChange];
uint[] retInts = [0];
HRESULT[] hresults = [0];
itemsChangedSink.OnItemsChanged(1, itemsChangedArray, retInts, hresults);
Assert.That((int)hresults[0], Is.EqualTo(HRESULT.S_OK));
}
[ComVisible(true), Guid("4da1a242-8634-433a-906d-9bdba3e60b11")]
internal class TestInlineSite(TextWriter tw) : ISearchNotifyInlineSite
{
public void OnItemIndexedStatusChange([In] SEARCH_INDEXING_PHASE sipStatus, [In] uint dwNumEntries,
SEARCH_ITEM_INDEXING_STATUS[] rgItemStatusEntries) => tw.WriteLine("OnItemIndexedStatusChange");
public void OnCatalogStatusChange(in Guid guidCatalogResetSignature, in Guid guidCheckPointSignature, uint dwLastCheckPointNumber) =>
tw.WriteLine("OnCatalogStatusChange");
}
}

View File

@ -448,6 +448,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WUApi", "UnitTests\PInvoke\
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Vanara.WindowsUpdate", "WindowsUpdate\Vanara.WindowsUpdate.csproj", "{DCD4CDCF-F963-48B6-9B8F-1F273C38952F}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SearchApi", "UnitTests\PInvoke\SearchApi\SearchApi.csproj", "{B359422A-F804-46B1-BC79-A55F241C5DF3}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@ -2433,7 +2435,6 @@ Global
{A96CFF10-0967-429A-8700-4A86C97C5603}.Debug|x86.ActiveCfg = Debug|x86
{A96CFF10-0967-429A-8700-4A86C97C5603}.Debug|x86.Build.0 = Debug|x86
{A96CFF10-0967-429A-8700-4A86C97C5603}.DebugNoTests|Any CPU.ActiveCfg = DebugNoTests|Any CPU
{A96CFF10-0967-429A-8700-4A86C97C5603}.DebugNoTests|Any CPU.Build.0 = DebugNoTests|Any CPU
{A96CFF10-0967-429A-8700-4A86C97C5603}.DebugNoTests|x64.ActiveCfg = DebugNoTests|x64
{A96CFF10-0967-429A-8700-4A86C97C5603}.DebugNoTests|x64.Build.0 = DebugNoTests|x64
{A96CFF10-0967-429A-8700-4A86C97C5603}.DebugNoTests|x86.ActiveCfg = DebugNoTests|x86
@ -3318,7 +3319,6 @@ Global
{40E5CA4E-527F-4F79-875D-2342D1136FDD}.Debug|x86.ActiveCfg = Debug|x86
{40E5CA4E-527F-4F79-875D-2342D1136FDD}.Debug|x86.Build.0 = Debug|x86
{40E5CA4E-527F-4F79-875D-2342D1136FDD}.DebugNoTests|Any CPU.ActiveCfg = DebugNoTests|Any CPU
{40E5CA4E-527F-4F79-875D-2342D1136FDD}.DebugNoTests|Any CPU.Build.0 = DebugNoTests|Any CPU
{40E5CA4E-527F-4F79-875D-2342D1136FDD}.DebugNoTests|x64.ActiveCfg = DebugNoTests|x64
{40E5CA4E-527F-4F79-875D-2342D1136FDD}.DebugNoTests|x64.Build.0 = DebugNoTests|x64
{40E5CA4E-527F-4F79-875D-2342D1136FDD}.DebugNoTests|x86.ActiveCfg = DebugNoTests|x86
@ -3929,6 +3929,22 @@ Global
{DCD4CDCF-F963-48B6-9B8F-1F273C38952F}.Release|x64.Build.0 = Release|x64
{DCD4CDCF-F963-48B6-9B8F-1F273C38952F}.Release|x86.ActiveCfg = Release|x86
{DCD4CDCF-F963-48B6-9B8F-1F273C38952F}.Release|x86.Build.0 = Release|x86
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Debug|Any CPU.Build.0 = Debug|Any CPU
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Debug|x64.ActiveCfg = Debug|x64
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Debug|x64.Build.0 = Debug|x64
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Debug|x86.ActiveCfg = Debug|x86
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Debug|x86.Build.0 = Debug|x86
{B359422A-F804-46B1-BC79-A55F241C5DF3}.DebugNoTests|Any CPU.ActiveCfg = DebugNoTests|Any CPU
{B359422A-F804-46B1-BC79-A55F241C5DF3}.DebugNoTests|x64.ActiveCfg = DebugNoTests|x64
{B359422A-F804-46B1-BC79-A55F241C5DF3}.DebugNoTests|x64.Build.0 = DebugNoTests|x64
{B359422A-F804-46B1-BC79-A55F241C5DF3}.DebugNoTests|x86.ActiveCfg = DebugNoTests|x86
{B359422A-F804-46B1-BC79-A55F241C5DF3}.DebugNoTests|x86.Build.0 = DebugNoTests|x86
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Release|Any CPU.ActiveCfg = Release|Any CPU
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Release|x64.ActiveCfg = Release|x64
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Release|x64.Build.0 = Release|x64
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Release|x86.ActiveCfg = Release|x86
{B359422A-F804-46B1-BC79-A55F241C5DF3}.Release|x86.Build.0 = Release|x86
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
@ -4129,6 +4145,7 @@ Global
{9E2D6D4B-69D0-46A0-A18A-186E3FA269BD} = {212ABBD0-B724-4CFA-9D6D-E3891547FA90}
{7A2BF2BB-B565-4F0F-8EBD-5C0A57A0773B} = {212ABBD0-B724-4CFA-9D6D-E3891547FA90}
{4E84A8EA-A180-4897-9542-C529A91702AC} = {385CAD2D-0A5E-4F80-927B-D5499D126B90}
{B359422A-F804-46B1-BC79-A55F241C5DF3} = {385CAD2D-0A5E-4F80-927B-D5499D126B90}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {543FAC75-2AF1-4EF1-9609-B242B63FEED4}