Adding SSO to Edge browser on ADFS 3.0

Hi all,

By default ADFS 3.0 doesn’t accept SSO on Edge browsers (and others modern browsers). To do that you need to configure it thru Powershell.

To list which browsers your ADFS are accepting you need to execute the following syntaxis:

Get-ADFSProperties | Select -ExpandProperty WIASupportedUserAgents

On the below image is showed the default config on ADFS 3.0. It has a few Microsoft platforms and browsers accepted.


If you want to enable other Microsoft browsers execute the below command:

Set-AdfsProperties -WIASupportedUserAgents @(“MSIE 6.0”, “MSIE 7.0; Windows NT”, “MSIE 8.0”, “MSIE 9.0”, “MSIE 10.0; Windows NT 6”, “Windows NT 6.3; Trident/7.0”, “Windows NT 6.3; Win64; x64; Trident/7.0”, “Windows NT 6.3; WOW64; Trident/7.0”, “Windows NT 6.2; Trident/7.0”, “Windows NT 6.2; Win64; x64; Trident/7.0”, “Windows NT 6.2; WOW64; Trident/7.0”, “Windows NT 6.1; Trident/7.0”, “Windows NT 6.1; Win64; x64; Trident/7.0”, “Windows NT 6.1; WOW64; Trident/7.0”, “MSIPC”, “Windows Rights Management Client”)

Execute now Get-ADFSProperties | Select -ExpandProperty WIASupportedUserAgents command to see if the new config was applied successfully:



Use the below instructions to add Edge browsers:

$Props=Get-ADFSProperties | Select -ExpandProperty WIASupportedUserAgents
$Props=$Props+ “Edge/14”
$Props=$Props+ “Edge/12”
Set-ADFSProperties -WIASupportedUserAgents $Props




Common commands to report info of mailboxes

Hi all,

Here are several useful reports for mailbox management:

With the following command we can obtain the size of each mailbox in the organization.

Get-mailbox | Get-Mailboxstatistics | select displayname,TotalItemSize

With the following command we can get the information exported to a csv file.

Get-mailbox | Get-Mailboxstatistics | select displayname,TotalItemSize | export-csv “c:\temp\mailboxsize.csv”

With the following command we can obtain the total of items in each mailbox.

Get-Mailbox | Get-MailboxStatistics | ft DisplayName,TotalItemSize,ItemCount

With the following command we can get the primary SMTP addresses and exported to csv.

Get-Mailbox -ResultSize Unlimited | Select-Object DisplayName,PrimarySmtpAddress | Export-CSV “c:\temp\PrimarySmtpAddress.csv”

With the following command we can obtain the statistics of the mailboxes in Mega Bytes and exported to csv.

Get-mailbox | Get-Mailboxstatistics | select displayname,TotalItemSize,ItemCount, @{expression={$_.totalitemsize.value.ToMB()};label=”Size(MB)”} | Export-CSV “c:\temp\Total_MB.csv”

With the following command we can obtain the statistics of the mailboxes in Mega Bytes and exported to Html

Get-mailbox | Get-Mailboxstatistics |Sort-Object TotalItemSize -Descending | convertto-html DisplayName, @{label=”TotalItemSize(MB)”;expression={$_.TotalItemSize.Value.ToMB()}} | set-content c:\temp\Total_MB.html

With the following command we can obtain the statistics of the mailboxes in Mega Bytes and in descending order.

Get-mailbox | Get-MailboxStatistics | where {$_.ObjectClass –eq “Mailbox”} | Sort-Object TotalItemSize –Descending | ft @{label=”User”;expression={$_.DisplayName}},@{label=”Total Size (MB)”;expression={$_.TotalItemSize.Value.ToMB()}},@{label=”Items”;expression={$_.ItemCount}},@{label=”Storage Limit”;expression={$_.StorageLimitStatus}} -auto

With the following command we can obtain the size and quota of mailboxes that are larger than their specified quota.

Get-Mailbox -ResultSize Unlimited | Get-MailboxStatistics | where {$_.StorageLimitStatus -notlike “BelowLimit*”} | Select DisplayName,StorageLimitStatus,@{name=”TotalItemSize (MB)”;expression={[math]::Round((($_.TotalItemSize.Value.ToString()).Split(“(“)[1].Split(” “)[0].Replace(“,”,””)/1MB),2)}},@{name=”TotalDeletedItemSize (MB)”;expression={[math]::Round((($_.TotalDeletedItemSize.Value.ToString()).Split(“(“)[1].Split(” “)[0].Replace(“,”,””)/1MB),2)}},ItemCount,DeletedItemCount | Sort “TotalItemSize (MB)” -Descending | Export-CSV “C:\temp\quotas_excedidas.csv” -NoTypeInformation

With the following command we can obtain which permissions are granted on the mailboxes of the organization.

Get-Mailbox | Get-MailboxPermission | where {$_.user.tostring() -ne “NT AUTHORITYSELF” -and $_.IsInherited -eq $false} | Select Identity,User,@{Name=’Access Rights’;Expression={[string]::join(‘, ‘, $_.AccessRights)}} | Export-Csv -NoTypeInformation c:\temp\mailboxpermissions.csv


Allowing mobile devices on Exchange Online with a bulk script

Hi guys,

In my last exchange migration to O365 my customer had the requirement to block all BYOD because for security reasons email department verify and manage all mobile devices. How? as always, asigning IMEI device ID to the user mailbox in O365.

Steps to acomplish that:

First of all you need to go to Exchange Online and there go to mobile section. Push on Edit.



On the window select Block access and push on save


After that action, you can use the below command to asign devices to usermailboxes:

Set-CASMailbox -ActiveSyncAllowedDeviceIDs “ID”

To check some user use:

Get-CasMailbox username | fl ActiveSyncAllowedDeviceIDs

If you have a large correlation of users – devices you can use my script. It’s very useful!!

  1.  You need a csv file with a list of users called migration.csv. Save it on C:\migration folder.


2. You need a file called Device_Info.csv where you have all device IMEI info exported from on-prem. Save it on C:\migration folder.


3. A csv file called LoteYYYYMMDD.csv where you have all users in O365.


4. The magic script:

[string]$Script:sourcefilename = “migration.csv”,
[System.Management.Automation.CredentialAttribute()]$cred = $null

Write-Host “This script must be run from a Powershell AD AZURE”
Write-Host “We load the list of users migrated from file $($Script:sourcefilename)”
$migrados = Import-Csv $Script:sourcefilename
if([String]::IsNullOrEmpty($cred)){$cred = Get-credential}

Write-Host “We load the list of devices.”
$Users = Import-Csv “C:\MIGRATION\Device_Info.csv” | Sort-Object PrimarySMTPAddress
$UserID = $null

Foreach ($user in $Users)
#Let’s see if the device line in the file contains a migrated user
$containsMailMigrado = $migrados | %{$_ -match $user.PrimarySMTPAddress}
If($containsMailMigrado -contains $true)
Write-Host ” Finded MailMigrado – $($user.PrimarySMTPAddress)”
$UserID = $user.PrimarySMTPAddress
$DeviceID = $user.DeviceID
Write-Host ” Adding device DeviceID = $($DeviceID)”
Set-CASMailbox -Identity $UserID -activesyncalloweddeviceid @{Add=$DeviceID}

Save that script as ScriptDevicesO365.PS1

Having all requisites showed above you can execute the line .\ScriptDevicesO365.PS1 LoteYYYMMDD.csv $UserCredential that will permit all your corporate devices be used with the assigned user on Office 365 – Exchange Online.





How to indicate a proxy to connect to Office 365 thru powershell


It’s possible that you can’t connect to O365 thru powershell directy because a Proxy in the middle between Inet and your corporate network so it is necessary to indicate it if we want to establish a session against Office365.

To do that execute the following lines:

  • $cred = Get-Credential
  • $proxysettings = New-PSSessionOption -ProxyAccessType IEConfig
  • $Session = New-PSSession -ConfigurationName Microsoft.Exchange -ConnectionUri -Credential $cred -Authentication Basic –AllowRedirection  -SessionOption $proxysettings
  • Import-PSSession $Session

To close session:

  • Remove-PSSession $Session


How to recover an ip lost on a VM bad deployment with SCVMM


Sometimes when I´m doing a deployment of various VM via scripting in my test lab and some thing fail for some reason as my smb file share are out of space or something like this the ip assigned to the machine is blocked… you have not the new virtual machine and you loose one ip from the pool.

The solution to that situation is the following:

First of all execute from PS Get-SCIPAddress


Second we seek the name of the virtual machine bad deployed and we copy the ip address.

Third we execute the following command with the ip address that we want to liberate $ip = get-scipaddress -IPAddress “”

Fourth we execute the command $ip | revoke-scipaddress to recover the ip.

Also, is more easy to do from the GUI… then go to Fabric Pane/Logical Networks and there over the Pool where you are deploying vms do right click and push on Inactive Address. Select All and push Release. Easy no? 🙂



Powershell Script to request info about state of AD Site links

Hi guys,

I read an interesting post in the Ashled McGlone blog that I think is good to remark.

See you!


Author’s note:  Before you dismiss this article you should know that the top two areas where I find issues for AD health are replication and DNS.  If you’re short on time skip to the bottom section “But Wait… There’s More” and run that report in your environment.  Otherwise I think you’ll get a lot of value from this content.

Freaky Neat

MonkIn my role as a Microsoft Premier Field Engineer I get to see what our customers do with Active Directory, both good and bad. Some admins are neat freaks about keeping everything pretty. (Imagine Adrian Monk as an AD admin.)  Others barely have time to open Facebook at work, and neatness is not a priority. Those are just the facts of IT life.  Consequently one area we frequently clean up is AD replication. You can see my former articles here on cleaning up replication settings.

What is hiding in your site links?

Today’s post will help you clean up site link descriptions and give you some nice reporting capability. For a quick overview of the terminology you can read the landmark TechNet article How Replication Works. To make a long story short admins create sites and then link them together with site links. Like most things in life change happens, and we don’t go back to clean up afterwards. I commonly find orphaned site links, mondo links with too many sites, and site link descriptions that haven’t been updated to reflect their member sites. (Use the free AD Topology Diagrammer to get a really cool Visio diagram of your sites and links.)

Some folks like to set their site link description field to list each of the member sites in the link. If that is you, then you’ll love this script.  Today’s script enumerates all of the member sites in a site link and then concatenates their names into the description of the site link.  Also, it will make a note in the description for any site links that have change notification enabled.  Now that’s handy!

Here is a screenshot from my lab showing what the descriptions can look like:


The Code

First let’s list the sitelinks:

# List all sitelinks            
Get-ADObject -LDAPFilter '(objectClass=siteLink)' ` 
    -SearchBase (Get-ADRootDSE).ConfigurationNamingContext ` 
    -Property Name, Cost, Description, Sitelist |            
    Format-List Name, Cost, Description, Sitelist

Now let’s update the descriptions:

# One ridiculous line of code            
# Broken down for readability            
Get-ADObject -LDAPFilter '(&(objectClass=siteLink)(siteList=*))' ` 
    -SearchBase (Get-ADRootDSE).ConfigurationNamingContext ` 
    -Property Name, Cost, Sitelist, Options |            
    ForEach {            
        Set-ADObject -Identity $_.DistinguishedName -Replace @{            
                ForEach ($site in $_.sitelist) {            
                    $s += "$($site.SubString(3,$site.IndexOf(",")-3)) <--> "            
                If ($_.Options -band 1) {' (Notify)'}            

Some site links have been orphaned and emptied by deleting the member sites and forgetting to delete the associated site link. For those here is a modified line that will update their description to ‘EMPTY SITE LINK’.

# Flag empty site links            
Get-ADObject -LDAPFilter '(&(objectClass=siteLink)(!siteList=*))' ` 
    -SearchBase (Get-ADRootDSE).ConfigurationNamingContext ` 
    -Property Name, Sitelist, Options |            
    % {Set-ADObject -Identity $_.DistinguishedName ` 
    -Replace @{Description='EMPTY SITE LINK'+` 
    $(If ($_.Options -band 1) {' (Notify)'})}}

The real magic in these lines are the LDAP filters:

  • All sitelinks: ‘(objectClass=siteLink)’
  • Sitelinks with member sites: ‘(&(objectClass=siteLink)(siteList=*))’
  • Sitelinks without member sites: ‘(&(objectClass=siteLink)(!siteList=*))’

Once you have imported the ActiveDirectory module you can type Get-Help about_ActiveDirectory_filter for more information on creating LDAP filter syntax.

But wait… there’s more!

In the script file attached at the end of the post I have included all of the scripts above plus some bonus content.  There is a site report script that will give you some schweet stats on your AD sites.  Use it to find those sites that are not in a site link, missing subnets, or do not have a DC.  The output looks like this:

Name     SiteLinkCount SubnetCount DCCount IsEmpty WhenCreated  Description
----     ------------- ----------- ------- ------- -----------  -----------
Bogus1               1           0       0    True 10/6/2010    Test site
Bogus2               0           0       0    True 1/25/2011    Test site
Bogus3               0           0       0    True 1/25/2011    Test site
Kentucky             3           1       2   False 4/13/2010    Kentucky
Lonely               2           1       1   False 2/17/2011    Remote site
Ohio                 2           2       2   False 4/13/2010    Ohio

Armed with this handy little report you will know where to begin your site, subnet, and site link remediation activities.

The Fine Print

This version of the script works with PowerShell v2 in your environment today. In AD PowerShell v3 there are new cmdlets to work with site links directly.

If you’re one of those who likes to note WAN speeds on site link descriptions, then you have a couple options:

  • Don’t run the script. It will overwrite your notes in the descriptions.
  • Export the descriptions, run this script, then manually add back the WAN speeds.

Unless you schedule this script to run as a scheduled task, you’ll need to run it again any time you update sites or site links. The descriptions are only as good as the last run of the script.

Currently the script inserts ‘<–>’ between the site names. Feel free to edit this to your liking.

If you have 1,000,000,000 sites jammed into a single site link, then it is likely that the concatenated description string will be too long and break the script.  Don’t do that if you can avoid it.

Running this script is harmless to your environment’s functionality, but it will overwrite your existing site link descriptions. As always you should test it in a lab first.