Параметр Get-AdComputer -filter не принимает вывод Get-Date

Я наткнулся на странную ошибку в сценарии PowerShell, который возвращает мне компьютеры в Active Directory в определенной OU (и sub OU), которые включены и вошли в систему в течение определенной даты.

Следующий фрагмент действительно работает:

$date = (get-date).AddDays(-100)
Get-ADComputer -Filter {(enabled -eq "true") -and (lastLogonTimestamp -gt  $date)} -Properties lastLogonTimestamp -SearchBase "CN=Computers,DC=some,DC=domain,DC=com"

... однако я сначала попытался сделать это одной строкой:

Get-ADComputer -Filter {(enabled -eq "true") -and (lastLogonTimestamp -gt  $((get-date).AddDays(-100)))} -Properties lastLogonTimestamp -SearchBase "CN=Computers,DC=some,DC=domain,DC=com"

... но я неоднократно получал ошибку ниже (которая заставила меня попробовать приведенный выше двухстрочный пример):

Get-ADComputer : Cannot process argument because the value of argument "path" is not valid. Change the value of the "path" argument and run the operation again.
At line:1 char:1
+ Get-ADComputer -Filter {(enabled -eq "true") -and (lastLogonTimestamp -gt  $((ge ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : NotSpecified: (:) [Get-ADComputer], PSArgumentException
    + FullyQualifiedErrorId : ActiveDirectoryCmdlet:System.Management.Automation.PSArgumentException,Microsoft.ActiveDirectory.Management.Commands.GetADComputer

Я запускал сценарий как в Windows 8, так и в Windows Server 2008 R2 - оба с PowerShell v3. Я предполагаю, что модуль Active Directory, установленный инструментами RSAT в обеих ОС, также может иметь несколько разные версии.

Что касается данных, у меня есть то, что мне нужно, но я не понимаю, почему однострочный не работает. Аргумент «путь» не требуется ни для командлетов Get-Date, ни для Get-AdComputer, но в качестве примера я также убедился, что моим рабочим каталогом является C :.

Мне интересно, сможет ли кто-нибудь дать некоторое представление о том, почему это может быть - я использовал этот тип синтаксиса раньше в командлетах модуля, отличного от ActiveDirectory, поэтому я склонен предположить, что, поскольку запрос находится в Параметр "filter", возможно, неправильно передается самому командлету Get-AdComputer (и это то, с чем нам всем приходится мириться).


person Tim de Vries    schedule 06.03.2013    source источник


Ответы (3)


Правая часть компонента фильтра должна быть значением, а не выражением.

Решение (как вы уже выяснили сами) состоит в том, чтобы присвоить значение, созданное выражением, переменной и использовать эту переменную в правой части фильтра:

$date = (get-date).AddDays(-100)
Get-ADComputer -Filter {(enabled -eq "true") -and (lastLogonTimestamp -gt  $date)} ...
person Ansgar Wiechers    schedule 06.03.2013
comment
У вас есть ссылка на документацию? help about_filter у меня не работает, и Technet ничего не показывает, но я вижу ссылки на него в других сообщениях и статьях (например, about_ActiveDirectory_Filter) - person Tim de Vries; 07.03.2013
comment
Get-Help Get-ADComputer -detailed показывает BNF для синтаксиса фильтра. В соответствии с этим компонент фильтра определяется как <FilterComponent> ::= <attr> <FilterOperator> <value> | "(" <FilterComponent> ")". - person Ansgar Wiechers; 07.03.2013
comment
Отлично, это многое объясняет. Цени свое время - person Tim de Vries; 08.03.2013
comment
Довольно печально, когда принятый ответ можно перефразировать: ну, это не сработает. - person bshacklett; 19.05.2015
comment
Чтобы расширить мой комментарий, в руководстве Stack Overflow по предоставлению хороших ответов прямо указано: Ответ может быть «не делай этого», но он также должен включать «попробуйте это вместо этого». - person bshacklett; 19.05.2015
comment
Проголосовать за ответ за изложение фактов - это то, что я считаю довольно грустным. OP уже нашел обходной путь, упомянутый в вопросе, и спрашивал почему другой подход не работает. - person Ansgar Wiechers; 19.05.2015
comment
Извините, но так работает демократия. Ваш ответ не соответствует правилам, поэтому он был отклонен. Ничего личного. - person bshacklett; 26.05.2015
comment
@bshacklett Я знаю об этом (я уже давно здесь). Тем не менее, с вопросом, A работает, но почему B не работает? Я, например, считаю, что B не работает, потому что это верный ответ в любой день. YMMV. - person Ansgar Wiechers; 26.05.2015
comment
@AnsgarWiechers Я могу оценить вашу позицию. Тем не менее, я ожидал, что некоторые люди (включая меня) найдут этот вопрос через Google, и они будут искать способ заставить все работать, а не только то, почему проблема существует. В конце концов, именно поэтому сайт существует (помимо заработка). На данный момент мы немного отклонились от этих комментариев. Возможно, имеет смысл задать вопрос по Мете. - person bshacklett; 26.05.2015

Извините за очень запоздалый ответ, у меня такая же проблема возникает на регулярной основе, и мне постоянно приходится возвращаться и выяснять ее, но это один лайнер, который обходит требование синтаксиса «выражение / значение» этого модуля. Надеюсь, это поможет другим, если не оригинальному плакату.

Попробуйте.

get-adcomputer -filter "lastlogondate -le '$((get-date).adddays(-14))'"

Насколько я понимаю, использование кавычек в этих местах заставляет вычислять выражение в строке и вставляет значение перед передачей выражения фильтра исходному командлету. Кто-то может исправить это объяснение по мере необходимости.

person BTag    schedule 05.07.2018

Пытался сделать это в одной строке целую вечность; как сказал BTag, вам нужно использовать двойные кавычки, чтобы указать фильтр, чтобы он заменял строку; Я также обнаружил, что вам нужно использовать метод DateTime ToFileTime, чтобы убедиться, что объект DateTime отправляется в формате времени тика LDAP FileTime, который требуется Get-ADComputer -Filter:

Get-ADComputer -Filter "enabled -eq 'true' -and lastLogonTimestamp -gt '$((Get-Date).AddDays(-90).ToFileTime())'" -Properties LastLogonTimeStamp -SearchBase "CN=Computers,DC=some,DC=domain,DC=com"

Наслаждаться!

person Minkus    schedule 22.04.2020