在 powershell 中为 Skype for Business 获取未分配的 phone 号码
Getting unassigned phone numbers for Skype for Business in powershell
有没有人在 powershell 中做过这样的事情?我正在自动创建新用户,并且必须设置他们的 Skype for business 帐户。这是我目前所拥有的:
<# set up skype for business #>
Enable-CsUser -Identity $FULLNAME `
-RegistrarPool REDACTED
-SipAddress $SIP
Set-CsUser $FULLNAME `
-EnterpriseVoiceEnabled $true `
-ExchangeArchivingPolicy Uninitialized `
-LineURI $PHONENUMBER
# only for driver manager/managers
Grant-CsConferencingPolicy $FULLNAME `
-PolicyName $ConferencingPolicy
Grant-CsExternalAccessPolicy -identity $FULLNAME `
-PolicyName 'Allow external access'
我只剩下分配 LineURI 的事情了,我似乎找不到任何关于如何做到这一点的信息。但是,我确实找到了一个 script 来执行此操作,但它似乎并不特定于我的需要。我的问题是:如何在 powershell 中查询 Skype for Business 以获取第一个未分配的号码并将其分配为 LineURI?我一直在使用 New-CSUnassignedNumber 但似乎无法取得任何进展。
SfB 不会记录您的号码范围,因此它不知道您分配的 1299 是否是范围中的最后一个,或者范围是否延伸到 1300's
Get-CsUser | ? LineUri | Select LineUri | Sort
这将为您提供组织中所有已分配 uri 的排序列表,因此您将能够挑选出可分配的 uri,无论您是否可以使用多种方法来查找您要查找的内容对于,但您可能对长期方法感兴趣,它是一个脚本,它接受您的数字范围,并在一个漂亮的 Csv 中输出已用和可用的列表。
#region Input
$NumRangeKeyTable = @{
#Make sure numbers are in the same format as they are in Skype,
#Do not include any ';ext' or 'tel:' etc. formatting!
#Put single numbers in the format:
# "+35313456789" = ""
#Put number ranges in the format:
# "+35313456700" = "+35313456799"
"+35313456789" = ""
"+35313456700" = "+35313456799"
}
#Save Location, set to $null to be prompted for location.
$FileName = $null
#endregion
#region Code
#region Helper Functions
Function Get-CsAssignedURIs {
$AllNumbers = @()
$Users = Get-CsUser
$Users | ? {$_.LineURI -ne ""} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "User" }}
$Users | ? {$_.PrivateLine -ne ""} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.PrivateLine ; Type = "PrivateLine" }}
Get-CsRgsWorkflow | Where-Object {$_.LineURI -ne ""} | Select Name,LineURI | %{$AllNumbers += New-Object PSObject -Property @{Name = $_.Name ; SipAddress = $_.PrimaryUri ; Number = $_.LineURI ; Type = "Workflow" }}
Get-CsCommonAreaPhone -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "CommonArea" }}
Get-CsAnalogDevice -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "AnalogDevice" }}
Get-CsExUmContact -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "ExUmContact" }}
Get-CsDialInConferencingAccessNumber -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.PrimaryUri ; Number = $_.LineURI ; Type = "DialInAccess" }}
Get-CsTrustedApplicationEndpoint -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "ApplicationEndpoint" }}
Return $AllNumbers
}
function Get-UniqueExt {
Param(
[string]$Uri1,
[string]$Uri2
)
$Reg = "^([0-9+])+$"
if ([string]::IsNullOrEmpty($uri1) -and [string]::IsNullOrEmpty($Uri2)) { return "Two blank strings provided" }
if ($Uri1 -eq $Uri2) { return $Uri1 }
if ([string]::IsNullOrEmpty($uri1)) { return $Uri2 }
if ([string]::IsNullOrEmpty($uri2)) { return $Uri1 }
if ($Uri1.Length -ne $Uri2.Length) { return "Strings cannot be different lengths" }
if (($Uri1 -notmatch $Reg) -or ($Uri2 -notmatch $Reg)) { return "Strings must be in the format '0123..' or '+123..'" }
($Uri1.Length-1)..0 | % {
if ($Uri1[$_] -ne $Uri2[$_]) { $Diff = $_ }
}
$Start = $Uri1.Substring(0,$Diff)
$Sub1 = $Uri2.Substring($Diff)
$Sub2 = $Uri1.Substring($Diff)
if ($Sub1 -lt $Sub2) {
$Min = $Sub1 ; $Max = $Sub2
} else {
$Min = $Sub2 ; $Max = $Sub1
}
$FormatStr = "" ; 1..$Min.Length | % { $FormatStr += "0"}
$Min..$Max | % { "$($Start)$($_.ToString($FormatStr))" }
}
function Save-ToFile {
Param(
[Parameter(ValueFromPipeline=$True)]
$Item = $null,
[switch]$ReturnName,
$ExtFilter = "*",
$WinTitle = "Select File",
$FileTypeDisplay = $null
)
If ($FileTypeDisplay -eq $null) {
If ($ExtFilter -eq "*") {
$ExtName = "All"
} Else {
$ExtName = (Get-Culture).TextInfo.ToTitleCase($ExtFilter)
}} Else {
$ExtName = (Get-Culture).TextInfo.ToTitleCase($FileTypeDisplay) }
[System.Reflection.Assembly]::LoadWithPartialName("System.windows.forms") | Out-Null
$FolderDialog = New-Object System.Windows.Forms.SaveFileDialog
$FolderDialog.Filter = "$($ExtName) files (*.$($ExtFilter.ToLowerInvariant()))| *.$($ExtFilter.ToLowerInvariant())"
$FolderDialog.Title = $WinTitle
$Result = $FolderDialog.ShowDialog()
If ($Result -eq "OK"){
$Item | Out-File $FolderDialog.FileName -Append
If ($ReturnName) { return $FolderDialog.FileName }}
Else {
Write-Error "No file selected" }
}
#endregion
Function Main {
Param ( [Hashtable]$NumRanges )
#region Process Data
$AllNums = $NumRanges.Keys | % {
Get-UniqueExt -Uri1 $_ -Uri2 $NumRanges[$_]
}
$S4BNums = Get-CsAssignedURIs
$S4BNums | % { $_.Number = ($_.Number.Split(';')[0] -ireplace "tel:","") }
$KT = @{}
$S4BNums | % {
$KT[$_.Number] = $_
}
$FullRecord = $AllNums | Sort | % {
$Number = $_
$Type = ""
$Name = ""
if ($KT[$_] -ne $null){
$UseDetails = $KT[$_]
$Name = $UseDetails.Name
$Type = $UseDetails.Type
}
[PSCustomObject]@{
Number = $Number
Name = $Name
Type = $Type
}
}
#endregion
return $FullRecord
}
$Results = Main $NumRangeKeyTable
#region Output-Data
if ($FileName -eq $null) {
$FileName = (Save-ToFile -Item "" -ReturnName -ExtFilter "Csv")
}
if ($FileName -ne $null) {
$Results | Export-Csv -Path $FileName -NoTypeInformation
} else { $Results | Out-GridView }
#endregion
#endregion
有没有人在 powershell 中做过这样的事情?我正在自动创建新用户,并且必须设置他们的 Skype for business 帐户。这是我目前所拥有的:
<# set up skype for business #>
Enable-CsUser -Identity $FULLNAME `
-RegistrarPool REDACTED
-SipAddress $SIP
Set-CsUser $FULLNAME `
-EnterpriseVoiceEnabled $true `
-ExchangeArchivingPolicy Uninitialized `
-LineURI $PHONENUMBER
# only for driver manager/managers
Grant-CsConferencingPolicy $FULLNAME `
-PolicyName $ConferencingPolicy
Grant-CsExternalAccessPolicy -identity $FULLNAME `
-PolicyName 'Allow external access'
我只剩下分配 LineURI 的事情了,我似乎找不到任何关于如何做到这一点的信息。但是,我确实找到了一个 script 来执行此操作,但它似乎并不特定于我的需要。我的问题是:如何在 powershell 中查询 Skype for Business 以获取第一个未分配的号码并将其分配为 LineURI?我一直在使用 New-CSUnassignedNumber 但似乎无法取得任何进展。
SfB 不会记录您的号码范围,因此它不知道您分配的 1299 是否是范围中的最后一个,或者范围是否延伸到 1300's
Get-CsUser | ? LineUri | Select LineUri | Sort
这将为您提供组织中所有已分配 uri 的排序列表,因此您将能够挑选出可分配的 uri,无论您是否可以使用多种方法来查找您要查找的内容对于,但您可能对长期方法感兴趣,它是一个脚本,它接受您的数字范围,并在一个漂亮的 Csv 中输出已用和可用的列表。
#region Input
$NumRangeKeyTable = @{
#Make sure numbers are in the same format as they are in Skype,
#Do not include any ';ext' or 'tel:' etc. formatting!
#Put single numbers in the format:
# "+35313456789" = ""
#Put number ranges in the format:
# "+35313456700" = "+35313456799"
"+35313456789" = ""
"+35313456700" = "+35313456799"
}
#Save Location, set to $null to be prompted for location.
$FileName = $null
#endregion
#region Code
#region Helper Functions
Function Get-CsAssignedURIs {
$AllNumbers = @()
$Users = Get-CsUser
$Users | ? {$_.LineURI -ne ""} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "User" }}
$Users | ? {$_.PrivateLine -ne ""} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.PrivateLine ; Type = "PrivateLine" }}
Get-CsRgsWorkflow | Where-Object {$_.LineURI -ne ""} | Select Name,LineURI | %{$AllNumbers += New-Object PSObject -Property @{Name = $_.Name ; SipAddress = $_.PrimaryUri ; Number = $_.LineURI ; Type = "Workflow" }}
Get-CsCommonAreaPhone -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "CommonArea" }}
Get-CsAnalogDevice -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "AnalogDevice" }}
Get-CsExUmContact -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "ExUmContact" }}
Get-CsDialInConferencingAccessNumber -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.PrimaryUri ; Number = $_.LineURI ; Type = "DialInAccess" }}
Get-CsTrustedApplicationEndpoint -Filter {LineURI -ne $null} | %{ $AllNumbers += New-Object PSObject -Property @{Name = $_.DisplayName ; SipAddress = $_.SipAddress ; Number = $_.LineURI ; Type = "ApplicationEndpoint" }}
Return $AllNumbers
}
function Get-UniqueExt {
Param(
[string]$Uri1,
[string]$Uri2
)
$Reg = "^([0-9+])+$"
if ([string]::IsNullOrEmpty($uri1) -and [string]::IsNullOrEmpty($Uri2)) { return "Two blank strings provided" }
if ($Uri1 -eq $Uri2) { return $Uri1 }
if ([string]::IsNullOrEmpty($uri1)) { return $Uri2 }
if ([string]::IsNullOrEmpty($uri2)) { return $Uri1 }
if ($Uri1.Length -ne $Uri2.Length) { return "Strings cannot be different lengths" }
if (($Uri1 -notmatch $Reg) -or ($Uri2 -notmatch $Reg)) { return "Strings must be in the format '0123..' or '+123..'" }
($Uri1.Length-1)..0 | % {
if ($Uri1[$_] -ne $Uri2[$_]) { $Diff = $_ }
}
$Start = $Uri1.Substring(0,$Diff)
$Sub1 = $Uri2.Substring($Diff)
$Sub2 = $Uri1.Substring($Diff)
if ($Sub1 -lt $Sub2) {
$Min = $Sub1 ; $Max = $Sub2
} else {
$Min = $Sub2 ; $Max = $Sub1
}
$FormatStr = "" ; 1..$Min.Length | % { $FormatStr += "0"}
$Min..$Max | % { "$($Start)$($_.ToString($FormatStr))" }
}
function Save-ToFile {
Param(
[Parameter(ValueFromPipeline=$True)]
$Item = $null,
[switch]$ReturnName,
$ExtFilter = "*",
$WinTitle = "Select File",
$FileTypeDisplay = $null
)
If ($FileTypeDisplay -eq $null) {
If ($ExtFilter -eq "*") {
$ExtName = "All"
} Else {
$ExtName = (Get-Culture).TextInfo.ToTitleCase($ExtFilter)
}} Else {
$ExtName = (Get-Culture).TextInfo.ToTitleCase($FileTypeDisplay) }
[System.Reflection.Assembly]::LoadWithPartialName("System.windows.forms") | Out-Null
$FolderDialog = New-Object System.Windows.Forms.SaveFileDialog
$FolderDialog.Filter = "$($ExtName) files (*.$($ExtFilter.ToLowerInvariant()))| *.$($ExtFilter.ToLowerInvariant())"
$FolderDialog.Title = $WinTitle
$Result = $FolderDialog.ShowDialog()
If ($Result -eq "OK"){
$Item | Out-File $FolderDialog.FileName -Append
If ($ReturnName) { return $FolderDialog.FileName }}
Else {
Write-Error "No file selected" }
}
#endregion
Function Main {
Param ( [Hashtable]$NumRanges )
#region Process Data
$AllNums = $NumRanges.Keys | % {
Get-UniqueExt -Uri1 $_ -Uri2 $NumRanges[$_]
}
$S4BNums = Get-CsAssignedURIs
$S4BNums | % { $_.Number = ($_.Number.Split(';')[0] -ireplace "tel:","") }
$KT = @{}
$S4BNums | % {
$KT[$_.Number] = $_
}
$FullRecord = $AllNums | Sort | % {
$Number = $_
$Type = ""
$Name = ""
if ($KT[$_] -ne $null){
$UseDetails = $KT[$_]
$Name = $UseDetails.Name
$Type = $UseDetails.Type
}
[PSCustomObject]@{
Number = $Number
Name = $Name
Type = $Type
}
}
#endregion
return $FullRecord
}
$Results = Main $NumRangeKeyTable
#region Output-Data
if ($FileName -eq $null) {
$FileName = (Save-ToFile -Item "" -ReturnName -ExtFilter "Csv")
}
if ($FileName -ne $null) {
$Results | Export-Csv -Path $FileName -NoTypeInformation
} else { $Results | Out-GridView }
#endregion
#endregion