Почему Kerberos по умолчанию использует NTLM в WCF? - PullRequest
7 голосов
/ 23 февраля 2010

Получил простое демонстрационное приложение WCF, которое имеет два консольных проекта - хост и клиент. Оба работают на моей машине (победа 7 бокса). Я использую netTcpBinding, который использует аутентификацию Windows.

Проблема в том, что аутентификация понижается до NTLM с kerberos, и я не могу понять, почему.

Если я использую

<clientCredentials>
   <windows allowNtlm="true" />
</clientCredentials>

на стороне клиента, все круто. Но если я изменю это на false, я получу следующее исключение:

SecurityNegotiationException: The удаленный сервер не удовлетворяет требование взаимной аутентификации.

Это говорит о том, что kerberos дает сбой, и, поскольку клиент не разрешает NTLM, вызов приводит к возникновению исключения.

Это проблема проекта или внешняя проблема, вызванная настройкой моей машины для разработки?


Решение:

Видимо, я должен указать идентификацию сервера в конфигурации клиента. В моем случае сервер работает под моим именем, поэтому я модифицирую клиента таким образом:

<client>
  <endpoint address="net.tcp://dev7.HurrDurr.com:12345/MyService" 
            binding="netTcpBinding" 
            bindingConfiguration="MyBindingConfigurationLol" 
            behaviorConfiguration="HurrDurrServiceEndpoint" 
            contract="ShaolinCore.ICommunicationService">
    <!-- start changes here -->
    <identity>
      <userPrincipalName value="myusername@mydomain"/>
    </identity>
    <!-- end changes here -->
  </endpoint>
</client>

Я не уверен, почему это решает проблему. Хорошо, теперь на стороне клиента я полностью доверяю серверу (эй, я знаю этого парня!). Но так как NTLM менее безопасен, чем Kerberos, почему не наоборот? Если я не полностью доверяю серверу, я использую kerberos, иначе ntlm подойдет.

Или, OTOH, если я не полностью доверяю серверу, почему он вообще работает? «SecurityException: идентификатор конечной точки не установлен. WCF не может доверять идентификатору сервера и не будет передавать идентификатор клиента».

Ответы [ 4 ]

7 голосов
/ 24 февраля 2010

Когда я работал в командах разработчиков IIS4, 5 и 6, мы много сталкивались с этим! Чтобы бордюр работал, вам нужно, чтобы выполнялись следующие условия:

1) Обе стороны поддерживают бордюр (все поддерживаемые версии Windows поддерживают сегодня бордюр)

2) Проверка подлинности машин в Active Directory

3) Имена участников службы (SPN), зарегистрированные для конечной точки сервера. В «старые добрые времена» вам приходилось делать это вручную, используя SetSPN.exe. SPN - это просто конечная точка, к которой будет подключаться Curb; ему нужны эти данные для поддержки взаимной аутентификации. Большинство приложений будут вызывать API подходящих для этой работы за вас (DsWriteAccountSpn)

Если какой-либо из вышеперечисленных шагов не соответствует действительности, Windows обычно по умолчанию использует NTLM, что дает вам только аутентификацию клиента.

Надеюсь, это поможет! - Майкл

1 голос
/ 23 февраля 2010

Может быть, эта страница в MSDN - Отладка ошибок аутентификации Windows - помогает вам выяснить, что происходит, - кажется довольно хитрым относительно того, когда используется NTLM против Kerberos.

1 голос
/ 23 февраля 2010

Fyi через MSDN: netTcpBinding: привязка по умолчанию использует безопасность транспорта с согласованной аутентификацией. В этом согласовании предпринимается попытка использовать Kerberos, но если это не сработает, он отступит и использует более старый протокол NTLM . Kerberos - отличный выбор, если вы находитесь в доменной среде; чтобы использовать его, вам нужно, чтобы и ваша служба, и клиенты работали под учетными записями домена. Вам также необходимо настроить имя участника-службы (SPN) для вашей службы.

1 голос
/ 23 февраля 2010

Как настроен сервер? У вас есть <authentication mode="Windows"/> и <identity impersonate="true"/> в файле конфигурации?

Вы устанавливаете режим аутентификации с помощью тега аутентификации в файле конфигурации:

<configuration>
  <system.web>
    <authentication mode="Windows" />
  </system.web>
</configuration>
...