Compare commits

..

24 Commits
v0.3.0 ... main

Author SHA1 Message Date
Doug Davis e4c6eb2053
add link to our security mailing list (#54)
Signed-off-by: Doug Davis <dug@microsoft.com>
2023-10-16 06:59:08 -07:00
Doug Davis de78f7abc0
Governance docs per CE PR 1226 (#53)
Signed-off-by: Doug Davis <dug@microsoft.com>
2023-09-28 06:56:32 -07:00
Mark Peek fce1f2a05b
Merge pull request #52 from cloudevents/addGovDocs
add some missing governance docs
2023-09-20 11:21:32 -07:00
Doug Davis 69b301acc5 add some missing governance docs
Signed-off-by: Doug Davis <dug@microsoft.com>
2023-09-11 19:47:35 +00:00
Michael Gasch 62f0995896
Merge pull request #51 from cloudevents/dep-1
chore: Update embano1/wip action
2023-04-26 14:12:55 +02:00
Michael Gasch 033df40cea
chore: Update embano1/wip action
Signed-off-by: Michael Gasch <15986659+embano1@users.noreply.github.com>
2023-04-25 17:43:53 +02:00
Michael Gasch 685b0fb6c2
Merge pull request #50 from cloudevents/create-pull-request/patch
Update CHANGELOG
2021-09-08 20:43:02 +02:00
embano1 f81400785b Update CHANGELOG for v0.3.3 2021-09-08 18:42:20 +00:00
Michael Gasch 112e84313d
Merge pull request #49 from dmilov/topic/bump-module-version-for-release
chore: Bump module version for new release
2021-09-08 20:38:53 +02:00
Michael Gasch 7fe15200b3
Merge pull request #48 from embano1/issue-47
chore: Trigger release on tag push
2021-09-08 20:38:28 +02:00
Dimitar Milov 32f333ba86 chore: Bump module version for new release
Signed-off-by: Dimitar Milov <dmilov@vmware.com>
2021-09-08 20:08:53 +03:00
Michael Gasch 5e2e221c24 chore: Trigger release on tag push
Closes: #47
Signed-off-by: Michael Gasch <mgasch@vmware.com>
2021-09-08 17:22:52 +02:00
dmilov 23e8b6714b
Merge pull request #46 from dmilov/topic/add-project-uri
chore: Add Project URI in the module manifest
2021-09-08 16:22:10 +03:00
Dimitar Milov c8b5958909 chore: Add Project URI in the module manifest
Signed-off-by: Dimitar Milov <dmilov@vmware.com>
2021-09-08 09:57:04 +03:00
Michael Gasch eda44f45bb
Merge pull request #44 from cloudevents/create-pull-request/patch
Update CHANGELOG
2021-08-30 11:54:45 +02:00
dmilov 4cebfdf75e Update CHANGELOG for v0.3.1 2021-08-30 09:48:51 +00:00
dmilov c715c5c97e
Merge pull request #43 from dmilov/topic/no-content-type
fix: Incorrect parsing of Binary Content Mode cloud events
2021-08-30 12:05:03 +03:00
Dimitar Milov 7eb0f9b4bd fix: Incorrect parsing of Binary Content Mode cloud events
Signed-off-by: Dimitar Milov <dmilov@vmware.com>
2021-08-30 10:45:53 +03:00
Michael Gasch 4e380882f8
Merge pull request #41 from embano1/issue-40 2021-06-23 10:26:22 +02:00
Michael Gasch 941816a414 chore: Add RELEASE instructions
Closes: #40
Signed-off-by: Michael Gasch <mgasch@vmware.com>
2021-06-21 20:30:46 +02:00
dmilov 4a8a5abcca
Merge pull request #39 from dmilov/topic/update-readme
chore: Update README with the new version output
2021-06-21 16:33:13 +03:00
Dimitar Milov 7876104118 Update README with the new version output
Signed-off-by: Dimitar Milov <dmilov@vmware.com>
2021-06-21 16:29:32 +03:00
Michael Gasch 36f8b25dce
Merge pull request #38 from cloudevents/create-pull-request/patch
Update CHANGELOG
2021-06-21 15:25:04 +02:00
embano1 75b318093c Update CHANGELOG for v0.3.0 2021-06-21 13:24:16 +00:00
9 changed files with 768 additions and 422 deletions

View File

@ -14,4 +14,4 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Check WIP in PR Title
uses: embano1/wip@v1
uses: embano1/wip@v2

View File

@ -6,7 +6,7 @@
name: Release
on:
create:
push:
tags:
- v*
workflow_dispatch:

89
CHANGELOG.md Normal file
View File

@ -0,0 +1,89 @@
<a name="v0.3.3"></a>
## [Release v0.3.3](https://github.com/cloudevents/sdk-powershell/compare/v0.3.2...v0.3.3)
> Release Date: 2021-09-08
### 🧹 Chore
- [32f333b] Bump module version for new release
- [5e2e221] Trigger release on tag push (#47)
### ⚠️ BREAKING
### 📖 Commits
- [32f333b] chore: Bump module version for new release
- [5e2e221] chore: Trigger release on tag push (#47)
<a name="v0.3.2"></a>
## [Release v0.3.2](https://github.com/cloudevents/sdk-powershell/compare/v0.3.1...v0.3.2)
> Release Date: 2021-09-08
### 🧹 Chore
- [c8b5958] Add Project URI in the module manifest
### ⚠️ BREAKING
### 📖 Commits
- [c8b5958] chore: Add Project URI in the module manifest
<a name="v0.3.1"></a>
## [Release v0.3.1](https://github.com/cloudevents/sdk-powershell/compare/v0.3.0...v0.3.1)
> Release Date: 2021-08-30
### 🐞 Fix
- [7eb0f9b] Incorrect parsing of Binary Content Mode cloud events
### 🧹 Chore
- [941816a] Add RELEASE instructions (#40)
### ⚠️ BREAKING
### 📖 Commits
- [7eb0f9b] fix: Incorrect parsing of Binary Content Mode cloud events
- [941816a] chore: Add RELEASE instructions (#40)
- [7876104] Update README with the new version output
<a name="v0.3.0"></a>
## v0.3.0
> Release Date: 2021-06-21
### 🧹 Chore
- [5b14f75] Include commit details in CHANGELOG (#35)
- [2c4d0ed] Add check WIP action (#31)
- [5764180] Add CHANGELOG configuration (#29)
- [0bd4192] Verify PRs and push to main (#6)
- [e08a275] Add stale action (#7)
### ⚠️ BREAKING
### 📖 Commits
- [2144695] Bump module version 0.3.0
- [5b14f75] chore: Include commit details in CHANGELOG (#35)
- [78b7e9e] Implement publish script
- [2c4d0ed] chore: Add check WIP action (#31)
- [5764180] chore: Add CHANGELOG configuration (#29)
- [a0e1078] Add PR template (#3)
- [ae6f848] Update issue templates
- [3a9010a] Improve examples. Remove unnecessary details.
- [401a475] Implement wait server to start in the integrations tests BeforeAll Fix Binary Mode HTTP Header DateTime format. It is UTC time formatted in ISO 8601 format including milliseconds. Bump revision of the module version
- [0bd4192] chore: Verify PRs and push to main (#6)
- [e08a275] chore: Add stale action (#7)
- [3629c77] Add Install Module Instructions to README ([#17](https://github.com/cloudevents/sdk-powershell/issues/17)) (#17) (#16)
- [aac584a] Enable process exit in build.ps1
- [84606b0] Create CONTRIBUTING.md ([#15](https://github.com/cloudevents/sdk-powershell/issues/15)) (#15)
- [d305f16] Renames Add-CloudEvent*Data to Set-CloudEvent*Data ([#12](https://github.com/cloudevents/sdk-powershell/issues/12)) (#12) (#9)
- [f23df54] Adds license headers in source code files ([#11](https://github.com/cloudevents/sdk-powershell/issues/11)) (#11)
- [62f14b6] Remove install instructions from an internal PS repository ([#10](https://github.com/cloudevents/sdk-powershell/issues/10)) (#10) (#1)
- [b2afcf8] Initial commit

9
MAINTAINERS.md Normal file
View File

@ -0,0 +1,9 @@
# Maintainers
Current active maintainers of this SDK:
- [William Lam](https://github.com/lamw)
- [Mark Peek](https://github.com/markpeek
- [Dimitar Milov](https://github.com/dmilov)
- [Michael Gasch](https://github.com/embano1)
- [Simeon Gerginov](https://github.com/SimeonGerginov)

View File

@ -1,5 +1,7 @@
# PowerShell 7.0 SDK for CloudEvents based on [.NET SDK for CloudEvents](https://github.com/cloudevents/sdk-csharp)
Official CloudEvents SDK to integrate your application with CloudEvents.
## Status
Supported CloudEvents versions:
@ -26,16 +28,17 @@ Install-Module CloudEvents.Sdk
Import-Module CloudEvents.Sdk
Get-Command -Module CloudEvents.Sdk
CommandType Name Version Source ----------- ---- ------- ------
Function ConvertFrom-HttpMessage 0.2.0 CloudEvents.Sdk
Function ConvertTo-HttpMessage 0.2.0 CloudEvents.Sdk
Function New-CloudEvent 0.2.0 CloudEvents.Sdk
Function Read-CloudEventData 0.2.0 CloudEvents.Sdk
Function Read-CloudEventJsonData 0.2.0 CloudEvents.Sdk
Function Read-CloudEventXmlData 0.2.0 CloudEvents.Sdk
Function Set-CloudEventData 0.2.0 CloudEvents.Sdk
Function Set-CloudEventJsonData 0.2.0 CloudEvents.Sdk
Function Set-CloudEventXmlData 0.2.0 CloudEvents.Sdk
CommandType Name Version Source
----------- ---- ------- ------
Function ConvertFrom-HttpMessage 0.3.0 CloudEvents.Sdk
Function ConvertTo-HttpMessage 0.3.0 CloudEvents.Sdk
Function New-CloudEvent 0.3.0 CloudEvents.Sdk
Function Read-CloudEventData 0.3.0 CloudEvents.Sdk
Function Read-CloudEventJsonData 0.3.0 CloudEvents.Sdk
Function Read-CloudEventXmlData 0.3.0 CloudEvents.Sdk
Function Set-CloudEventData 0.3.0 CloudEvents.Sdk
Function Set-CloudEventJsonData 0.3.0 CloudEvents.Sdk
Function Set-CloudEventXmlData 0.3.0 CloudEvents.Sdk
```
## Using **`CloudEvents.Sdk`** Module
@ -73,7 +76,7 @@ $cloudEvent | Set-CloudEventXmlData -Data @{
'xml' = @{
'Foo' = 'Hello'
'Bar' = 'World'
}
}
} `
-AttributesKeysInElementAttributes $true
@ -158,4 +161,41 @@ Read-CloudEventData -CloudEvent $cloudEvent
108
100
33
```
```
## Community
- There are bi-weekly calls immediately following the
[Serverless/CloudEvents call](https://github.com/cloudevents/spec#meeting-time)
at 9am PT (US Pacific). Which means they will typically start at 10am PT, but
if the other call ends early then the SDK call will start early as well. See
the
[CloudEvents meeting minutes](https://docs.google.com/document/d/1OVF68rpuPK5shIHILK9JOqlZBbfe91RNzQ7u_P7YCDE/edit#)
to determine which week will have the call.
- Slack: #cloudeventssdk channel under
[CNCF's Slack workspace](https://slack.cncf.io/).
- Email: https://lists.cncf.io/g/cncf-cloudevents-sdk
- Contact for additional information: Michael Gasch (`@Michael Gasch`
on slack).
Each SDK may have its own unique processes, tooling and guidelines, common
governance related material can be found in the
[CloudEvents `community`](https://github.com/cloudevents/spec/tree/master/community)
directory. In particular, in there you will find information concerning
how SDK projects are
[managed](https://github.com/cloudevents/spec/blob/master/community/SDK-GOVERNANCE.md),
[guidelines](https://github.com/cloudevents/spec/blob/master/community/SDK-maintainer-guidelines.md)
for how PR reviews and approval, and our
[Code of Conduct](https://github.com/cloudevents/spec/blob/master/community/GOVERNANCE.md#additional-information)
information.
If there is a security concern with one of the CloudEvents specifications, or
with one of the project's SDKs, please send an email to
[cncf-cloudevents-security@lists.cncf.io](mailto:cncf-cloudevents-security@lists.cncf.io).
## Additional SDK Resources
- [List of current active maintainers](MAINTAINERS.md)
- [How to contribute to the project](CONTRIBUTING.md)
- [SDK's License](LICENSE)
- [SDK's Release process](RELEASING.md)

57
RELEASING.md Normal file
View File

@ -0,0 +1,57 @@
# How to create a Release
We use `tags` to drive the creation of the releases. This is handled by the
Github Actions release workflow in
[`ps-ce-sdk-release.yaml`](.github/workflows/ps-ce-sdk-release.yaml).
A new release will upload the `PowerShell` module artifacts to the `PowerShell`
[gallery](https://www.powershellgallery.com/packages/CloudEvents.Sdk).
## Step 1 - Bump Module Version
Bump the `ModuleVersion` in
[`src/CloudEventsPowerShell/CloudEvents.Sdk.psd1`](./src/CloudEventsPowerShell/CloudEvents.Sdk.psd1)
to the next semantic release version (without `"v"` prefix).
```powershell
# Version number of this module.
ModuleVersion = '0.3.0'
```
Create a pull request with this change, review and approve it **after** all checks
have passed.
## Step 2 - Update local `main` branch
Pull in the latest changes, incl. the merged PR above, into your local `main`
branch of this repository **before** creating a `tag` via the `git` CLI.
```console
git checkout main
git fetch -avp
git pull upstream main
```
**Note:** the above commands assume `upstream` pointing to the remote
`https://github.com/cloudevents/sdk-powershell.git`
## Step 3 - Create and push a Tag
```console
RELEASE=v0.3.0
git tag -a $RELEASE -m "Release ${RELEASE}"
git push upstream refs/tags/${RELEASE}
```
This will trigger the release
[workflow](https://github.com/cloudevents/sdk-powershell/actions/workflows/ps-ce-sdk-release.yaml).
**Verify** that it executed successfully and that a new Github
[release](https://github.com/cloudevents/sdk-powershell/releases) was created.
The release workflow also creates a pull request with the updated
[`CHANGELOG.md`](CHANGELOG.md). **Verify**, approve and merge accordingly.
If you need to make changes to the Github release notes, you can edit them on the [release](https://github.com/cloudevents/sdk-powershell/releases) page.

View File

@ -9,7 +9,7 @@
RootModule = 'CloudEvents.Sdk.psm1'
# Version number of this module.
ModuleVersion = '0.3.0'
ModuleVersion = '0.3.3'
# Supported PSEditions
CompatiblePSEditions = @('Core')
@ -80,5 +80,38 @@ VariablesToExport = '*'
# Aliases to export from this module, for best performance, do not use wildcards and do not delete the entry, use an empty array if there are no aliases to export.
AliasesToExport = @()
# Private data to pass to the module specified in RootModule/ModuleToProcess. This may also contain a PSData hashtable with additional module metadata used by PowerShell.
PrivateData = @{
PSData = @{
# Tags applied to this module. These help with module discovery in online galleries.
Tags = 'CloudEvents','SDK'
# A URL to the license for this module.
# LicenseUri = ''
# A URL to the main website for this project.
ProjectUri = 'https://github.com/cloudevents/sdk-powershell'
# A URL to an icon representing this module.
# IconUri = ''
# ReleaseNotes of this module
# ReleaseNotes = ''
# Prerelease string of this module
# Prerelease = ''
# Flag to indicate whether the module requires explicit user acceptance for install/update
# RequireLicenseAcceptance = $false
# External dependent modules of this module
# ExternalModuleDependencies = @()
} # End of PSData hashtable
} # End of PrivateData hashtable
}

View File

@ -7,7 +7,7 @@ $xmlDataSerilizationLibPath = Join-Path (Join-Path $PSScriptRoot 'dataserializat
. $xmlDataSerilizationLibPath
function New-CloudEvent {
<#
<#
.SYNOPSIS
This function creates a new cloud event.
@ -35,46 +35,46 @@ function New-CloudEvent {
Creates a cloud event with Type, Source, Id, and Time
#>
[CmdletBinding()]
param(
[Parameter(Mandatory = $true)]
[ValidateNotNullOrEmpty()]
[string]
$Type,
[CmdletBinding()]
param(
[Parameter(Mandatory = $true)]
[ValidateNotNullOrEmpty()]
[string]
$Type,
[Parameter(Mandatory = $true)]
[ValidateNotNullOrEmpty()]
[System.Uri]
$Source,
[Parameter(Mandatory = $true)]
[ValidateNotNullOrEmpty()]
[System.Uri]
$Source,
[Parameter(Mandatory = $true)]
[ValidateNotNullOrEmpty()]
[string]
$Id,
[Parameter(Mandatory = $true)]
[ValidateNotNullOrEmpty()]
[string]
$Id,
[Parameter(Mandatory = $false)]
[ValidateNotNullOrEmpty()]
[DateTime]
$Time
)
[Parameter(Mandatory = $false)]
[ValidateNotNullOrEmpty()]
[DateTime]
$Time
)
PROCESS {
$cloudEvent = New-Object `
-TypeName 'CloudNative.CloudEvents.CloudEvent' `
-ArgumentList @(
$Type,
$Source,
$Id,
$Time,
@())
PROCESS {
$cloudEvent = New-Object `
-TypeName 'CloudNative.CloudEvents.CloudEvent' `
-ArgumentList @(
$Type,
$Source,
$Id,
$Time,
@())
Write-Output $cloudEvent
}
Write-Output $cloudEvent
}
}
#region Set Data Functions
function Set-CloudEventData {
<#
<#
.SYNOPSIS
This function sets data in a cloud event.
@ -98,45 +98,45 @@ function Set-CloudEventData {
Sets xml data to the cloud event
#>
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[Parameter(Mandatory = $true,
ValueFromPipeline = $false)]
[ValidateNotNullOrEmpty()]
[object]
$Data,
[Parameter(Mandatory = $true,
ValueFromPipeline = $false)]
[ValidateNotNullOrEmpty()]
[object]
$Data,
# CloudEvent 'datacontenttype' attribute. Content type of the 'data' attribute value.
# This attribute enables the data attribute to carry any type of content, whereby
# format and encoding might differ from that of the chosen event format.
[Parameter(Mandatory = $false,
ValueFromPipeline = $false)]
[string]
$DataContentType)
# CloudEvent 'datacontenttype' attribute. Content type of the 'data' attribute value.
# This attribute enables the data attribute to carry any type of content, whereby
# format and encoding might differ from that of the chosen event format.
[Parameter(Mandatory = $false,
ValueFromPipeline = $false)]
[string]
$DataContentType)
PROCESS {
PROCESS {
# https://github.com/cloudevents/spec/blob/master/spec.md#datacontenttype
$contentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ($DataContentType)
# https://github.com/cloudevents/spec/blob/master/spec.md#datacontenttype
$contentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ($DataContentType)
$cloudEvent.Data = $Data
$cloudEvent.DataContentType = $dataContentType
$cloudEvent.Data = $Data
$cloudEvent.DataContentType = $dataContentType
Write-Output $CloudEvent
}
Write-Output $CloudEvent
}
}
function Set-CloudEventJsonData {
<#
<#
.SYNOPSIS
This function sets JSON format data in a cloud event.
@ -163,43 +163,43 @@ function Set-CloudEventJsonData {
Sets JSON data to the cloud event
#>
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[Parameter(Mandatory = $true,
ValueFromPipeline = $false)]
[ValidateNotNull()]
[Hashtable]
$Data,
[Parameter(Mandatory = $true,
ValueFromPipeline = $false)]
[ValidateNotNull()]
[Hashtable]
$Data,
[Parameter(Mandatory = $false,
ValueFromPipeline = $false)]
[int]
$Depth = 3)
[Parameter(Mandatory = $false,
ValueFromPipeline = $false)]
[int]
$Depth = 3)
PROCESS {
PROCESS {
# DataContentType is set to 'application/json'
# https://github.com/cloudevents/spec/blob/master/spec.md#datacontenttype
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Json)
# DataContentType is set to 'application/json'
# https://github.com/cloudevents/spec/blob/master/spec.md#datacontenttype
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Json)
$cloudEvent.DataContentType = $dataContentType
$cloudEvent.Data = ConvertTo-Json -InputObject $Data -Depth $Depth
$cloudEvent.DataContentType = $dataContentType
$cloudEvent.Data = ConvertTo-Json -InputObject $Data -Depth $Depth
Write-Output $CloudEvent
}
Write-Output $CloudEvent
}
}
function Set-CloudEventXmlData {
<#
<#
.SYNOPSIS
This function sets XML format data in a cloud event.
@ -229,43 +229,43 @@ function Set-CloudEventXmlData {
Sets XML data in the cloud event
#>
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[Parameter(Mandatory = $true,
ValueFromPipeline = $false)]
[ValidateNotNull()]
[Hashtable]
$Data,
[Parameter(Mandatory = $true,
ValueFromPipeline = $false)]
[ValidateNotNull()]
[Hashtable]
$Data,
[Parameter(Mandatory = $true)]
[bool]
$AttributesKeysInElementAttributes)
[Parameter(Mandatory = $true)]
[bool]
$AttributesKeysInElementAttributes)
PROCESS {
PROCESS {
# DataContentType is set to 'application/xml'
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Xml)
# DataContentType is set to 'application/xml'
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Xml)
$cloudEvent.DataContentType = $dataContentType
$cloudEvent.Data = ConvertTo-CEDataXml -InputObject $Data -AttributesKeysInElementAttributes $AttributesKeysInElementAttributes
$cloudEvent.DataContentType = $dataContentType
$cloudEvent.Data = ConvertTo-CEDataXml -InputObject $Data -AttributesKeysInElementAttributes $AttributesKeysInElementAttributes
Write-Output $CloudEvent
}
Write-Output $CloudEvent
}
}
#endregion Set Data Functions
#region Read Data Functions
function Read-CloudEventData {
<#
<#
.SYNOPSIS
This function gets the data from a cloud event.
@ -282,23 +282,23 @@ function Read-CloudEventData {
Reads data from a cloud event received on the http response
#>
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent
)
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent
)
PROCESS {
Write-Output $CloudEvent.Data
}
PROCESS {
Write-Output $CloudEvent.Data
}
}
function Read-CloudEventJsonData {
<#
<#
.SYNOPSIS
This function gets JSON fromat data from a cloud event as a PowerShell hashtable.
@ -320,56 +320,57 @@ function Read-CloudEventJsonData {
#>
<#
<#
.DESCRIPTION
Returns PowerShell hashtable that represents the CloudEvent Json Data
if the data content type is 'application/json', otherwise otherwise non-terminating error and no result
#>
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[Parameter(Mandatory = $false,
ValueFromPipeline = $false)]
[int]
$Depth = 3
)
[Parameter(Mandatory = $false,
ValueFromPipeline = $false)]
[int]
$Depth = 3
)
PROCESS {
PROCESS {
# DataContentType is expected to be 'application/json'
# https://github.com/cloudevents/spec/blob/master/spec.md#datacontenttype
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Json)
# DataContentType is expected to be 'application/json'
# https://github.com/cloudevents/spec/blob/master/spec.md#datacontenttype
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Json)
if ($CloudEvent.DataContentType -eq $dataContentType -or `
($CloudEvent.DataContentType -eq $null -and ` # Datacontent Type is Optional, if it is not specified we assume it is JSON as per https://github.com/cloudevents/spec/blob/v1.0.1/spec.md#datacontenttype
$cloudEvent.Data -is [Newtonsoft.Json.Linq.JObject])) {
if ($CloudEvent.DataContentType -eq $dataContentType -or `
($CloudEvent.DataContentType -eq $null -and # Datacontent Type is Optional, if it is not specified we assume it is JSON as per https://github.com/cloudevents/spec/blob/v1.0.1/spec.md#datacontenttype
$cloudEvent.Data -is [Newtonsoft.Json.Linq.JObject])) {
$data = $cloudEvent.Data
$data = $cloudEvent.Data
if ($cloudEvent.Data -is [byte[]]) {
$data = [System.Text.Encoding]::UTF8.GetString($data)
}
if ($cloudEvent.Data -is [byte[]]) {
$data = [System.Text.Encoding]::UTF8.GetString($data)
}
$result = $data.ToString() | ConvertFrom-Json -AsHashtable -Depth $Depth
$result = $data.ToString() | ConvertFrom-Json -AsHashtable -Depth $Depth
Write-Output $result
} else {
Write-Error "Cloud Event '$($cloudEvent.Id)' has no json data"
}
}
Write-Output $result
}
else {
Write-Error "Cloud Event '$($cloudEvent.Id)' has no json data"
}
}
}
function Read-CloudEventXmlData {
<#
<#
.SYNOPSIS
This function gets XML fromat data from a cloud event as a PowerShell hashtable.
@ -430,55 +431,56 @@ function Read-CloudEventXmlData {
#>
<#
<#
.DESCRIPTION
Returns PowerShell hashtable that represents the CloudEvent Xml Data
if the data content type is 'application/xml', otherwise non-terminating error and no result
#>
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[CmdletBinding()]
param(
[Parameter(Mandatory = $true,
ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[Parameter(Mandatory = $true)]
[ValidateSet("SkipAttributes", "AlwaysAttrValue", "AttrValueWhenAttributes")]
[string]
$ConvertMode
)
[Parameter(Mandatory = $true)]
[ValidateSet("SkipAttributes", "AlwaysAttrValue", "AttrValueWhenAttributes")]
[string]
$ConvertMode
)
PROCESS {
PROCESS {
# DataContentType is expected to be 'application/xml'
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Xml)
# DataContentType is expected to be 'application/xml'
$dataContentType = New-Object `
-TypeName 'System.Net.Mime.ContentType' `
-ArgumentList ([System.Net.Mime.MediaTypeNames+Application]::Xml)
if ($CloudEvent.DataContentType -eq $dataContentType) {
if ($CloudEvent.DataContentType -eq $dataContentType) {
$data = $cloudEvent.Data
$data = $cloudEvent.Data
if ($cloudEvent.Data -is [byte[]]) {
$data = [System.Text.Encoding]::UTF8.GetString($data)
}
if ($cloudEvent.Data -is [byte[]]) {
$data = [System.Text.Encoding]::UTF8.GetString($data)
}
$result = $data.ToString() | ConvertFrom-CEDataXml -ConvertMode $ConvertMode
$result = $data.ToString() | ConvertFrom-CEDataXml -ConvertMode $ConvertMode
Write-Output $result
} else {
Write-Error "Cloud Event '$($cloudEvent.Id)' has no xml data"
}
}
Write-Output $result
}
else {
Write-Error "Cloud Event '$($cloudEvent.Id)' has no xml data"
}
}
}
#endregion Read Data Functions
#region HTTP Protocol Binding Conversion Functions
function ConvertTo-HttpMessage {
<#
<#
.SYNOPSIS
This function converts a cloud event object to a Http Message.
@ -519,121 +521,121 @@ function ConvertTo-HttpMessage {
Sends a cloud event http requests to a server
#>
[CmdletBinding()]
param(
[Parameter(
Mandatory = $true,
ValueFromPipeline = $true,
ValueFromPipelineByPropertyName = $false)]
[ValidateNotNull()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[CmdletBinding()]
param(
[Parameter(
Mandatory = $true,
ValueFromPipeline = $true,
ValueFromPipelineByPropertyName = $false)]
[ValidateNotNull()]
[CloudNative.CloudEvents.CloudEvent]
$CloudEvent,
[Parameter(
Mandatory = $true,
ValueFromPipeline = $false,
ValueFromPipelineByPropertyName = $false)]
[CloudNative.CloudEvents.ContentMode]
$ContentMode)
[Parameter(
Mandatory = $true,
ValueFromPipeline = $false,
ValueFromPipelineByPropertyName = $false)]
[CloudNative.CloudEvents.ContentMode]
$ContentMode)
PROCESS {
# Output Object
$result = New-Object -TypeName PSCustomObject
PROCESS {
# Output Object
$result = New-Object -TypeName PSCustomObject
$cloudEventFormatter = New-Object 'CloudNative.CloudEvents.JsonEventFormatter'
$cloudEventFormatter = New-Object 'CloudNative.CloudEvents.JsonEventFormatter'
$HttpHeaderPrefix = "ce-";
$SpecVersionHttpHeader1 = $HttpHeaderPrefix + "cloudEventsVersion";
$SpecVersionHttpHeader2 = $HttpHeaderPrefix + "specversion";
$HttpHeaderPrefix = "ce-";
$SpecVersionHttpHeader1 = $HttpHeaderPrefix + "cloudEventsVersion";
$SpecVersionHttpHeader2 = $HttpHeaderPrefix + "specversion";
$headers = @{}
$headers = @{}
# Build HTTP headers
foreach ($attribute in $cloudEvent.GetAttributes()) {
if (-not $attribute.Key.Equals([CloudNative.CloudEvents.CloudEventAttributes]::DataAttributeName($cloudEvent.SpecVersion)) -and `
-not $attribute.Key.Equals([CloudNative.CloudEvents.CloudEventAttributes]::DataContentTypeAttributeName($cloudEvent.SpecVersion))) {
if ($attribute.Value -is [string]) {
$headers.Add(($HttpHeaderPrefix + $attribute.Key), $attribute.Value.ToString())
}
elseif ($attribute.Value -is [DateTime]) {
$headers.Add(($HttpHeaderPrefix + $attribute.Key), $attribute.Value.ToUniversalTime().ToString('yyyy-MM-ddTHH:mm:ss.fffZ'))
}
elseif ($attribute.Value -is [Uri] -or $attribute.Value -is [int]) {
$headers.Add(($HttpHeaderPrefix + $attribute.Key), $attribute.Value.ToString())
}
else
{
$headers.Add(($HttpHeaderPrefix + $attribute.Key),
[System.Text.Encoding]::UTF8.GetString($cloudEventFormatter.EncodeAttribute($cloudEvent.SpecVersion, $attribute.Key,
$attribute.Value,
$cloudEvent.Extensions.Values)));
}
}
}
# Add Headers property to the output object
$result | Add-Member -MemberType NoteProperty -Name 'Headers' -Value $headers
# Process Structured Mode
# Structured Mode supports non-batching JSON format only
# https://github.com/cloudevents/spec/blob/v1.0.1/http-protocol-binding.md#14-event-formats
if ($ContentMode -eq [CloudNative.CloudEvents.ContentMode]::Structured) {
# Format Body as byte[]
$contentType = $null
# CloudEventFormatter is instance of 'CloudNative.CloudEvents.JsonEventFormatter' from the
# .NET CloudEvents SDK for the purpose of fomatting structured mode
$buffer = $cloudEventFormatter.EncodeStructuredEvent($cloudEvent, [ref] $contentType)
$result | Add-Member -MemberType NoteProperty -Name 'Body' -Value $buffer
$result.Headers.Add('Content-Type', $contentType)
}
# Process Binary Mode
if ($ContentMode -eq [CloudNative.CloudEvents.ContentMode]::Binary) {
$bodyData = $null
if ($cloudEvent.DataContentType -ne $null) {
$result.Headers.Add('Content-Type', $cloudEvent.DataContentType)
}
if ($cloudEvent.Data -is [byte[]]) {
$bodyData = $cloudEvent.Data
}
elseif ($cloudEvent.Data -is [string]) {
$bodyData = [System.Text.Encoding]::UTF8.GetBytes($cloudEvent.Data.ToString())
}
elseif ($cloudEvent.Data -is [IO.Stream]) {
$buffer = New-Object 'byte[]' -ArgumentList 1024
$ms = New-Object 'IO.MemoryStream'
try {
$read = 0
while (($read = $cloudEvent.Data.Read($buffer, 0, 1024)) -gt 0)
{
$ms.Write($buffer, 0, $read);
# Build HTTP headers
foreach ($attribute in $cloudEvent.GetAttributes()) {
if (-not $attribute.Key.Equals([CloudNative.CloudEvents.CloudEventAttributes]::DataAttributeName($cloudEvent.SpecVersion)) -and `
-not $attribute.Key.Equals([CloudNative.CloudEvents.CloudEventAttributes]::DataContentTypeAttributeName($cloudEvent.SpecVersion))) {
if ($attribute.Value -is [string]) {
$headers.Add(($HttpHeaderPrefix + $attribute.Key), $attribute.Value.ToString())
}
elseif ($attribute.Value -is [DateTime]) {
$headers.Add(($HttpHeaderPrefix + $attribute.Key), $attribute.Value.ToUniversalTime().ToString('yyyy-MM-ddTHH:mm:ss.fffZ'))
}
elseif ($attribute.Value -is [Uri] -or $attribute.Value -is [int]) {
$headers.Add(($HttpHeaderPrefix + $attribute.Key), $attribute.Value.ToString())
}
else {
$headers.Add(($HttpHeaderPrefix + $attribute.Key),
[System.Text.Encoding]::UTF8.GetString($cloudEventFormatter.EncodeAttribute($cloudEvent.SpecVersion, $attribute.Key,
$attribute.Value,
$cloudEvent.Extensions.Values)));
}
}
$bodyData = $ms.ToArray()
} finally {
$ms.Dispose()
}
}
} else {
$bodyData = $cloudEventFormatter.EncodeAttribute($cloudEvent.SpecVersion,
[CloudNative.CloudEvents.CloudEventAttributes]::DataAttributeName($cloudEvent.SpecVersion),
$cloudEvent.Data, $cloudEvent.Extensions.Values)
}
# Add Headers property to the output object
$result | Add-Member -MemberType NoteProperty -Name 'Headers' -Value $headers
# Add Body property to the output object
$result | Add-Member -MemberType NoteProperty -Name 'Body' -Value $bodyData
}
# Process Structured Mode
# Structured Mode supports non-batching JSON format only
# https://github.com/cloudevents/spec/blob/v1.0.1/http-protocol-binding.md#14-event-formats
if ($ContentMode -eq [CloudNative.CloudEvents.ContentMode]::Structured) {
# Format Body as byte[]
$contentType = $null
Write-Output $result
}
# CloudEventFormatter is instance of 'CloudNative.CloudEvents.JsonEventFormatter' from the
# .NET CloudEvents SDK for the purpose of fomatting structured mode
$buffer = $cloudEventFormatter.EncodeStructuredEvent($cloudEvent, [ref] $contentType)
$result | Add-Member -MemberType NoteProperty -Name 'Body' -Value $buffer
$result.Headers.Add('Content-Type', $contentType)
}
# Process Binary Mode
if ($ContentMode -eq [CloudNative.CloudEvents.ContentMode]::Binary) {
$bodyData = $null
if ($cloudEvent.DataContentType -ne $null) {
$result.Headers.Add('Content-Type', $cloudEvent.DataContentType)
}
if ($cloudEvent.Data -is [byte[]]) {
$bodyData = $cloudEvent.Data
}
elseif ($cloudEvent.Data -is [string]) {
$bodyData = [System.Text.Encoding]::UTF8.GetBytes($cloudEvent.Data.ToString())
}
elseif ($cloudEvent.Data -is [IO.Stream]) {
$buffer = New-Object 'byte[]' -ArgumentList 1024
$ms = New-Object 'IO.MemoryStream'
try {
$read = 0
while (($read = $cloudEvent.Data.Read($buffer, 0, 1024)) -gt 0) {
$ms.Write($buffer, 0, $read);
}
$bodyData = $ms.ToArray()
}
finally {
$ms.Dispose()
}
}
else {
$bodyData = $cloudEventFormatter.EncodeAttribute($cloudEvent.SpecVersion,
[CloudNative.CloudEvents.CloudEventAttributes]::DataAttributeName($cloudEvent.SpecVersion),
$cloudEvent.Data, $cloudEvent.Extensions.Values)
}
# Add Body property to the output object
$result | Add-Member -MemberType NoteProperty -Name 'Body' -Value $bodyData
}
Write-Output $result
}
}
function ConvertFrom-HttpMessage {
<#
<#
.SYNOPSIS
This function converts a Http Message to a cloud event object
@ -655,136 +657,150 @@ function ConvertFrom-HttpMessage {
Converts a http response to a cloud event object
#>
[CmdletBinding()]
param(
[Parameter(
Mandatory = $true,
ValueFromPipeline = $false,
ValueFromPipelineByPropertyName = $false)]
[ValidateNotNull()]
[hashtable]
$Headers,
[CmdletBinding()]
param(
[Parameter(
Mandatory = $true,
ValueFromPipeline = $false,
ValueFromPipelineByPropertyName = $false)]
[ValidateNotNull()]
[hashtable]
$Headers,
[Parameter(
Mandatory = $false,
ValueFromPipeline = $false,
ValueFromPipelineByPropertyName = $false)]
[ValidateNotNull()]
$Body)
[Parameter(
Mandatory = $false,
ValueFromPipeline = $false,
ValueFromPipelineByPropertyName = $false)]
[ValidateNotNull()]
$Body)
PROCESS {
$HttpHeaderPrefix = "ce-";
$SpecVersionHttpHeader1 = $HttpHeaderPrefix + "cloudEventsVersion";
$SpecVersionHttpHeader2 = $HttpHeaderPrefix + "specversion";
PROCESS {
$HttpHeaderPrefix = "ce-";
$SpecVersionHttpHeader = $HttpHeaderPrefix + "specversion";
$result = $null
$result = $null
# Always Convert Body to byte[]
# Conversion works with byte[] while
# body can be string in HTTP responses
# for text content type
if ($Body -is [string]) {
$Body = [System.Text.Encoding]::UTF8.GetBytes($Body)
}
# Always Convert Body to byte[]
# Conversion works with byte[] while
# body can be string in HTTP responses
# for text content type
if ($Body -is [string]) {
$Body = [System.Text.Encoding]::UTF8.GetBytes($Body)
}
if ($Headers['Content-Type'] -ne $null) {
$ContentType = $Headers['Content-Type']
if ($ContentType -is [array]) {
# Get the first content-type value
$ContentType = $ContentType[0]
}
if ($ContentType.StartsWith([CloudNative.CloudEvents.CloudEvent]::MediaType,
[StringComparison]::InvariantCultureIgnoreCase)) {
# Handle Structured Mode
$ctParts = $ContentType.Split(';')
if ($ctParts[0].Trim().StartsWith(([CloudNative.CloudEvents.CloudEvent]::MediaType) + ([CloudNative.CloudEvents.JsonEventFormatter]::MediaTypeSuffix),
[StringComparison]::InvariantCultureIgnoreCase)) {
# Structured Mode supports non-batching JSON format only
# https://github.com/cloudevents/spec/blob/v1.0.1/http-protocol-binding.md#14-event-formats
# .NET SDK 'CloudNative.CloudEvents.JsonEventFormatter' type is used
# to decode the Structured Mode CloudEvents
$json = [System.Text.Encoding]::UTF8.GetString($Body)
$jObject = [Newtonsoft.Json.Linq.JObject]::Parse($json)
$formatter = New-Object 'CloudNative.CloudEvents.JsonEventFormatter'
$result = $formatter.DecodeJObject($jObject, $null)
$result.Data = $result.Data
} else {
# Throw error for unsupported encoding
throw "Unsupported CloudEvents encoding"
}
} else {
# Handle Binary Mode
$version = [CloudNative.CloudEvents.CloudEventsSpecVersion]::Default
if ($Headers.Contains($SpecVersionHttpHeader1)) {
$version = [CloudNative.CloudEvents.CloudEventsSpecVersion]::V0_1
}
if ($Headers.Contains($SpecVersionHttpHeader2)) {
if ($Headers[$SpecVersionHttpHeader2][0] -eq "0.2") {
$version = [CloudNative.CloudEvents.CloudEventsSpecVersion]::V0_2
} elseif ($Headers[$SpecVersionHttpHeader2][0] -eq "0.3") {
$version = [CloudNative.CloudEvents.CloudEventsSpecVersion]::V0_3
if ($null -ne $Headers['Content-Type']) {
$ContentType = $Headers['Content-Type']
if ($ContentType -is [array]) {
# Get the first content-type value
$ContentType = $ContentType[0]
}
}
$cloudEvent = New-Object `
-TypeName 'CloudNative.CloudEvents.CloudEvent' `
-ArgumentList @($version, $null);
if ($ContentType.StartsWith([CloudNative.CloudEvents.CloudEvent]::MediaType,
[StringComparison]::InvariantCultureIgnoreCase)) {
$attributes = $cloudEvent.GetAttributes();
# Handle Structured Mode
$ctParts = $ContentType.Split(';')
if ($ctParts[0].Trim().StartsWith(([CloudNative.CloudEvents.CloudEvent]::MediaType) + ([CloudNative.CloudEvents.JsonEventFormatter]::MediaTypeSuffix),
[StringComparison]::InvariantCultureIgnoreCase)) {
# Get attributes from HTTP Headers
foreach ($httpHeader in $Headers.GetEnumerator()) {
if ($httpHeader.Key.Equals($SpecVersionHttpHeader1, [StringComparison]::InvariantCultureIgnoreCase) -or `
$httpHeader.Key.Equals($SpecVersionHttpHeader2, [StringComparison]::InvariantCultureIgnoreCase)) {
continue
}
# Structured Mode supports non-batching JSON format only
# https://github.com/cloudevents/spec/blob/v1.0.1/http-protocol-binding.md#14-event-formats
if ($httpHeader.Key.StartsWith($HttpHeaderPrefix, [StringComparison]::InvariantCultureIgnoreCase)) {
$headerValue = $httpHeader.Value
if ($headerValue -is [array]) {
# Get the first object
$headerValue = $headerValue[0]
}
$name = $httpHeader.Key.Substring(3);
# .NET SDK 'CloudNative.CloudEvents.JsonEventFormatter' type is used
# to decode the Structured Mode CloudEvents
# Abolished structures in headers in 1.0
if ($version -ne [CloudNative.CloudEvents.CloudEventsSpecVersion]::V0_1 -and `
$headerValue -ne $null -and `
$headerValue.StartsWith('"') -and `
$headerValue.EndsWith('"') -or `
$headerValue.StartsWith("'") -and $headerValue.EndsWith("'") -or `
$headerValue.StartsWith("{") -and $headerValue.EndsWith("}") -or `
$headerValue.StartsWith("[") -and $headerValue.EndsWith("]")) {
$json = [System.Text.Encoding]::UTF8.GetString($Body)
$jObject = [Newtonsoft.Json.Linq.JObject]::Parse($json)
$formatter = New-Object 'CloudNative.CloudEvents.JsonEventFormatter'
$result = $formatter.DecodeJObject($jObject, $null)
$jsonFormatter = New-Object 'CloudNative.CloudEvents.JsonEventFormatter'
$result.Data = $result.Data
}
else {
# Throw error for unsupported encoding
throw "Unsupported CloudEvents encoding"
}
}
else {
# Handle Binary Mode
$version = $null
if ($Headers.Contains($SpecVersionHttpHeader) -and `
$null -ne $Headers[$SpecVersionHttpHeader] -and `
($Headers[$SpecVersionHttpHeader] | Select-Object -First 1).StartsWith('1.0')) {
# We do support the 1.0 cloud event version
$version = [CloudNative.CloudEvents.CloudEventsSpecVersion]::V1_0
}
$attributes[$name] = $jsonFormatter.DecodeAttribute($version, $name,
[System.Text.Encoding]::UTF8.GetBytes($headerValue), $null);
} else {
$attributes[$name] = $headerValue
}
}
}
if ($null -ne $version) {
# SpecVersion is REQUIRED attribute, it it is not specified this is not a CloudEvent
# https://github.com/cloudevents/spec/blob/v1.0.1/spec.md#specversion
$cloudEvent = New-Object `
-TypeName 'CloudNative.CloudEvents.CloudEvent' `
-ArgumentList @($version, $null);
if ($Headers['Content-Type'] -ne $null -and $Headers['Content-Type'][0] -is [string]) {
$cloudEvent.DataContentType = New-Object 'System.Net.Mime.ContentType' -ArgumentList @($Headers['Content-Type'][0])
}
$attributes = $cloudEvent.GetAttributes();
# Get Data from HTTP Body
$cloudEvent.Data = $Body
# Get attributes from HTTP Headers
foreach ($httpHeader in $Headers.GetEnumerator()) {
if ($httpHeader.Key.Equals($SpecVersionHttpHeader, [StringComparison]::InvariantCultureIgnoreCase)) {
continue
}
$result = $cloudEvent
}
}
if ($httpHeader.Key.StartsWith($HttpHeaderPrefix, [StringComparison]::InvariantCultureIgnoreCase)) {
$headerValue = $httpHeader.Value
if ($headerValue -is [array]) {
# Get the first object
$headerValue = $headerValue[0]
}
$name = $httpHeader.Key.Substring(3);
Write-Output $result
}
# Abolished structures in headers in 1.0
if ( $null -ne $headerValue -and `
$headerValue.StartsWith('"') -and `
$headerValue.EndsWith('"') -or `
$headerValue.StartsWith("'") -and $headerValue.EndsWith("'") -or `
$headerValue.StartsWith("{") -and $headerValue.EndsWith("}") -or `
$headerValue.StartsWith("[") -and $headerValue.EndsWith("]")) {
$jsonFormatter = New-Object 'CloudNative.CloudEvents.JsonEventFormatter'
$attributes[$name] = $jsonFormatter.DecodeAttribute($version, $name,
[System.Text.Encoding]::UTF8.GetBytes($headerValue), $null);
}
else {
$attributes[$name] = $headerValue
}
}
}
# Verify parsed attributes from HTTP Headers
if ($null -ne $attributes['datacontenttype']) {
# ce-datatype is prohibitted by the protocol -> throw error
# https://github.com/cloudevents/spec/blob/v1.0.1/http-protocol-binding.md#311-http-content-type
throw "'ce-datacontenttype' HTTP header is prohibited for Binary ContentMode CloudEvent"
}
if ($Headers['Content-Type'] -is [string]) {
$cloudEvent.DataContentType = New-Object 'System.Net.Mime.ContentType' -ArgumentList @($Headers['Content-Type'])
} elseif ($Headers['Content-Type'][0] -is [string]) {
$cloudEvent.DataContentType = New-Object 'System.Net.Mime.ContentType' -ArgumentList @($Headers['Content-Type'][0])
}
# Id, Type, and Source are reuiqred to be non-empty strings otherwise consider this is not a CloudEvent
# https://github.com/cloudevents/spec/blob/v1.0.1/spec.md#required-attributes
if ( -not [string]::IsNullOrEmpty($cloudEvent.Id) -and `
-not [string]::IsNullOrEmpty($cloudEvent.Source) -and `
-not [string]::IsNullOrEmpty($cloudEvent.Type)) {
# Get Data from HTTP Body
$cloudEvent.Data = $Body
$result = $cloudEvent
}
}
}
}
Write-Output $result
}
}
#endregion HTTP Protocol Binding Conversion Functions

View File

@ -4,9 +4,9 @@
# **************************************************************************
Describe "ConvertFrom-HttpMessage Function Tests" {
BeforeAll {
$expectedSpecVersion = '1.0'
$expectedStructuredContentType = 'application/cloudevents+json'
BeforeEach {
$script:expectedSpecVersion = '1.0'
$script:expectedStructuredContentType = 'application/cloudevents+json'
}
Context "Converts CloudEvent in Binary Content Mode" {
@ -77,6 +77,7 @@ Describe "ConvertFrom-HttpMessage Function Tests" {
$expectedType = 'test'
$expectedSource = 'urn:test'
$expectedDataContentType = 'application/xml'
$expectedId = 'test-id-2'
$expectedData = [Text.Encoding]::UTF8.GetBytes('<much wow="xml"/>')
$headers = @{
@ -84,6 +85,7 @@ Describe "ConvertFrom-HttpMessage Function Tests" {
'ce-specversion' = $expectedSpecVersion
'ce-type' = $expectedType
'ce-source' = $expectedSource
'ce-id' = $expectedId
}
$body = $expectedData
@ -95,6 +97,7 @@ Describe "ConvertFrom-HttpMessage Function Tests" {
# Assert
$actual | Should -Not -Be $null
$actual.Id | Should -Be $expectedId
$actual.Type | Should -Be $expectedType
$actual.Source | Should -Be $expectedSource
$actual.DataContentType | Should -Be $expectedDataContentType
@ -105,6 +108,81 @@ Describe "ConvertFrom-HttpMessage Function Tests" {
$actualData | Should -Be $expectedData
}
It 'Returns null when ce-id is not specified' {
# Arrange
$expectedType = 'test'
$expectedSource = 'urn:test'
$expectedDataContentType = 'application/xml'
$expectedData = [Text.Encoding]::UTF8.GetBytes('<much wow="xml"/>')
$headers = @{
'Content-Type' = @($expectedDataContentType, 'charset=utf-8')
'ce-specversion' = $expectedSpecVersion
'ce-type' = $expectedType
'ce-source' = $expectedSource
}
$body = $expectedData
# Act
$actual = ConvertFrom-HttpMessage `
-Headers $headers `
-Body $body
# Assert
$actual | Should -Be $null
}
It 'Returns null when ce-source is not specified' {
# Arrange
$expectedType = 'test'
$expectedDataContentType = 'application/xml'
$expectedId = 'test-id-3'
$expectedData = [Text.Encoding]::UTF8.GetBytes('<much wow="xml"/>')
$headers = @{
'Content-Type' = @($expectedDataContentType, 'charset=utf-8')
'ce-specversion' = $expectedSpecVersion
'ce-type' = $expectedType
'ce-id' = $expectedId
}
$body = $expectedData
# Act
$actual = ConvertFrom-HttpMessage `
-Headers $headers `
-Body $body
# Assert
$actual | Should -Be $null
}
It 'Returns null when ce-type is not specified' {
# Arrange
$expectedSource = 'urn:test'
$expectedDataContentType = 'application/xml'
$expectedId = 'test-id-4'
$expectedData = [Text.Encoding]::UTF8.GetBytes('<much wow="xml"/>')
$headers = @{
'Content-Type' = @($expectedDataContentType, 'charset=utf-8')
'ce-specversion' = $expectedSpecVersion
'ce-source' = $expectedSource
'ce-id' = $expectedId
}
$body = $expectedData
# Act
$actual = ConvertFrom-HttpMessage `
-Headers $headers `
-Body $body
# Assert
$actual | Should -Be $null
}
}
Context "Converts CloudEvent in Structured Content Mode" {
@ -245,5 +323,29 @@ Describe "ConvertFrom-HttpMessage Function Tests" {
-Body $body } | `
Should -Throw "*Unsupported CloudEvents encoding*"
}
It 'Returns null when no Content-Type header' {
# Arrange
$expectedType = 'test'
$expectedSource = 'urn:test'
$expectedDataContentType = 'application/xml'
$expectedData = [Text.Encoding]::UTF8.GetBytes('<much wow="xml"/>')
$structuredJsonBody = @{
'specversion' = $expectedSpecVersion
'type' = $expectedType
'source' = $expectedSource
'datacontenttype' = $expectedDataContentType
'data' = $expectedData
}
$body = [Text.Encoding]::UTF8.GetBytes(($structuredJsonBody | ConvertTo-Json))
# Act & Assert
$ce = ConvertFrom-HttpMessage `
-Headers @{} `
-Body $body
$ce | Should -Be $null
}
}
}