diff --git a/PSModule.build.ps1 b/PSModule.build.ps1 index 562c887..f6f1a48 100644 --- a/PSModule.build.ps1 +++ b/PSModule.build.ps1 @@ -105,33 +105,33 @@ Enter-Build { Get-Variable | select-object name, value, visibility | format-table -autosize | out-string | write-verbose } - #Register Nuget - if (!(get-packageprovider "Nuget" -ForceBootstrap -ErrorAction silentlycontinue)) { - write-verbose "Nuget Provider Not found. Fetching..." - Install-PackageProvider Nuget -forcebootstrap -scope currentuser @PassThruParams | out-string | write-verbose - write-verboseheader "Installed Nuget Provider Info" - Get-PackageProvider Nuget @PassThruParams | format-list | out-string | write-verbose - } - - #Fix a bug with the Appveyor 2017 image having a broken nuget (points to v3 URL but installed packagemanagement doesn't query v3 correctly) - #Next command will add this back - if ($ENV:APPVEYOR -and ($ENV:APPVEYOR_BUILD_WORKER_IMAGE -eq 'Visual Studio 2017')) { - write-verbose "Detected Appveyor VS2017 Image, using v2 Nuget API" - UnRegister-PackageSource -Name nuget.org - } - - #Add the nuget repository so we can download things like GitVersion - if (!(Get-PackageSource "nuget.org" -erroraction silentlycontinue)) { - write-verbose "Registering nuget.org as package source" - Register-PackageSource -provider NuGet -name nuget.org -location http://www.nuget.org/api/v2 -Trusted @PassThruParams | out-string | write-verbose - } - else { - $nugetOrgPackageSource = Set-PackageSource -name 'nuget.org' -Trusted @PassThruParams - if ($PassThruParams.Verbose) { - write-verboseheader "Nuget.Org Package Source Info " - $nugetOrgPackageSource | format-table | out-string | write-verbose - } - } + # #Register Nuget + # if (!(get-packageprovider "Nuget" -ForceBootstrap -ErrorAction silentlycontinue)) { + # write-verbose "Nuget Provider Not found. Fetching..." + # Install-PackageProvider Nuget -forcebootstrap -scope currentuser @PassThruParams | out-string | write-verbose + # write-verboseheader "Installed Nuget Provider Info" + # Get-PackageProvider Nuget @PassThruParams | format-list | out-string | write-verbose + # } + + # #Fix a bug with the Appveyor 2017 image having a broken nuget (points to v3 URL but installed packagemanagement doesn't query v3 correctly) + # #Next command will add this back + # if ($ENV:APPVEYOR -and ($ENV:APPVEYOR_BUILD_WORKER_IMAGE -eq 'Visual Studio 2017')) { + # write-verbose "Detected Appveyor VS2017 Image, using v2 Nuget API" + # UnRegister-PackageSource -Name nuget.org + # } + + # #Add the nuget repository so we can download things like GitVersion + # if (!(Get-PackageSource "nuget.org" -erroraction silentlycontinue)) { + # write-verbose "Registering nuget.org as package source" + # Register-PackageSource -provider NuGet -name nuget.org -location http://www.nuget.org/api/v2 -Trusted @PassThruParams | out-string | write-verbose + # } + # else { + # $nugetOrgPackageSource = Set-PackageSource -name 'nuget.org' -Trusted @PassThruParams + # if ($PassThruParams.Verbose) { + # write-verboseheader "Nuget.Org Package Source Info " + # $nugetOrgPackageSource | format-table | out-string | write-verbose + # } + # } #Move to the Project Directory if we aren't there already Set-Location $buildRoot @@ -476,7 +476,7 @@ task PublishPSGallery -if (-not $SkipPublish) { ### SuperTasks # These are the only supported items to run directly from Invoke-Build task Deploy PreDeploymentChecks,Package,PublishGitHubRelease,PublishPSGallery -task Build Clean,CopyFilesToBuildDir,UpdateMetadata +task Build Clean, CopyFilesToBuildDir task Test Pester #Default Task - Build, Test with Pester, Deploy diff --git a/PowerHTML.psd1 b/PowerHTML.psd1 index 886411d..dc2741a 100644 --- a/PowerHTML.psd1 +++ b/PowerHTML.psd1 @@ -12,7 +12,7 @@ RootModule = 'PowerHTML.psm1' # Version number of this module. -ModuleVersion = '0.0.1' +ModuleVersion = '0.2.0' # Supported PSEditions # CompatiblePSEditions = @() @@ -27,7 +27,7 @@ Author = 'Justin Grote' CompanyName = 'Unspecified' # Copyright statement for this module -Copyright = '(c) 2018 Justin Grote. All rights reserved.' +Copyright = '(c) 2024 Justin Grote. All rights reserved.' # Description of the functionality provided by this module Description = 'Provides a wrapper for HTML Agility Pack for use where the IE HTML DOM from Invoke-WebRequest is not available such as Powershell Core' @@ -63,7 +63,7 @@ Description = 'Provides a wrapper for HTML Agility Pack for use where the IE HTM # TypesToProcess = @() # Format files (.ps1xml) to be loaded when importing this module -FormatsToProcess = @('.\Types\*.ps1xml') +FormatsToProcess = @('.\Types\HtmlAgilityPack.HtmlTextNode.ps1xml') # Modules to import as nested modules of the module specified in RootModule/ModuleToProcess # NestedModules = @() @@ -95,13 +95,13 @@ PrivateData = @{ PSData = @{ # Tags applied to this module. These help with module discovery in online galleries. - # Tags = @() + Tags = @('HTML','Invoke-WebRequest','Scraping','Agility','Pack','ScreenScraping') # A URL to the license for this module. - # LicenseUri = '' + LicenseUri = 'https://github.com/JustinGrote/PowerHTML/blob/master/LICENSE' # A URL to the main website for this project. - # ProjectUri = '' + ProjectUri = 'https://github.com/JustinGrote/PowerHTML' # A URL to an icon representing this module. # IconUri = '' @@ -120,5 +120,3 @@ PrivateData = @{ # DefaultCommandPrefix = '' } - - diff --git a/PowerHTML.psm1 b/PowerHTML.psm1 index b5488f3..0761432 100644 --- a/PowerHTML.psm1 +++ b/PowerHTML.psm1 @@ -1,9 +1,9 @@ #Get public and private function definition files. -$PublicFunctions = @( Get-ChildItem -Path $PSScriptRoot\Public\*.ps1 -ErrorAction SilentlyContinue ) -$PrivateFunctions = @( Get-ChildItem -Path $PSScriptRoot\Private\*.ps1 -ErrorAction SilentlyContinue ) +$PublicFunctions = @( Get-ChildItem -Path $PSScriptRoot\Public\*.ps1 -ErrorAction Ignore ) +$PrivateFunctions = @( Get-ChildItem -Path $PSScriptRoot\Private\*.ps1 -ErrorAction Ignore ) #Get JSON settings files -$ModuleSettings = @( Get-ChildItem -Path $PSScriptRoot\Settings\*.json -ErrorAction SilentlyContinue ) +$ModuleSettings = @( Get-ChildItem -Path $PSScriptRoot\Settings\*.json -ErrorAction Ignore ) #Determine which assembly versions to load #See if .Net Standard 2.0 is available on the system and if not, load the legacy Net 4.0 library @@ -40,23 +40,15 @@ if ($AssembliesToLoad) { } #Dot source the files -Foreach($FunctionToImport in @($PublicFunctions + $PrivateFunctions)) -{ - Try - { +foreach ($FunctionToImport in @($PublicFunctions + $PrivateFunctions)) { + try { . $FunctionToImport.fullname - } - Catch - { + } catch { Write-Error -Message "Failed to import function $($import.fullname): $_" } } #Import Settings files as global objects based on their filename -foreach ($ModuleSettingsItem in $ModuleSettings) -{ +foreach ($ModuleSettingsItem in $ModuleSettings) { New-Variable -Name "$($ModuleSettingsItem.basename)" -Scope Global -Value (convertfrom-json (Get-Content -raw $ModuleSettingsItem.fullname)) -Force -} - -#Export the public functions. This requires them to match the standard Noun-Verb powershell cmdlet format as a safety mechanism -Export-ModuleMember -Function ($PublicFunctions.Basename | where {$PSitem -match '^\w+-\w+$'}) \ No newline at end of file +} \ No newline at end of file diff --git a/Public/ConvertFrom-HTML.ps1 b/Public/ConvertFrom-HTML.ps1 index 723a1c2..64ecb4a 100644 --- a/Public/ConvertFrom-HTML.ps1 +++ b/Public/ConvertFrom-HTML.ps1 @@ -1,122 +1,109 @@ -<# -.SYNOPSIS - Takes an HTML input and converts it to an HTMLAgilityPack htmlNode object that can be navigated using Linq -.DESCRIPTION - Long description -.EXAMPLE - PS C:\> $HTMLString = @" - - -
-My first paragraph.
d - - - "@ - PS C:\> $HTMLString | ConvertFrom-HTML -OutVariable result - -NodeType Name AttributeCount ChildNodeCount ContentLength InnerText --------- ---- -------------- -------------- ------------- --------- -Document #document 0 4 103 … - - PS C:\> $result.SelectSingleNode("//body/h1") - -NodeType Name AttributeCount ChildNodeCount ContentLength InnerText --------- ---- -------------- -------------- ------------- --------- -Element h1 0 1 16 My First Heading - - Convert HTML string to a HtmlNode via the pipeline. - -.EXAMPLE - PS C:\> $uri = "https://www.powershellgallery.com/" - PS C:\> $result = ConvertFrom-HTML -uri $uri - PS C:\> $result - -NodeType Name AttributeCount ChildNodeCount ContentLength InnerText --------- ---- -------------- -------------- ------------- --------- -Document #document 0 4 17550 … - - Fetch and parse $uri directly via the URI pipeline. -.EXAMPLE - PS C:\> Get-Item $testFilePath | ConvertFrom-Html - -NodeType Name AttributeCount ChildNodeCount ContentLength InnerText --------- ---- -------------- -------------- ------------- --------- -Document #document 0 5 105 … - - Parse an HTML file piped from Get-Item. -.INPUTS - [String[]] - [System.IO.FileInfo[]] -.OUTPUTS - [HtmlAgilityPack.HtmlDocument] - [HtmlAgilityPack.HtmlNode] -.NOTES - General notes -#> + function ConvertFrom-Html { - [CmdletBinding(DefaultParameterSetName="String")] - param ( + <# + .SYNOPSIS + Takes an HTML input and converts it to an HTMLAgilityPack htmlNode object that can be navigated using Linq + .DESCRIPTION + Long description + .EXAMPLE + $HTMLString = @' + + + +My first paragraph.
d + + +'@ | ConvertFrom-HTML + + $HTMLString + + NodeType Name AttributeCount ChildNodeCount ContentLength InnerText + -------- ---- -------------- -------------- ------------- --------- + Document #document 0 4 103 … + + $HTMLString.SelectSingleNode('//body/h1') + + NodeType Name AttributeCount ChildNodeCount ContentLength InnerText + -------- ---- -------------- -------------- ------------- --------- + Element h1 0 1 16 My First Heading + + Convert HTML string to a HtmlNode via the pipeline. + + .EXAMPLE + $uri = [Uri]'https://www.powershellgallery.com/' | ConvertFrom-HTML + $uri + + NodeType Name AttributeCount ChildNodeCount ContentLength InnerText + -------- ---- -------------- -------------- ------------- --------- + Document #document 0 4 17550 … + + Fetch and parse a url. + .EXAMPLE + Get-Item $testFilePath | ConvertFrom-Html + + NodeType Name AttributeCount ChildNodeCount ContentLength InnerText + -------- ---- -------------- -------------- ------------- --------- + Document #document 0 5 105 … + + Parse an HTML file piped from Get-Item. + .INPUTS + [String[]] + [System.IO.FileInfo[]] + [System.URI[]] + .OUTPUTS + [HtmlAgilityPack.HtmlDocument] + [HtmlAgilityPack.HtmlNode] + .NOTES + General notes + #> + [OutputType([HtmlAgilityPack.HtmlNode])] + [OutputType([HtmlAgilityPack.HtmlDocument])] + [CmdletBinding(DefaultParameterSetName = 'String')] + param( #The HTML text to parse. Accepts multiple separate documents as an array. This also accepts pipeline from Invoke-WebRequest - [Parameter(ParameterSetName="String",Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName,Position=0)] - [String[]]$Content, + [Parameter(ParameterSetName = 'String', Mandatory, ValueFromPipeline, ValueFromPipelineByPropertyName, Position = 0)] + [String[]] $Content, #The URI or URIs from which to retrieve content. This may be faster than using Invoke-WebRequest but is less flexible in the method of retrieval (for instance, no POST) - [Parameter(ParameterSetName="URI",Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName)] - [System.URI[]]$URI, + [Parameter(ParameterSetName = 'URI', Mandatory, ValueFromPipeline, ValueFromPipelineByPropertyName, Position = 0)] + [System.URI[]] $URI, #Path to file or files containing HTML content to convert. This accepts pipeline from Get-Childitem or Get-Item - [Parameter(ParameterSetName="Path",Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName)] - [System.IO.FileInfo[]]$Path, + [Parameter(ParameterSetName = 'Path', Mandatory, ValueFromPipeline, ValueFromPipelineByPropertyName, Position = 0)] + [System.IO.FileInfo[]] $Path, #Do not return the Linq documentnode, instead return the HTMLDocument object. This is useful if you want to do XPath queries instead of Linq queries - [switch]$Raw - + [switch] $Raw ) - begin { + $html = [HtmlAgilityPack.HtmlDocument]::new() + $web = [HtmlAgilityPack.HtmlWeb]::new() } - process { - #Find the type of input and bind it to inputObject - $inputObject = $null - foreach ($contentType in "Content","URI","Path") { - if ((Get-Variable -erroraction SilentlyContinue $contentType).value) { - $inputObject = (Get-Variable $contentType).value - break - } - } - if (-not $inputObject) {write-error "Input Object Type Not Identified. If you see this then ConvertFrom-HTML needs better input validation"} - - #Unwrap any arrays. This allows us to accept both pipeline and parameter input - $inputObject | ForEach-Object { - $inputItem = $PSItem - $htmlDoc = new-object HtmlAgilityPack.HtmlDocument - - #Process all object types into a common HTML document format - switch ($inputItem.GetType().FullName) { - "System.String" { - $htmlDoc.LoadHtml($inputItem) + switch ($PSCmdlet.ParameterSetName) { + 'String' { + $Content | ForEach-Object { + Write-Verbose "Loading HTML" + $html.LoadHtml($_) + if ($Raw) { $html } else { $html.DocumentNode } } - "System.Uri" { - $htmlDoc = (new-object HtmlAgilityPack.HtmlWeb).Load($inputItem) - } - "System.IO.FileInfo" { - $htmlDoc.Load($inputItem) - } - Default { - write-error "Object Type not supported or implemented. If you see this error then ConvertFrom-HTML has improper input validation" - continue + } + 'URI' { + $URI | ForEach-Object { + Write-Verbose "Loading URI $_" + $site = $web.Load($_) + if ($Raw) { $site } else { $site.DocumentNode } } } - if ($inputItem) { - if ($Raw) { - $htmlDoc - } else { - $htmlDoc.DocumentNode + 'Path' { + $Path | ForEach-Object { + Write-Verbose "Loading File $_" + $html.Load($_.FullName) + if ($Raw) { $html } else { $html.DocumentNode } } } } - } -} \ No newline at end of file + +} diff --git a/Tests/00-PowershellModule.Tests.ps1 b/Tests/00-PowershellModule.Tests.ps1 index 51bfdab..abe2634 100644 --- a/Tests/00-PowershellModule.Tests.ps1 +++ b/Tests/00-PowershellModule.Tests.ps1 @@ -1,78 +1,84 @@ #requires -module BuildHelpers -if (-not (import-module BuildHelpers -PassThru -verbose:$false -erroraction silentlycontinue)) { - install-module buildhelpers -scope currentuser -erroraction stop -force - import-module BuildHelpers -erroraction stop -verbose:$false -} -Set-BuildEnvironment -force -$PSVersion = $PSVersionTable.PSVersion.Major -$BuildOutputProject = Join-Path $env:BHBuildOutput $env:BHProjectName -$ModuleManifestPath = Join-Path $BuildOutputProject '\*.psd1' -if (-not (Test-Path $ModuleManifestPath)) {throw "Module Manifest not found at $ModuleManifestPath. Did you run 'Invoke-Build Build' first?"} +#Must be done during discovery as contexts contain build info +Set-BuildEnvironment -Force -Describe 'Powershell Module' { +BeforeAll { + if (-not (Import-Module BuildHelpers -PassThru -Verbose:$false -ErrorAction silentlycontinue)) { + Install-Module BuildHelpers -Scope currentuser -ErrorAction stop -Force + Import-Module BuildHelpers -ErrorAction stop -Verbose:$false + } + $SCRIPT:PSVersion = $PSVersionTable.PSVersion.Major + $SCRIPT:BuildOutputProject = Join-Path $env:BHBuildOutput $env:BHProjectName + $SCRIPT:ModuleManifestPath = Join-Path $BuildOutputProject '\*.psd1' + if (-not (Test-Path $ModuleManifestPath)) { throw "Module Manifest not found at $ModuleManifestPath. Did you run 'Invoke-Build Build' first?" } +} +Describe 'Powershell Module' { Context "$env:BHProjectName" { - $ModuleName = $env:BHProjectName + BeforeAll { + $SCRIPT:ModuleName = $env:BHProjectName + } It 'Has a valid Module Manifest' { - if ($isCoreCLR -or $PSVersionTable.PSVersion -ge [Version]"5.1") { + if ($isCoreCLR -or $PSVersionTable.PSVersion -ge [Version]'5.1') { $Script:Manifest = Test-ModuleManifest $ModuleManifestPath } else { #Copy the Module Manifest to a temp file in order to test to fix a bug where #Test-ModuleManifest caches the first result, thus not catching changes $TempModuleManifestPath = [System.IO.Path]::GetTempFileName() + '.psd1' - copy-item $ModuleManifestPath $TempModuleManifestPath + Copy-Item $ModuleManifestPath $TempModuleManifestPath $Script:Manifest = Test-ModuleManifest $TempModuleManifestPath - remove-item $TempModuleManifestPath -verbose:$false + Remove-Item $TempModuleManifestPath -Verbose:$false } } It 'Has a valid root module' { - $Manifest.RootModule | Should Be "$ModuleName.psm1" + $Manifest.RootModule | Should -Be "$ModuleName.psm1" } It 'Has a valid Description' { - $Manifest.Description | Should Not BeNullOrEmpty + $Manifest.Description | Should -Not -BeNullOrEmpty } It 'Has a valid GUID' { - [Guid]$Manifest.Guid | Should BeOfType 'System.GUID' + [Guid]$Manifest.Guid | Should -BeOfType System.GUID } It 'Has a valid Copyright' { - $Manifest.Copyright | Should Not BeNullOrEmpty + $Manifest.Copyright | Should -Not -BeNullOrEmpty } It 'Exports all public functions' { - $FunctionFiles = Get-ChildItem "$BuildOutputProject\Public" -Filter *.ps1 | Select -ExpandProperty BaseName - $FunctionNames = $FunctionFiles | foreach {$_ -replace '-', "-$($Manifest.Prefix)"} + $FunctionFiles = Get-ChildItem "$BuildOutputProject\Public" -Filter *.ps1 | Select-Object -ExpandProperty BaseName + $FunctionNames = $FunctionFiles | ForEach-Object { $_ -replace '-', "-$($Manifest.Prefix)" } $ExFunctions = $Manifest.ExportedFunctions.Values.Name - foreach ($FunctionName in $FunctionNames) - { - $ExFunctions -contains $FunctionName | Should Be $true + foreach ($FunctionName in $FunctionNames) { + $ExFunctions -contains $FunctionName | Should -BeTrue } } It 'Has at least 1 exported command' { - $Script:Manifest.exportedcommands.count | Should BeGreaterThan 0 + $Script:Manifest.exportedcommands.count | Should -BeGreaterThan 0 } It 'Can be imported as a module successfully' { Remove-Module $ModuleName -ErrorAction SilentlyContinue - Import-Module $BuildOutputProject -PassThru -verbose:$false -OutVariable BuildOutputModule | Should BeOfType System.Management.Automation.PSModuleInfo - $BuildOutputModule.Name | Should Be $ModuleName + Import-Module $BuildOutputProject -PassThru -Verbose:$false -OutVariable BuildOutputModule | Should -BeOfType System.Management.Automation.PSModuleInfo + $BuildOutputModule.Name | Should -Be $ModuleName } It 'Is visible in Get-Module' { $module = Get-Module $ModuleName - $Module | Should BeOfType System.Management.Automation.PSModuleInfo - $Module.Name | Should Be $ModuleName + $Module | Should -BeOfType System.Management.Automation.PSModuleInfo + $Module.Name | Should -Be $ModuleName } } } Describe 'PSScriptAnalyzer' { - $results = Invoke-ScriptAnalyzer -Path $BuildOutputProject -Recurse -ExcludeRule "PSAvoidUsingCmdletAliases","PSAvoidGlobalVars" -Verbose:$false + BeforeAll { + $SCRIPT:SAResults = Invoke-ScriptAnalyzer -Path $BuildOutputProject -Recurse -ExcludeRule 'PSAvoidUsingCmdletAliases', 'PSAvoidGlobalVars' -Verbose:$false + } + It 'PSScriptAnalyzer returns zero errors for all files in the repository' { - $results - $results.Count | Should Be 0 + $SAResults.Count | Should -Be 0 } -} \ No newline at end of file +} diff --git a/Tests/PowerHTML.Tests.ps1 b/Tests/PowerHTML.Tests.ps1 index 2d537b3..74d0854 100644 --- a/Tests/PowerHTML.Tests.ps1 +++ b/Tests/PowerHTML.Tests.ps1 @@ -1,95 +1,97 @@ #Move out of tests to the subdirectory of the modulepwd -if ((get-item .).Name -match 'Tests') {Set-Location $PSScriptRoot\..} +if ((get-item .).Name -match 'Tests') { Set-Location $PSScriptRoot\.. } -$ModuleName = 'PowerHTML' -$ModuleManifestName = "$ModuleName.psd1" -$ModuleManifestPath = "$PSScriptRoot\..\$ModuleManifestName" Describe 'HTML Basic Conversion' { - $HTMLString = @" - + BeforeAll { + if (-not (Get-Module PowerHTML)) { + Import-Module $PSScriptRoot\..\PowerHTML.psd1 + } + $HTMLString = @' +My first paragraph.
d +My first paragraph.
-"@ - - $HTMLString2 = @" +'@ + $HTMLString2 = @' -My first paragraph.
+Paragraph 1.
-"@ - - #Generate test files to a random path - $testFilePath1 = [System.IO.Path]::GetTempFileName() - $testFilePath2 = [System.IO.Path]::GetTempFileName() - $testFilePathAll = @($testFilePath1,$testFilePath2) - $HTMLString > $testFilePath1 - $HTMLString > $testFilePath2 - +'@ + #Generate test files to a random path + $testFilePath1 = New-TemporaryFile + $testFilePath2 = New-TemporaryFile + $testFilePathAll = @($testFilePath1,$testFilePath2) + Set-Content -Path $testFilePath1 -Value $HTMLString + Set-Content -Path $testFilePath2 -Value $HTMLString2 + } It 'Can convert an HTML string to a raw HTMLDocument via the pipeline' { - $HTMLString | ConvertFrom-HTML -Raw | Should Be HtmlAgilityPack.HTMLDocument + $HTMLString | ConvertFrom-Html -Raw | Should -BeOfType HtmlAgilityPack.HTMLDocument } It 'Can parse an HTML string to a HtmlNode via the pipeline' { - $HTMLString | ConvertFrom-HTML | Should Be HtmlAgilityPack.HTMLNode + $HTMLString | ConvertFrom-Html | Should -BeOfType HtmlAgilityPack.HTMLNode } It 'Can parse multiple HTML strings to HtmlNodes when passed via the pipeline as an array' { $result = $HTMLString,$HTMLString2 | ConvertFrom-HTML - $result.count | Should Be 2 + $result.count | Should -Be 2 foreach ($resultItem in $result) { - $resultItem | Should Be HtmlAgilityPack.HTMLNode + $resultItem | Should -BeOfType HtmlAgilityPack.HTMLNode } } It 'Can parse an HTML file' { - ConvertFrom-Html -Path $testFilePath1 | Should Be HtmlAgilityPack.HTMLNode + ConvertFrom-Html -Path $testFilePath1 | Should -BeOfType HtmlAgilityPack.HTMLNode } It 'Can parse multiple HTML files' { $result = ConvertFrom-Html -Path $testFilePath1,$testFilePath2 - $result.count | Should Be 2 + $result.count | Should -Be 2 foreach ($resultItem in $result) { - $resultItem | Should Be HtmlAgilityPack.HTMLNode + $resultItem | Should -BeOfType HtmlAgilityPack.HTMLNode } } It 'Can parse an HTML file piped from Get-Item' { - Get-Item $testFilePath1 | ConvertFrom-Html | Should Be HtmlAgilityPack.HTMLNode + Get-Item $testFilePath1 | ConvertFrom-Html | Should -BeOfType HtmlAgilityPack.HTMLNode } It 'Can parse multiple HTML files piped from Get-Item' { $result = Get-Item $testFilePathAll | ConvertFrom-Html - $result.count | Should Be 2 + $result.count | Should -Be 2 foreach ($resultItem in $result) { - $resultItem | Should Be HtmlAgilityPack.HTMLNode + $resultItem | Should -BeOfType HtmlAgilityPack.HTMLNode } } + AfterAll { + Remove-Item $testFilePath1,$testFilePath2 -ErrorAction silentlycontinue -force + } - #Cleanup - Remove-Item $testFilePath1,$testFilePath2 -Erroraction silentlycontinue -force } Describe 'HTTP Operational Tests - REQUIRES INTERNET CONNECTION!' { - $uri = "https://www.google.com" - $uriObjects = [uri]$uri,[uri]"https://www.facebook.com",[uri]"https://www.twitter.com" - It "Can fetch and parse $uri directly via the URI pipeline" { - $result = ConvertFrom-HTML -uri $uri - $result | Should Be HtmlAgilityPack.HTMLNode - $result.innertext -match 'Google' | Should Be $true + BeforeAll { + $uri = 'https://www.google.com' + $uriObjects = [uri]$uri, [uri]'https://www.facebook.com', [uri]'https://www.x.com' + } + It 'Can fetch and parse $uri directly via the URI pipeline' { + $result = ConvertFrom-Html -URI $uri + $result | Should -BeOfType HtmlAgilityPack.HTMLNode + $result.innertext -match 'Google' | Should -BeTrue } - It "Can parse $uri piped from Invoke-WebRequest" { - $result = Invoke-WebRequest -verbose:$false $uri | ConvertFrom-HTML - $result | Should Be HtmlAgilityPack.HTMLNode - $result.innertext -match 'Google' | Should Be $true + It 'Can parse $uri piped from Invoke-WebRequest' { + $result = Invoke-WebRequest -Verbose:$false $uri | ConvertFrom-Html + $result | Should -BeOfType HtmlAgilityPack.HTMLNode + $result.innertext -match 'Google' | Should -BeTrue } - It "Can parse multiple URI objects passed via the pipeline (Google,Facebook,Twiiter)" { - $result = $uriObjects | ConvertFrom-HTML + It 'Can parse multiple URI objects passed via the pipeline (Google,Facebook,Twiiter)' { + $result = $uriObjects | ConvertFrom-Html foreach ($resultItem in $result) { - $resultItem | Should Be HtmlAgilityPack.HTMLNode + $resultItem | Should -BeOfType HtmlAgilityPack.HTMLNode } - $result[0].innertext -match 'Google' | Should Be $true - $result[1].innertext -match 'Facebook' | Should Be $true - $result[2].innertext -match 'Twitter' | Should Be $true + $result[0].innertext | Should -Match 'Google' + $result[1].innertext | Should -Match 'Facebook' + $result[2].innertext | Should -Match 'X\.com' } -} \ No newline at end of file +} diff --git a/appveyor.yml b/appveyor.yml deleted file mode 100644 index 41357a9..0000000 --- a/appveyor.yml +++ /dev/null @@ -1,30 +0,0 @@ -# See http://www.appveyor.com/docs/appveyor-yml for many more options -version: '{build}-{branch}' - -#Publish to PowerShell Gallery with this key -environment: - NuGetApiKey: - secure: HncD30pn+cWRepdP28pyB1l4BNg3x3MdvcNV8EysOhQ5kBFMHVyXiQM0whuUW78P - -image: - - Visual Studio 2017 -install: - - ps: Install-Module -Name InvokeBuild -Confirm:$false -ErrorAction Stop -Force - -# Skip on updates to the readme. -# We can force this by adding [skip ci] or [ci skip] anywhere in commit message -skip_commits: - message: /updated README.*|Update README.*s/ - -#Kick off the CI/CD pipeline. We do test and build in the same script -#To be portable to non-Appveyor builds -#We run it at the test step so that we can upload test results back to the system. -build_script: - - ps: Invoke-Build Build,Package -test_script: - - ps: Invoke-Build Test - -deploy: false - -on_finish: - - ps: if ($env:APPVEYOR_REPO_COMMIT_MESSAGE -match 'AppveyorRDPDebug') {$blockRdp = $true; iex ((new-object net.webclient).DownloadString('https://raw.githubusercontent.com/appveyor/ci/master/scripts/enable-rdp.ps1'))} \ No newline at end of file diff --git a/lib/HtmlAgilityPack-1.11.60-net40-client.dll b/lib/HtmlAgilityPack-1.11.60-net40-client.dll new file mode 100644 index 0000000..4629698 Binary files /dev/null and b/lib/HtmlAgilityPack-1.11.60-net40-client.dll differ diff --git a/lib/HtmlAgilityPack-1.11.60-netstandard2.dll b/lib/HtmlAgilityPack-1.11.60-netstandard2.dll new file mode 100644 index 0000000..e154368 Binary files /dev/null and b/lib/HtmlAgilityPack-1.11.60-netstandard2.dll differ diff --git a/lib/HtmlAgilityPack-1.7.0.LICENSE b/lib/HtmlAgilityPack-1.11.60.LICENSE similarity index 100% rename from lib/HtmlAgilityPack-1.7.0.LICENSE rename to lib/HtmlAgilityPack-1.11.60.LICENSE diff --git a/lib/HtmlAgilityPack-1.7.0-net40-client.dll b/lib/HtmlAgilityPack-1.7.0-net40-client.dll deleted file mode 100644 index 9aaa4b6..0000000 Binary files a/lib/HtmlAgilityPack-1.7.0-net40-client.dll and /dev/null differ diff --git a/lib/HtmlAgilityPack-1.7.0-netstandard2.dll b/lib/HtmlAgilityPack-1.7.0-netstandard2.dll deleted file mode 100644 index 74b0f21..0000000 Binary files a/lib/HtmlAgilityPack-1.7.0-netstandard2.dll and /dev/null differ