Отправка почты powershell: Powershell отправка почты с авторизацией через SMTP сервер Яндекса
Отправка почты из PowerShell | Windows для системных администраторов
Я уже рассказывал про то, как можно отправить почту из командной строки при помощи telnet. Теперь возникла задача написания скрипта для системы мониторинга, который бы в случае наступления некого события отправлял почтовое сообщение ответственному лицу.
Так как в последнее время все чаще приходится использовать скрипты на PowerShell, то и скрипт отправки почты я решил реализовать именно на нем. Этот небольшой скрипт PowerShell отправляет e-mail письмо определённому адресату, указанному в его коде. Данный скрипт используется в самописной системе мониторинга определенной не майкрософтовской службы, запущенной на Windows Server 2008. В случае, если служба остановиться, то в техподдержку тут же отправляется письмо с оповещением о проблеме. Мой PowerShell код выглядит следующим образом:
$EmailFrom = “[email protected]”
$EmailTo = “[email protected]”
$Subject = “Check service at your Windows Server 2008 NOW”
$Body = “Monitoring service is stop!!”
$SmtpServer = “smtp.winitpro.ru”
$smtp = New-Object net.mail.smtpclient($SmtpServer)
$smtp.Send($EmailFrom, $EmailTo, $Subject, $Body)
При использовании скриптов на PowerShell есть ряд ограничений. По соображениям безопасности скрипт PowerShell нельзя запустить, просто дважды щелкнув по файлу с расширением.PS1. Поэтому, если вы хотите запустить скрипт PowerShell из планировщика заданий или еще каким-то автоматизированным способом, то можно создать скрипт VBS, который в свою очередь будет вызывать скрипт на PowerShell:
Set objShell = CreateObject(“WScript.Shell”)
objShell.Run(“powershell.exe c:\script\send_email.ps1>”)
В итоге у вас должны получится два файла: один содержит vbs код (расширение.VBS ), во втором находится PowerShell код отправки почты (расширение .PS1 ).
В том случае, если вы используете Windows Server 2008, не забудьте включить функцию поддержки PowerShell, иначе скрипты PS работать не будут.
Мне пригодился код С++, позволяющий скрыть окно windows: How to Hide Another Person’s Window.
отправить письмо на почту » Pechenek.NET
Всем привет! В этой небольшой статье я вам расскажу – как отправить письмо на почту через PowerShell. Сегодня возьмем какой-нибудь текст. В рамках автоматизации процессов (не важно каких), иногда появляется необходимость получить информацию прямо с сервера. Для таких целей можно воспользоваться решением, которое представлено ниже.
PowerShell – как отправить письмо на почту
Давайте разберем простой пример, который мы в дальнейшем немножечко разовьем. Итак, что нужно для того, чтобы отправить письмо на почту через PowerShell?
- Адресат – адресат, который будет отправлять почту. Как правило это должен быть какой-то системный ящик, находящийся в домене.
- Получатель – электронная почта, которая будет принимать сообщения, после выполнения скрипта.
- Тема сообщения – ее можно оставить пустой, но мы ее разберем, так как она является одной из переменных, которые внесут целостность и понимание составления структуры письма.
- Тело письма – думаю тут все понятно. Хотя, мы с вами разберем интересную ситуацию, в которой необходимо переносить строчку в письме.
- Почтовый сервер – это обязательный реквизит, потому что почтовый сервер осуществляет необходимые операции по обработке и отправке письма.
- Далее необходимо создать объект, который будет являться smtp клиентом, подключенным к почтовому серверу.
Окей, с требованиями разобрались, как это все выглядит в коде? Все просто. Создаем файл с расширением *.ps1, назовем его test.ps1. Что нужно внутри? Переменные сохранены в соответствии с пунктами выше:
- $EmailFrom = “[email protected]”
- $EmailTo = “[email protected]”
- $Subject = “test”
- $Body = “test”
- $SmtpServer = “post.domain.ru”
- $smtp = New-Object net.mail.smtpclient($SmtpServer)
- $smtp.Send($EmailFrom, $EmailTo, $Subject, $Body)
Откуда взялся 7-ой пункт? А это и и есть ответ на вопрос “как отправить письмо на почту через PowerShell” . В этом пункте мы сказали Smtp-клиенту отправить письмо, от адресата пункта 1, получателю пункта 2, с темой письма пункта 3, и содержимым пункта 4. Что получилось и как проверить? Правой кнопкой мыши по нашему файлу -> Run with powershell…
Кастомизация.
Итак… Выглядит не очень, простенько, что тут еще скажешь, какой код, такой и вывод. Давайте попробуем украсить. Добавил имя сервера в Subject, с которого выполняется скрипт и в тело добавим папку профиля PowerShell:
$server=hostname
$EmailFrom = «[email protected]»
$EmailTo = «[email protected]»
$Subject = «Скрипт выполнен на $server»
$Body = «Рабочая папка: $profile»
$SmtpServer = «postm.domain.ru»
$smtp = New-Object net.mail.smtpclient($SmtpServer)
$smtp.Send($EmailFrom, $EmailTo, $Subject, $Body)
$server=hostname $EmailFrom = «[email protected]» $EmailTo = «[email protected]» $Subject = «Скрипт выполнен на $server» $Body = «Рабочая папка: $profile» $SmtpServer = «postm.domain.ru» $smtp = New-Object net.mail.smtpclient($SmtpServer) $smtp.Send($EmailFrom, $EmailTo, $Subject, $Body) |
Запускаем, проверяем…
Окей, приступим к разбору изменений. Добавилась новая переменная (первая строка) $server=hostname. Дело в том, hostname является командлетом, и чтобы переменная получила значение, необходимо выполнить этот командлет. Соответственно имя сервера попало в тему письма, а именно SOFT889.
Далее в строке 5 произошли изменения содержимого: “Рабочая папка: $profile”. PowerShell способен обрабатывать системные переменные во время передачи строки. Получили соответствующий результат. Давайте усложним… Например, выведем имя операционной системы, но на новой строке. Меняем код так:
$os=(Get-WmiObject -class Win32_OperatingSystem).Caption
$server=hostname
$EmailFrom = «[email protected]»
$EmailTo = «[email protected]»
$Subject = «Скрипт выполнен на $server»
$Body = «Рабочая папка: $profile» +
[System.Environment]::NewLine + «Название операционной системы: $os»
$SmtpServer = «postm.domain.ru»
$smtp = New-Object net.mail.smtpclient($SmtpServer)
$smtp.Send($EmailFrom, $EmailTo, $Subject, $Body)
$os=(Get-WmiObject -class Win32_OperatingSystem).Caption $server=hostname $EmailFrom = «[email protected]» $EmailTo = «[email protected]» $Subject = «Скрипт выполнен на $server» $Body = «Рабочая папка: $profile» + [System.Environment]::NewLine + «Название операционной системы: $os» $SmtpServer = «postm.domain.ru» $smtp = New-Object net.mail.smtpclient($SmtpServer) $smtp.Send($EmailFrom, $EmailTo, $Subject, $Body) |
Выполняем:
Отлично, разнообразили. Давайте разбираться.
- Добавили строку с определением операционной системы – $os=(Get-WmiObject -class Win32_OperatingSystem).Caption
- В $Body добавили строку, которая отвечает за перенос строки и склейку этих строк в одну переменную – “+ [System.Environment]::NewLine +”
- Добавили вывод новой переменной с названием операционной системы – “”Название операционной системы: $os”.
Итог:
Мы научились отправлять письмо на почту через PowerShell, кастомизировали его, научились работать с функцией (или методом) отправки письма smtp клиента. В дальнейшем будем более детально изучать компоненты и их ответвления/вариации. Спасибо за внимание! Подписывайтесь на наш Youtube и группу в ВК. Ну и на печеньки к чаю тоже было бы неплохо 🙂
Powershell отправка почты | Заметки программиста 1с
function SendMail($Settings)
{
#Адрес сервера SMTP для отправки и порт сервера
$serverSmtp = «XXXX.ru» #Для яндекса «smtp.yandex.ru»
$port = 25 #Для яндекса 587
#От кого и кому
$From = «[email protected]»
$To = «[email protected]»
#Тема письма
$subject = «Компьютер: » + $env:COMPUTERNAME.ToString() + «. Свободное место на дисках + srvinfo»
#Логин и пароль от ящики с которого отправляете
$user = «[email protected]» #Для яндекса «…[email protected]»
$pass = «ПАРОЛЬ»
#Создаем два экземпляра класса
$att = New-object Net.Mail.Attachment($Settings[1]) #Файлы
$mes = New-Object System.Net.Mail.MailMessage #Письмо
#Формируем данные для отправки
$mes.From = $from
$mes.To.Add($to)
$mes.Subject = $subject
$mes.IsBodyHTML = $true
$mes.Body = $Settings[0]
#Добавляем файл
$mes.Attachments.Add($att)
#Создаем экземпляр класса подключения к SMTP серверу
$smtp = New-Object Net.Mail.SmtpClient($serverSmtp, $port)
#Сервер использует SSL
$smtp.EnableSSL = $False #Для яндекса $TRUE
#Создаем экземпляр класса для авторизации на сервере
$smtp.Credentials = New-Object System.Net.NetworkCredential($user, $pass);
#Отправляем письмо, освобождаем память
$smtp.Send($mes)
$att.Dispose()
}
$InfoDisk = get-WmiObject win32_logicaldisk | select @{Name=»Диск»;Expression={$_.name}}, @{Name=»Свободное место GB»;Expression={$_.FreeSpace / 1Gb}} | ConvertTo-HTML
$File = «D:\SrvinfoServer.txt»
$Settings = $InfoDisk, $File
SendMail($Settings)
Powershell отправка почты через gmail
В данной записи описан простой и короткий скрипт на Powershell для отправки почты через gmail и решение ошибки 5.5.1.
При попытке отправить письмо через gmail в Powershell скрипте я получал следующую ошибку:
Серверу SMTP требовалось защищенное соединение, или подлинность клиента не была установлена. Ответ сервера: 5.5.1 Authentication Required. Learn more at
Или по английски:
The SMTP server requires a secure connection or the client was not authenticated. The server response was: 5.5.1 Authentication Required
Далее опишу что нужно сделать, чтобы избавиться от ошибки и приведу пример самого powershell скрипта.
Если у вас в google НЕ включена двух-факторная авторизация (подтверждение входа через отправку sms на телефон)
Необходимо разрешить непроверенным приложениям доступ к вашему аккаунту, это делается на странице: google.com/settings/security/lesssecureapps
Если не разрешите, то к Вам на почту будут приходить письма с темой «Предотвращ
Если у вас в google включена двух-факторная авторизация
Нужно сгенерировать отдельный пароль для доступа powershell-скрипта к Вашему аккаунту. Это делается на странице security.google.com/settings/security/apppasswords
Выбираем в выпадающем списке «Приложение» пункт «Другое» и пишем какое-то свое название, я написал «Powershell on elimS Notebook». Жмем кнопку «Создать» и Вам будет выдан шестнадцатизначный пароль, который нужно использовать в скрипте, пример пароля: «ifizbeaatmuzqonp» — 16 букв в нижнем регистре, без пробелов.
Powershell скрипт для отправки почты через gmail
#Входящие данные сообщения: $From = "[email protected]" $To = "[email protected]" $SMTPServer = "smtp.gmail.com" $SMTPPort = "587" $Username = "elimsmail" $Password = "yourpassword" $subject = "hello" $body = "bodytext" #формируем сообщение в формате html: $message = New-Object System.Net.Mail.MailMessage $From, $To $message.Subject = $subject $message.IsBodyHTML = $true $message.Body = $body #Отправляем: $smtp = New-Object System.Net.Mail.SmtpClient($SMTPServer, $SMTPPort) $smtp.EnableSSL = $true $smtp.Credentials = New-Object System.Net.NetworkCredential($Username, $Password) $smtp.Send($message)
Не забудьте в переменных указать свои данные: почтовый ящик, пароль и т.п.
Где этот скрипт можно применить? Я таким образом настроил автопостинг в twitter (вернее автотвитеринг =) ) через сервис ifttt.com и рецепт «If send [email protected] any email from [email protected], then post a tweet to @мой_твитер_аккаунт»
Понравилось? =) Поделись с друзьями:
Отправка писем из PowerShell с авторизацией
Отправка писем из PowerShell с авторизацией
В свое время я столкнулся с задачей по отправке различных отчетов из powershell. Есть замечательный командлет send-mailmessage, он хорошо описан в справке по PowerShell.
Но есть небольшая проблема с которой сталкиваются администраторы, нет возможности авторизоваться на почтовом сервере. Самое распространенное решение это OpenRelay для IP вашего сервера. Но такое решение не совсем корректно (привет ИБ коллегам кто читает статью 🙂 ). Со временем, у меня созрел небольшой скрипт, по отправке уведомлений, который я использую в работе. Он отправляет отчет в формате HTML + encoding utf8 + авторизация на почтовом сервере.
Выглядит это так:
##—HTML—##
$a = «<style>»
$a = $a + «BODY{background-color:#f1f0ef;}»
$a = $a + «TABLE{border-width: 1px;border-style: solid;border-color: black;border-collapse: collapse;}»
$a = $a + «TH{border-width: 2px;padding: 40px;border-style: solid;border-color: black;background-color:#f5eff5}»
$a = $a + «TD{border-width: 2px;padding: 10px;border-style: solid;border-color: black;background-color:#ecfbff}»
$a = $a + «</style>»
$D = «<h3>-</h3>»
$D = $D + «<h4>Это автоматическое уведомление.</h4>»
$D = $D + «<h5>-<h5>»
$D = $D + «<h5>Статус процесса idle<h5>»
$D = $D + «<h4>Формируется каждые 3 часа<h4>»
##—HTML—##
##—MAIN—##
Get-Process | Where-Object {$_.»Id» -like 0 } | ConvertTo-HTML -head $a,$d | Out-File C:\test\get.html
$report = c:\test\get.html
##—MAIN—##
#—Делаем креденталы—#
$secpasswd = ConvertTo-SecureString «your_password» -AsPlainText -Force
$mycreds = New-Object System.Management.Automation.PSCredential («your_users», $secpasswd)
#—Делаем креденталы—#
#—MAIL—#
$MailBody= Get-Content $Report
#Отправляем письмо send-mailmessage
$encoding = [System.Text.Encoding]::UTF8
send-mailmessage -to «[email protected]» -from «[email protected]» -subject «—Report status process id 1—» -body «$mailbody» -BodyAsHtml -smtpserver ex10.win13.ru -credential $mycreds -Encoding $encoding
##—MAIL—##
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
| ##—HTML—## $a = «<style>» $a = $a + «BODY{background-color:#f1f0ef;}» $a = $a + «TABLE{border-width: 1px;border-style: solid;border-color: black;border-collapse: collapse;}» $a = $a + «TH{border-width: 2px;padding: 40px;border-style: solid;border-color: black;background-color:#f5eff5}» $a = $a + «TD{border-width: 2px;padding: 10px;border-style: solid;border-color: black;background-color:#ecfbff}» $a = $a + «</style>» $D = «<h3>-</h3>» $D = $D + «<h4>Это автоматическое уведомление.</h4>» $D = $D + «<h5>-<h5>» $D = $D + «<h5>Статус процесса idle<h5>» $D = $D + «<h4>Формируется каждые 3 часа<h4>» ##—HTML—## ##—MAIN—## Get-Process | Where-Object {$_.»Id» -like 0 } | ConvertTo-HTML -head $a,$d | Out-File C:\test\get.html $report = c:\test\get.html ##—MAIN—## #—Делаем креденталы—# $secpasswd = ConvertTo-SecureString «your_password» -AsPlainText -Force $mycreds = New-Object System.Management.Automation.PSCredential («your_users», $secpasswd) #—Делаем креденталы—# #—MAIL—# $MailBody= Get-Content $Report #Отправляем письмо send-mailmessage $encoding = [System.Text.Encoding]::UTF8 send-mailmessage -to «[email protected]» -from «[email protected]» -subject «—Report status process id 1—» -body «$mailbody» -BodyAsHtml -smtpserver ex10.win13.ru -credential $mycreds -Encoding $encoding ##—MAIL—## |
html выглядит так
Минусы очевидны, логин\пароль от учетной записи будет лежать в открытом виде. Но с другой стороны, ничего не мешает создать учетную запись, только на возможность отправки писем внутри организации.
Posted in PowerShell on and tagged PowerShell, Report, smtp
No Comments »
Создание отчетов в PowerShell / Хабр
Рассмотрены вопросы вывода текста, создания отчетов, отправки почты. Даются советы как писать отчеты так чтобы много раз можно было использовать фрагменты кода, добавить недостающие фрагменты, и собирать в отчет большей длины.
Однозначно нужно всем кто делает сбор информации используя PowerShell, или хочет научится его эффективному применению.
Секреты создания отчетов Глава 33
Эта глава содержит
- Работа с HTML фрагментами
- Создание стильных HTML отчетов
- Отправка отчетов поэлектронной почте
В этой главе мы рассмотрим приемы работы с PowerShell при создании отчетов. PowerShell не блещет если нужно работать со строками, старайтесь использовать для этого объекты. Чем больше вы будете использовать при создании отчетов объекты, тем лучше вы сможете сделать обработку.
33.1 Что не нужно делать.
Начнем главу с того что мы считаем примером плохой техники создания отчетов. Мы постоянно встречаем такой стиль. Большая часть IT профессионалов не задумываются об этом и увековечивают в коде стиль из других языков, таких как VBScript.
Следующий код написан в стиле, который как мы надеемся вы не будете применять, и который вы увидите в коде менее информированных системных администраторов.
Листинг 33.1 Плохо спроектированный скрипт инвентаризации
param ($computername)
Write-Host '------- COMPUTER INFORMATION -------'
Write-Host "Computer Name: $computername"
$os = Get-WmiObject -Class Win32_OperatingSystem -ComputerName $computername
Write-Host " OS Version: $($os.version)"
Write-Host " OS Build: $($os.buildnumber)"
Write-Host " Service Pack: $($os.servicepackmajorversion)"
$cs = Get-WmiObject -Class Win32_ComputerSystem -ComputerName $computername
Write-Host " RAM: $($cs.totalphysicalmemory)"
Write-Host " Manufacturer: $($cs.manufacturer)"
Write-Host " Model: $($cd.model)"
Write-Host " Processors: $($cs.numberofprocessors)"
$bios = Get-WmiObject -Class Win32_BIOS -ComputerName $computername
Write-Host "BIOS Serial: $($bios.serialnumber)"
Write-Host ''
Write-Host '------- DISK INFORMATION -------'
Get-WmiObject -Class Win32_LogicalDisk -Comp $computername –Filt 'drivetype=3' |
Select-Object @{n='Drive';e={$_.DeviceID}},
@{n='Size(GB)';e={$_.Size / 1GB -as [int]}},
@{n='FreeSpace(GB)';e={$_.freespace / 1GB -as [int]}} | Format-Table –AutoSize
Код приведенный в листинге 33.1 произведет вывод подобный этому
Фигура 33.1 вывод, основанный на строках.
Как видно этот скрипт работает, Дон Джонс (один из авторов) видя вывод из скрипта чистыми строками гневно произносит поговорку с участием божества и щенков (наверное, ругательство в оригинале Don has a saying involving angry deities and puppies that he utters whenever he sees a script that outputs pure text like this). Прежде всего – этот сценарий может выводить только на экран, т.к. вывод ведется через Write-Host. В большинстве случаев, когда вы будете использовать Write-Host, вы будете делать это неправильно. Было бы неплохо если была бы возможность вывести эту информацию в файл, или в HTML? Вы можете добиться этого изменяя все Write-Host на Write-Output, но это по-прежнему будет неправильный путь.
Есть более эффективные способы формирования отчета, и это причина по которой мы написали эту главу. Во-первых, мы предложили бы для каждого блока или функции, где происходит генерация информации создавать один объект содержащий всю нужную информацию. Чем больше вы разобьете на блоки код, тем больше вы сможете повторно использовать эти блоки. В нашем плохом примере, первый раздел «информация о компьютере», должно осуществляться функцией которую мы напишем. Ее можно будет использовать во всех отчетах подобного вида. В разделе «информация о диске» данные указываются одним объектом, объединять информацию из разных источников не нужно, но все командлеты на Write должны уйти. (прим переводчика. Как надо делать смотрите в примере к разделу 33.2.1 Получение исходной информации)
Исключения из каждого правила
Есть исключения из каждого правила. Ричард Сиддэвэй проводит много времени проводя аудит чужих систем. Он делает это стандартным набором сценариев. Сценарии предназначены для производства вывода, которые затем идут либо непосредственно в документ Word, либо генерируются файлики которые затем вставляются в документ. Таким образом первоначальные данные могут быть очень быстро получены и просмотрены, так что их анализ и обсуждение не задерживается.
Правила нарушающиеся в этих сценариях следующие
- Выход представляет собой смесь текста и объектов
- Вывод сразу отформатирован
Это осознанное решение, так как известно, как будут применяться скрипты и как должен выглядеть отчет. Мораль этой истории выводить объектами, и быть готовым выйти за пределы парадигмы если на то есть причины.
33.2 Работа с HTML фрагментами и файлами
Хитрость нашего способа в том, что ConvertTo-HTML можно использовать двумя различными способами. Первый способ – производить полную HTML страницу, второй – производить HTML фрагмент. Этот фрагмент всего лишь HTML таблица с данными что были переданы в командлет, мы произведем каждую секцию отчета в виде фрагмента, а затем соберем фрагменты в полную HTML страницу.
33.2.1 Получение исходной информации
Мы начнем с того что соберем данные в объекты, по одному объекту для каждого раздела отчета. В нашем случае будет два объекта – информация о компьютере и информация о дисках. Условимся что для кротости и ясности мы пропустим обработку ошибок и другие тонкости. В реальных условиях мы добавили бы их. Get-WMIObject сама по себе производит объект содержащий информацию по дискам. Значит нужно еще создать функцию выдающую объект с информацией о компьютере.
function Get-CSInfo {
param($computername)
$os = Get-WmiObject -Class Win32_OperatingSystem -ComputerName $computername
$cs = Get-WmiObject -Class Win32_ComputerSystem -ComputerName $computername
$bios = Get-WmiObject -Class Win32_BIOS -ComputerName $computername
#property names with spaces need to be enclosed in quotes
$props = @{ComputerName = $computername
'OS Version' = $os.version
'OS Build' = $os.buildnumber
'Service Pack' = $os.sevicepackmajorversion
RAM = $cs.totalphysicalmemory
Processors = $cs.numberofprocessors
'BIOS Serial' = $bios.serialnumber}
$obj = New-Object -TypeName PSObject -Property $props
Write-Output $obj
}
Функция извлекает информацию из трех различных классов WMI. Создаем объект используя хеш таблицу, собранную из трех объектов т.к., хотим иметь возможность передавать вывод функции по конвейеру. Обычно мы предпочитаем давать свойствам имена без пробелов, сейчас отклонимся от этого правила потому что собираемся использовать имена в итоговом отчете.
33.2.2 Производство фрагментов HTML отчетов.
Теперь мы можем использовать написанную функцию чтобы получить отчет в HTML
$frag1 = Get-CSInfo –computername SERVER2 | ConvertTo-Html -As LIST -Fragment –PreContent '<h3>Computer Info</h3>' | Out-String
Мы долго двигались к этому трюку, так что его обязательно нужно разобрать:
1. Вы сохраняете вывод в виде фрагмента HTML в переменную с именем $frag1, позже мы сможем вставить его в нужное место вывода либо целиком сохранить в файл.
2. запускается Get-CSInfo, ему передается имя компьютера с которого мы хотим получить данные, сейчас мы прописываем имя компьютера жестко, в будущем мы заменим его на переменную.
3. Получившийся вывод подаем на ConvertTo-HTML, эта команда формирует на выходе фрагмент HTML в виде вертикального списка, а не горизонтально. Список будет имитировать вид старого отчета по негодной-технике-выводить-информацию.
4. Мы используем параметр –PreContent чтобы добавить надпись перед табличкой отчета. Мы добавили теги чтобы получился жирный заголовок.
5. Все что получилось – это и есть трюк – передается дальше на Out-String. Вы увидите что ConvertTo-HTML поставит кучу всего в конвейер. Вы видите, что в конвейер пишутся строки, коллекции строк, всякие разные другие объекты. Все это приведет в конце к проблемам, когда вы попытаетесь собрать это все в окончательную HTML страницу, вместо мы просто подали на Out-String и получили на выходе старую добрую строку.
Можно пойти дальше и произвести второй фрагмент. Это легче т.к. не нужно писать функцию, генерация HTML будет выглядеть точно также. Единственное отличие что мы соберем данные этой секции в таблицу, а не список:
$frag2 = Get-WmiObject -Class Win32_LogicalDisk -Filter 'DriveType=3' -ComputerName SERVER2 |
Select-Object @{name='Drive';expression={$_.DeviceID}},
@{name='Size(GB)';expression={$_.Size / 1GB -as [int]}},
@{name='FreeSpace(GB)';expression={
$_.freespace / 1GB -as [int]}} | ConvertTo-Html -Fragment -PreContent '<h3>Disk Info</h3>' | Out-String
У нас есть оба фрагмента, можно приступить к формированию окончательного отчета.
33.2.3 Сборка финального HTML файла
Сборка включает в себя добавление ваших двух фрагментов, и таблицы стилей. Использование таблицы стилей CSS и языка выходит за рамки этой книги. Таблица стилей позволяет контролировать форматирование HTML страницы так чтобы она выглядела намного лучше. Если вы хотите хороший учебник и ссылки на дополнительные материалы по CSS, проверьте http://www.w3schools.com/css/
$head = @'
<style>
body { background-color:#dddddd;
font-family:Tahoma;
font-size:12pt; }
td, th { border:1px solid black;
border-collapse:collapse; }
th { color:white;
background-color:black; }
table, tr, td, th { padding: 2px; margin: 0px }
table { margin-left:50px; }
</style>
'@
ConvertTo-HTML -head $head -PostContent $frag1, $frag2 -PreContent "<h2>Hardware Inventory for SERVER2</h2>"
Создается таблица стилей $head, в переменной типа строка описывается нужный стиль. Затем эта переменная передается в параметр –head, а ваши фрагменты перечисляются через запятую в параметре –PostContent. Также добавляется заголовок отчета в параметре –PreContent. Сохраните весь сценарий как C: \ Good.ps1 и запустите его следующим образом:
./good > Report.htm
Это перенаправит вывод в файл Report.htm, который будет красив, как на рисунке 33.2
Рисунок 33.2 отчет из нескольких фрагментов
Может быть это не произведение искусства, но это отчет который выглядит лучше чем отчет на экране которым начиналась эта глава. В листинге 33.2 показан завешенный скрипт, где вы можете задать имя компьютера, по умолчанию localhost. В заголовке прописан [CmdletBinding()], что позволяет использовать –verbose. В теле скрипта вставлены Write-Verbose, вы можете видеть что делает каждый шаг.
Листинг 33.2 скрипт HTML инвентаризации
<#
.DESCRIPTION
Retrieves inventory information and produces HTML
.EXAMPLE
./Good > Report.htm
.PARAMETER
The name of a computer to query. The default is the local computer.
#>
[CmdletBinding()]
param([string]$computername=$env:computername)
# function to get computer system info
function Get-CSInfo {
param($computername)
$os = Get-WmiObject -Class Win32_OperatingSystem -ComputerName $computername
$cs = Get-WmiObject -Class Win32_ComputerSystem -ComputerName $computername
$bios = Get-WmiObject -Class Win32_BIOS -ComputerName $computername
$props = @{'ComputerName'=$computername
'OS Version'=$os.version
'OS Build'=$os.buildnumber
'Service Pack'=$os.servicepackmajorversion
'RAM'=$cs.totalphysicalmemory
'Processors'=$cs.numberofprocessors
'BIOS Serial'=$bios.serialnumber}
$obj = New-Object -TypeName PSObject -Property $props
Write-Output $obj
}
Write-Verbose 'Producing computer system info fragment'
$frag1 = Get-CSInfo -computername $computername | ConvertTo-Html -As LIST -Fragment -PreContent '<h3>Computer Info</h3>' | Out-String
Write-Verbose 'Producing disk info fragment'
$frag2 = Get-WmiObject -Class Win32_LogicalDisk -Filter 'DriveType=3' -ComputerName $computername |
Select-Object @{name='Drive';expression={$_.DeviceID}},
@{name='Size(GB)';expression={$_.Size / 1GB -as [int]}},
@{name='FreeSpace(GB)';expression={$_.freespace / 1GB -as [int]}} |
ConvertTo-Html -Fragment -PreContent '<h3>Disk Info</h3>' | Out-String
Write-Verbose 'Defining CSS'
$head = @'
<style>
body { background-color:#dddddd;
font-family:Tahoma;
font-size:12pt; }
td, th { border:1px solid black;
border-collapse:collapse; }
th { color:white;
background-color:black; }
table, tr, td, th { padding: 2px; margin: 0px }
table { margin-left:50px; }
</style>
'@
Write-Verbose 'Producing final HTML'
Write-Verbose 'Pipe this output to a file to save it'
ConvertTo-HTML -head $head -PostContent $frag1,$frag2 -PreContent "<h2>Hardware Inventory for $ComputerName</h2>"
Использование скрипта
PS C:\> $computer = SERVER01
PS C:\> C:\Scripts\good.ps1 -computername $computer |
>> Out-File "$computer.html"
>>
PS C:\> Invoke-Item "$computer.html"
Скрипт генерирует HTML файл, который можно использовать в будущем, и выводит на экран отчет. Имейте в ввиду что функция Get-CSInfo может использоваться повторно. Поскольку она выводит объект, а не текст вы можете его использовать в самых разных местах где потребуется выводить туже информацию.
Если вам понадобилось добавить добавить еще информации к отчету, то для добавления новой секции вам будет нужно:
- Написать функцию или команду генерирующую объект, с информацией новой секции отчета.
- Создать из этого объекта HTML фрагмент и сохранить в переменную.
- Добавить эту переменную в список переменных команды сборки окончательного отчета. Таким образом вы дополните отчет.
- Все
Да этот отчет — это текст. В конечном счете каждый отчет будет текстом, потому что текст — это то что мы читаем. Сутью этого метода является то что все остается объектами до последнего момента. Вы позволяете PowerShell форматировать за вас. Рабочие элементы этого скрипта могут быть скопированы и использованы в другом месте, что невозможно сделать с помощью исходного текста в начале главы.
33.3 отправка электронного письма
Что может быть лучше HTML отчета? Отчет, который автоматически придет на email!
К частью PowerShell уже содержит командлет Send-MailMessage. Немного исправим наш скрипт:
Write-Verbose 'Producing final HTML'
Write-Verbose 'Pipe this output to a file to save it'
ConvertTo-HTML -head $head -PostContent $frag1,$frag2 -PreContent "<h2>Hardware Inventory for $ComputerName</h2>" | Out-File report.htm
Write-Verbose "Sending e-mail"
$params = @{'To'='[email protected]'
'From'='[email protected]'
'Subject'='That report you wanted'
'Body'='Please see the attachment.'
'Attachments'='report.htm'
'SMTPServer'='mail.company.com'}
Send-MailMessage @params
мы изменили конец конвейера перенаправив вывод в файл. Затем использовали Send-MailMessage в качестве вложения. Можно отправить HTML как само тело сообщения. Вам не нужно для этого создавать файл на диске, вы можете взять вывод с конвейера непосредственно. Вот альтернативный пример
Write-Verbose 'Producing final HTML'
$body = ConvertTo-HTML -head $head -PostContent $frag1,$frag2 -PreContent "<h2>Hardware Inventory for $ComputerName</h2>" | Out-String
Write-Verbose "Sending e-mail"
$params = @{'To'='[email protected]'
'From'='[email protected]'
'Subject'='That report you wanted'
'Body'=$Body
'BodyAsHTML'=$True
'SMTPServer'='mail.company.com'}
Send-MailMessage @params
Здесь мы построили параметры Send-MailMessage в хеш таблице и сохранили их в переменной $Param. Это позволяет использовать splat технику и скормить все параметры команде сразу. Нет никакой разницы что вы наберете их как параметры или укажете через хэш таблицу, работать будет в любом случае, но так лучше читать.
33.4 Итог
Построение отчетов, безусловно большая потребность для администраторов, мы хотели показать, что PowerShell хорошо подходит для этой задачи. Хитрость заключается в том, чтобы создавать отчеты таким образом, чтобы извлечение информации отделить от форматирования и создания выхода. На самом деле PowerShell способен предоставить большие возможности по форматированию и выводу при небольшом количество работы с вашей стороны.
З.Ы. от переводчика
для корректного отображения русского текста нужно использовать
$encoding = [System.Text.Encoding]::UTF8
Send-MailMessage @params -Encoding $encoding
Отсылаем сообщение пользователю через Powershell
Для того, что бы через powershell отправить сообщение пользователю нужно иметь работающий PSRemoting. Если вы не знаете что это, то коротко говоря это возможность удаленного выполнения команд. Эта возможность рассматривалась тут. Коротко говоря если все получатели пользователи домена, а вы являетесь администратором на их компьютере, то единственная настройка, которая вам понадобится это включить WinRM:
Enable-PSRemoting
Если собираетесь использовать IP, или не в домене, то вы будете использовать не Kerberos, а NTLM и нужно сделать следующее:
Enable-PSRemoting
Set-Item wsman:\localhost\Client\TrustedHosts -value *
Если в последующем будут ошибки, то стоит прочитать статью, т.к. настроек может понадобится больше.
Отправление сообщение пользователю компьютера через WinRM
Для отправки сообщения есть старая утилита msg. Сообщение, которое получит пользователь, будет popup (всплывающее на главном экране). Мы можем проверить его так:
msg * "Ожидается перезагрузка сервера 1С"
Для того что бы отправить такое сообщение одному или нескольким пользователям через powershell нужно использовать:
Invoke-Command -ComputerName AD,AD2 -ScriptBlock {msg * "1C Restart in 10 minutes"}
Где:
ComputerName — имена одного или нескольких компьютеров, на которые будут отправлены сообщения. Можно и IP, но с оговорками выше…
Scriptblock — скрипт, который мы отсылаем на компьютеры. В нашем случае это msg
Сообщение будет выглядеть так:
Отправка сообщений всем пользователям компьютеров в AD
Сначала получим все имена всех компьютеров в домене и присвоим переменную. Если мой домен называется domain.local, то командлет будет выглядеть так:
$computers = (Get-ADComputer -SearchBase "DC=domain,DC=local" -Filter *).Name
Мы можем добавить OU, если у нас нужные компьютеры находятся в отдельной организационной единице:
$computers = (Get-ADComputer -SearchBase "OU=AllComputers,DC=domain,DC=local" -Filter *).Name
Далее, для каждого компьютера в переменной используем такую команду powershell:
$computers | ForEach {Invoke-Command -ComputerName $_ {msg * "1C Restart in 2 minutes"}}
Сообщения получат все пользователи, которые залогинены.
Отправка сообщений через powershell пользователям терминального сервера
Для отправки сообщения терминальным пользователям сначала нужно получить список их сессий:
$session = Get-RDUserSession -ConnectionBroker "rdcb.fixmypc.ru"
Затем мы можем отправить сообщения:
$message = "Ожидается перезагрузка сервера в течении 10 минут"
$session | Send-RDUserMessage -HostServer "rdsh.domain.local" -MessageBody $message
…
Теги:
#powershell
#ad
PowerShell: отправка сообщений электронной почты с вложениями с помощью SMTP-сервера Office 365 и Gmail — статьи TechNet — США (английский)
У нас есть возможность отправлять письма из PowerShell. Мы можем отправить тело в виде текста или даже в виде вложения по почте. Чтобы упростить отправку почты, мы можем использовать различные доступные SMTP-серверы. В этой демонстрации мы увидим
как использовать SMTP-серверы Office 365 для ретрансляции почты бизнес-пользователям. В рамках пошагового руководства мы увидим, как отправлять обычный текст в теле письма.
В демонстрации мы будем читать данные JSON из службы REST, и мы будем использовать SMTP-сервер Office 365 для ретрансляции почты бизнес-пользователям. Прежде чем перейти к функции отправки почты, давайте взглянем на службу REST, которой мы будем
использование для демонстрации.
Веб-служба REST
Хотя мы можем создать собственную службу REST, на данный момент мы можем опробовать уже существующую. Мы будем использовать доступные здесь бесплатные веб-службы RESTful, которые
мы будем потреблять из PowerShell.Мы будем использовать конкретную веб-службу REST, которая получает состояния и
территории США.
Конечная точка REST, которую мы будем использовать, —
.
http://services.groupkt.com/state/get/USA/all
PowerShell версии 3.0
Мы используем командлет Invoke-WebRequest, представленный в версии 3.0, для вызова веб-службы REST и получения данных из Интернета. Поэтому мы должны убедиться, что в системе установлен PowerShell версии 3.0 или выше.Мы можем проверить версию, выполнив следующую команду.
(Get-Host). Версия
↑ Вернуться к началу
Конечная точка веб-службы
REST может быть вызвана из PowerShell с помощью командлета Invoke-WebRequest. Как только мы получим возвращенные данные, они будут в формате JSON, но для работы с ними мы должны преобразовать их в объект PowerShell. Будет использован командлет ConvertFrom-Json.
для преобразования строки в формате JavaScript Object Notation (JSON) в пользовательский объект PSCustomObject, у которого есть свойство для каждого поля в строке JSON.Точно так же для генерации строки JSON из любого объекта мы можем использовать командлет ConvertTo-Json.
Поскольку свойства (страна, столица, самый большой_город) хранятся в свойстве RestResponse и result как встроенные объекты, нам нужно развернуть эти свойства с помощью атрибута «-expand», а затем выбрать необходимые свойства из встроенного объекта.
После получения данных JSON мы будем использовать «ConvertFrom-Json» для преобразования данных из JSON в настраиваемые объекты PowerShell
.
Вызов веб-запроса и получение необходимых свойств после выполнения команды ConvertFrom-JSON даст нам следующие результаты:
Код:
$ результат = Invoke-WebRequest $ запрос
$ JSONResult = $ результат | ConvertFrom-Json | select -expand RestResponse | select -expand результат
$ JSONResult | Выберите страну, столицу, самый большой_город | Сорт-Объект капитал
Преобразование данных в HTML
Чтобы отправить приведенную выше таблицу в теле письма, мы преобразуем ее в HTML с помощью команды ConvertTo-HTML.
- $ Body = $ JSONResult | Выберите страну, название, столицу, самый большой_город | Имя объекта сортировки | ConvertTo-HTML
↑ Вернуться к началу
Чтобы отправить электронное письмо из PowerShell, нам нужно указать SMTP-сервер. Мы будем использовать SMTP Office 365 для ретрансляции почты. Нам нужно будет заполнить несколько параметров, прежде чем запускать команду «Send-MailMessage», которая будет ретранслировать электронную почту.
- $ SmtpServer = ‘smtp.office365.com ‘- это адрес SMTP-сервера Office 365, который мы будем использовать.
- $ SmtpUser = ‘[email protected]’ — укажите свой идентификатор пользователя Office 365
- $ smtpPassword = ‘<Введите пароль Office 365 здесь>’ — укажите пароль для Office 365
- $ MailtTo = ‘[email protected]’ — укажите пользователей, которым следует отправлять письма
- $ MailFrom = ‘[email protected]’ — укажите идентификатор исходного адреса электронной почты
- $ MailSubject = «Тест с использованием $ SmtpServer» — это строка темы сообщения.
Наконец, создайте объект учетных данных, используя имя пользователя и пароль, которые мы ввели выше.Поскольку мы используем SMTP-сервер Office 365, мы указали соответствующие учетные данные. Если вы используете Gmail SMTP, убедитесь, что вы используете учетные данные Gmail.
$ Credentials = New-Object System.Management.Automation.PSCredential -ArgumentList $ SmtpUser, $ ($ smtpPassword | ConvertTo-SecureString -AsPlainText -Force)
Убедитесь, что учетные данные верны, иначе мы получим указанную выше ошибку. Итак, мы установили параметры. Теперь мы можем вызвать команду Send-MailMessage для отправки почты пользователям, как показано ниже:
Send-MailMessage -To «$ MailtTo» -from «$ MailFrom» -Subject $ MailSubject -Body «$ Body» -SmtpServer $ SmtpServer -BodyAsHtml -UseSsl -Credential $ Credentials
Полный код:
$ результат = Invoke-WebRequest $ request -UseBasicParsing
$ JSONResult = $ результат | ConvertFrom-Json | select -expand RestResponse | выберите - развернуть результат
$ Body = $ JSONResult | Выберите страну, название, столицу, самый большой_город | Имя объекта сортировки | ConvertTo-HTML
$ SmtpServer =
'smtp.office365.com '
$ SmtpUser =
«[email protected]»
$ smtpPassword = ‘
365
Пароль здесь> ’
$ MailtTo =
"[email protected]"
$ MailFrom =
«[email protected]»
$ MailSubject =
«Тест с использованием $ SmtpServer»
$ Учетные данные = Система новых объектов.Management.Automation.PSCredential -ArgumentList $ SmtpUser, $ ($ smtpPassword | ConvertTo-SecureString -AsPlainText -Force)
Send-MailMessage - Кому
"$ MailtTo"
-от
"$ MailFrom"
-Subject $ MailSubject-Body
"$ Body"
-SmtpServer $ SmtpServer -BodyAsHtml -UseSsl -Credential $ Credentials
запись-вывод
«Специальное сообщение: данные JSON службы REST проанализированы и электронное письмо отправлено бизнес-пользователям»
Давайте сохраним приведенный выше код в файл ps1 и запустим его из консоли.
Мы видим, что письмо было инициировано и достигло почтового ящика.
Таким образом, мы увидели, как отправлять почту из PowerShell с помощью SMTP-сервера Office 365. Теперь давайте посмотрим, как сделать то же самое с помощью SMTP-сервера Gmail.
↑ Вернуться к началу
Чтобы отправить электронное письмо из PowerShell, нам нужно указать SMTP-сервер. Мы будем использовать Gmail SMTP для ретрансляции почты. Нам нужно будет заполнить несколько параметров, прежде чем запускать команду «Send-MailMessage», которая будет ретранслировать электронную почту.
- $ SmtpServer = 'smtp.gmail.com' - это адрес SMTP-сервера Gmail, который мы будем использовать.
- $ SmtpUser = ‘[email protected]’ - укажите свой идентификатор пользователя Gmail.
- $ smtpPassword = «<Введите пароль учетной записи Gmail>» - укажите пароль учетной записи Gmail.
- $ MailtTo = ‘[email protected] '- укажите пользователей, которым следует отправлять письма.
- $ MailFrom = ‘[email protected]’ - укажите исходный идентификатор электронной почты.
- $ MailSubject = "Тест с использованием $ SmtpServer" - это строка темы письма.
Наконец, создайте объект учетных данных, используя имя пользователя и пароль, которые мы ввели выше.
- $ Credentials = New-Object System.Management.Automation.PSCredential -ArgumentList $ SmtpUser, $ ($ smtpPassword | ConvertTo-SecureString -AsPlainText -Force)
Убедитесь, что учетные данные верны, иначе мы получим указанную выше ошибку.Итак, мы настроили параметры. Теперь мы можем вызвать команду Send-MailMessage для отправки почты пользователям, как показано ниже:
- Send-MailMessage -To «$ MailtTo» -from «$ MailFrom» -Subject $ MailSubject -Body «$ Body» -SmtpServer $ SmtpServer -BodyAsHtml -UseSsl -Credential $ Credentials
Полный код:
$ результат = Invoke-WebRequest $ request -UseBasicParsing
$ JSONResult = $ результат | ConvertFrom-Json | select -expand RestResponse | выберите - развернуть результат
$ Body = $ JSONResult | Выберите страну, название, столицу, самый большой_город | Имя объекта сортировки | ConvertTo-HTML
$ SmtpServer =
'smtp.gmail.com '
$ SmtpUser =
"[email protected]"
$ smtpPassword =
'<Введите пароль учетной записи Gmail>'
$ MailtTo =
'[email protected]'
$ MailFrom =
"[email protected]"
$ MailSubject =
«Тест с использованием $ SmtpServer»
$ Учетные данные = Система новых объектов.Management.Automation.PSCredential -ArgumentList $ SmtpUser, $ ($ smtpPassword | ConvertTo-SecureString -AsPlainText -Force)
Send-MailMessage - Кому
"$ MailtTo"
-от
"$ MailFrom"
-Subject $ MailSubject-Body
"$ Body"
-SmtpServer $ SmtpServer -BodyAsHtml -UseSsl -Credential $ Credentials
write-Output "Пользовательское сообщение: данные JSON службы REST, которые анализируются, и бизнес-пользователям отправляется электронное письмо.
Мы можем отправлять файлы как вложения, при отправке почты из PowerShell. Это делается путем добавления дополнительного параметра -Attachment ’к команде Send-MailMessage. Помимо тела письма, мы можем указать расположение файла вложения, который
должен быть отправлен вместе с почтой. В приведенном ниже блоке кода мы используем сервер ретрансляции Gmail для ретрансляции почты, содержащей файл, расположенный на локальном компьютере. Это место вложения указывается непосредственно в команде «Send-MailMessage» с помощью
параметр «Вложение».
Код отправки вложения приведен ниже.
$ Кузов =
«Образец тела письма»
$ SmtpServer =
"smtp.gmail.com"
$ SmtpUser =
"[email protected]"
$ smtpPassword =
'<Введите пароль учетной записи Gmail>'
$ MailtTo =
'[email protected]'
$ MailFrom =
'kspriyaranjan @ gmail.com '
$ MailSubject =
"Тестирование почтовых вложений с помощью $ SmtpServer"
$ Credentials = New-Object System.Management.Automation.PSCredential -ArgumentList $ SmtpUser, $ ($ smtpPassword |
ConvertTo-SecureString -AsPlainText -Force)
Send-MailMessage - Кому
"$ MailtTo"
-от
"$ MailFrom"
-Subject $ MailSubject-Body
"Кузов"
-Приспособления
"C: \ PS \ SampleAttachment.txt "
-SmtpServer $ SmtpServer -BodyAsHtml -UseSsl -Credential $ Credentials
запись-вывод
«Пользовательское сообщение: электронное письмо с вложением, отправленное бизнес-пользователям»
Мы можем сохранить приведенный выше код в файл PS1 и запустить его из командной строки, как показано ниже,
Подойдя к почтовому ящику, мы видим, что письмо было доставлено с указанным файлом вложения.
Таким образом, мы увидели, как отправлять почту из PowerShell, используя SMTP-сервер Office 365 / Gmail, а также увидели, как отправлять файлы в виде вложений, используя PowerShell.
↑ Вернуться к началу
.
Как отправить электронное письмо с помощью Windows PowerShell
Хотите отправить электронное письмо гиковским способом? Вот как можно отправить электронное письмо с помощью Windows PowerShell.
Электронная почта настолько проста, что большинство людей даже не задумывается о ней.Откройте свой почтовый клиент, введите сообщение и получателя и нажмите «Отправить». Не так уж и сложно, правда?
Но задумывались ли вы когда-нибудь об альтернативных способах отправки электронных писем? Хотите ли вы просто поиграть и заняться чем-то техническим или отправить электронное письмо, не отвлекаясь на свой почтовый ящик, есть полезный инструмент, который скрывается прямо на рабочем столе Windows.Это называется PowerShell.
Как отправить электронное письмо с помощью PowerShell
- Откройте окно PowerShell, выполнив поиск PowerShell в меню «Пуск».
- Используйте указанный ниже шаблон Gmail, чтобы настроить электронную почту. Первые строки, начинающиеся со знаков доллара, устанавливают переменные для отправки сообщения, а строка Send-MailMessage - это фактическая команда:
$ From = "[email protected]"
$ To = "[email protected]"
$ Cc = "[email protected]"
$ Attachment = "C: \ users \ Username \ Documents \ SomeTextFile.txt "
$ Subject =" Вот тема письма "
$ Body =" Это то, что я хочу сказать "
$ SMTPServer =" smtp.gmail.com "
$ SMTPPort =" 587 "
Send-MailMessage -From $ От -to $ To -Cc $ Cc -Subject $ Subject-Body $ Body -SmtpServer $ SMTPServer -port $ SMTPPort -UseSsl
- При использовании почты Yahoo сервер smtp.mail.yahoo.com , а порт - 465 . Для Outlook сервер smtp-mail.outlook.com с портом 587 .
- Вы можете удалить строки Attachment и CC , если они вам не нужны. Не забудьте также удалить их из строки Send-MailMessage .
- Включение –UseSsl обеспечивает надежное распознавание электронной почты. Вы также можете включить -DeliveryNotificationOption OnSuccess , если хотите получить подтверждение об успешной отправке.
- После того, как вы введете команду, она предложит вам ввести имя пользователя и пароль благодаря (Get-Credential) . Введите это, и ваша электронная почта уже в пути!
Еще один интересный способ сделать это - узнать, как отправить электронное письмо с помощью Google Таблиц. Что касается PowerShell, знаете ли вы, что PowerShell может использоваться как средство проверки хэша для проверки целостности файла?
Сочетания клавиш Microsoft Word для Windows
Узнайте, как эффективно использовать Microsoft Word с помощью этих удобных сочетаний клавиш для Windows.
Об авторе
Бен Штегнер
(Опубликовано 1558 статей)
Бен - заместитель редактора и менеджер по адаптации в MakeUseOf. Он оставил свою работу в сфере ИТ, чтобы писать полный рабочий день в 2016 году, и никогда не оглядывался назад.В качестве профессионального писателя он освещал технические руководства, рекомендации по видеоиграм и многое другое уже более шести лет.
Ещё от Ben Stegner
Подпишитесь на нашу рассылку новостей
Подпишитесь на нашу рассылку, чтобы получать технические советы, обзоры, бесплатные электронные книги и эксклюзивные предложения!
Еще один шаг…!
Подтвердите свой адрес электронной почты в только что отправленном вам электронном письме.
.Безопасность
- отправляйте почту через Gmail с помощью PowerShell V2 Send-MailMessage
Переполнение стека
- Около
Продукты
- Для команд
Переполнение стека
Общественные вопросы и ответыПереполнение стека для команд
Где разработчики и технологи делятся частными знаниями с коллегамиВакансии
Программирование и связанные с ним технические возможности карьерного ростаТалант
Нанимайте технических специалистов и создавайте свой бренд работодателяРеклама
Обратитесь к разработчикам и технологам со всего мира- О компании
.
PowerShell - Управление почтовым ящиком Outlook с помощью PowerShell
- 10 минут на чтение
В этой статье
Март 2013
Том 28 Номер 03
Джо Лейбовиц | Март 2013
Приходилось ли вам когда-нибудь найти сообщение электронной почты, отправленное год или два назад, которое, если вы не могли его найти, могло бы отрицательно повлиять на ваши обстоятельства? Ваша компания автоматически удаляет сообщения из папки «Входящие» или «Отправленные»? Вы устали копировать электронные письма в несколько папок, когда они касаются нескольких интересующих тем - конкретного проекта, менеджера, предмета, подразделения компании и т. Д.?
Скажем, пришло электронное письмо от Стива Мастерс о финансах проекта X в Дубае.Было бы полезно иметь автоматический способ распространения копий этого сообщения в папки для Project X, Steve Masters и Dubai и, в конечном итоге, в еще одну папку для безопасного хранения. И все это без необходимости вручную щелкать по интерфейсу Microsoft Outlook несколько раз для каждого письма. (А если вы получаете большой объем электронной почты, тем важнее автоматизировать некоторые связанные с этим задачи управления.)
Средство правил в Outlook часто бывает полезным для решения таких ситуаций, и код, который я представлю в этой статье, показывает, как автоматизировать создание правил.Например, копирование сообщений от Стива Мастерс в связанную папку в Outlook - относительно простой вопрос. И это касается других стандартных операций с правилами.
Что труднее сделать, и, как правило, за пределами возможностей правил Outlook, - это поместить одно электронное письмо в несколько папок на основе более аморфных критериев, чем предполагают стандартные правила. В то время как электронное письмо Стива Мастерс можно легко скопировать в связанную папку, другие важные факторы в его сообщении, касающиеся финансов, Дубая и проекта X, среди других возможных критериев, гораздо сложнее воплотить в действия.Строка темы может охватывать один или два критерия и быть восприимчивой к формальным манипуляциям со стороны правила Outlook, но это часто вызывает слишком большое доверие к теме письма любого конкретного отправителя. Что нам нужно, так это быстрый автоматический метод присвоения значений сообщениям электронной почты как в папке «Входящие», так и в «Отправленные», чтобы можно было запустить сценарий PowerShell для распределения их по нужным папкам.
Программирование правил Outlook
В этом разделе делается попытка продемонстрировать программное создание двух правил Outlook.Одно правило считывает строку темы сообщения для конкретной строки «Уведомление», а затем копирует соответствующие сообщения в указанную папку (с именем «Уведомления»).
Первое, что нужно сделать - вызвать Outlook API с помощью следующего кода. Этот код дает нам доступ к пространству имен обмена сообщениями Outlook API, в котором типичными объектами являются сообщения электронной почты, правила Outlook и почтовые папки, а также другие объекты (для получения дополнительной информации см. Http://msdn.microsoft.com/en -us / библиотека / ff866465.aspx).
Add-Type - сборка "Microsoft.Office.Interop.Outlook"
$ Outlook = New-Object -comobject Outlook.Application
$ namespace = $ Outlook.GetNameSpace ("MAPI")
Имея под рукой пространство имен, мы указываем исходную папку (Входящие), создаем новое правило и указываем папку для копирования в (Уведомления).
$ входящие =
$ namespace.GetDefaultFolder ([Microsoft.Office.Interop.Outlook.OlDefaultFolders] :: olFolderInbox)
$ MyFolder1 =
$ namespace.Folders.Элемент ('[email protected] '). Folders.Item (' УВЕДОМЛЕНИЯ ')
$ rules = $ namespace.DefaultStore.GetRules ()
$ rule = $ rules.create ("Мое правило1: получение уведомления",
[Microsoft.Office.Interop.Outlook.OlRuleType] :: olRuleReceive)
Навигация по папкам
Это интересное упражнение - запустить несколько строк кода, чтобы увидеть, как папки перечислены в пространстве имен MAPI. Следующие строки показывают, как переходить к различным уровням глубины в дереве папок:
$ пространство имен.Папки
# в моем Outlook дает '[email protected]'
# и 'Общие папки - [email protected]'$ namespace.Folders.Item (1)
#gives 'joe.leibowitz @ companyname.com '$ namespace.Folders.Item (2) .Folders
#gives' Public Folders - Favorites 'и' Public Folders - All '$ namespace.Folders.Item (1) .Folders
#gives all вложенные папки в '[email protected]' основная папка$ namespace.Folders.Item (1) .Folders.Item (1)
# дает одну подпапку, пространство имен 'Deleted Items'$.Folders.Item (1) .Folders.Item ('My Projects'). Folders
# предоставляет все подпапки в 'My Projects'$ namespace.Folders.Item (1) .Folders.Item ('My Projects')
.Folders.Item ('Outlook scripts'). Items
# выдает все электронные письма из подпапки 'Outlook scripts'
# папки 'My Projects'
Создав новый экземпляр правила, мы можем определить его параметры и свойства следующим образом:
$ rule_body = $ rule.Conditions.Subject
$ rule_body.Enabled = $ true
$ rule_body.Text = @ ('Завершенное уведомление')
$ action = $ rule.Actions.CopyToFolder
$ action.enabled = $ true
[Microsoft.Office.Interop.Outlook._MoveOrCopyRuleAction] .InvokeMember (
"Папка",
[System.Reflection.BindingFlags] :: SetProperty,
$ null,
$ действие,
$ MyFolder1)
$ rules.Save ()
Первая строка связывает правило с темой входящего электронного письма. Строка для поиска («Завершенное уведомление») указывается, а действие, которое нужно предпринять, - это CopyToFolder (в отличие, например, от MoveToFolder).Вызов повторяет действие и папку назначения.
На рис. 1 показан второй пример программного создания правила, в котором мы смотрим на получателей, а не на строку темы.
Рисунок 1. Создание правила для получателей
$ MyFolder2 = $ namespace.Folders.Item ('[email protected] '). Folders.Item (' FRANCISCO ')
$ rule = $ rules.create («Мое правило2: получено от Гонсалеса», [Microsoft.Office.Interop.Outlook.OlRuleType] :: olRuleReceive)
$ body = $ rule.Conditions.From.Recipients.Add ('[email protected] ')
$ rule.Conditions.From.Recipients.ResolveAll ()
$ rule.Conditions.From.Enabled = $ true
$ action = $ rule.Actions.CopyToFolder
$ action.enabled = $ true
[Microsoft.Office.Interop.Outlook._MoveOrCopyRuleAction] .InvokeMember (
"Папка",
[System.Reflection.BindingFlags] :: SetProperty,
$ null,
$ действие,
$ MyFolder2)
$ rules.Save ()
Все сообщения электронной почты от Марии Гонсалес в домене companyname.com будут скопированы во вложенную папку Francisco.
Хорошее общее руководство по программированию правил Outlook см. На http://tinyurl.com/ayyack5.
Управление сообщениями с помощью скрипта
Очевидно, что с помощью встроенного средства правил в Outlook можно многое сделать, но что, если вы хотите разделить сообщения на такие категории, как «Проект», «Финансы», «Персонал», «Имя получателя», «Отдел отправки», «Месяц получения», «Город», «Штат», Страна или любая другая из практически безграничного количества категорий, где любое данное электронное письмо может относиться к нескольким категориям, которые невозможно идентифицировать по теме или даже по телу сообщения? В подобных случаях настраиваемый сценарий может работать как особое правило.
В следующем примере мы управляем папкой «Отправленные», вручную отмечая строку темы каждого сообщения акронимами (например, «\\\ Admin, FOR»), где каждый акроним связывает сообщение с целевой папкой (Административная, Иностранный в примере), на который следует скопировать электронное письмо. Этот процесс требует ручных действий только для того, чтобы пометить строки темы отправленных элементов указанными вами сокращениями.
Когда сценарий запускается, он находит сокращения и копирует электронное письмо в столько папок, на которые ссылаются сокращения, перечисленные в строке темы.Кроме того, отправленные элементы «устаревают» из этих папок с помощью кода, который проверяет соответствующие даты приема и отправки для заданного периода и перемещает соответствующие сообщения в соответствующие места хранения, как только возрастные критерии будут выполнены.
Написанная мной функция называется CopyMove-Email. У него есть три параметра: список сокращений или символов, соответствующий список папок и целое число, представляющее максимальное количество дней, в течение которых сообщение будет храниться в разделе «Отправленные» перед его перемещением на ответственное хранение.(Для использования с элементами папки «Входящие» - код не отображается - следует добавить четвертый параметр, чтобы указать количество дней для обслуживания элемента папки «Входящие».)
ФУНКЦИЯ CopyMove-Email
{
парам
(
[строка []] $ акронимы,
[строка []] $ папки,
[int] $ sent_max_keep
)
Затем, как и в случае создания правила, вызывается API обмена сообщениями:
Надстройка-сборка "Microsoft.Office.Interop.Outlook"
$ Outlook = New-Object -comobject Outlook.Application
$ namespace = $ Outlook.GetNameSpace ("MAPI")
Если вы посмотрите в диспетчере задач, вы увидите два экземпляра Outlook. Одна - это исходная отображаемая версия, в которой вы работаете, а другая - фоновый процесс Outlook, используемый этим сценарием.
Затем мы строим интервал времени, чтобы отметить абсолютный предел для хранения отправленных элементов в этой папке, независимо от того, отмечен ли элемент для копирования или нет.
$ timespanSentMax = TimeSpan нового объекта ($ sent_max_keep, 0,0,0,0)
Используя временной интервал, мы создаем даты, по которым будет проверяться каждый элемент электронной почты в папке «Отправленные».
$ Date = DateTime нового объекта
$ SentMaxDate = DateTime нового объекта
$ Date = Get-Date
$ SentMaxDate = $ Date.Subtract ($ timespanSentMax)
Нам также нужна дата в формате строки для использования в именовании текстовых файлов, в которых будет храниться работа этого приложения за определенный день. В текстовых файлах будут храниться, соответственно, скопированная и перемещенная почта.
$ dt = $ Date.ToString (). Заменить ('/', '')
$ dt = $ dt.Replace ('', '')
$ dt = $ dt.Replace (':', '')
Затем нам нужно накопить данные о ходах и копиях во временных массивах хранения:
$ array_of_move_results = @ ()
$ array_of_copy_results = @ ()
Опыт показывает, что простого перебора всех сообщений в папке «Отправленные» недостаточно; в первом цикле одни элементы обрабатываются, а другие не затрагиваются.Для обработки всех элементов, требующих обработки, может потребоваться три или четыре таких цикла. Количество циклов, вероятно, зависит от того, сколько почтовых элементов готово для операций копирования и перемещения, а также от других факторов, влияющих на взаимодействие Outlook с вашим компьютером. В любом случае решение состоит в том, чтобы использовать структуру Do-While для продолжения цикла до тех пор, пока все отмеченные элементы не будут должным образом управляться.
сделать
{
$ hit = 0
Теперь приложение готово к синтаксическому анализу отправленных сообщений:
foreach ($ mail в $ namespace.Folders.Item ('[email protected] '). Folders.Item (' Отправленные '). Items)
{
Обратите внимание, что [email protected] - это имя автора Outlook для группы папок, в которую входят «Отправленные». Вы, конечно, должны использовать имя, которое отображается в вашем собственном клиенте Outlook.
Первый тест If - это ag
.