Creating MapiCalendar in Aspose.Email

I’m trying to create a MapiCalendar from fields of OLM calendar items , but it shows Win32 FileTime error .

bool ConvertOlmToPst(string olmFilePath, string fullPstPath)//last
{

    // Create a new PST
    PersonalStorage pst = PersonalStorage.Create(fullPstPath, FileFormatVersion.Unicode);
    var root = pst.RootFolder;

    FolderInfo inboxFolder = pst.CreatePredefinedFolder("Inbox", StandardIpmFolder.Inbox);
    ageDict.Add("Inbox", inboxFolder.ContainerClass);
    FolderInfo sent = pst.CreatePredefinedFolder("Sent Items", StandardIpmFolder.SentItems);
    ageDict.Add("Sent Items", sent.ContainerClass);
    FolderInfo drafts = pst.CreatePredefinedFolder("Drafts", StandardIpmFolder.Drafts);
    ageDict.Add("Drafts", drafts.ContainerClass);
    FolderInfo junk = pst.CreatePredefinedFolder("Junk Email", StandardIpmFolder.JunkEmail);
    ageDict.Add("Junk Email", junk.ContainerClass);
    FolderInfo calendar = root.AddSubFolder("Calendar", "IPF.Appointment");
    ageDict.Add("Calendar", calendar.ContainerClass);
    FolderInfo contacts = root.AddSubFolder("Contacts", "IPF.Contact");
    ageDict.Add("Contacts", contacts.ContainerClass);
    FolderInfo journal = root.AddSubFolder("Journal", "IPF.Journal");
    ageDict.Add("Journal", journal.ContainerClass);
    FolderInfo notes = pst.CreatePredefinedFolder("Notes", StandardIpmFolder.Notes);
    ageDict.Add("Notes", notes.ContainerClass);
    FolderInfo tasks = root.AddSubFolder("Tasks", "IPF.Task");
    ageDict.Add("Tasks", tasks.ContainerClass);
    //Add redifine folder Types//.............................//
    ageDict.Add("Address Book", "IPF.Contact");
    ageDict.Add("Suggested Contacts", "IPF.Contact");

    ageDict.Add("Junk E - mail", "IPF.Note");
    ageDict.Add("Outbox", "IPF.Note");
    ageDict.Add("Deleted Items", "IPF.Note");
    ageDict.Add("All", "IPF.Note");
    ageDict.Add("Follow-Up", "IPF.Note");
    ageDict.Add("Inbox-Categorized1", "IPF.Note");//Suggested Contacts
                                                  //--------------------------------------------------------//

    OlmStorage olm = new OlmStorage(olmFilePath);
    nTotalCount = GetOlmTotalItemCount(olm);
    //nTotalCount = GetTotalItems(olm);
    if (nTotalCount == 0)
    {
        //Console.WriteLine("⚠️ No items found in OLM file.");
        return false;
    }

    List<OlmFolder> folders = GetAllOlmFolders(olmFilePath);
    string Type;
    for (int i = 0; i < folders.Count; i++)
    {
        var folder = folders[i];
        if (ageDict.TryGetValue(folder.Name, out Type))
        {
            //Console.WriteLine($"Alice's age is {Type}");
        }
        else
        {
            Type = DetectFolderType(olm, folder);
            if (string.IsNullOrEmpty(Type))
            {
                Type = "IPM.Note";
            }
        }
        if (folder.Name != "Accounts")
        {
            FolderInfo folderfull = EnsureFolderPath(pst, folder.Path, Type);
            try
            {
                try
                {
                    // ✅ Enumerate messages safely
                    var messages = olm.EnumerateMessages(folder);
                    if (messages == null)
                        return false;

                    foreach (MapiMessage mapi in messages) // ✅ Correct type for v25.11
                    {
                        try
                        {
                            if (mapi == null)
                                continue;

                            // ✅ Handle calendar items safely
                            //if (mapi.MessageClass.StartsWith("IPM.Appointment", StringComparison.OrdinalIgnoreCase))
                            //{
                            //    var calItem = (MapiCalendar)mapi.ToMapiMessageItem();  // renamed variable

                            //    // Sanitize invalid dates
                            //    if (calItem.StartDate < new DateTime(1900, 1, 1))
                            //        calItem.StartDate = DateTime.Now;

                            //    if (calItem.EndDate < new DateTime(1900, 1, 1) || calItem.EndDate < calItem.StartDate)
                            //        calItem.EndDate = calItem.StartDate.AddHours(1);

                            //    folderfull.AddMapiMessageItem(calItem);
                            //}

                            if (mapi.MessageClass.StartsWith("IPM.Appointment", StringComparison.OrdinalIgnoreCase))
                            {
                                try
                                {
                                    var calItem = (MapiCalendar)mapi.ToMapiMessageItem();

                                    calItem.StartDate = FixDate(calItem.StartDate);
                                    calItem.EndDate = FixDate(calItem.EndDate);

                                    if (calItem.EndDate < calItem.StartDate)
                                        calItem.EndDate = calItem.StartDate.AddHours(1);

                                    //calItem.ReminderTime = FixDate(calItem.ReminderTime);

                                    folderfull.AddMapiMessageItem(calItem);
                                }
                                catch (Exception exCal)
                                {
                                    LogMessage($"Calendar repair failed in folder {folder.Name}: {exCal.Message}");
                                    continue;
                                }
                            }


                            else if (mapi.MessageClass.StartsWith("IPM.Contact", StringComparison.OrdinalIgnoreCase))
                            {
                                var contactItem = (MapiContact)mapi.ToMapiMessageItem();
                                try
                                {
                                    folderfull.AddMapiMessageItem(contactItem);
                                }
                                catch (Exception ex1)
                                {
                                    // Console.WriteLine($"⚠️ Skipped message in folder {folder.Name}: {ex1.Message}");
                                }
                            }

                            else if (mapi.MessageClass.StartsWith("IPM.Task", StringComparison.OrdinalIgnoreCase))
                            {
                                var task = (MapiTask)mapi.ToMapiMessageItem();
                                folderfull.AddMapiMessageItem(task);
                            }
                            else if (mapi.MessageClass.StartsWith("IPM.StickyNote", StringComparison.OrdinalIgnoreCase))
                            {
                                var note = (MapiNote)mapi.ToMapiMessageItem();
                                folderfull.AddMapiMessageItem(note);
                            }
                            else if (mapi.MessageClass.StartsWith("IPM.Activity", StringComparison.OrdinalIgnoreCase))
                            {
                                var journalItem = (MapiJournal)mapi.ToMapiMessageItem();
                                folderfull.AddMapiMessageItem(journalItem);
                            }
                            else
                            {
                                folderfull.AddMessage(mapi);

                            }

                            totalMessageCount++;
                            if (nTotalCount > 0)
                                progress.Progress = (int)((totalMessageCount * 100) / nTotalCount);

                            WriteProgress();
                        }
                        catch (Exception ex)
                        {
                            //Console.WriteLine($"⚠️ Skipped message in folder {folder.Name}: {ex.Message}");
                        }
                    }
                }
                catch (Exception ex)
                {
                    // Console.WriteLine("ConvertOstToPst Exception: " + ex.Message);
                    UpdateProgress("Error");
                }

            }

            catch (Exception ey)
            {
                //Console.WriteLine("ConvertOstToPst Exception: " + ey.Message);

            }
            //Console.WriteLine($"Folder {i}: {folder.Name}");
            //Console.WriteLine($"Folder {i}: {folder.Path}");
        }
    }
    // ✅ Calculate final PST size
    if (File.Exists(fullPstPath))
    {
        FileInfo pstInfo = new FileInfo(fullPstPath);
        double sizeInMB = pstInfo.Length / (1024.0 * 1024.0);
        progress.Convertedpstsize = $"{sizeInMB:F2} MB";

    }
    else
    {
        progress.Convertedpstsize = "0.00 MB";
    }
    pst.Dispose();
    //Console.WriteLine($" Conversion complete: {totalMessageCount} items processed.");

    //Console.WriteLine($"Total folders found: {folders.Count}");      
    return true;
}
//public DateTime FixDate(DateTime date)
//{
//    if (date < new DateTime(1900, 1, 1) || date > DateTime.MaxValue)
//        return DateTime.Now;
//    return date;
//}

private static DateTime FixDate(DateTime date)
{
    try
    {
       
        DateTime minFileTime = new DateTime(1900, 1, 1);

        if (date == DateTime.MinValue || date < minFileTime)
            return DateTime.Now;

        return date;
    }
    catch
    {
        // If Win32 FileTime error happens while reading
        return DateTime.Now;
    }
}

@ritikruhela26

Based on your description, here is a likely technical approach for Aspose.Email when converting olm to pst.

The Win32 FileTime exception is thrown when a DateTime value that is written to the PST is outside the range that a Windows FILETIME can represent (earlier than 01‑01‑1601 UTC or later than 31‑12‑30827).
When you convert an OLM calendar item to a MapiCalendar you have to sanitize every date field ( StartDate, EndDate, ReminderTime, RecurrencePattern dates, etc.) before calling AddMapiMessageItem. A quick way to do this is to wrap the conversion in a helper that replaces out‑of‑range values with a safe default (e.g. DateTime.Now or a minimum allowed value) and then assign the corrected dates back to the MapiCalendar object:

private static DateTime EnsureValidFileTime(DateTime dt)
{
    // FILETIME minimum is 1601‑01‑01 UTC
    DateTime min = new DateTime(1601, 1, 1, 0, 0, 0, DateTimeKind.Utc);
    if (dt == DateTime.MinValue || dt < min)
        return DateTime.UtcNow;               // or any other fallback you prefer
    return dt;
}

// inside the loop where you handle calendar items
if (mapi.MessageClass.StartsWith("IPM.Appointment", StringComparison.OrdinalIgnoreCase))
{
    var cal = (MapiCalendar)mapi.ToMapiMessageItem();

    cal.StartDate   = EnsureValidFileTime(cal.StartDate);
    cal.EndDate     = EnsureValidFileTime(cal.EndDate);
    cal.ReminderTime = EnsureValidFileTime(cal.ReminderTime);

    // also fix recurrence dates if they exist
    if (cal.RecurrencePattern != null)
    {
        cal.RecurrencePattern.StartDate = EnsureValidFileTime(cal.RecurrencePattern.StartDate);
        cal.RecurrencePattern.EndDate   = EnsureValidFileTime(cal.RecurrencePattern.EndDate);
    }

    // guarantee EndDate >= StartDate
    if (cal.EndDate < cal.StartDate)
        cal.EndDate = cal.StartDate.AddHours(1);

    folderfull.AddMapiMessageItem(cal);
}

Make sure you apply the same logic to any other Mapi* objects that contain DateTime properties (contacts, tasks, notes, journals). After the dates are normalized, the AddMapiMessageItem call should no longer raise the Win32 FileTime error.


Clarifying questions

  1. Which specific DateTime property of the MapiCalendar (e.g., StartDate, EndDate, ReminderTime, recurrence dates) triggers the exception in your test data?
  2. Are you using the default MapiCalendar conversion (mapi.ToMapiMessageItem()) or do you set any additional custom properties on the calendar item before adding it to the PST?

Following error has accured,
‘MapiCalendar’ does not contain a definition for ‘RecurrencePattern’ and no accessible extension method ‘RecurrencePattern’ accepting a first argument of type ‘MapiCalendar’ could be found (are you missing a using directive or an assembly reference?)

Hello @ritikruhela26,

MapiCalendar does not have a direct RecurrencePattern property. The recurrence information is nested within the Recurrence property. You must access it via cal.Recurrence.RecurrencePattern , as shown in the code.

if (cal.Recurrence != null && cal.Recurrence.RecurrencePattern != null)
{
    cal.Recurrence.RecurrencePattern.StartDate = EnsureValidFileTime(cal.Recurrence.RecurrencePattern.StartDate);
    cal.Recurrence.RecurrencePattern.EndDate = EnsureValidFileTime(cal.Recurrence.RecurrencePattern.EndDate);
}

I have latest version of Aspose.Email installed , but again it gives the same kind of error

Error :- The name ‘EnsureValidFileTime’ does not exist in the current context

@ritikruhela26,

EnsureValidFileTime is not part of Aspose.Email, it was clearly shown as a custom helper method in the message above. You need to copy and add that method to your own code.

As already shown earlier:

private static DateTime EnsureValidFileTime(DateTime dt)
{
    DateTime min = new DateTime(1601, 1, 1, 0, 0, 0, DateTimeKind.Utc);
    return (dt == DateTime.MinValue || dt < min) ? DateTime.UtcNow : dt;
}

This method was provided in the previous reply — it must be defined in your class before you call it.