Skip to content

Commit 24d34b8

Browse files
authored
Merge pull request #1176 from Gijsreyn/gh-57/main/add-uri-functions
Add `uriComponent()` and `uriComponentToString()` functions
2 parents 735d319 + a80ecfd commit 24d34b8

File tree

10 files changed

+898
-4
lines changed

10 files changed

+898
-4
lines changed

Cargo.lock

Lines changed: 7 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,8 @@ utfx = { version = "0.1" }
194194
# dsc-lib
195195
uuid = { version = "1.18", features = ["v4"] }
196196
# dsc-lib
197+
urlencoding = { version = "2.1" }
198+
# dsc-lib
197199
which = { version = "8.0" }
198200

199201
# build-only dependencies
Lines changed: 271 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,271 @@
1+
---
2+
description: Reference for the 'uriComponent' DSC configuration document function
3+
ms.date: 01/10/2025
4+
ms.topic: reference
5+
title: uriComponent
6+
---
7+
8+
# uriComponent
9+
10+
## Synopsis
11+
12+
Encodes a string for use as a URI component using percent-encoding.
13+
14+
## Syntax
15+
16+
```Syntax
17+
uriComponent(<stringToEncode>)
18+
```
19+
20+
## Description
21+
22+
The `uriComponent()` function encodes a string using percent-encoding (also known as URL encoding)
23+
to make it safe for use as a component of a URI. The function encodes all characters except the
24+
unreserved characters defined in RFC 3986:
25+
26+
- **Unreserved characters** (not encoded): `A-Z`, `a-z`, `0-9`, `-`, `_`, `.`, `~`
27+
- **All other characters** are percent-encoded as `%XX` where `XX` is the hexadecimal value
28+
29+
Use this function when you need to include user-provided data, special characters, or spaces in
30+
URLs, query strings, or other URI components. This ensures that the resulting URI is valid and that
31+
special characters don't break the URI structure.
32+
33+
## Examples
34+
35+
### Example 1 - Encode query parameter value
36+
37+
The following example shows how to encode a string containing spaces for use in a URL query
38+
parameter.
39+
40+
```yaml
41+
# uricomponent.example.1.dsc.config.yaml
42+
$schema: https://aka.ms/dsc/schemas/v3/bundled/config/document.json
43+
parameters:
44+
searchTerm:
45+
type: string
46+
defaultValue: hello world
47+
resources:
48+
- name: Build search URL
49+
type: Microsoft.DSC.Debug/Echo
50+
properties:
51+
output:
52+
original: "[parameters('searchTerm')]"
53+
encoded: "[uriComponent(parameters('searchTerm'))]"
54+
fullUrl: "[concat('https://example.com/search?q=', uriComponent(parameters('searchTerm')))]"
55+
```
56+
57+
```bash
58+
dsc config get --file uricomponent.example.1.dsc.config.yaml
59+
```
60+
61+
```yaml
62+
results:
63+
- name: Build search URL
64+
type: Microsoft.DSC.Debug/Echo
65+
result:
66+
actualState:
67+
output:
68+
original: hello world
69+
encoded: hello%20world
70+
fullUrl: https://example.com/search?q=hello%20world
71+
messages: []
72+
hadErrors: false
73+
```
74+
75+
### Example 2 - Encode email address
76+
77+
The following example demonstrates encoding an email address that contains special characters.
78+
79+
```yaml
80+
# uricomponent.example.2.dsc.config.yaml
81+
$schema: https://aka.ms/dsc/schemas/v3/bundled/config/document.json
82+
parameters:
83+
email:
84+
type: string
85+
defaultValue: [email protected]
86+
resources:
87+
- name: Encode email for URL
88+
type: Microsoft.DSC.Debug/Echo
89+
properties:
90+
output:
91+
encoded: "[uriComponent(parameters('email'))]"
92+
mailtoLink: "[concat('mailto:', uriComponent(parameters('email')))]"
93+
```
94+
95+
```bash
96+
dsc config get --file uricomponent.example.2.dsc.config.yaml
97+
```
98+
99+
```yaml
100+
results:
101+
- name: Encode email for URL
102+
type: Microsoft.DSC.Debug/Echo
103+
result:
104+
actualState:
105+
output:
106+
encoded: user%2Btag%40example.com
107+
mailtoLink: mailto:user%2Btag%40example.com
108+
messages: []
109+
hadErrors: false
110+
```
111+
112+
### Example 3 - Encode complete URL
113+
114+
The following example shows how `uriComponent()` encodes an entire URL, including the protocol,
115+
slashes, and special characters.
116+
117+
```yaml
118+
# uricomponent.example.3.dsc.config.yaml
119+
$schema: https://aka.ms/dsc/schemas/v3/bundled/config/document.json
120+
resources:
121+
- name: Encode complete URL
122+
type: Microsoft.DSC.Debug/Echo
123+
properties:
124+
output:
125+
originalUrl: https://example.com/path?query=value
126+
encodedUrl: "[uriComponent('https://example.com/path?query=value')]"
127+
```
128+
129+
```bash
130+
dsc config get --file uricomponent.example.3.dsc.config.yaml
131+
```
132+
133+
```yaml
134+
results:
135+
- name: Encode complete URL
136+
type: Microsoft.DSC.Debug/Echo
137+
result:
138+
actualState:
139+
output:
140+
originalUrl: https://example.com/path?query=value
141+
encodedUrl: https%3A%2F%2Fexample.com%2Fpath%3Fquery%3Dvalue
142+
messages: []
143+
hadErrors: false
144+
```
145+
146+
### Example 4 - Build API request with encoded parameters
147+
148+
The following example demonstrates using `uriComponent()` with [`concat()`][01] and [`uri()`][02]
149+
to build an API URL with safely encoded query parameters.
150+
151+
```yaml
152+
# uricomponent.example.4.dsc.config.yaml
153+
$schema: https://aka.ms/dsc/schemas/v3/bundled/config/document.json
154+
parameters:
155+
apiBase:
156+
type: string
157+
defaultValue: https://api.example.com
158+
resourcePath:
159+
type: string
160+
defaultValue: /users/search
161+
nameFilter:
162+
type: string
163+
defaultValue: John Doe
164+
ageFilter:
165+
type: string
166+
defaultValue: '30'
167+
resources:
168+
- name: Build API URL with query string
169+
type: Microsoft.DSC.Debug/Echo
170+
properties:
171+
output:
172+
apiUrl: >-
173+
[concat(
174+
uri(parameters('apiBase'), parameters('resourcePath')),
175+
'?name=',
176+
uriComponent(parameters('nameFilter')),
177+
'&age=',
178+
parameters('ageFilter')
179+
)]
180+
```
181+
182+
```bash
183+
dsc config get --file uricomponent.example.4.dsc.config.yaml
184+
```
185+
186+
```yaml
187+
results:
188+
- name: Build API URL with query string
189+
type: Microsoft.DSC.Debug/Echo
190+
result:
191+
actualState:
192+
output:
193+
apiUrl: https://api.example.com/users/search?name=John%20Doe&age=30
194+
messages: []
195+
hadErrors: false
196+
```
197+
198+
### Example 5 - Unreserved characters remain unchanged
199+
200+
The following example shows that unreserved characters (letters, numbers, hyphen, underscore,
201+
period, and tilde) are not encoded.
202+
203+
```yaml
204+
# uricomponent.example.5.dsc.config.yaml
205+
$schema: https://aka.ms/dsc/schemas/v3/bundled/config/document.json
206+
resources:
207+
- name: Unreserved character handling
208+
type: Microsoft.DSC.Debug/Echo
209+
properties:
210+
output:
211+
original: ABCabc123-_.~
212+
encoded: "[uriComponent('ABCabc123-_.~')]"
213+
identical: "[equals(uriComponent('ABCabc123-_.~'), 'ABCabc123-_.~')]"
214+
```
215+
216+
```bash
217+
dsc config get --file uricomponent.example.5.dsc.config.yaml
218+
```
219+
220+
```yaml
221+
results:
222+
- name: Unreserved character handling
223+
type: Microsoft.DSC.Debug/Echo
224+
result:
225+
actualState:
226+
output:
227+
original: ABCabc123-_.~
228+
encoded: ABCabc123-_.~
229+
identical: true
230+
messages: []
231+
hadErrors: false
232+
```
233+
234+
## Parameters
235+
236+
### stringToEncode
237+
238+
The string value to encode using percent-encoding. All characters except unreserved characters
239+
(A-Z, a-z, 0-9, -, _, ., ~) are encoded.
240+
241+
```yaml
242+
Type: string
243+
Required: true
244+
Position: 1
245+
```
246+
247+
## Output
248+
249+
The `uriComponent()` function returns a string with all characters except unreserved characters
250+
replaced with their percent-encoded equivalents (e.g., space becomes `%20`, `@` becomes `%40`).
251+
252+
```yaml
253+
Type: string
254+
```
255+
256+
## Related functions
257+
258+
- [`uri()`][02] - Combines base and relative URIs
259+
- [`concat()`][01] - Concatenates multiple strings together
260+
- [`format()`][03] - Creates a formatted string from a template
261+
- [`base64()`][04] - Encodes a string to base64
262+
- [`parameters()`][05] - Retrieves parameter values
263+
- [`equals()`][06] - Compares two values for equality
264+
265+
<!-- Link reference definitions -->
266+
[01]: ./concat.md
267+
[02]: ./uri.md
268+
[03]: ./format.md
269+
[04]: ./base64.md
270+
[05]: ./parameters.md
271+
[06]: ./equals.md

0 commit comments

Comments
 (0)