AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / server / 问题 / 911399
Accepted
user879
user879
Asked: 2018-05-09 22:43:21 +0800 CST2018-05-09 22:43:21 +0800 CST 2018-05-09 22:43:21 +0800 CST

如何在交换混合环境中将 Office 365 电子邮件备份/导出到 pst?

  • 772

我们有一个交换混合环境。(有些用户在本地交换,有些用户是office 365。)

当我们想从onpremis中导出电子邮件时,我们使用下面的命令来导出邮箱和存档。

 New-MailboxExportRequest -Mailbox "user" -FilePath \\mysrv\l$\PST\Mailbox-user.pst; New-MailboxExportRequest -Mailbox "user" -IsArchive  -FilePath \\mysrv\l$\PST\Mailbox-user-archive.pst -confirm:$false

New-MailboxExportRequest 适用于 onpremis 用户而不适用于 office 365。有没有办法使用 powershell 将 office 365 用户邮箱导出到 pst?

到目前为止我已经尝试过:

我登录了office 365

$UserCredential = Get-Credential
Import-Module MSOnline

Connect-MsolService -Credential $UserCredential
$Session = New-PSSession -ConfigurationName Microsoft.Exchange -ConnectionUri https://outlook.office365.com/powershell-liveid/ -Credential $UserCredential -Authentication  Basic -AllowRedirection

Import-PSSession $Session

并尝试过New-MailboxExportRequest

但它会产生错误。显然 Office 365 不知道该命令

PS C:\Users\pp> New-MailboxExportRequest
New-MailboxExportRequest : The term 'New-MailboxExportRequest' is not recognized as the name of a cmdlet, function,
script file, or operable program. Check the spelling of the name, or if a path was included, verify that the path is
correct and try again.
At line:1 char:1
+ New-MailboxExportRequest
+ ~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : ObjectNotFound: (New-MailboxExportRequest:String) [], CommandNotFoundException
    + FullyQualifiedErrorId : CommandNotFoundException

结果Get-Command *Export*如下

在此处输入图像描述

尝试谷歌搜索,但找不到可行的选择。有人可以指导我吗?办公环境中兼容的命令是什么?

PS: 我尝试过https://www.codetwo.com/admins-blog/how-to-export-office-365-mailboxes-to-pst-using-ediscovery/使用 E5 许可证,它可以在 GUI 中完美运行。但我担心的是电子发现,并且有许可证有可能用 powershell 做吗?我的意思是通过 powershell 编写脚本/自动化?

powershell
  • 2 2 个回答
  • 20765 Views

2 个回答

  • Voted
  1. Best Answer
    Don Zoomik
    2018-05-12T11:08:26+08:002018-05-12T11:08:26+08:00

    您无法使用内置工具通过 PowerShell 将 Exchange Online 邮箱直接导出到 PST。必需的 New-MailboxExportRequest 在线不存在(或未暴露给我们凡人)。

    你可以:

    • eDiscovery,这似乎只是 GUI。
    • 将邮箱卸载/迁移到本地 Exchange 并在本地运行 New-MailboxExportRequest(并在需要时迁移回 Exchange Online)
    • 使用通过 EWS 或 MAPI 执行导出的各种 3rd 方工具
    • 脚本委派完全访问权限,Outlook 绑定到委派邮箱并导出到 PST。从技术上讲很可能是可行的,但我从未见过有人这样做。我没有深入研究过电子数据展示,但我相信电子数据展示如何导出到 PST(旧交易所也用于绑定到 Outlook 以进行 PST 导出)。但是如果没有丰富的 MAPI 经验,Outlook COM 模型的使用非常复杂(我已经编写了一些 Outlook 脚本,但至少可以说模拟 PST 导出具有挑战性)。

    我和你一样沮丧。为离开的用户导出邮箱以进行长期存储是不必要的烦人。如果我们可以像导入一样导出到 Azure Blob,那将是一个好的开始。

    • 5
  2. ErikE
    2019-01-10T12:52:04+08:002019-01-10T12:52:04+08:00

    这不是问题的答案:我还没有尝试直接从 Exchange Online 导出到 PST。

    这是对@DonZoomiks 答案最后一点的补充。有点 Powershell,来自各种不为人知的来源的科学怪人,它从 Exchange Online 中提取邮件。根据需要进行定制。

    产品是包含检索到的邮件的自定义对象。也许有人可以解决并分享如何在不通过 Outlook 的情况下从那里到 PST?

    要求是Exchange Web 服务 (EWS) 托管 API 2.2

    所以前两个功能:

    function Enter-ExchangeOnlineSession {
      <#
          .Synopsis
          Sets up a user session with ExchangeOnline, typically to fetch mail.
          .DESCRIPTION
          Sets up a user session with ExchangeOnline, typically to fetch mail.
          .EXAMPLE
          $CredMail = Get-Credential -UserName [email protected]
          $Service = Enter-ExchangeOnlineSession -Credential $CredMail -MailDomain domain.com
          .INPUTS
          Inputs to this cmdlet (if any)
          .OUTPUTS
          Output from this cmdlet (if any)
          .NOTES
          General notes
          .COMPONENT
          The component this cmdlet belongs to
          .ROLE
          The role this cmdlet belongs to
          .FUNCTIONALITY
          The functionality that best describes this cmdlet
      #>
      Param(
        [Parameter(ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true,
            Position=0)]
        [ValidateNotNullOrEmpty()]
        [string]$EWSAssemblyPath = 'C:\Program Files\Microsoft\Exchange\Web Services\2.2\Microsoft.Exchange.WebServices.dll',
    
        # Parameter Credential
        [Parameter(Mandatory=$true, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=1)]
        [System.Management.Automation.CredentialAttribute()]
        $Credential,
    
        # Parameter Maildomain
        [Parameter(Mandatory=$true, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=2)]
        [string]$MailDomain,
    
        # Parameter Maildomain
        [Parameter(Mandatory=$false, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=3)]
        [string]$AutoDiscoverCallbackUrl = 'https://autodiscover-s.outlook.com/autodiscover/autodiscover.xml'
    
      )
    
      # Set the path to your copy of EWS Managed API and load the assembly.
      [void][Reflection.Assembly]::LoadFile($EWSAssemblyPath) 
    
      # Establish the session and return the service connection object.
      $service =  New-Object Microsoft.Exchange.WebServices.Data.ExchangeService
      $Service.Credentials = New-Object System.Net.NetworkCredential($Credential.UserName, $Credential.GetNetworkCredential().Password, $MailDomain)
    
      $TestUrlCallback = {
        param ([string] $url)
        if ($url -eq $AutoDiscoverCallbackUrl) {$true} else {$false}
      }
      $service.AutodiscoverUrl($Credential.UserName, $TestUrlCallback)
    
      return $Service
    }
    

    和

    function Get-ExchangeOnlineMailContent {
      <#
          .Synopsis
          Fetches content from an Exchange Online user session, typically mail.
          .DESCRIPTION
          Fetches content from an Exchange Online user session, typically mail.
          .EXAMPLE
          $Service = Enter-ExchangeOnlineSession -Credential $CredMail -MailDomain example.com
          Get-ExchangeOnlineMailContent -ServiceObject $Service -PageSize 5 -Offset 0 -PageIndexLimit 15 -WellKnownFolderName Inbox
          .INPUTS
          Inputs to this cmdlet (if any)
          .OUTPUTS
          Output from this cmdlet (if any)
          .NOTES
          General notes
          .COMPONENT
          The component this cmdlet belongs to
          .ROLE
          The role this cmdlet belongs to
          .FUNCTIONALITY
          The functionality that best describes this cmdlet
      #>
    
      Param(
        [Parameter(Mandatory=$true, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=0)]
        $ServiceObject,
    
        # Define paging as described in https://msdn.microsoft.com/en-us/library/office/dn592093(v=exchg.150).aspx
        [Parameter(Mandatory=$true, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=1)]
        [int]$PageSize,
    
        [Parameter(Mandatory=$true, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=2)]
        [int]$Offset,
    
        #Translates into multiples of $PageSize
        [Parameter(Mandatory=$true, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=3)]
        [int]$PageIndexLimit,
    
        # WellKnownFolderNames doc https://msdn.microsoft.com/en-us/library/microsoft.exchange.webservices.data.wellknownfoldername(v=exchg.80).aspx
        [Parameter(Mandatory=$true, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=4)]
        [ValidateSet('Calendar',
                    'Contacts',
                    'DeletedItems',
                    'Drafts',
                    'Inbox',
                    'Journal',
                    'Notes',
                    'Outbox',
                    'SentItems',
                    'Tasks',
                    'MsgFolderRoot',
                    'PublicFoldersRoot',
                    'Root',
                    'JunkEmail',
                    'SearchFolders',
                    'VoiceMail',
                    'RecoverableItemsRoot',
                    'RecoverableItemsDeletions',
                    'RecoverableItemsVersions',
                    'RecoverableItemsPurges',
                    'ArchiveRoot',
                    'ArchiveMsgFolderRoot',
                    'ArchiveDeletedItems',
                    'ArchiveRecoverableItemsRoot',
                    'ArchiveRecoverableItemsDeletions',
                    'ArchiveRecoverableItemsVersions',
                    'ArchiveRecoverableItemsPurges',
                    'SyncIssues',
                    'Conflicts',
                    'LocalFailures',
                    'ServerFailures',
                    'RecipientCache',
                    'QuickContacts',
                    'ConversationHistory',  
                    'ToDoSearch')]
        [string]$WellKnownFolderName,
    
        [Parameter(Mandatory=$false, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=5)]
        [switch]$ParseOriginalRecipient,
    
        [Parameter(Mandatory=$false, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=6)]
        [switch]$OriginalRecipientAddressOnly,
    
        [Parameter(Mandatory=$false, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=7)]
        [datetime]$MailFromDate,
    
        [Parameter(Mandatory=$false, 
            ValueFromPipeline=$true,
            ValueFromPipelineByPropertyName=$true, 
            ValueFromRemainingArguments=$false, 
            Position=8)]
        [switch]$ConsoleOutput
      )
    
      # Create Property Set to include body and header, set body to text.
      $PropertySet = New-Object Microsoft.Exchange.WebServices.Data.PropertySet([Microsoft.Exchange.WebServices.Data.BasePropertySet]::FirstClassProperties)
      $PropertySet.RequestedBodyType = [Microsoft.Exchange.WebServices.Data.BodyType]::Text
    
      if ($ParseOriginalRecipient)
      {
        $PR_TRANSPORT_MESSAGE_HEADERS = new-object Microsoft.Exchange.WebServices.Data.ExtendedPropertyDefinition(0x007D,[Microsoft.Exchange.WebServices.Data.MapiPropertyType]::String)
        $PropertySet.add($PR_TRANSPORT_MESSAGE_HEADERS)
      }
    
      $PageIndex = 0
    
      # Page through folder.
      do 
      { 
        # Limit the view to $pagesize number of email starting at $Offset.
        $PageView = New-Object Microsoft.Exchange.WebServices.Data.ItemView($PageSize,$PageIndex,$Offset)
    
        # Get folder data.
        $FindResults = $ServiceObject.FindItems([Microsoft.Exchange.WebServices.Data.WellKnownFolderName]::$WellKnownFolderName,$PageView) 
        foreach ($MailItem in $FindResults.Items)
        {
          # Load extended properties.
          $MailItem.Load($propertySet)
    
          if ($ParseOriginalRecipient)
          {
            # Extended properties are one string, split by linebreak then find the line beginning with 'To:', containing original recipient address before exchange aliasing replaces it.
            $OriginalRecipientStringRaw = ($MailItem.ExtendedProperties.value.split([Environment]::NewLine) | Where-Object {$_ -match '^To:'}).trimstart('To:').trim()
    
            $MailItem | Add-Member -NotePropertyName ExtendedHeader -NotePropertyValue $OriginalRecipientStringRaw
    
            if ($OriginalRecipientAddressOnly)
            {
              # Removes everything but the address '[email protected]' when string has form of e.g. '"My Name" <[email protected]>'
              $MailItem | Add-Member -NotePropertyName OriginalRecipient -NotePropertyValue ($OriginalRecipientStringRaw | ForEach-Object {($_.ToString() -creplace '^[^<]*<', '').trimend('>')})
            }
            else
            {
              $MailItem | Add-Member -NotePropertyName OriginalRecipient -NotePropertyValue $OriginalRecipientStringRaw
            }
            if ($ConsoleOutput) {write-host -ForegroundColor Cyan "$($MailItem.DateTimeReceived) | $($MailItem.OriginalRecipient) | $($MailItem.Sender)"}
          }
    
          # Output result.
          $MailItem | Select-Object -Property *
        } 
    
        # Increment $index to next page.
        $PageIndex += $PageSize
      } while (($FindResults.MoreAvailable) `
                -and ($PageIndex -lt $PageIndexLimit) `
                -and ($MailItem.DateTimeReceived -gt $MailFromDate)) # Do/While there are more emails to retrieve and pagelimit is not exceeded and datetimereceived is later than date.
    }
    

    那么可以:

    $Cred = Get-Credential #Example user: [email protected]
    $domain = 'example.com'
    
    # Set how many emails we want to read at a time
    $PageSizeNumOfEmails = 10
    $OffSet = 0
    $PageIndexLimit = 2000
    $MailFolder = 'Inbox'
    $DeltaTimeStamp = (Get-Date).AddDays(-30) #Go how many days back?
    
    try
    {
      $Session = Enter-ExchangeOnlineSession -Credential $Cred -MailDomain $domain
    }
    catch
    {
      $Message = $_.exception.message
      Write-Host -ForegroundColor Yellow $Message
    }
    
    $Mails = Get-ExchangeOnlineMailContent -ServiceObject $Session `
                                            -PageSize $PageSizeNumOfEmails `
                                            -Offset $OffSet `
                                            -PageIndexLimit $PageIndexLimit `
                                            -WellKnownFolderName $MailFolder `
                                            -ParseOriginalRecipient `
                                            -OriginalRecipientAddressOnly `
                                            -MailFromDate $DeltaTimeStamp | Where-Object {$_.DateTimeReceived -gt $DeltaTimeStamp} | select *
    

    最后$Mails按您的意愿处理。

    • 0

相关问题

  • 资源锁和电源外壳

  • 脚本 - 如何断开远程桌面会话?

  • 如何限制向通讯组发送到外部地址?

  • Powershell对值与数组的作用不同?

  • Windows Powershell Vim 键绑定

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    新安装后 postgres 的默认超级用户用户名/密码是什么?

    • 5 个回答
  • Marko Smith

    SFTP 使用什么端口?

    • 6 个回答
  • Marko Smith

    命令行列出 Windows Active Directory 组中的用户?

    • 9 个回答
  • Marko Smith

    什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同?

    • 3 个回答
  • Marko Smith

    如何确定bash变量是否为空?

    • 15 个回答
  • Martin Hope
    Tom Feiner 如何按大小对 du -h 输出进行排序 2009-02-26 05:42:42 +0800 CST
  • Martin Hope
    Noah Goodrich 什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同? 2009-05-19 18:24:42 +0800 CST
  • Martin Hope
    Brent 如何确定bash变量是否为空? 2009-05-13 09:54:48 +0800 CST
  • Martin Hope
    cletus 您如何找到在 Windows 中打开文件的进程? 2009-05-01 16:47:16 +0800 CST

热门标签

linux nginx windows networking ubuntu domain-name-system amazon-web-services active-directory apache-2.4 ssh

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve