다음을 통해 공유


SQL 및 AQS 접근 방식을 사용하여 인덱스 쿼리

Windows Search를 사용하여 인덱스 쿼리를 하는 방법에는 여러 가지가 있습니다. 이 항목에서는 AQS(고급 쿼리 구문) 및 SQL(구조적 쿼리 언어) 기반 방법을 간략하게 설명합니다.

이 항목은 다음과 같이 구성됩니다.

SQL 기반 쿼리

SQL은 쿼리를 정의하는 텍스트 언어입니다. SQL은 다양한 데이터베이스 기술에서 일반적입니다. Windows Search는 SQL을 사용하고, SQL의 하위 집합을 구현하고, 언어에 요소를 추가하여 확장합니다. Windows Search에서 사용하는 Windows Search SQL은 표준 SQL-92 및 SQL-99 데이터베이스 쿼리 구문의 일부를 확장하여 텍스트 기반 검색을 통해 유용성을 향상시킵니다. Windows Search SQL의 모든 기능은 Windows XP 및 Windows Server 2003 이상의 Windows Search와 호환됩니다.

Windows Search SQL 구문을 사용하는 방법에 대한 자세한 내용은 Windows Search SQL 구문을 사용하여 인덱스 쿼리 및 Windows Search SQL 구문 개요를 참조하세요.

인덱스를 쿼리하기 위한 다음 방법은 SQL 기반입니다.

OLE DB 사용

OLE DB(개체 연결 및 포함 데이터베이스)는 스프레드시트와 같은 비관계형 데이터베이스를 포함하여 여러 유형의 데이터 저장소에 균일하게 액세스할 수 있는 COM(구성 요소 개체 모델) API입니다. OLE DB는 셸 데이터 원본, 세션, 명령 및 행 집합을 포함하는 추상화 집합을 통해 액세스하는 애플리케이션에서 데이터 저장소를 분리합니다. OLE DB 공급자는 OLE DB 인터페이스를 구현하여 특정 데이터 저장소의 애플리케이션에 데이터를 제공하는 소프트웨어 구성 요소입니다.

C#의 OleDbConnection 및 OleDbSession 개체를 사용하고 C++(atlclidb.h를 통해)의 ATL(Active Template Library)에 기본 제공되는 OLE DB 지원을 사용하여 프로그래밍 방식으로 Windows Search OLE DB 공급자에 액세스할 수 있습니다. 설정해야 하는 유일한 속성은 공급자 문자열입니다.

다음 문자열을 사용할 수 있습니다.

provider=Search.CollatorDSO;EXTENDED PROPERTIES="Application=Windows"

또는 ISearchQueryHelper::get_ConnectionString 호출하여 연결 문자열 가져올 수 있습니다. 예제는 ISearchQueryHelper 사용을 참조하세요.

참고 항목

Windows Search OLE DB 공급자는 읽기 전용이며 SELECT 및 GROUP ON 문을 지원합니다. INSERT 및 DELETE 문은 지원되지 않습니다.

#include <atldbcli.h>
CDataSource cDataSource;
hr = cDataSource.OpenFromInitializationString(L"provider=Search.CollatorDSO.1;EXTENDED PROPERTIES=\"Application=Windows\"");

if (SUCCEEDED(hr))
{
    CSession cSession;
    hr = cSession.Open(cDataSource);

    if (SUCCEEDED(hr))
    {
        CCommand<CDynamicAccessor, CRowset> cCommand;
        hr = cCommand.Open(cSession, pszSQL);

        if (SUCCEEDED(hr))
        {
            for (hr = cCommand.MoveFirst(); S_OK == hr; hr = cCommand.MoveNext())
            {
                for (DBORDINAL i = 1; i <= cCommand.GetColumnCount(); i++)
                {
                    PCWSTR pszName = cCommand.GetColumnName(i);
                    // do something with the column here
                }
            }
            cCommand.Close();
        }
    }
}

OLE DB에 대한 자세한 내용은 OLE DB 프로그래밍 개요를 참조 하세요. .NET Framework Data Provider for OLE DB에 대한 자세한 내용은 System.Data.OleDb 네임스페이스 설명서를 참조하세요.

ADO 및 ADO.NET 사용

Microsoft ADO(ActiveX Data Objects) 및 ADO.NET 사용하면 공급자를 통해 데이터베이스 서버의 데이터에 액세스하고 조작할 클라이언트 애플리케이션을 작성할 수 있습니다. Windows Search는 읽기 전용 기술입니다. 데스크톱 검색을 사용하여 데이터를 검색할 수 있지만 Windows Search를 사용하여 데이터를 변경할 수는 없습니다. 그러나 검색 결과를 데이터를 변경할 수 있는 기술에 전달할 수 있습니다.

다음 코드 예제에서는 데이터 원본에 대한 연결을 열고, Windows Search SQL SELECT 문을 사용하여 RecordSet을 만들고 열고, 인덱스에서 가장 큰 5개 파일의 URL을 가져오는 방법을 보여 줍니다.

참고 항목

연결 문자열 가져오는 방법에 대한 자세한 내용은 ISearchQueryHelper 및 ISearchQueryHelper::get_Connection String을 사용하여 인덱스 쿼리를 참조하세요.

ADO 및 VBScript

'To run this snippet, save it to a file and run it using cscript.exe from a command line.
'Running the .vbs file with Windows Script Host may cause dialog boxes to open for each item returned from the index.

On Error Resume Next

Set objConnection = CreateObject("ADODB.Connection")
Set objRecordSet = CreateObject("ADODB.Recordset")

objConnection.Open "Provider=Search.CollatorDSO;Extended Properties='Application=Windows';"

objRecordSet.Open "SELECT Top 5 System.ItemPathDisplay FROM SYSTEMINDEX WHERE scope='file:' ORDER BY System.Size DESC", objConnection

objRecordSet.MoveFirst
Do Until objRecordset.EOF
    Wscript.Echo objRecordset.Fields.Item("System.ItemPathDisplay")
    objRecordset.MoveNext
Loop

ADO 및 C++

#import "msado15.dll" rename_namespace("ADO") rename("EOF", "EndOfFile") implementation_only

ADO::_ConnectionPtr connection = NULL;
HRESULT hr = connection.CreateInstance(__uuidof(ADO::Connection));
if (SUCCEEDED(hr))
{
    ADO::_RecordsetPtr recordset = NULL;
    hr = recordset.CreateInstance(__uuidof(ADO::Recordset));
    if (SUCCEEDED(hr))
    {
        connection->CursorLocation = ADO::adUseClient;
        hr = connection->Open(L"Provider=Search.CollatorDSO;Extended Properties='Application=Windows';",
            L"", L"", ADO::adConnectUnspecified);
        if (SUCCEEDED(hr))
        {
            hr = recordset->Open("SELECT Top 5 System.ItemPathDisplay FROM SYSTEMINDEX WHERE scope='file:' ORDER BY System.Size DESC",
            connection.GetInterfacePtr(), ADO::adOpenForwardOnly, ADO::adLockReadOnly, ADO::adCmdText);
            if (SUCCEEDED(hr))
            {
                while (!recordset->EndOfFile)
                {
                    _variant_t var;
                    var = recordset->Fields->GetItem(L"System.ItemPathDisplay")->GetValue();
                    std::cout << static_cast<char *>(_bstr_t(var.bstrVal)) << std::endl;
                    recordset->MoveNext();
                };
                recordset->Close();
            }
            connection->Close();
        }
    }
}

ADO 및 VisualBasic

먼저 프로젝트에서 ADODB에 대한 참조를 추가합니다.

Dim con As ADODB.Connection
Dim rst As ADODB.Recordset

con = New ADODB.Connection
rst = New ADODB.Recordset

Dim sConString As String
Dim sSQLString As String

sConString = "Provider=Search.CollatorDSO;Extended Properties='Application=Windows';"
con.Open(sConString)

sSQLString = "SELECT Top 5 System.ItemPathDisplay FROM SYSTEMINDEX
                WHERE scope='file:'
                ORDER BY System.Size DESC"

rst = con.Execute(sSQLString)

Do Until (rst.EOF)
    Print(1, rst("System.ItemPathDisplay").Value)
    rst.MoveNext
Loop

rst.Close
rst = Nothing

con.Close
con = Nothing

ADO.NET 및 C#

string query = @"SELECT Top 5 System.ItemPathDisplay FROM SYSTEMINDEX
                WHERE scope='file:'
                ORDER BY System.Size DESC";

using (OleDbConnection objConnection =
    new OleDbConnection
    ("Provider=Search.CollatorDSO.1;Extended?Properties='Application=Windows';"))
{
    objConnection.Open();
    OleDbCommand cmd = new OleDbCommand(query, objConnection);
    using (OleDbDataReader rdr = cmd.ExecuteReader())
    {
        for (int i = 0; i < rdr.FieldCount; i++)
        {
            Console.Write(rdr.GetName(i));
            Console.Write('\t');
        }
        while (rdr.Read())
        {
            Console.WriteLine();
            for (int i = 0; i < rdr.FieldCount; i++)
            {
                Console.Write(rdr[i]);
                Console.Write('\t');
            }
        }
        Console.ReadKey();
    }
}

로컬 및 원격 쿼리에서 SQL 사용

로컬 또는 원격으로 쿼리를 실행할 수 있습니다. FROM 절사용하는 로컬 쿼리는 다음 예제에 나와 있습니다. 로컬 쿼리는 로컬 SystemIndex 카탈로그만 쿼리합니다.

FROM SystemIndex

FROM 절사용하는 원격 쿼리는 다음 예제에 나와 있습니다. ComputerName을 추가하면 이전 예제가 원격 쿼리로 변환됩니다.

FROM [<ComputerName>.]SystemIndex

기본적으로 Windows XP 및 Windows Server 2003에는 Windows Search가 설치되어 있지 않습니다. WS4(Windows Search 4)만 원격 쿼리 지원을 제공합니다. 3.01 이하와 같은 이전 버전의 WDS(Windows 데스크톱 검색)는 원격 쿼리를 지원하지 않습니다. Windows 탐색기를 사용하면 원격 컴퓨터의 로컬 인덱스에서 파일 시스템 항목("file:" 프로토콜에서 처리되는 항목)을 쿼리할 수 있습니다.

원격 쿼리로 항목을 검색하려면 항목이 다음 요구 사항을 충족해야 합니다.

  • UNC(유니버설 명명 규칙) 경로를 통해 액세스할 수 있습니다.
  • 클라이언트가 액세스할 수 있는 원격 컴퓨터에 존재합니다.
  • 클라이언트가 읽기 권한을 가질 수 있도록 해당 보안 집합을 갖습니다.

Windows 탐색기에는 네트워크 및 공유 센터의 "공용" 공유(\\Machine\Public\...) 및 공유 마법사를 통해 공유되는 항목에 대한 "사용자" 공유(\\Machine\Users\...)를 비롯한 항목을 공유하는 기능이 있습니다. 폴더를 공유한 후에는 다음 예제와 같이 FROM 절에서 원격 컴퓨터의 컴퓨터 이름과 SCOPE 절의 원격 머신에 대한 UNC 경로를 지정하여 로컬 인덱스 쿼리를 수행할 수 있습니다.

SELECT System.ItemName FROM MachineName.SystemIndex WHERE SCOPE='file://MachineName/<path>'

AQS 기반 쿼리

AQS는 인덱스를 쿼리하고 검색 매개 변수를 구체화하고 좁히기 위해 Windows Search에서 사용하는 기본 쿼리 구문입니다. AQS는 주로 사용자 연결이지만 개발자가 프로그래밍 방식으로 쿼리를 빌드하는 데 사용할 수 있습니다. Windows 7 정식 AQS가 도입되었으며 프로그래밍 방식으로 AQS 쿼리를 생성하려면 Windows 7 이상에서 사용해야 합니다. AQS에 대한 자세한 내용은 프로그래밍 방식으로 고급 쿼리 구문 사용을 참조 하세요.

인덱스를 쿼리하는 다음 방법은 AQS 기반입니다.

ISearchQueryHelper 사용

ISearchQueryHelper 인터페이스를 사용하여 인덱스를 쿼리하는 구성 요소 또는 도우미 클래스를 개발할 수 있습니다. 이를 통해 시스템의 일부 기능을 활용하고 Windows Search 사용을 간소화할 수 있습니다. 이 인터페이스는 다음을 도와줍니다.

  • Windows Search 데이터베이스에 연결할 OLE DB 연결 문자열 가져옵니다.
  • 사용자 쿼리를 AQS에서 Windows Search SQL로 변환합니다.

이 인터페이스는 ISearchCatalogManager에 대한 도우미 클래스로 구현되며 다음 C++ 예제와 같이 ISearchCatalogManager::GetQueryHelper를 호출하여 가져옵니다.

HRESULT GetQueryHelper(ISearchQueryHelper **ppQueryHelper)
{
    *ppQueryHelper = NULL;

    // Create an instance of the search manager

    ISearchManager *pSearchManager;
    HRESULT hr = CoCreateInstance(__uuidof(CSearchManager), NULL, CLSCTX_LOCAL_SERVER, IID_PPV_ARGS(&pSearchManager));
    if (SUCCEEDED(hr))
    {
        // Get the catalog manager from the search manager
        ISearchCatalogManager *pSearchCatalogManager;
        hr = pSearchManager->GetCatalog(L"SystemIndex", &pSearchCatalogManager);
        if (SUCCEEDED(hr))
        {
            // Get the query helper from the catalog manager
            hr = pSearchCatalogManager->GetQueryHelper(ppQueryHelper);
            pSearchCatalogManager->Release();
        }
        pSearchManager->Release();
    }

    return hr;
}

ISearchQueryHelper 인터페이스를 구현하려면 ISearchQueryHelper 인터페이스 ISearchQueryHelper 참조 항목 사용을 참조하세요.

참고 항목

레거시 Microsoft WDS(Windows Desktop Search) 2x 호환성: Windows XP 및 Windows Server 2003 이상을 실행하는 컴퓨터에서는 ISearchDesktop 이 더 이상 사용되지 않습니다. 대신 개발자는 ISearchQueryHelper를 사용하여 연결 문자열 가져와서 사용자의 쿼리를 SQL로 구문 분석한 다음 OLE DB를 통해 쿼리해야 합니다.

search-ms 프로토콜 사용

search-ms 애플리케이션 프로토콜은 Windows 탐색기 같은 애플리케이션을 시작하여 Windows Search 인덱스 쿼리를 위한 규칙입니다. 속성 인수, 이전에 저장된 검색, AQS(고급 쿼리 구문), NQS(자연 쿼리 구문) 및 인덱서와 쿼리 자체 모두에 대한 LCID(언어 코드 식별자)를 비롯한 매개 변수 값 인수를 사용하여 쿼리를 작성할 수 있습니다.

search-ms 프로토콜 구문에 대한 자세한 내용은 search-ms 프로토콜을 사용하여 인덱스 쿼리를 참조 하세요.

프로그래밍 방식으로 인덱스 쿼리

ISearchQueryHelper를 사용하여 인덱스 쿼리

search-ms 프로토콜을 사용하여 인덱스 쿼리

Windows Search SQL 구문을 사용하여 인덱스 쿼리

프로그래밍 방식으로 고급 쿼리 구문 사용하기