Translate

dimanche 1 mai 2016

Convertir un DAG classique en DAG sans point d'administration (et vice-versa)

Bonjour,


"It's been a while" (encore :)), comme le disent nos amis anglosaxons...
Aujourd'hui je voulais partager une technique permettant de convertir des groupes de disponibilité de base de données (autrement dit des Database Availability Groups, ou DAG) Exchange d'un mode "classique" (avec point d'administration, adresse IP + enregistrement DNS + objet ordinateur dans l'AD) à un mode "sans point d'administration".
Comme vous le savez, ce mode est supporté et recommandé depuis Exchange Server 2013 SP1/CU4 dès lors que le système d'exploitation utilisé est à la version Windows Server 2012 R2 ou ultérieure (rappel: il n'y a pas de version "ultérieure" supportée pour l'instant puisque Windows Server 2016 est toujours en Preview).
Les DAG sans point d'administration sont 200% recommandés pour des raisons très simples:
  1. Ils permettent d'éviter l'utilisation d'une ou plusieurs adresses IP (groupe du Cluster),
  2. Ils permettent d'éviter l'utilisation d'un objet dans l'AD (Cluster Network Object),
  3. Ils permettent d'éviter l'utilisation d'un enregistrement DNS pour le nom du DAG.
Bref, il permettent d'éviter tous les problèmes potentiels liés à un Cluster Windows classique... :)

La problématique de la conversion est qu'il n'est pas possible de changer de mode lorsque le Cluster Windows est déjà créé. Il s'agit d'une limitation des Clusters Windows et non d'Exchange.

Le principe est donc de partir d'un DAG existant (avec X membres et Y copies) et de supprimer le Cluster Windows sous-jacent, de reconfigurer le DAG puis de recréer le Cluster Windows sous-jacent. Afin d'en arriver là il faut passer par une phase où le DAG existe toujours mais où toute la haute disponibilité des bases de données n'existe plus:
  1. Supprimer toutes les copies de bases de données,
  2. Supprimer tous les membres du DAG.
Et, une fois le DAG reconfiguré, de:
  1. Rejoindre les serveurs au DAG,
  2. Recréer les copies.
L'avantage de cette technique est qu'elle peut s'exécuter à chaud, sans démontage des bases de données. Cependant il existe forcément un état à un instant T pendant lequel il n'existe plus qu'une copie de chaque base de données. Même si ce temps est relativement court (quelques minutes, max 5 tout au plus - le temps de rejoindre les membres et de recréer les copies), cela peut ne pas être jugé acceptable. Si tel est le cas, la seule option est de migrer vers un nouveau DAG. Hélas, cette option n'est pas toujours possible car cela demande de réinvestir.

Pour les personnes ayant donc installé un DAG sur Windows Server 2012 R2 avant Exchange 2013 SP1/CU4, et/ou n'ayant pas initialement voulu "tenter" le mode "DAG sans point d'administration", un peu d'automatisation peu permettre de faire la conversion en un minimum de temps et sans erreur.

Voici donc un petit script permettant d'effectuer la conversion d'un DAG classique vers un DAG sans point d'administration - ce script est aussi capable de faire l'inverse (même si je trouve l’intérêt de faire le chemin inverse limité...).

Le script prend soin de récupérer les paramètres existants du DAG et des copies:

  • mode DAC (DatacenterActivation DagOnly)
  • réseaux du DAG (Database Availabiltiy Group Networks)
  • désactivation puis restauration du Circular Logging (ex: pour les DAGs sans sauvegarde)
  • copies décalées (ReplayLagTime et/ou TruncationLagTime)
  • ordre de préférence d'activation (ActivationPreference)
  • et pour les DAGs Exchange 2016 CU1 ou +, le gestion du ReplayLagMaxDelay
Utilisation:

.\Convert-DatabaseAvailabilityGroup.ps1 -Identity -Verbose -- conversion vers un DAG sans point d'administration

ou 

.\Convert-DatabaseAvailabilityGroup.ps1 -Identity -DatabaseAvailabilityGroupIpAddresses 255.255.255.255 -Verbose -- conversion vers un DAG sans point d'administration

A l'inverse:

.\Convert-DatabaseAvailabilityGroup.ps1 -Identity -DatabaseAvailabilityGroupIpAddresses 0.0.0.0 -Verbose -- conversion vers un DAG avec point d'administration mais utilisant DHCP

.\Convert-DatabaseAvailabilityGroup.ps1 -Identity -DatabaseAvailabilityGroupIpAddresses [, IP2, IP3...] -Verbose -- conversion vers un DAG avec point d'administration et une ou plusieurs adresses IP statiques

Le script est disponible ici.

mardi 8 juillet 2014

[INFO]: Un bel "oubli" de la DevTeam Exchange concernant le POP3 et l'IMAP pour des rôles Exchange 2013 consolidés

Bonjour,

Cela faisait TRÈS LONGTEMPS que je n'avais posté un petit article... Un an et demi en sous-marin chez un client et un nouveau bébé, ça occupe !

Bref...

Aujourd'hui je voulais vous faire partager un souci rencontré chez un client.

Nous avons chez ce client une infrastructure Exchange Server 2013, les rôles Client Access Server et Mailbox Server sont consolidés et les services POP3 sont utilisés par quelques boîtes aux lettres applicatives.
Rien de bien extraordinaire donc, si ce n'est que suite à l'installation du CU5 d'Exchange 2013 le service POP3 Back-End (MSExchangePOP3BE) n'avait pas redémarré.

Coup de chance, personne n'avait redémarré le serveur, sinon cela aurait probablement "masqué" le problème sans trouver la vraie cause (et donc celui-ci aurait pu survenir à nouveau). Vous comprendrez pourquoi en lisant le reste de cet article... ;)
NB: je parle de CU5 ici, mais il n'est pas en cause...

Le problème

Le service MSExchangePOP3BE ne démarrait pas tout simplement car le service n'arrivait pas à ouvrir le port 9995/tcp. Ce port est bien le port du service POP3 Back-End (les ports utilisés par la partie POP3 Front-End étant 110/tcp (non SSL/TLS) et 995/tcp (SSL/TLS)).

Diagnostic et identification de la cause

Après un petit netstat -an il a vite été mis en évidence que ce port était déjà utilisé, en l’occurrence par une chose (vraiment) anodine: en tant que port source à destination d'une connexion vers un Global Catalog. Une simple connexion vers l'AD... déroutant :) ! Le service essayant de se lier à "0.0.0.0:9955", cela échoue.

Pourquoi est-ce arrivé ? Probablement la faute a pas de chance: lors de la mise à niveau vers le CU5, tous les services Exchange ont été arrêtés puis redémarrés. Entre temps, un processus a pris ce port, puisqu'il fait partie des ports utilisables dynamiquement dans Windows...

Oui... et non! Depuis Windows Server 2008 Microsoft a réduit la plage des ports dynamiques (aussi appelée plage de ports éphémères) de 49152 à 65535.

Cependant, et il s'agit d'un héritage d'Exchange Server 2010, lorsque le rôle Client Access est installé sur un serveur, la plage de ports dynamiques est modifiée pour être [6005-59530]. Ce comportement a été conservé par le Setup d'Exchange Server 2013.

Vous pouvez consulter la plage de ports dynamiques sur vos serveurs en utilisant la commande suivante:
netsh int ipv4 show dynamicport tcp
(variantes avec ipv6 et udp)



De même, la liste des exclusions (sur processus ayant réservé des ports ou exclusions permanentes):
netsh int ipv4 show excludedportange protocol=tcp
(variantes avec ipv6 et udp)

NB: j'ai un peu raté ma capture d'écran (ipv6 deux fois), mais cela ne change rien au principe... :P



La résolution

Un simple redémarrage du serveur aurait résolu le problème, mais n'aurait pas éliminé la cause et donc n'aurait pas garanti que celui-ci puisse survenir à nouveau.

Afin de bloquer le port 9955/tcp sur IPv4 et IPv6 il suffit d'exécuter les commandes suivantes:

netsh int ipv4 add excludedportrange protocol=tcp startport=9955 numberofports=1
netsh int ipv6 add excludedportrange protocol=tcp startport=9955 numberofports=1

Et pour ne rien oublier, en ce qui concerne le service IMAP4 Back-End (MSExchangeIMAP4BE):

netsh int ipv4 add excludedportrange protocol=tcp startport=9933 numberofports=1
netsh int ipv6 add excludedportrange protocol=tcp startport=9933 numberofports=1

Post-mortem

Je n'ai pas trouvé d'autre cas similaires avec des services Back-End. HTTP, Transport et UM utilisent tous (que je sache) des ports inférieurs à 6005/tcp. Il est cependant toujours bon de conserver à l'esprit que cela pourrait arriver de nouveau, sur d'autres services...
Cependant, il semblerait que la DevTeam Exchange n'ait pas pensé à ce cas. Fait rigolo, cela ne serait pas survenu sur une installation Exchange pure "Mailbox", ni même avec Exchange Server 2010. Or, l'équipe Exchange préconise plus que fortement depuis quelques temps déjà de consolider les rôles. Certains changements d'architecture liés à Exchange Server 2013 (Front-End / Back-End).

dimanche 26 mai 2013

[INFO]: Résoudre une mauvaise conception des choses... conversion de MailUser vers Maibox...

Hier, je suis tombé un peu par hasard sur un blog où l'auteur proposait un script permettant de convertir un objet de type "MailUser" en "Mailbox". Typique lorsque l'on souhaite effectuer des migrations rapides (bascule) et éventuellement récupérer les données après...

D'après l'auteur, il faudrait désactiver le MailUser (faire un "Disable-MailUser") et ensuite activer la BàL ("Enable-Mailbox"). Il y a une époque où c'était vrai et surtout pour ceux habitués à n'utiliser que la console Exchange...

Si vous êtes dans ce cas (besoin de convertir), ne vous prenez pas la tête, la commande "Enable-Mailbox" permet de directement activer les fonctionnalités de BàL Exchange sans autre forme de procès. Cerise(s) sur le gâteau: l'attribut "legacyExchangeDN" est préservé (chose que le bloggeur donc je parlais précédemment à oublié) ainsi que d'autres attributs (type Alias) qui sont nettoyés lors du "Disable-MailUser".

Notez aussi que cela fonctionne pour le "Enable-RemoteMailbox".




dimanche 17 mars 2013

[TECH]: Corriger les erreurs d'Exchange 2013 avec l'Indexation de Contenu



Exchange Server 2013 est jeune, trop jeune peut-être ? :)

L'autre jour j'ai rencontré un problème sur mon lab: toutes mes Mailbox Databases sont entrées en échec sur l'indexation du contenu (Content Indexing). Après avoir cherché un peu, j'ai fini par trouver que cela est un problème connu, probablement une erreur de développeur...

Articlehttp://support.microsoft.com/kb/2807668 (Content Index status of all or most of the mailbox databases in the environment shows "Failed").

Si l'on s'en réfère à l'article, il existe en deux moyens de corriger le problème:

  1. Créer un groupe de sécurité dans l'Active Directory, nommé "ContentSubmitters" et de donner aux administrateurs Exchange et aux comptes d'ordinateurs Exchange l'accès "complet" au groupe - selon l'article, le groupe ne sert à rien d'autre...
  2. Supprimer la référence au groupe de sécurité (qui n'existe pas par défaut, donc...) dans les fichiers de configuration WCF.
Personnellement, la résolution #1 me semble tenir plus de la bidouille qu'autre chose. D'autre part on ne peut pas dire que la méthode de résolution soit très claire... J'ai donc opté pour la solution #2 et afin d'appliquer le correctif sur tous mes futurs serveurs, j'ai donc crée un script.

Vous pourrez le trouver ici: http://sdrv.ms/15eH1BH
Il suffit de le lancer ainsi: .\FixContentIndexing.ps1 - une fois les corrections effectuées les services adéquats seront redémarrés. L'indexation de contenu sera alors rétablie dans les 5-10 minutes suivantes.



vendredi 22 février 2013

[TECH]: Exchange 2013 - Monitoring & ActiveSync - Attention aux restrictions éventuelles !

Un petit article rapide en passant, au cas où cela vous arrive un jour...

Exchange 2013 introduit le concept de boîte aux lettres de Monitoring: des boîtes aux lettres testant régulièrement l'accès aux services, permettant ainsi de remonter facilement des alertes de disponibilité via les Event Logs.

Dans leur grande bienveillance, vos serveurs Exchange 2013 vont donc tenter de se connecter au Web Services, et dans ce qui va nous intéresser ici, au service Exchange Active Sync.

En effet, dans des tests sur mon lab, j'avais configuré ma Stratégie ActiveSync afin de ne pas autoriser la connexion de terminaux ActiveSync non provisionnés. Le but était à l'époque de probablement tester cette stratégie pour un client (honnêtement, je ne me rappelle plus)... bref...

En regardant mes Events, j'ai donc vu ceci:

On voit au travers de cette capture d'écran que le compte CORP\SM_xxxxxxxxxxx (qui correspond à une boite HealthMailbox de Monitoring) est bloqué. Le message est issu de la Web App ActiveSync dans le but de prévenir un éventuel administrateur de ce fait. Le hic, c'est qu'il s'agit précisément d'une boîte aux lettres système.

C'est donc en voyant cet entrée dans le journal d'évènements que je me suis rappelé de la restriction que j'avais mise sur la Stratégie ActiveSync par défaut (AllowNonProvisionableDevices à False):


Il existe dans l'absolu plusieurs façons de résoudre ce problème:

  1. Changer la stratégie par défaut et autoriser les terminaux non provisionnés, pas toujours faisable si vous les aviez bloqués pour une raison particulière...
  2. Créer une nouvelle stratégie plus permissive et l'assigner aux bâls de Monitoring avec la commande: Get-Mailbox -Monitoring | Set-CASMailbox -ActiveSyncMailboxPolicy  
  3. On peut aussi imaginer une troisième solution, que je n'ai pas testée: ajouter l'Id du pseudo-terminal associé à la BàL dans la liste des terminaux autorisés (avec Set-CASMailbox aussi).
Tant que je suis sur le sujet des Monitoring Mailboxes: en essayant de déterminer la cause de mon évènement ActiveSync, je me suis rendu compte que j'avais oublié de déplacer les BàL de Monitoring des Mailbox Databases créées par défaut à l'installation du rôle Mailbox. Or, je supprime toujours ces bases plutôt que de les réutiliser.

Lors de leur suppression, Exchange n'a pas bronché (il n'a pas mentionné qu'il restait des BàL :p): j'avais bien pensé aux BàL "User", BàL "Arbitration", BàL "PublicFolder"... Du coup, il suffit de déplacer logiquement les BàL sur d'autres Mailbox Databases, comme illustré ci-dessous:

Problème résolu, mais petit contre-temps... :)

mardi 19 février 2013

[TECH]: Get-ClientAccessServer et la coexistence Exchange 2010/2013

Je dois l'avouer, ce n'est pas bien: j'ai installé Exchange Server 2013 dans mon organisation Exchange 2010 (mise à niveau en SP3 pour que cela soit possible) sans attendre la disponibilité du Cumulative Update 1...

Honte à moi... :)

Cependant, cela me permet de tester pas mal de chose en coexistence, dont en particulier tous mes scripts visant à configurer ou opérer Exchange, que l'on soit en mono-version (2010 _ou_ 2013) ou en mixité (2010 _et_ 2013 donc).

En coexistence, la majorité des commandes Exchange 2010 (Get-ExchangeServer, Get-) ne "voient" pas (par défaut) les objets Exchange 2013... tant mieux, cela facilite la compatibilité des commandes Exchange 2010 sur des objets 2013 et donc permet d'éviter qu'une commande 2010 ne casse quelque chose.

Cependant, j'ai déjà trouvé une exception à la règle: Get-ClientAccessArray...

Dans sa version 2010, la commande retourne l'objet du Cas Array défini dans mon site Active Directory. S’exécutant sur un serveur Exchange 2010, et à fortiori les Cas Arrays étant une notion Exchange 2010 et retirée en Exchange 2013, on était en droit de s'attendre au fait que la liste calculée des membres du Cas Array ne soient que des serveurs CAS Exchange 2010. Et bien que nenni !

La commande Get-ClientAccessArray d'Exchange 2010 retourne dans la propriété "Members" les serveurs CAS Exchange 2013 ! Là où le bât blesse, c'est que la réciproque n'est pas vraie: la commande Get-ClientAccessArray d'Exchange 2013 ne retourne _que_ les serveurs CAS Exchange 2010.

La preuve en images:
Ci-dessus: Get-ClientAccessArray (retourne le serveur CAS Ex2013)
 
Ci-dessus: Get-ClientAccessArray Exchange 2013 (ne retourne que les serveurs Ex2010)

Dans le même style, je disais précédemment que les cmdlets Exchange 2010 ne "voient" pas les serveurs Exchange 2013. Par exemple, un "Get-ExchangeServer" ne va lister que les serveurs à version 2010 (et antérieures):

Et cependant, en utilisant le paramètre -Identity, je peux récupérer l'objet (Get-ExchangeServer -Identity ):
La raison: lorsque l'on fait un Get-ExchangeServer de base, un filtre de version est positionné (type "inférieur ou égal à la version actuelle") alors que lorsque l'on spécifie une identité, la commande ne créé pas un filtre sur la version... C'est aussi vrai pour les autres cmdlets type "Get-MailboxServer", "Get-ClientAccessServer", "Get-TransportServer", "Get-UmServer"...


Voilà, attention donc lorsque vous serez en mixité de versions Exchange 2010/2013. Pensez à bien tester vos scripts et vos procédures opérationnelles afin d'éviter quelques sournoiseries...

mardi 12 février 2013

[INFO]: Premières MàJ Office, dont Lync Client 2013

En plus des mises à jour côté serveurs, Microsoft a également publié des mises à jour des clients Office, dont en particulier Lync 2013:
  • Ajoute une fonctionnalité permettant de cacher les contacts hors-ligne, inactifs et ayant un statut de présence inconnu de la liste des contacts principale (dans un groupe séparé);
  • Ajoute une fonctionnalité permettant de recevoir des invitations de personnes externes à l'organisation et faisant partie d'une réseau source non vérifié;
  • Corrige quelques bugs liés aux fonctionnalités de Localisation (partage, configuration);
  • Corrige quelques bugs liés à la fonctionnalité d'onglets de conversations;
  • Permet à des utilisateurs de se joindre à des conférences via leur téléphone même si l'organisateur n'est pas activé pour la téléphonie;
  • Améliore la gestion des terminaux ayant deux caméras (faciale/dorsale);
  • Améliore l'expérience utilisateur lors de l'utilisations de salles virtuelles;
  • Améliore la prise en charge de périphériques à forte densité de pixles.
La description complète est ici: http://support.microsoft.com/kb/2810076/en-us?sd=rss&spid=11335.

Mise à jour du 13 février 2013: voici l'option à cocher si vous souhaitez activer la fonctionnalité visant à trier les contacts hors-ligne/inactifs/à statut inconnu dans un groupe séparé:

[INFO]: Exchange Server 2010 SP3 !

Je disais il y a quelques minutes que le Service Pack 3 d'Exchange Server 2010 serait bientôt disponible. A croire que j'étais plus près de la vérité que prévu... :)

L'équipe Exchange a annoncé il y a moins d'une heure la mise à disposition du SP3:
Il apporte en outre la coexistence avec Exchange Server 2013 CU1 (qui n'est donc pas encore disponible :)), mais aussi les support de clients Internet Explorer 10. En outre il permet d'installer Exchange Server 2010 sur Windows Server 2012 (en installant bien sûr directement le package SP3) et de Windows 8 (outils d'administration).

Il faudra donc patienter encore quelques semaines avant de pouvoir faire coexister Exchange 2010 et 2013 !

MàJ du 13 février 2013: pour les plus tecchies, voici les versions d'objets suite au passage du SP3 ce matin dans mon lab:

  • Organisation: version 14322 (attribut "objectVersion" sur l'objet représentant l'organisation)
  • Schema: version 14734 (attribut "rangeUpper" sur l'objet ms-Exch-Schema-Version-Pt dans la partition du schéma AD)
Il semblerait que les modifications du Schéma Exchange 2010 SP3 n'inclut que l'ajout d'un attribut nommé ms-Exch-Calendar-Logging-Quota et modifie les attributs suivants: {ms-Exch-Schema-Version-Pt, ms-Exch-UM-Enabled-Text, ms-Exch-UM-Fax-Message-Text, ms-Exch-UM-Reset-PIN-Text, ms-Exch-UM-Voice-Mail-Text} ainsi que les classes {ms-Exch-Mail-Storage, ms-Exch-MDB}.





[INFO]: Exchange 2010 SP2 Rollup 6 et Exchange 2007 SP3 Rollup 10

Microsoft vient de publier le Rollup 6 d'Exchange Server 2010 SP2. Je vous passe la description détaillée, disponible ici: http://support.microsoft.com/kb/2746164. On notera aussi le Rollup 10 pour Exchange Server 2007 SP3 dnt la description est ici: http://support.microsoft.com/kb/2788321/en-us?sd=rss&spid=10926.

Les deux Rollups corrigent en particulier la faille décrite dans le bulletin de sécurité MS13-012 (voir ici: http://technet.microsoft.com/en-us/security/Bulletin/MS13-012).

De manière plus anecdotique, une mise à jour cumulative pour Outlook 2010 résolvant des problèmes de téléchargement de l'OAB en mode Outlook Anywhere (http://support.microsoft.com/kb/2597090/en-us?sd=rss&spid=14864) mais qui contient aussi les correctifs précédents d'amélioration de performances et de stabilité... Pensez-y !

Au menu:

Le Rollup 6 corrige quelques bugs liés à l’utilisation des Web Services, pour Blackberry entre autres et des problèmes de performance potentiels avec BES aussi. J’aime aussi (enfin !!!) la correction de l’OABGen lorsqu’il rencontre des lingering objects… avant ça crashait, maintenant on espère que cela ne crash plus J

Quelques nouveautés:

Note: Le SP3 est à priori pour bientôt !

Comme toujours, soyez prudents afin d'éviter des déconvenues telles que celles rencontrées avec des Rollups précédents (rappellez-vous du Rollup 5 pour Exchange Server 2010 SP2...).

Bon patching !

jeudi 20 décembre 2012

[TECH]: Utiliser l'objet COM+ Internet Explorer sur Windows Server 2012

Avec Exchange et Lync, il est souvent sympa de pouvoir générer des rapports divers et variés via un document HTML riche et bien formaté (au delà donc du simple usage des sorties formatées en HTML standard). Un exemple est un script que je fournis à mes clients et qui génère un rapport de santé d'un DAG et des composants d'infrastructure liés. Un exemple ci-dessous avec mon petit DAG Exchange 2013...


Le principe est de créer un objet COM Internet Explorer et de peupler un Document vide. Cela offre l'avantage de pouvoir utiliser les méthodes standards de l'objet comme getElementById() et d'aller modifier un style sur un code HTML généré en amont, par exemple ici le statut global qui passerait rouge en cas d'erreur. De plus, cela permet d'ouvrir une sorte de console IE en plain écran, de faire des rafraîchissements automatiques, ou même de sauvegarder le document complet au format HTML pour d'autres actions, type envoi par E-mail ou mise à disposition sur une racine IIS.

$IE = New-Object -comObject InternetExplorer.Application
$IE.Navigate2("about:blank")

A partir de là, la logique est d'attendre la fin du statut occupé de l'objet IE, puis de travailler avec l'attribut membre "Document", en utilisant les méthodes write() et writeln() afin de générer le code HTML.

Lorsque j'ai commencé à mettre à jour mon script de rapport de santé pour le rendre compatible Exchange 2013, je me suis retrouvé face à un problème de taille: mes serveurs Exchange 2013 étant installés sur un système d'exploitation Windows Server 2012, impossible d'utiliser les méthodes write() et writeln(). Elles existent toujours mais ne prennent aucun argument. Rien n'y faisait, impossible de générer le code.

Puis j'ai regardé le comportement sur un autre serveur Windows 2012, mis à jour lui depuis un Windows Server 2008 R2. Et là: les méthodes existent mais les arguments à passer sont dans un type bizarre issu du code en C/C++ de vieux bouts de code IE.

On a donc une différence fonctionnelle entre:

  • Windows Server 2008 R2
  • Windows Server 2012 avec des composants issus du système originel mis à jour
  • Windows Server 2012 installé en partant de rien
J'ai donc commencé à m'intéresser à l'objet "Document", comprendre voir quelle est la nature des différences. J'ai donc regardé le type sur les trois environnements:
$IE.Document.GetType().ToString()
et
$IE |fl Document

Et là ! J'ai enfin été mis sur une piste sérieuse: les objets sont de type de base "ComObject" (des objets COM+ donc). Sur les environnements où les méthodes on bien un prototype définissant des arguments, l'objet est de type "mshtml.HTMLDocumentClass". Sur l'environnement Windows Server 2012 installé en partant de rien, l'objet apparaît être d'un type "System.__ComObject" et donc chargé sans support des méthodes MSHTML.

Après quelques recherches, j'ai fini par trouver que cette classe est définie dans une "Primary Interop Assembly" nommée "Microsoft.mshtml" et définie dans la DLL "Microsoft.mshtml.dll". Une recherche rapide sur mes serveurs à permis de confirmer que cette assembly est bien installée sur les serveurs qui me fournissent un objet définissant les méthodes write() et writeln().

Le hic c'est que cette assembly n'est pas installée en standard/par défaut. Puisqu'il semblerait qu'IE sache l'utiliser lorsqu'elle est installée, je me suis dit qu'un chargement de l'assembly à la volée pourrait faire l'affaire.

Me voici donc à développer une fonction PowerShell pour le faire, appelée naturellement "Load-Assembly". Le code est disponible ici sous forme d'un script PowerShell: http://sdrv.ms/U6j7Wn.


J'ai ensuite copié la DLL de l'assembly depuis mon serveur Windows Server 2008 R2 vers l'emplacement réseau de mes scripts, dans un sous-répertoire "bin\PrimaryInteropAssemblies".

Avant la création de mon objet Internet Explorer, j'ai donc ajouté le code suivant:

if ( ("mshtml.HTMLDocumentClass" -as [Type]) -eq $null )
{
    $assembly = Load-Assembly -Path ".\bin\PrimaryInteropAssemblies\Microsoft.mshtml.dll"
    if ( $assembly -eq $null )
    {
        throw "Failed to load the MSHTML Primary Interoperability Assembly."
        return
    }
    Write-Verbose "PrimaryInteropAssembly MSHTML loaded: $($assembly.FullName)"
}


Et enfin, une fois mon assembly chargée, le type étant défini correctement, l'objet Document redevient un objet de la classe attendue, à savoir "mshtml.HTMLDocumentClass". Une fois l'assembly chargée, mes objets COM réagissent de la même manière sur mon serveur Windows 2012 qui ne fonctionnait pas auparavant.

Me reste maintenant un problème à élucider: les méthodes write() et writeln() se refusent à fonctionner correctement malgré l'objet chargé avec la bonne classe. Faute probablement ici au PowerShell v3 je pense, qui gère les types ou la conversion de type différemment. Le type attendu est un SAFEARRAY (cf la capture d'écran en PowerShell v2) qui est un type C/C++. Imaginez la galère en partant de PowerShell...

Et là miracle: en explorant l'objet Document, je me suis rendu compte qu'il existe des méthodes additionelles à celles disponibles en PowerShell v2... bizarre mais elles sont nommées IHTMLDocument2_xxx(), IHTMLDocument3_xxx(), IHTMLDocument4_xxx() et IHTMLDocument5_xxx(). Cela ressemble fort à des méthodes de compatibilité descendante !!!

J'essaye donc IHTMLDocument2_write() et IHTMLDocument2_writeln() avec succès !!!

Au final:
  • rajout d'un bout de code permettant de charger l'assembly,
  • utilisation des méthodes de compatibilité à la place des méthodes natives... dans mon cas j'ai codé une "surobjet" Document qui s'adapte et appelle la bonne méthode en fonction de la présence ou non de la méthode IHTMLDocument2_write().
Le bug avait été remonté via Connect, ici: http://connect.microsoft.com/PowerShell/feedback/details/764756/powershell-v3-internetexplorer-application-issue

mardi 11 décembre 2012

[INFO]: Nouveaux Rollups Exchange 2010 et Exchange 2007 disponibles

La DevTeam Exchange vient de publier les Rollups 5v2 Exchange 2010 SP2, Rollup 8 Exchange 2010 SP1 et Rollup 9 Exchange 2007 SP3.

Tous corrigent un bug de sécurité considérée Critique décrite dans le bulletin MS12-080.

N'oubliez pas de bien tester dans votre environnement de pré-production afin d'éviter des sueurs froides comme celles créées par le Rollup 5 Exchange 2010 SP2... :)

samedi 8 décembre 2012

[TUTORIEL]: Comment créer vous même un répartiteur de charge avec Ubuntu Server et HAProxy (v2)

En août dernier je m'étais finalement décidé à publier mon guide décrivant un approche pas-à-pas permettant de créer votre propre solution de répartition de charge basé sur HAProxy et stunnel.

Tout récemment, Willy Tarreau et l'équipe de développeurs contribuant aux évolutions du code d'HAProxy ont implémenté de nouvelles fonctionnalités en version 1.5-dev7 puis dev12, 13 et 14: à savoir (entre autres) le support de la terminaison SSL sur HAPproxy, ce qui permet naturellement des scénarios de SSL Offloading ou de SSL Bridging sans stunnel ou autre wrapper SSLJe rappelle que HAProxy est le composant clef des boîtiers Exceliance (http://www.exceliance.fr/), des solutions de répartition de charge très performances et peu onéreuses.

Voici donc le lien de téléchargement du guide v2, entièrement basé sur Ubuntu Server et HAProxy:


jeudi 22 novembre 2012

[TUTORIEL]: Exchange 2013 - Configurer l'accès Client et Kerberos (load-balancer ou DNS round-robin)

Depuis Exchange Server 2010 SP1, il est hautement recommandé d'activer Kerberos pour les accès clients. Cela se faisait au travers d'un ensemble de manipulations visant à créer un objet de sécurité dans l'Active Directory, puis de définir les Service Principal Names Kerberos sur cet objet.
Cet objet devait ensuite être défini sur la configuration des serveurs CAS comme le "Alternate Service Account", ce qui permettait alors au service "Microsoft Exchange Protected Service Host" de répondre en mode Negotiate à un challenge SPNEGO.

J'avais documenté le pas-à-pas dans un tutoriel Exchange 2010 SP1 >> ici << (à l'époque c'était sur la Beta du SP1 mais la procédure est toujours applicable).

Qu'en est-il d'Exchange Server 2013... ?

Plusieurs points:
  • Exchange 2013 n'utilise plus le Mapi/Rpc (pour les accès clients), seulement le Mapi sur Http (autrement dit, le Rpc/Http)
  • Exchange 2013 est configuré par défaut en mode Ntml, afin de conserver une compatibilité large et surtout parce que la configuration en Kerberos requiert des manipulations qui ne peuvent être faites automatiquement au moment du Setup
  • La haute disponibilité d'Exchange 2013 s'effectue uniquement au niveau du protocole HTTP, il n'y a par conséquent plus besoin de définir une VIP pour le Mapi/Rpc.
Ce que cela implique:
  • Au niveau de la haute-disponibilité: il devient possible de se passer de répartiteur de charge (load-balancer, HLB) et de ne faire que du DNS round-robin (DNS RR). Il s'agit avant tout d'une logique du client et donc ne fonctionnera pas dans 100% des cas (vous devrez avoir des clients dits "modernes") - il reste bien sûr (et je le recommande pour plein de raisons) la possibilité de faire de la répartition de charge classique, en mode 100% HTTP/HTTPS désormais. Cependant, point noir pour Exchange 2013 RTM: il n'y a pas de support du SSL Offloading. Pour l'avoir testé, cela ne fonctionne pas du tout et j'essayerai de vous faire un tutoriel sur le SSL Bridging, qui lui devrait (en théorie) fonctionner.
  • Au niveau de la configuration: il faudra configurer Outlook Anywhere et les Web Services afin de faire référence à un nom générique (load-balancé donc, ou en DNS RR). Cela permettra donc aux clients d'utiliser des URI liées à des points de connexion uniques, et non comme cela est le cas, directement liées au nom complet qualifié (Fqdn) de chaque serveur.

Première partie: configuration des Web Services

La configuration des Web Services est simple et presque identique à ce que l'on avait l'habitude de faire sur Exchange 2010, à savoir:
  • Définition d'une "InternalURL" pour les services suivants: OWA/ECP, Exchange Web Services, OAB, Exchange ActiveSync. La configuration du Web Service Autodiscover n'est désormais plus utile, mais il faudra conserver la partie de la configuration visant à changer le Service Connection Point HTTP pour la découverte automatique via l'Active Directory (pour rappel: en utilisant le cmdlet Set-ClientAccessServer). A cela viendra s'ajouter la configuration, maintenant O-BLI-GA-TOIRE d'Outlook Anywhere, activé par défaut et référençant le Fqdn de chaque serveur.
  • Optionnellement, définition des "ExternalURL", si vous souhaitez supporter des clients externes (pour du vrai Outlook Anywhere, dans le sens originel du terme... :)). Nous verrons cela dans un prochain article.
Pour l'exemple, nous allons donc configurer en premier lieu les URLs Internes et monter comment un client se connecte par défaut (il sera en Rpc/HTTP _et_ en Ntlm).
Le nom générique dans mon Lab sera "ex.w15-lab.com". J'ai ici deux serveurs (SV-E15-1 et SV-15-2) exécutant les rôles CAS et MBX, nous ne devrons configurer que la partie CAS. Pour l'exemple, je vais découper les actions en mode pas-à-pas et serveur par serveur.

Configuration des Web Services:
Regardons d'abord l'état de mon premier serveur pour le VDir Outlook Web App:
  • Get-OwaVirtualDirectory -Server SV-E15-1 -ADPropertiesOnly | fl *Url
Il est est de même pour les autres Web Services, nous allons donc les configurer individuellement (ici en Shell pour le premier):
  • Get-OwaVirtualDirectory -Server SV-E15-1 -ADPropertiesOnly | Set-OwaVirtualdirectory -InternalUrl "https://ex.w15-lab.com/owa"
  • Get-EcpVirtualDirectory -Server SV-E15-1 -ADPropertiesOnly | Set-EcpVirtualdirectory -InternalUrl "https://ex.w15-lab.com/ecp"
  • Get-WebServicesVirtualDirectory -Server SV-E15-1 -ADPropertiesOnly | Set-WebServicesVirtualDirectory -InternalUrl "https://ex.w15-lab.com/EWS/Exchange.asmx"
  • Get-OabVirtualDirectory -Server SV-E15-1 -ADPropertiesOnly | Set-OabVirtualDirectory -InternalUrl "https://ex.w15-lab.com/OAB"
  • Get-ActiveSyncVirtualDirectory -Server SV-E15-1 -ADPropertiesOnly | Set-ActiveSyncVirtualDirectory -InternalUrl "https://ex.w15-lab.com/Microsoft-Server-ActiveSync"
Note: Attention à la casse sur les "/répertoire". Il y a des scripts disponibles sur la blogosphère permettant de soit-disant les configurer "facilement". Historiquement il y a eu des soucis si la casse d'origine n'était pas respectée: typiquement en mode Proxy-CAS sur l'Exchange Control Panel où l'InternalURL était en autre chose que "/ecp" (en minuscules) et "cassait" le cookie msExchCanary. Mon conseil: écrivez votre propre script et respectez exactement la même casse que celle originellement trouvée sur l'InternalURL. Pour les ExternalURL, utilisez la même nomenclature que l'InternalURL.
Nous voyons ici que nous n'avons pas utilisé la Cmdlet Set-AutodiscoverVirtualDirectory, contrairement à ce que nous aurions fait dans Exchange 2010 et Exchange 2007. Cependant ces actions n'avaient que très peu d’intérêt  même dans les versions précédentes. Il semblerait donc que la directive dans Exchange 2013 est de ne même pas s'y attarder... :)
Par contre, nous devons absolument configurer le Service Connection Point de l'Autodiscover afin d'arriver sur notre URI générique. Cela ne peut se faire qu'en Shell. Notez que vous pouvez vous passer ce cette configuration si vous voulez disposer un certificat sur vos CAS ayant chaque Fqdn de chaque CAS dans le Subject Alternate Name. La meilleure méthode reste cela dit de définir une URI générique, comme pour tous les autres Web Services...

Nous y sommes presque ! Reste donc la partie Rpc/Http, autrement dit, Outlook Anywhere !

La grosse nouveauté ici est qu'il existe désormais un "InternalHostname" à Outlook Anywhere. Rappelez vous que pour Exchange 2007 et Exchange 2010, il n'était possible que de définir un  "ExternalHostName"... Vous l'aurez sans doute compris, le "InternalHostname" va être le point de connexion de vos clients et va complètement supprimer la notion de "Client Access Array" (NDLR: vous ne trouverez plus de Cmdlet New-ClientAccessArray, c'est donc normal :)).
Nous allons donc configurer l'InternalHostname afin qu'il pointe aussi sur notre nom générique. Cela s'effectue au travers de la Cmdlet Set-OutlookAnywhere:
  • Get-OutlookAnywhere -Server SV-E15-1 -ADPropertiesOnly | Set-OutlookAnywhere -InternalHostName "ex.w15-lab.com" -InternalClientsRequireSsl:$true
Vous pouvez vérifier la bonne application du changement en utilisant la Cmdlet Get-OutlookAnywhere:
  • Get-OutlookAnywhere -Server SV-E15-1 -ADPropertiesOnly | fl *Internal*
Dès lors, vous pouvez reproduire la même configuration pour vos autres serveurs CAS. Vous pouvez utiliser l'Exchange Administration Center (https://serveur.domaine.com/ecp en vous authentifiant avec un compte appartenant au(x) bon(s) Role Group(s)) et en allant dans les sections suivantes:
  • Servers ==> Virtual directories pour les Web Services classiques (OWA/ECP, EWS, EAS, OAB)
  • Servers ==> Servers ==> double-click puis section "Outlook Anywhere" pour la configuration du "InternalHostName" Outlook Anywhere.
Rappelez vous qu'il faudra quand même configurer l'AutodiscoverServiceInternalUri en Shell, l'EAC ne proposant pas la modification du champ.
Avant de tester la connexion avec un client Outlook, vous devrez attendre que les changements soient effectifs/commités dans la base IIS et la configuration Exchange de tous vos serveurs. Pour cela, cherchez dans l'eventlog Application une écriture au journal de l'évènement ID3025 de la source "MSExchange RPC Over HTTP Autoconfig".
En attendant que cela soit le cas, vous devez faire les actions suivantes:
  • Créer un certificat à base d'un modèle "Web Server" ou d'un dérivé, et l'assigner à IIS. Pour ma part j'utilise un certificat "Wildcard" généré par un script, et ayant le InternalHostName et optionnellement (nous y viendrons plus tard) le ExternalHostName dans l'attribut SAN. Mon certificat n'a pas les Fqd des serveurs CAS dans le SAN, c'est mon côté puriste même si je comprends que certains préfèrent les avoir.
  • Créer le ou les enregistrements DNS correspondant(s) au nom générique de connexion
    • Pour du DNS round-robin, créez 'n' enregistrement de type A ayant le même nom. Dans mon cas, cela fait 2 enregistrements DNS dans ma zone DNS "w15-lab.com"
    • Pour du load-balancing classique, il suffit de faire pointer l'enregistrement A sur la VIP créée à cet effet.
Faites ensuite un redémarrage d'IIS sur chacun des CAS (iisreset /noforce). Cette étape n'est normalement pas requise mais j'ai eu des comportements bizarres sur les URL retournées lors de l'Autodiscover.
Une fois toutes ces actions effectuées, vous pouvez démarrer votre client Outlook (testé avec Outlook 2010 ici).

Configuration Serveur Exchange et Exchange Rpc/HTTP Proxy
Etat des connexions:

On notera en particulier les points suivants:
  • Le nom du serveur Exchange (ou anciennement du CAS Array) n'a plus lieu d'être est est remplacé par un GUID (GUID@forest.com)
  • La configuration du Rpc/HTTP s'est fait automatiquement, comme pour les versions précédentes mais avec la subtilité d'avoir détecté une connectivité "interne" et donc une configuration du Rpc/HTTP Proxy faisant référence à l'InternalHostName configuré précédemment.
  • On remarquera aussi que les deux options visant à forcer l'utilisation du Rpc/HTTP sont forcées, et ceci sans configurer l'OutlookProvider EXPR.
  • On voit aussi clairement que la configuration par défaut se fait en Ntlm (auto-configuré ainsi) et en SSL (par défaut aussi).
Nous sommes maintenant connectés, passons donc à la seconde partie: le Kerberos !

Seconde partie: configuration du Kerberos


La configuration du Kerberos pour Exchange 2013 est dans la continuité d'Exchange 2010. Nous devons procéder ainsi:
  • Créer un objet pour l'Alternate Service Account
  • Lui assigner les Service Pincipal Names qui nous intéressent
  • Le configurer sur chaque serveur CAS
  • Reconfigurer le mode d'authentification
Création de l'Alternate Service Account:
J'utilise un objet de type "Computer", nommé ici EXCHANGE-MAIN$. La subtilité ici est qu'un compte d'ordinateur n'a pas de mot de passe positionné lorsqu'il est ajouté au domaine via la pré-création d'un objet. Puisqu'il n'y a pas à proprement parler de serveur à joindre au domaine, nous allons devoir positionner un mot de passe.
Pour ma part, j'utilise un script pour générer un mot de passe très long et très aléatoire puis un autre script pour faire une réinitialisation du mot de passe du compte ordinateur.

Lorsque l'objet est créé, il ne dispose d'aucun nom de service associé. Nous allons donc les créer à l'aide de la commande SETSPN.
  • setspn.exe -A HTTP/ex.w15-lab.com WFLAB\EXCHANGE-MAIN$
Assignation de l'Alternate Service Account:
Vous devrez procéder en mettant les Credentials de l'objet dans une variable, ici $ASA. L’assignation s'effectue au travers de la Cmdlet Set-ClientAccessServer, comme dans Exchange 2010:
  • $ASA = Get-Credential -Credential "WFLAB\EXCHANGE-MAIN$"
  • Set-ClientAccessServer -Identity SV-E15-1 -AlternateServiceAccountCredential $ASA
Répétez l'opération pour chaque serveur CAS partageant le même pool. Rappelez vous que l'Alternate Service Account ne peut être manipulé à distance (même en utilisant un Connect-ExchangeServer -Fqdn . Le plus simple est donc de se connecter en RDP à chaque serveur ou d'utiliser le script RollAlternateServiceAccountPassword.ps1 (qui - fait rigolo - affiche fièrement ne pas avoir été testé avec cette version d'Exchange :)).
Par exemple:
  • .\RollAlternateServiceAccountPassword.ps1 -CopyFrom SV-E15-1 -ToSpecificServers SV-E15-2
Reconfiguration du mode d'authentification
Comme nous l'avons vu précédemment, Outlook Anywhere est donc configuré par défaut en Ntlm. Nous devons donc reconfigurer chaque serveur CAS afin de bascule l'authentification en mode Negotiate afin de faire du Kerberos (avec fail-back en Ntlm potentiel). Nous le verrons plus tard, mais il existe d'autres modes d'authentification, comme le Nego2 mais qui n'est semble-t-il pas supporté sur Windows XP, même avec Outlook 2010. A terme, l'idée serait peut-être même de forcer le Kerberos, ce qui est totalement possible avec Exchange 2013 (à tester !).
Nous utiliserons la Cmdlet Set-OutlookAnywhere afin de reconfigurer l'authentification, l'Exchange Administration Center ne permettant que de modifier la méthode d'authentification externe (NDLR: Microsoft a encore pas mal de boulot pour finaliser l'EAC, trop léger à mon goût...).
  • Get-OutlookAnywhere -Server SV-E15-1 -ADPropertiesOnly | Set-OutlookAnywhere -InternalClientAuthenticationMethod Negotiate -IISAuthenticationMethods Negotiate,Ntlm
  • Get-OutlookAnywhere -Server SV-E15-2 -ADPropertiesOnly | Set-OutlookAnywhere -InternalClientAuthenticationMethod Negotiate -IISAuthenticationMethods Negotiate,Ntlm
Encore une fois, vous devrez surveiller l'eventlog Application afin de vérifier que la configuration Outlook Anywhere a bien été prise en compte et la configuration IIS alignée en conséquence (event ID 3025). Rappel: L'attente peut durer jusqu'à 15 minutes.
Vous pouvez aussi vérifier les Authentication Providers dans IIS sur l'application /Rpc et assurez-vous d'avoir (dans cet ordre: Negotiate et NTLM). Cette partie est normalement gérée par Exchange mais il semblerait que la synchronisation AD - Exchange - IIS ne fonctionne pas toujours très bien lors de modifications successives trop fréquentes... MEF !
Dès lors, vous pouvez redémarrer votre client Outlook. Celui-ci va se reconnecter en Ntlm puisque telle est la configuration actuellement en place coté client. L'avantage du mode Negotiate est donc de supporter une transition vers le Kerberos s'il est disponible, sans pour autant perturber le fonctionnement des clients déjà configurés.
Si vous ne voulez pas attendre une reconfiguration automatique de votre client (ce qui peut prendre jusqu'à 2 heures), effectuez une réparation de votre service Exchange, ce qui a pour effet de refaire appel au Web Service Autodiscover.
On voit bien d'ailleurs lorsque l'on fait un Test d'AutoConfiguration que l'on est configuré sur un autre mode d'authentification (ici, Nego2).
Et voici donc le résultat en se reconnectant et après une purge des tickets Kerberos (klist purge):

Promotion en Kerberos complet
Maintenant que nous avons vu comment configurer le mode Negotiate (le plus compatible), nous pouvons pousser l'exercice plus loin et forcer l'utilisation de Kerberos. N'appliquez pas cette procédure sur un environnement de production sans l'avoir testée dans un environnement de pré-production fonctionnellement similaire à la production.
La reconfiguration se fait de la même manière que précédemment, en utilisant la Cmdlet Set-OutlookAnywhere:
  • Get-OutlookAnywhere -Server SV-E15-1 -ADPropertiesOnly | Set-OutlookAnywhere -InternalClientAuthenticationMethod NegoEx -IISAuthenticationMethods Kerberos
  • Get-OutlookAnywhere -Server SV-E15-2 -ADPropertiesOnly | Set-OutlookAnywhere -InternalClientAuthenticationMethod NegoEx -IISAuthenticationMethods Kerberos
Note: vous pouvez utiliser "NegoEx" ou "Negotiate" pour l'InternalClientAuthenticationMethod.
D'un point de vue client, rien de change, on reste en Negotiate mais ce qui change est surtout côté serveur et des Authentication Providers, où l'on passe de "Negotiate" et "NTLM" à "Negotiate:Kerberos".

Notez que forcer le Kerberos sur cette partie d'IIS va impacter vos connexions externe, puisque un client hors Active Directory ne pourra utiliser Kerberos. Cela dépendra donc de la capacité de fournir une authentification externe en Negotiate et d'effectuer ou non de la délégation Kerberos via le Reverse Proxy, type ISA/TMG.

mardi 20 novembre 2012

[INFO]: Activer Kerberos pour Outlook Anywhere (clients internes)

Les avantages d'activer Kerberos avec Exchange 2010 ne fait plus de doute pour personne. C'est pleinement supporté depuis Exchange Server 2010 SP1 et fait partie du béa-ba d'une implémentation propre et pouvant monter en charge.

Qu'en est-il d'Outlook Anywhere ou plus précisément du Rpc/HTTP.

Pourquoi faire la distinction? Je m'explique...

Lorsque l'on parle d'Outlook Anywhere, cela représente la fonctionnalité (se connecter sans VPN avec un client lourd, et hors des frontières de l'Entreprise, autrement dit, généralement depuis une connexion Internet lambda et via un Reverse Proxy). La fonctionnalité Outlook Anywhere inclut de facto un ensemble d'aspect techniques: les Web Services (Autodiscover, OAB, EWS) et le fameux Rpc/HTTP.
En mode stricto-sensu Outlook Anywhere, nous n'avons pas accès à l'Active Directory et donc à un "Key Distribution Center" (KDC). La négociation Kerberos ne peut donc se faire. Dès lors, les modes d'authentification possible deviennent "Basic" et "Ntlm". Soit... ça c'était "avant"... :)
Lorsque l'on est en interne, il arrive que l'on veuille forcer l'utilisation du Rpc/HTTP afin de rester dans un mode "Web" et donc passer outre les équipements de sécurité plus facilement. Il arrive aussi que cela soit à des fins de sécurité (un RSSI a plus confiance en SSL qu'en un cryptage MAPI par exemple...). Dès lors, il était donc possible (et recommandé) d'activer le "Ntlm" afin de conserver du Single-Sign On (SSO).

Mais le Kerberos n'était pas disponible... Jusqu'à semble-t-il récemment.

Sachant qu'Exchange 2013 fait seulement du Rpc/HTTP, cela permet de donner un avant goût d'un mode Rpc/HTTP full Kerberos avec Exchange 2010 !
Le principe est simple: il s'agit de permettre à Exchange de répondre au nom de service Outlook Anywhere (un nom généralement externe) et d'activer l'authentification par négociation sur les CAS (ce qui est le cas pour tous les Web Services, mais ne l'est pas par défaut pour le Rpc/HTTP).
  • Pour le premier point, il s'agit d'ajouter le Fqdn d'Outlook Anywhere au compte de service Kerberos d'Exchange (le fameux "AlternateServiceAccount") - cela se fait en utilisant SETSPN (par exemple: setspn -A HTTP/outlookanywhere.domain.com DOMAIN\AlternateServiceAccount)
  • Pour le second point, il faut configurer Outlook Anywhere sur chaque CAS afin d'utiliser le mode "NegoEx" (par exemple:  Get-OutlookAnywhere -Server MonServeurCAS1 -ADPropertiesOnly | Set-OutlookAnywhere -ClientAuthenticationMethod NegoEx -IISAuthenticationMethods Ntlm)
    • Note: la valeur "Ntlm" positionnée pour les méthodes d'authentification IIS configurera en fait le répertoire virtuel "/Rpc" en activant l'authentification intégrée Windows avec les fournisseurs suivants: "Negotiate" et "NTLM" (dans cet ordre).
  • Vous devrez ensuite créer un nouveau pool d'application dans IIS (Application Pool). Nous pouvons le nommer par exemple "MSExchangeRpcProxyAppPool" (même nom qu'Exchange 2013 :)) et utiliser les paramètres suivants:
    • IdentityType: LocalSystem
    • QueueLength: 1000 pour une infrastructure de taille moyenne, 10000 pour une infrastructure devant supporter une majorité de clients en Rpc/Http
    • ProcessModel / LoadUserProfile: False
    • ProcessModel / IdleTimeout: 0
    • Recycling / PeriodicRestart / Time: 0 (jamais)
    • Failure / RapidFailProtection: False
  • Vous devrez ensuite assigner l'Application Pool au répertoire virtuel "/Rpc" (et idéalement, au répertoire virtuel "/RcpWithCert", que nous n'utiliserons pas ici).
Une fois ces modifications effectuées, il est recommandé d'attendre quelques minutes afin que les changement soient effectivement pris en compte.
Il reste un point essentiel, voire deux:
  • Créer un "Split DNS" afin de résoudre le Fqdn d'Outlook Anywhere via un DNS interne. Cela peut se faire facilement si vous avez déjà un split DNS. Sinon, il suffit de créer une zone DNS nommé "outlookanywhere.domain.com" et de créer un enregistrement de type "A" (Host) vide en spécifiant l'adresse IP du load-balancer. La relativité du DNS fait le reste...
  • Sur la partie load-balancer ou sur les CAS si vous ne faites pas de SSL Offloading ou de SSL Briding, et si ce n'était pas déjà le cas, remplacez le certificat de manière à avoir le Fqdn d'Outlook Anywhere en "Subject Name" et les autres noms (internes) en "Subject Alternate Names". Si vous ne voulez/pouvez pas faire ces modifications, vous pouvez configurer l'Outlook Provider "EXPR" afin que le nom pour l'authentification mutuelle SSL se fasse avec le Fqdn porté par le "Subject Name" du certificat. Attention toutefois, cela impacte vos clients "externes" et le nom doit être en adéquation avec le certificat porté par le Reverse Proxy. Par conséquent, la manipulation peut s'avérer plus ou moins complexe en fonction de la configuration en place.
Il est pris l'hypothèse que vous êtes déjà capable de load-balancer le Rpc/HTTP avec une bonne affinité (par exemple, cookie applicatif "OutlookSession") ou sinon n'utilisiez pas d'affinité du tout (le composant RPCHTTP-LB le faisant pour vous côté des serveurs Exchange au prix d'une consommation CPU accrue).
Dès lors, lors du prochain démarrage d'un client Outlook 2010 SP1 et pleinement mis à jour (testé avec les mises à jour de Novembre 2012) et après avoir forcé l'Autodiscover à reconfigurer la partie Rpc/HTTP proxy (un "repair" du profil s'impose, sinon attendre au max 2 heures), le client est maintenant configuré en mode "Negotiate" et non plus "Basic" ou "Ntlm".


Une petite vérification d'impose aussi sur les tickets Kerberos (avec KLIST):



Malheureusement, je n'ai pas encore réussi à faire fonctionner l'authentification par négociation avec un client Outlook 2007 SP3, même pleinement mis à jour. Cependant le mode d'authentification est disponible dans les propriétés Rpc/HTTP d'Outlook 2007 (depuis longtemps en fait).
En effet, lorsque mon client Outlook 2007 tente de se connecter, il échoue et se connecte en Mapi/Rpc classique et la méthode d'authentification se repositionne systématiquement sur "Basic". Il semble donc qu'il ne sache pas interpréter le mode d'authentification NegoEx (ci-dessous "Nego2" dans Outlook 2010 SP1).
Démonstration: