Gestión de mensajes en archivos PST

Obtener información de mensajes de un archivo PST de Outlook

En Leer archivos PST y recuperar información En el artículo discutimos cómo cargar un archivo PST de Outlook y explorar sus carpetas para obtener los nombres de carpetas y la cantidad de mensajes en ellas. Este artículo explica cómo leer todas las carpetas y subcarpetas del archivo PST y mostrar la información de los mensajes, por ejemplo, asunto, remitente y destinatarios. El archivo PST de Outlook puede contener carpetas anidadas. Para obtener información de los mensajes de estas, así como de las carpetas de nivel superior, usa un método recursivo para leer todas las carpetas. El siguiente fragmento de código muestra cómo leer un archivo PST de Outlook y mostrar recursivamente el contenido de carpetas y mensajes.

// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
public static void Run()
{            
    string dataDir = RunExamples.GetDataDir_Outlook();

    // Load the Outlook file
    string path = dataDir + "PersonalStorage.pst";

    try
    {
       
        // Load the Outlook PST file
        PersonalStorage personalStorage = PersonalStorage.FromFile(path);

        // Get the Display Format of the PST file
        Console.WriteLine("Display Format: " + personalStorage.Format);

        // Get the folders and messages information
        FolderInfo folderInfo = personalStorage.RootFolder;

        // Call the recursive method to display the folder contents
        DisplayFolderContents(folderInfo, personalStorage);
    }
    catch (Exception ex)
    {
        Console.WriteLine(ex.Message);               
    }            
}

/// <summary>
/// This is a recursive method to display contents of a folder
/// </summary>
/// <param name="folderInfo"></param>
/// <param name="pst"></param>
private static void DisplayFolderContents(FolderInfo folderInfo, PersonalStorage pst)
{
    // Display the folder name
    Console.WriteLine("Folder: " + folderInfo.DisplayName);
    Console.WriteLine("==================================");
    // Display information about messages inside this folder
    MessageInfoCollection messageInfoCollection = folderInfo.GetContents();
    foreach (MessageInfo messageInfo in messageInfoCollection)
    {
        Console.WriteLine("Subject: " + messageInfo.Subject);
        Console.WriteLine("Sender: " + messageInfo.SenderRepresentativeName);
        Console.WriteLine("Recipients: " + messageInfo.DisplayTo);
        Console.WriteLine("------------------------------");
    }

    // Call this method recursively for each subfolder
    if (folderInfo.HasSubFolders == true)
    {
        foreach (FolderInfo subfolderInfo in folderInfo.GetSubFolders())
        {
            DisplayFolderContents(subfolderInfo, pst);
        }
    }
}

Extracción de mensajes de archivos PST

Este artículo muestra cómo leer archivos PST de Microsoft Outlook y extraer mensajes. Los mensajes se guardan luego en disco en formato MSG.

El siguiente fragmento de código muestra cómo extraer mensajes de un archivo PST:

  • Utilice un método recursivo para explorar todas las carpetas (incluyendo carpetas anidadas) y llame al método PersonalStorage.ExtractMessage() para obtener mensajes de Outlook en una instancia del MapiMessage clase.
  • Después de eso, llame al método MapiMessage.Save() para guardar el mensaje en disco o en un flujo en formato MSG.
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
public static void Run()
{            
    // The path to the file directory.
    string dataDir = RunExamples.GetDataDir_Outlook();

    // Load the Outlook file
    string path = dataDir + "PersonalStorage.pst";

    try
    {
        // load the Outlook PST file
        PersonalStorage pst = PersonalStorage.FromFile(path);

        // get the Display Format of the PST file
        Console.WriteLine("Display Format: " + pst.Format);

        // get the folders and messages information
        FolderInfo folderInfo = pst.RootFolder;

        // Call the recursive method to extract msg files from each folder
        ExtractMsgFiles(folderInfo, pst);
    }
    catch (Exception ex)
    {
        Console.WriteLine(ex.Message);
    }            
}

/// <summary>
/// This is a recursive method to display contents of a folder
/// </summary>
/// <param name="folderInfo"></param>
/// <param name="pst"></param>
private static void ExtractMsgFiles(FolderInfo folderInfo, PersonalStorage pst)
{
    // display the folder name
    Console.WriteLine("Folder: " + folderInfo.DisplayName);
    Console.WriteLine("==================================");
    // loop through all the messages in this folder
    MessageInfoCollection messageInfoCollection = folderInfo.GetContents();
    foreach (MessageInfo messageInfo in messageInfoCollection)
    {
        Console.WriteLine("Saving message {0} ....", messageInfo.Subject);
        // get the message in MapiMessage instance
        MapiMessage message = pst.ExtractMessage(messageInfo);
        // save this message to disk in msg format
        message.Save(message.Subject.Replace(":", " ") + ".msg");
        // save this message to stream in msg format
        MemoryStream messageStream = new MemoryStream();
        message.Save(messageStream);
    }

    // Call this method recursively for each subfolder
    if (folderInfo.HasSubFolders == true)
    {
        foreach (FolderInfo subfolderInfo in folderInfo.GetSubFolders())
        {
            ExtractMsgFiles(subfolderInfo, pst);
        }
    }
}

Identificación de tipos de elementos MAPI

El MapiItemType enum representa un tipo de elemento MAPI que puede convertirse explícitamente en un objeto de la clase correspondiente derivada de la IMapiMessageItem interfaz. De esta manera los usuarios pueden evitar comprobar el MessageClass valor de la propiedad antes de la conversión del mensaje.

El siguiente ejemplo de código muestra cómo definir un tipo para el elemento a convertir:

foreach (var messageInfo in folder.EnumerateMessages())
{
    var msg = pst.ExtractMessage(messageInfo);

    switch (msg.SupportedType)
    {
        // Non-supported type. MapiMessage cannot be converted to an appropriate item type.
        // Just use in MSG format.
        case MapiItemType.None:
            break;
        // An email message. Conversion isn't required.
        case MapiItemType.Message:
            break;
        // A contact item. Can be converted to MapiContact.
        case MapiItemType.Contact:
            var contact = (MapiContact)msg.ToMapiMessageItem();
            break;
        // A calendar item. Can be converted to MapiCalendar.
        case MapiItemType.Calendar:
            var calendar = (MapiCalendar)msg.ToMapiMessageItem();
            break;
        // A distribution list. Can be converted to MapiDistributionList.
        case MapiItemType.DistList:
            var dl = (MapiDistributionList)msg.ToMapiMessageItem();
            break;
        // A Journal entry. Can be converted to MapiJournal.
        case MapiItemType.Journal:
            var journal = (MapiJournal)msg.ToMapiMessageItem();
            break;
        // A StickyNote. Can be converted to MapiNote.
        case MapiItemType.Note:
            var note = (MapiNote)msg.ToMapiMessageItem();
            break;
        // A Task item. Can be converted to MapiTask.
        case MapiItemType.Task:
            var task = (MapiTask)msg.ToMapiMessageItem();
            break;
    }
}

Búsqueda y recuperación de mensajes

Aspose.Email proporciona los siguientes métodos sobrecargados de la FolderInfo clase para filtrar y recuperar mensajes:

Recuperación paginada del contenido de carpetas

Al trabajar con carpetas PST grandes, recuperar todos los mensajes de una vez puede ser ineficiente. Para mejorar el rendimiento y el control, Aspose.Email para .NET ofrece soporte de paginación en el FolderInfo.GetContents método. Este método recupera un subconjunto de mensajes que coinciden con la consulta especificada, comenzando desde un índice dado y limitado por un recuento. Esto le permite obtener mensajes en lotes más pequeños y manejables. El método toma los siguientes parámetros:

IList<MessageInfo> FolderInfo.GetContents(MailQuery query, int startIndex, int count)
  • query — un filtro para aplicar a los mensajes (opcional)

  • startIndex — el índice basado en cero desde el cual comenzar a recuperar

  • count — el número de mensajes a devolver

El ejemplo de código a continuación demuestra cómo implementar este método en un proyecto:

// Load the PST file
using (var pst = PersonalStorage.FromFile(fileName))
{
    // Access a specific subfolder
    var folder = pst.RootFolder.GetSubFolder("Inbox");

    // Build a query to filter messages by sender address
    var queryBuilder = new PersonalStorageQueryBuilder();
    queryBuilder.From.Contains("report-service", true);

    // Define the page size
    int pageSize = 5;

    // Retrieve and process messages in pages
    for (int pageIndex = 0; pageIndex < 6; pageIndex++)
    {
        int startIndex = pageIndex * pageSize;

        // Get a page of messages
        var messages = folder.GetContents(queryBuilder.GetQuery(), startIndex, pageSize);

        foreach (MessageInfo messageInfo in messages)
        {
            // Output basic info about each message
            Console.WriteLine($"Subject: {messageInfo.Subject}, Sender: {messageInfo.SenderRepresentativeName}");
        }
    }
}

Guardar mensajes directamente de PST a flujo

Para guardar mensajes de un archivo PST directamente a un flujo, sin extraer el MsgInfo de los mensajes, use el método SaveMessageToStream(). El siguiente fragmento de código muestra cómo guardar mensajes directamente desde PST a un flujo.

// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
// The path to the file directory.
string dataDir = RunExamples.GetDataDir_Outlook();

// Load the Outlook file
string path = dataDir + "PersonalStorage.pst";

// Save message to MemoryStream
using (PersonalStorage personalStorage = PersonalStorage.FromFile(path))
{
    FolderInfo inbox = personalStorage.RootFolder.GetSubFolder("Inbox");
    foreach (MessageInfo messageInfo in inbox.EnumerateMessages())
    {
        using (MemoryStream memeorystream = new MemoryStream())
        {
            personalStorage.SaveMessageToStream(messageInfo.EntryIdString, memeorystream);
        }
    }
}

// Save message to file
using (PersonalStorage pst = PersonalStorage.FromFile(path))
{
    FolderInfo inbox = pst.RootFolder.GetSubFolder("Inbox");
    foreach (MessageInfo messageInfo in inbox.EnumerateMessages())
    {
        using (FileStream fs = File.OpenWrite(messageInfo.Subject + ".msg"))
        {
            pst.SaveMessageToStream(messageInfo.EntryIdString, fs);
        }
    }
}

using (PersonalStorage pst = PersonalStorage.FromFile(path))
{
    FolderInfo inbox = pst.RootFolder.GetSubFolder("Inbox");
    
    // To enumerate entryId of messages you may use FolderInfo.EnumerateMessagesEntryId() method:
    foreach (string entryId in inbox.EnumerateMessagesEntryId())
    {
        using (MemoryStream ms = new MemoryStream())
        {
            pst.SaveMessageToStream(entryId, ms);
        }
    }
}            

Extraer número específico de mensajes

El siguiente fragmento de código le muestra cómo extraer un número determinado de mensajes de un PST. Simplemente proporcione el índice del primer mensaje y el número total de mensajes a extraer.

// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
FolderInfo inbox = personalStorage.RootFolder.GetSubFolder("Inbox");

// Extracts messages starting from 10th index top and extract total 100 messages
MessageInfoCollection messages = inbox.GetContents(10, 100);

Obtener recuento total de ítems del PST

Aspose.Email proporciona el GetTotalItemsCount() método del PersonalStorage.Store propiedad. Devuelve el número total de elementos de mensaje contenidos en el PST.

El siguiente ejemplo de código muestra cómo obtener el recuento total de elementos (mensajes, citas, contactos, etc.) almacenados dentro del archivo PST:

using (var pst = PersonalStorage.FromFile("my.pst", false))
{
    var count = pst.Store.GetTotalItemsCount();
}

Extraer adjuntos sin extraer el mensaje completo

La API de Aspose.Email puede usarse para extraer adjuntos de mensajes PST sin extraer primero el mensaje completo. El ExtractAttachments método de PersonalStorage puede usarse para hacer esto. El siguiente fragmento de código muestra cómo extraer archivos adjuntos sin extraer un mensaje completo.

// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
string dataDir = RunExamples.GetDataDir_Outlook();

using (PersonalStorage personalstorage = PersonalStorage.FromFile(dataDir + "Outlook.pst"))
{
    FolderInfo folder = personalstorage.RootFolder.GetSubFolder("Inbox");

    foreach (var messageInfo in folder.EnumerateMessagesEntryId())
    {
        MapiAttachmentCollection attachments = personalstorage.ExtractAttachments(messageInfo);

        if (attachments.Count != 0)
        {
            foreach (var attachment in attachments)
            {
                if (!string.IsNullOrEmpty(attachment.LongFileName))
                {
                    if (attachment.LongFileName.Contains(".msg"))
                    {
                        continue;
                    }
                    else
                    {
                        attachment.Save(dataDir + @"\Attachments\" + attachment.LongFileName);
                    }
                }
            }
        }
    }
}

Extraer destinatarios de mensajes de archivos PST

Los destinatarios de un mensaje pueden extraerse de archivos PST usando una ID de entrada del mensaje. Esta característica está disponible en el PersonalStorage clase. Los ejemplos de código a continuación demuestran cómo extraer los destinatarios del mensaje:

por EntryD (usando el ExtractRecipients(string entryId) método del PersonalStorage clase)

using (var pst = PersonalStorage.FromFile(fileName))
{  
    // Recipients are extracted using the entry ID
    var recipients = pst.ExtractRecipients("AAAAADzSMygQQFJOkKwVhb8v5EUkASAA");
}

de MessageInfo (usando el MapiRecipientCollection ExtractRecipients(MessageInfo messageInfo) método)

using (var pst = PersonalStorage.FromFile(fileName))
{  
    // The "Inbox" folder is obtained
    var folder = pst.RootFolder.GetSubfolder("Inbox");

    // Each message in the "Inbox" folder is iterated
    foreach (var messageInfo in folder.EnumerateMessages())
    {
        // Recipients are extracted from each message
        var recipients = pst.ExtractRecipients(messageInfo);
    }
}

Buscar mensajes y carpetas

Buscar por criterio

Los archivos Personal Storage (PST) pueden contener una gran cantidad de datos. Buscar datos que cumplan un criterio específico en archivos tan grandes requiere incluir múltiples puntos de verificación en el código para filtrar la información. Con el PersonalStorageQueryBuilder clase, Aspose.Email permite buscar registros específicos en un PST basándose en un criterio de búsqueda especificado. Un PST puede buscarse por mensajes usando parámetros de búsqueda como remitente, destinatario, asunto, importancia del mensaje, presencia de archivos adjuntos, tamaño del mensaje e incluso ID del mensaje. El PersonalStorageQueryBuilder también puede usarse para buscar subcarpetas.

Buscar mensajes y carpetas en PST

El siguiente fragmento de código muestra cómo usar el PersonalStorageQueryBuilder clase para buscar contenidos en un PST basándose en diferentes criterios de búsqueda. Por ejemplo, muestra la búsqueda en un PST basada en:

  • Importancia del mensaje.
  • Clase del mensaje.
  • Presencia de archivos adjuntos.
  • Tamaño del mensaje.
  • Mensajes no leídos.
  • Mensajes no leídos con archivos adjuntos, y
  • carpetas con un nombre de subcarpeta específico.
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
// The path to the File directory.
string dataDir = RunExamples.GetDataDir_Outlook();

using (PersonalStorage personalStorage = PersonalStorage.FromFile(dataDir + "Outlook.pst"))
{
    FolderInfo folder = personalStorage.RootFolder.GetSubFolder("Inbox");
    PersonalStorageQueryBuilder builder = new PersonalStorageQueryBuilder();

    // High importance messages
    builder.Importance.Equals((int)MapiImportance.High);
    MessageInfoCollection messages = folder.GetContents(builder.GetQuery());
    Console.WriteLine("Messages with High Imp:" + messages.Count);

    builder = new PersonalStorageQueryBuilder();
    builder.MessageClass.Equals("IPM.Note");
    messages = folder.GetContents(builder.GetQuery());
    Console.WriteLine("Messages with IPM.Note:" + messages.Count);

    builder = new PersonalStorageQueryBuilder();
    // Messages with attachments AND high importance
    builder.Importance.Equals((int)MapiImportance.High);
    builder.HasFlags(MapiMessageFlags.MSGFLAG_HASATTACH);
    messages = folder.GetContents(builder.GetQuery());
    Console.WriteLine("Messages with atts: " + messages.Count);

    builder = new PersonalStorageQueryBuilder();
    // Messages with size > 15 KB
    builder.MessageSize.Greater(15000);
    messages = folder.GetContents(builder.GetQuery());
    Console.WriteLine("messags size > 15Kb:" + messages.Count);

    builder = new PersonalStorageQueryBuilder();
    // Unread messages
    builder.HasNoFlags(MapiMessageFlags.MSGFLAG_READ);
    messages = folder.GetContents(builder.GetQuery());
    Console.WriteLine("Unread:" + messages.Count);

    builder = new PersonalStorageQueryBuilder();
    // Unread messages with attachments
    builder.HasNoFlags(MapiMessageFlags.MSGFLAG_READ);
    builder.HasFlags(MapiMessageFlags.MSGFLAG_HASATTACH);
    messages = folder.GetContents(builder.GetQuery());
    Console.WriteLine("Unread msgs with atts: " + messages.Count);

    // Folder with name of 'SubInbox'
    builder = new PersonalStorageQueryBuilder();
    builder.FolderName.Equals("SubInbox");
    FolderInfoCollection folders = folder.GetSubFolders(builder.GetQuery());
    Console.WriteLine("Folder having subfolder: " + folders.Count);

    builder = new PersonalStorageQueryBuilder();
    // Folders with subfolders
    builder.HasSubfolders();
    folders = folder.GetSubFolders(builder.GetQuery());
    Console.WriteLine(folders.Count);
}

Búsqueda sin distinción de mayúsculas/minúsculas

El siguiente fragmento de código le muestra cómo buscar una cadena en PST con el parámetro de ignorar mayúsculas/minúsculas.

using (PersonalStorage personalStorage = PersonalStorage.Create("CaseSensitivity.pst", FileFormatVersion.Unicode))
{
	FolderInfo folderinfo = personalStorage.CreatePredefinedFolder("Inbox", StandardIpmFolder.Inbox);
	folderinfo.AddMessage(MapiMessage.FromMailMessage(MailMessage.Load("Sample.eml")));
	PersonalStorageQueryBuilder builder = new PersonalStorageQueryBuilder();
	// IgnoreCase is True
	builder.From.Contains("automated", true);
	MailQuery query = builder.GetQuery();
	MessageInfoCollection coll = folderinfo.GetContents(query);
	Console.WriteLine(coll.Count);
}

Buscar asuntos de mensajes por múltiples palabras clave

Puede usar MailQueryBuilder.Or método para encontrar mensajes con un asunto que contenga al menos una de las palabras especificadas, como se muestra a continuación:

var builder1 = new PersonalStorageQueryBuilder();
builder1.Subject.Contains("Review"); // 'Review' is key word for the search

var builder2 = new PersonalStorageQueryBuilder();
builder2.Subject.Contains("Error"); // 'Error' is also key word for the search

var queryBuilder = new PersonalStorageQueryBuilder();
queryBuilder.Or(builder1.GetQuery(), builder2.GetQuery()); // message subjects must contain 'Review' or 'Error' words

using (var storage = PersonalStorage.FromFile("example.pst"))
{
    var folderInfo = storage.RootFolder.GetSubFolder("Inbox");
    var messageInfos = folderInfo.GetContents(queryBuilder.GetQuery());

    foreach (var messageInfo in messageInfos)
    {
        Console.WriteLine(messageInfo.Subject);
    }
}

Manipular mensajes

Mover elementos a otras carpetas

Aspose.Email permite mover elementos desde una carpeta de origen a otra carpeta en el mismo archivo de Almacenamiento Personal (PST). Esto incluye:

  • Moviendo una carpeta especificada a una nueva carpeta padre.
  • Moviendo mensajes especificados a una nueva carpeta.
  • Moviendo el contenido a una nueva carpeta.
  • Moviendo subcarpetas a una nueva carpeta padre.

El siguiente fragmento de código le muestra cómo mover elementos como mensajes y carpetas desde una carpeta de origen a otra carpeta en el mismo archivo PST.

// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET

using(PersonalStorage personalStorage = PersonalStorage.FromFile("test.pst"))
{
    FolderInfo inbox = personalStorage.GetPredefinedFolder(StandardIpmFolder.Inbox);
    FolderInfo deleted = personalStorage.GetPredefinedFolder(StandardIpmFolder.DeletedItems);
    FolderInfo subfolder = inbox.GetSubFolder("Subfolder");

    // Move folder and message to the Deleted Items
    personalStorage.MoveItem(subfolder, deleted);
    MessageInfoCollection contents = subfolder.GetContents();
    personalStorage.MoveItem(contents[0], deleted);

    // Move all inbox subfolders and subfolder contents to the Deleted Items
    inbox.MoveSubfolders(deleted);
    subfolder.MoveContents(deleted);
}

Actualizar propiedades de los mensajes

A veces es necesario actualizar ciertas propiedades de los mensajes, como cambiar el asunto, marcar la importancia del mensaje y otras similares. Actualizar un mensaje en un archivo PST con dichos cambios en las propiedades del mensaje puede lograrse usando el FolderInfo.ChangeMessages método. Este artículo muestra cómo actualizar mensajes en bloque en un archivo PST para cambios en las propiedades. El siguiente fragmento de código muestra cómo actualizar las propiedades de los mensajes en modo masivo para múltiples mensajes en un archivo PST.

// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
// The path to the File directory.
string dataDir = RunExamples.GetDataDir_Outlook() + "Sub.pst";

// Load the Outlook PST file
PersonalStorage personalStorage = PersonalStorage.FromFile(dataDir);
            
// Get Requierd Subfolder 
FolderInfo inbox = personalStorage.RootFolder.GetSubFolder("Inbox");

// find messages having From = "someuser@domain.com"
PersonalStorageQueryBuilder queryBuilder = new PersonalStorageQueryBuilder();
queryBuilder.From.Contains("someuser@domain.com");

// Get Contents from Query
MessageInfoCollection messages = inbox.GetContents(queryBuilder.GetQuery());

// Save (MessageInfo,EntryIdString) in List
IList<string> changeList = new List<string>();
foreach (MessageInfo messageInfo in messages)
{
    changeList.Add(messageInfo.EntryIdString);
}

// Compose the new properties
MapiPropertyCollection updatedProperties = new MapiPropertyCollection();
updatedProperties.Add(MapiPropertyTag.PR_SUBJECT_W, new MapiProperty(MapiPropertyTag.PR_SUBJECT_W, Encoding.Unicode.GetBytes("New Subject")));
updatedProperties.Add(MapiPropertyTag.PR_IMPORTANCE, new MapiProperty(MapiPropertyTag.PR_IMPORTANCE, BitConverter.GetBytes((long)2)));

// update messages having From = "someuser@domain.com" with new properties
inbox.ChangeMessages(changeList, updatedProperties);

Actualizar propiedades personalizadas

A veces es necesario marcar los elementos que han sido procesados dentro del archivo PST. La API Aspose.Email permite lograr esto usando MapiProperty y MapiNamedProperty. Los siguientes métodos son útiles para ello.

  • ctor MapiNamedProperty(long propertyTag, string nameIdentifier, Guid propertyGuid, byte[] propertyValue)
  • ctor MapiNamedProperty(long propertyTag, long nameIdentifier, Guid propertyGuid, byte[] propertyValue)
  • FolderInfo.ChangeMessages(MapiPropertyCollection updatedProperties) - changes all messages in folder
  • PersonalStorage.ChangeMessage(string entryId, MapiPropertyCollection updatedProperties) - changes message properties
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET

public static void Run()
{
	// Load the Outlook file
	string dataDir = RunExamples.GetDataDir_Outlook() + "Sub.pst";
	using (PersonalStorage personalStorage = PersonalStorage.FromFile(dataDir))
	{
		FolderInfo testFolder = personalStorage.RootFolder.GetSubFolder("Inbox");

		// Create the collection of message properties for adding or updating
		MapiPropertyCollection newProperties = new MapiPropertyCollection();

		// Normal,  Custom and PidLidLogFlags named  property
		MapiProperty property = new MapiProperty(MapiPropertyTag.PR_ORG_EMAIL_ADDR_W,Encoding.Unicode.GetBytes("test_address@org.com"));
		MapiProperty namedProperty1 = new MapiNamedProperty(GenerateNamedPropertyTag(0, MapiPropertyType.PT_LONG),"ITEM_ID",Guid.NewGuid(),BitConverter.GetBytes(123));
		MapiProperty namedProperty2 = new MapiNamedProperty(GenerateNamedPropertyTag(1, MapiPropertyType.PT_LONG),0x0000870C,new Guid("0006200A-0000-0000-C000-000000000046"),BitConverter.GetBytes(0));
		newProperties.Add(namedProperty1.Tag, namedProperty1);
		newProperties.Add(namedProperty2.Tag, namedProperty2);
		newProperties.Add(property.Tag, property);
		testFolder.ChangeMessages(testFolder.EnumerateMessagesEntryId(), newProperties);
	}
}

private static long GenerateNamedPropertyTag(long index, MapiPropertyType dataType)
{
	return (((0x8000 | index) << 16) | (long)dataType) & 0x00000000FFFFFFFF;
}

Eliminar mensajes

Este artículo muestra cómo usar el FolderInfo clase para acceder a carpetas específicas en un archivo PST. Para eliminar mensajes de la subcarpeta Enviados de un archivo PST previamente cargado o creado:

  1. Cree una instancia de la FolderInfo clase y cargue su contenido con la subcarpeta Enviados.
  2. Eliminar mensajes de la carpeta Enviados llamando al FolderInfo.DeleteChildItem() método y pasando el MessageInfo.EntryId como parámetro. El siguiente fragmento de código le muestra cómo eliminar mensajes de la subcarpeta Enviados de un archivo PST.
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
// The path to the File directory.
string dataDir = RunExamples.GetDataDir_Outlook() + "Sub.pst";

// Load the Outlook PST file
PersonalStorage personalStorage = PersonalStorage.FromFile(dataDir);

// Get the Sent items folder
FolderInfo folderInfo = personalStorage.GetPredefinedFolder(StandardIpmFolder.SentItems);

MessageInfoCollection msgInfoColl = folderInfo.GetContents();
foreach (MessageInfo msgInfo in msgInfoColl)
{
    Console.WriteLine(msgInfo.Subject + ": " + msgInfo.EntryIdString);
    if (msgInfo.Subject.Equals("some delete condition") == true)
    {
        // Delete this item
        folderInfo.DeleteChildItem(msgInfo.EntryId);
        Console.WriteLine("Deleted this message");
    }
}

Eliminar carpetas

Puede eliminar una carpeta PST moviéndola a la carpeta Elementos eliminados.

using (PersonalStorage pst = PersonalStorage.FromFile(@"test.pst"))
{
    FolderInfo deletedItemsFolder = pst.GetPredefinedFolder(StandardIpmFolder.DeletedItems);
    FolderInfo emptyFolder = pst.RootFolder.GetSubFolder("Empty folder");
	  FolderInfo someFolder = pst.RootFolder.GetSubFolder("Some folder");
    pst.MoveItem(emptyFolder, deletedItemsFolder);
	  pst.MoveItem(someFolder, deletedItemsFolder);
}

La ventaja de este método es que la carpeta eliminada puede recuperarse fácilmente.

FolderInfo someFolder = deletedItemsFolder.GetSubFolder("Some folder");
pst.MoveItem(someFolder, pst.RootFolder);

También puede eliminar permanentemente una carpeta de la carpeta Elementos eliminados, si es necesario.

deletedItemsFolder.DeleteChildItem(emptyFolder.EntryId);

El DeleteChildItem() El método puede usarse para cualquier carpeta si deseas eliminar inmediatamente y permanentemente una subcarpeta, evitando la carpeta Elementos eliminados.

FolderInfo someFolder = pst.RootFolder.GetSubFolder("Some folder");
pst.RootFolder.DeleteChildItem(someFolder.EntryId);

Eliminar elementos del PST

Eliminar elementos (carpetas o mensajes) de una Personal Storage Table (PST) usando el entryId único asociado al elemento llamando al método DeleteItem(string entryId) de PersonalStorage clase.

El siguiente fragmento de código puede usarse para llamar al método DeleteItem y pasar entryId como parámetro:

var pst = PersonalStorage.FromFile("sample.pst");

// ...

pst.DeleteItem(entryId);

// ...

Nota:

  • Este método eliminará permanentemente el elemento del PST y no podrá deshacerse. Usa precaución al utilizar este método para evitar pérdida de datos accidental.
  • Según las convenciones estándar, asegúrate de que entryId sea válido y corresponda a un elemento existente dentro del PST.
  • De lo contrario, se lanzará una excepción. Es aconsejable tener una copia de seguridad del PST o implementar medidas adecuadas para recuperar los elementos eliminados si es necesario.

Eliminación masiva

La API de Aspose.Email puede usarse para eliminar elementos en bloque de un archivo PST. Esto se logra usando la DeleteChildItems() método que acepta una lista de elementos Entry ID que hacen referencia a los elementos a eliminar. El siguiente fragmento de código le muestra cómo eliminar elementos en bloque de un archivo PST.

// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
// The path to the File directory.
string dataDir = RunExamples.GetDataDir_Outlook() + @"Sub.pst";
using (PersonalStorage personalStorage = PersonalStorage.FromFile(dataDir))
{
    // Get Inbox SubFolder from Outlook file
    FolderInfo inbox = personalStorage.RootFolder.GetSubFolder("Inbox");

    // Create instance of PersonalStorageQueryBuilder
    PersonalStorageQueryBuilder queryBuilder = new PersonalStorageQueryBuilder();

    queryBuilder.From.Contains("someuser@domain.com");
    MessageInfoCollection messages = inbox.GetContents(queryBuilder.GetQuery());
    IList<string> deleteList = new List<string>();
    foreach (MessageInfo messageInfo in messages)
    {
        deleteList.Add(messageInfo.EntryIdString);
    }

    // delete messages having From = "someuser@domain.com"
    inbox.DeleteChildItems(deleteList);
}

Recuperar elementos eliminados suavemente de archivos PST y OST

Aspose.Email para .NET proporciona un método para recuperar elementos eliminados suavemente de archivos PST y OST. Esta funcionalidad se implementa a través del PersonalStorage clase, que incluye el FindAndExtractSoftDeletedItems método. Este método permite localizar y restaurar elementos que han sido eliminados suavemente, permitiendo recuperar datos importantes que de otro modo se perderían. Los elementos recuperados se guardan en sus respectivas carpetas como .msg archivos, asegurando que se mantenga la estructura original de carpetas. El siguiente ejemplo de código muestra cómo implementar esta funcionalidad en tu proyecto:

using (var pst = PersonalStorage.FromFile(fileName))
{
    // Soft deleted items are found and extracted
    var entries = pst.FindAndExtractSoftDeletedItems();

    // The recovered items are iterated through
    for (var index = 0; index < entries.Count; index++)
    {
        // Folder information is obtained by ID
        var folderInfo = pst.GetFolderById(entries[index].FolderId);

        // A directory for the folder is created if it doesn't exist
        if (!Directory.Exists(folderInfo.DisplayName))
        {
            Directory.CreateDirectory(Path.Combine(path, folderInfo.DisplayName));
        }
        
        // The restored item is obtained
        var msg = entries[index].Item;
        
        // The restored item is saved as a .msg file
        msg.Save(Path.Combine(path, folderInfo.DisplayName, $"{index}.msg"));
    }
}

Enumerar mensajes eliminados suavemente en archivos PST

Los mensajes eliminados suavemente en un archivo PST son elementos que han sido eliminados dos veces: primero movidos a Elementos eliminados, luego removidos nuevamente. Estos mensajes no se borran permanentemente y aún pueden accederse programáticamente. Aspose.Email para .NET permite recuperar estos mensajes eliminados suavemente para revisión o recuperación.

Para enumerar y recuperar elementos que han sido eliminados suavemente (eliminados dos veces) en archivos PST, usa el FindAndEnumerateSoftDeletedItems() método. Este método recupera una lista enumerable de dichos elementos, cada uno incluye tanto el mensaje como el ID de la carpeta de la que fue eliminado.

El siguiente ejemplo de código muestra cómo enumerar y recuperar correos que han sido eliminados dos veces. Devuelve el RestoredItemEntry clase que representa una entrada para un elemento eliminado suavemente recuperado de un archivo PST. La clase contiene las siguientes propiedades:

// Load the PST file
using (var pst = PersonalStorage.FromFile("archive.pst"))
{
    // Enumerate soft-deleted items
    foreach (var entry in pst.FindAndEnumerateSoftDeletedItems())
    {
        var message = entry.Item;
        var folderId = entry.FolderId;

        Console.WriteLine($"Subject: {message.Subject}");
        Console.WriteLine($"Deleted from Folder ID: {folderId}");
        Console.WriteLine("-----------------------------------");
    }
}

Dividir archivos PST

Dividir en varios PST

La API Aspose.Email brinda la capacidad de dividir un archivo PST único en varios archivos PST del tamaño deseado.

El ejemplo de código a continuación describe el proceso de división de un archivo:

  1. Primero, utiliza el FromFile método del PersonalStorage clase para especificar el nombre del archivo.

  2. Luego, llama al StorageProcessedEventHandler delegado para manejar un evento StorageProcessed.

  3. StorageProcessingEventArgs proporciona datos para el evento PersonalStorage.StorageProcessing. Su StorageProcessingEventArgs.FileName propiedad permite recuperar el nombre del archivo PST. Para MergeWith método será el nombre del PST actual que se fusionará con el principal, y para SplitInto método será el nombre de la parte actual.

  4. Finalmente, SplitInto(long chunkSize, string partFileNamePrefix, string path) El método sobrecargado iniciará la división del almacenamiento PST en partes de menor tamaño. Toma los siguientes parámetros:

  • chunkSize: El tamaño aproximado de cada fragmento en bytes.
  • partFileNamePrefix: El prefijo que se añadirá al nombre de archivo de cada parte del PST. Si se proporciona, el prefijo se añadirá al inicio de cada nombre de archivo. Si no se proporciona (null o vacío), las partes del PST se crearán sin prefijo.
  • path: La ruta de la carpeta donde se crearán los fragmentos.

El nombre de archivo de cada parte sigue la plantilla: {prefix}part{number}.pst, donde {prefix} representa el prefijo del nombre de archivo (si se proporciona), y {number} representa el número del fragmento.

var pst = PersonalStorage.FromFile("sample.pst");

// ...

pst.StorageProcessing += (sender, args) =>
{
    Console.WriteLine("Storage processing event raised for file: " + args.FileName);
};

// ...

pst.SplitInto(5000000, "prefix_", outputFolderPath);

Dividir PST según criterio especificado

El siguiente fragmento de código muestra cómo dividir un PST basado en un criterio especificado.

Fusionar archivos PST

Fusionar en un solo PST

También puede fusionar varios archivos PST en un único archivo PST. Tanto las operaciones de división como de fusión de PST pueden rastrearse añadiendo eventos a estas operaciones.

El siguiente fragmento de código muestra cómo fusionar en un solo PST.

Fusionar carpetas de otro PST

El siguiente fragmento de código muestra cómo fusionar carpetas de otro PST.