Coverage Report

Created: 2026-05-16 06:08

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/rust/registry/src/index.crates.io-1949cf8c6b5b557f/uuid-1.8.0/src/fmt.rs
Line
Count
Source
1
// Copyright 2013-2014 The Rust Project Developers.
2
// Copyright 2018 The Uuid Project Developers.
3
//
4
// See the COPYRIGHT file at the top-level directory of this distribution.
5
//
6
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
7
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
8
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
9
// option. This file may not be copied, modified, or distributed
10
// except according to those terms.
11
12
//! Adapters for alternative string formats.
13
14
use crate::{
15
    std::{borrow::Borrow, fmt, ptr, str},
16
    Uuid, Variant,
17
};
18
19
#[cfg(feature = "std")]
20
use crate::std::string::{String, ToString};
21
22
impl std::fmt::Debug for Uuid {
23
    #[inline]
24
0
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
25
0
        fmt::LowerHex::fmt(self, f)
26
0
    }
27
}
28
29
impl fmt::Display for Uuid {
30
0
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
31
0
        fmt::LowerHex::fmt(self, f)
32
0
    }
33
}
34
35
#[cfg(feature = "std")]
36
impl From<Uuid> for String {
37
0
    fn from(uuid: Uuid) -> Self {
38
0
        uuid.to_string()
39
0
    }
40
}
41
42
impl fmt::Display for Variant {
43
0
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
44
0
        match *self {
45
0
            Variant::NCS => write!(f, "NCS"),
46
0
            Variant::RFC4122 => write!(f, "RFC4122"),
47
0
            Variant::Microsoft => write!(f, "Microsoft"),
48
0
            Variant::Future => write!(f, "Future"),
49
        }
50
0
    }
51
}
52
53
impl fmt::LowerHex for Uuid {
54
0
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
55
0
        fmt::LowerHex::fmt(self.as_hyphenated(), f)
56
0
    }
57
}
58
59
impl fmt::UpperHex for Uuid {
60
    #[inline]
61
0
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
62
0
        fmt::UpperHex::fmt(self.as_hyphenated(), f)
63
0
    }
64
}
65
66
/// Format a [`Uuid`] as a hyphenated string, like
67
/// `67e55044-10b1-426f-9247-bb680e5fe0c8`.
68
#[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
69
#[repr(transparent)]
70
pub struct Hyphenated(Uuid);
71
72
/// Format a [`Uuid`] as a simple string, like
73
/// `67e5504410b1426f9247bb680e5fe0c8`.
74
#[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
75
#[repr(transparent)]
76
pub struct Simple(Uuid);
77
78
/// Format a [`Uuid`] as a URN string, like
79
/// `urn:uuid:67e55044-10b1-426f-9247-bb680e5fe0c8`.
80
#[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
81
#[repr(transparent)]
82
pub struct Urn(Uuid);
83
84
/// Format a [`Uuid`] as a braced hyphenated string, like
85
/// `{67e55044-10b1-426f-9247-bb680e5fe0c8}`.
86
#[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
87
#[repr(transparent)]
88
pub struct Braced(Uuid);
89
90
impl Uuid {
91
    /// Get a [`Hyphenated`] formatter.
92
    #[inline]
93
0
    pub const fn hyphenated(self) -> Hyphenated {
94
0
        Hyphenated(self)
95
0
    }
96
97
    /// Get a borrowed [`Hyphenated`] formatter.
98
    #[inline]
99
0
    pub fn as_hyphenated(&self) -> &Hyphenated {
100
        // SAFETY: `Uuid` and `Hyphenated` have the same ABI
101
0
        unsafe { &*(self as *const Uuid as *const Hyphenated) }
102
0
    }
103
104
    /// Get a [`Simple`] formatter.
105
    #[inline]
106
0
    pub const fn simple(self) -> Simple {
107
0
        Simple(self)
108
0
    }
109
110
    /// Get a borrowed [`Simple`] formatter.
111
    #[inline]
112
0
    pub fn as_simple(&self) -> &Simple {
113
        // SAFETY: `Uuid` and `Simple` have the same ABI
114
0
        unsafe { &*(self as *const Uuid as *const Simple) }
115
0
    }
116
117
    /// Get a [`Urn`] formatter.
118
    #[inline]
119
0
    pub const fn urn(self) -> Urn {
120
0
        Urn(self)
121
0
    }
122
123
    /// Get a borrowed [`Urn`] formatter.
124
    #[inline]
125
0
    pub fn as_urn(&self) -> &Urn {
126
        // SAFETY: `Uuid` and `Urn` have the same ABI
127
0
        unsafe { &*(self as *const Uuid as *const Urn) }
128
0
    }
129
130
    /// Get a [`Braced`] formatter.
131
    #[inline]
132
0
    pub const fn braced(self) -> Braced {
133
0
        Braced(self)
134
0
    }
135
136
    /// Get a borrowed [`Braced`] formatter.
137
    #[inline]
138
0
    pub fn as_braced(&self) -> &Braced {
139
        // SAFETY: `Uuid` and `Braced` have the same ABI
140
0
        unsafe { &*(self as *const Uuid as *const Braced) }
141
0
    }
142
}
143
144
const UPPER: [u8; 16] = [
145
    b'0', b'1', b'2', b'3', b'4', b'5', b'6', b'7', b'8', b'9', b'A', b'B', b'C', b'D', b'E', b'F',
146
];
147
const LOWER: [u8; 16] = [
148
    b'0', b'1', b'2', b'3', b'4', b'5', b'6', b'7', b'8', b'9', b'a', b'b', b'c', b'd', b'e', b'f',
149
];
150
151
#[inline]
152
0
const fn format_simple(src: &[u8; 16], upper: bool) -> [u8; 32] {
153
0
    let lut = if upper { &UPPER } else { &LOWER };
154
0
    let mut dst = [0; 32];
155
0
    let mut i = 0;
156
0
    while i < 16 {
157
0
        let x = src[i];
158
0
        dst[i * 2] = lut[(x >> 4) as usize];
159
0
        dst[i * 2 + 1] = lut[(x & 0x0f) as usize];
160
0
        i += 1;
161
0
    }
162
0
    dst
163
0
}
164
165
#[inline]
166
0
const fn format_hyphenated(src: &[u8; 16], upper: bool) -> [u8; 36] {
167
0
    let lut = if upper { &UPPER } else { &LOWER };
168
0
    let groups = [(0, 8), (9, 13), (14, 18), (19, 23), (24, 36)];
169
0
    let mut dst = [0; 36];
170
171
0
    let mut group_idx = 0;
172
0
    let mut i = 0;
173
0
    while group_idx < 5 {
174
0
        let (start, end) = groups[group_idx];
175
0
        let mut j = start;
176
0
        while j < end {
177
0
            let x = src[i];
178
0
            i += 1;
179
0
180
0
            dst[j] = lut[(x >> 4) as usize];
181
0
            dst[j + 1] = lut[(x & 0x0f) as usize];
182
0
            j += 2;
183
0
        }
184
0
        if group_idx < 4 {
185
0
            dst[end] = b'-';
186
0
        }
187
0
        group_idx += 1;
188
    }
189
0
    dst
190
0
}
191
192
#[inline]
193
0
fn encode_simple<'b>(src: &[u8; 16], buffer: &'b mut [u8], upper: bool) -> &'b mut str {
194
0
    let buf = &mut buffer[..Simple::LENGTH];
195
0
    let dst = buf.as_mut_ptr();
196
197
    // SAFETY: `buf` is guaranteed to be at least `LEN` bytes
198
    // SAFETY: The encoded buffer is ASCII encoded
199
0
    unsafe {
200
0
        ptr::write(dst.cast(), format_simple(src, upper));
201
0
        str::from_utf8_unchecked_mut(buf)
202
0
    }
203
0
}
204
205
#[inline]
206
0
fn encode_hyphenated<'b>(src: &[u8; 16], buffer: &'b mut [u8], upper: bool) -> &'b mut str {
207
0
    let buf = &mut buffer[..Hyphenated::LENGTH];
208
0
    let dst = buf.as_mut_ptr();
209
210
    // SAFETY: `buf` is guaranteed to be at least `LEN` bytes
211
    // SAFETY: The encoded buffer is ASCII encoded
212
0
    unsafe {
213
0
        ptr::write(dst.cast(), format_hyphenated(src, upper));
214
0
        str::from_utf8_unchecked_mut(buf)
215
0
    }
216
0
}
217
218
#[inline]
219
0
fn encode_braced<'b>(src: &[u8; 16], buffer: &'b mut [u8], upper: bool) -> &'b mut str {
220
0
    let buf = &mut buffer[..Braced::LENGTH];
221
0
    buf[0] = b'{';
222
0
    buf[Braced::LENGTH - 1] = b'}';
223
224
    // SAFETY: `buf` is guaranteed to be at least `LEN` bytes
225
    // SAFETY: The encoded buffer is ASCII encoded
226
0
    unsafe {
227
0
        let dst = buf.as_mut_ptr().add(1);
228
0
229
0
        ptr::write(dst.cast(), format_hyphenated(src, upper));
230
0
        str::from_utf8_unchecked_mut(buf)
231
0
    }
232
0
}
233
234
#[inline]
235
0
fn encode_urn<'b>(src: &[u8; 16], buffer: &'b mut [u8], upper: bool) -> &'b mut str {
236
0
    let buf = &mut buffer[..Urn::LENGTH];
237
0
    buf[..9].copy_from_slice(b"urn:uuid:");
238
239
    // SAFETY: `buf` is guaranteed to be at least `LEN` bytes
240
    // SAFETY: The encoded buffer is ASCII encoded
241
0
    unsafe {
242
0
        let dst = buf.as_mut_ptr().add(9);
243
0
244
0
        ptr::write(dst.cast(), format_hyphenated(src, upper));
245
0
        str::from_utf8_unchecked_mut(buf)
246
0
    }
247
0
}
248
249
impl Hyphenated {
250
    /// The length of a hyphenated [`Uuid`] string.
251
    ///
252
    /// [`Uuid`]: ../struct.Uuid.html
253
    pub const LENGTH: usize = 36;
254
255
    /// Creates a [`Hyphenated`] from a [`Uuid`].
256
    ///
257
    /// [`Uuid`]: ../struct.Uuid.html
258
    /// [`Hyphenated`]: struct.Hyphenated.html
259
0
    pub const fn from_uuid(uuid: Uuid) -> Self {
260
0
        Hyphenated(uuid)
261
0
    }
262
263
    /// Writes the [`Uuid`] as a lower-case hyphenated string to
264
    /// `buffer`, and returns the subslice of the buffer that contains the
265
    /// encoded UUID.
266
    ///
267
    /// This is slightly more efficient than using the formatting
268
    /// infrastructure as it avoids virtual calls, and may avoid
269
    /// double buffering.
270
    ///
271
    /// [`Uuid`]: ../struct.Uuid.html
272
    ///
273
    /// # Panics
274
    ///
275
    /// Panics if the buffer is not large enough: it must have length at least
276
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
277
    /// sufficiently-large temporary buffer.
278
    ///
279
    /// [`LENGTH`]: #associatedconstant.LENGTH
280
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
281
    ///
282
    /// # Examples
283
    ///
284
    /// ```rust
285
    /// use uuid::Uuid;
286
    ///
287
    /// fn main() -> Result<(), uuid::Error> {
288
    ///     let uuid = Uuid::parse_str("936DA01f9abd4d9d80c702af85c822a8")?;
289
    ///
290
    ///     // the encoded portion is returned
291
    ///     assert_eq!(
292
    ///         uuid.hyphenated()
293
    ///             .encode_lower(&mut Uuid::encode_buffer()),
294
    ///         "936da01f-9abd-4d9d-80c7-02af85c822a8"
295
    ///     );
296
    ///
297
    ///     // the buffer is mutated directly, and trailing contents remains
298
    ///     let mut buf = [b'!'; 40];
299
    ///     uuid.hyphenated().encode_lower(&mut buf);
300
    ///     assert_eq!(
301
    ///         &buf as &[_],
302
    ///         b"936da01f-9abd-4d9d-80c7-02af85c822a8!!!!" as &[_]
303
    ///     );
304
    ///
305
    ///     Ok(())
306
    /// }
307
    /// ```
308
    /// */
309
    #[inline]
310
0
    pub fn encode_lower<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
311
0
        encode_hyphenated(self.0.as_bytes(), buffer, false)
312
0
    }
313
314
    /// Writes the [`Uuid`] as an upper-case hyphenated string to
315
    /// `buffer`, and returns the subslice of the buffer that contains the
316
    /// encoded UUID.
317
    ///
318
    /// This is slightly more efficient than using the formatting
319
    /// infrastructure as it avoids virtual calls, and may avoid
320
    /// double buffering.
321
    ///
322
    /// [`Uuid`]: ../struct.Uuid.html
323
    ///
324
    /// # Panics
325
    ///
326
    /// Panics if the buffer is not large enough: it must have length at least
327
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
328
    /// sufficiently-large temporary buffer.
329
    ///
330
    /// [`LENGTH`]: #associatedconstant.LENGTH
331
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
332
    ///
333
    /// # Examples
334
    ///
335
    /// ```rust
336
    /// use uuid::Uuid;
337
    ///
338
    /// fn main() -> Result<(), uuid::Error> {
339
    ///     let uuid = Uuid::parse_str("936da01f9abd4d9d80c702af85c822a8")?;
340
    ///
341
    ///     // the encoded portion is returned
342
    ///     assert_eq!(
343
    ///         uuid.hyphenated()
344
    ///             .encode_upper(&mut Uuid::encode_buffer()),
345
    ///         "936DA01F-9ABD-4D9D-80C7-02AF85C822A8"
346
    ///     );
347
    ///
348
    ///     // the buffer is mutated directly, and trailing contents remains
349
    ///     let mut buf = [b'!'; 40];
350
    ///     uuid.hyphenated().encode_upper(&mut buf);
351
    ///     assert_eq!(
352
    ///         &buf as &[_],
353
    ///         b"936DA01F-9ABD-4D9D-80C7-02AF85C822A8!!!!" as &[_]
354
    ///     );
355
    ///
356
    ///     Ok(())
357
    /// }
358
    /// ```
359
    /// */
360
    #[inline]
361
0
    pub fn encode_upper<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
362
0
        encode_hyphenated(self.0.as_bytes(), buffer, true)
363
0
    }
364
365
    /// Get a reference to the underlying [`Uuid`].
366
    ///
367
    /// # Examples
368
    ///
369
    /// ```rust
370
    /// use uuid::Uuid;
371
    ///
372
    /// let hyphenated = Uuid::nil().hyphenated();
373
    /// assert_eq!(*hyphenated.as_uuid(), Uuid::nil());
374
    /// ```
375
0
    pub const fn as_uuid(&self) -> &Uuid {
376
0
        &self.0
377
0
    }
378
379
    /// Consumes the [`Hyphenated`], returning the underlying [`Uuid`].
380
    ///
381
    /// # Examples
382
    ///
383
    /// ```rust
384
    /// use uuid::Uuid;
385
    ///
386
    /// let hyphenated = Uuid::nil().hyphenated();
387
    /// assert_eq!(hyphenated.into_uuid(), Uuid::nil());
388
    /// ```
389
0
    pub const fn into_uuid(self) -> Uuid {
390
0
        self.0
391
0
    }
392
}
393
394
impl Braced {
395
    /// The length of a braced [`Uuid`] string.
396
    ///
397
    /// [`Uuid`]: ../struct.Uuid.html
398
    pub const LENGTH: usize = 38;
399
400
    /// Creates a [`Braced`] from a [`Uuid`].
401
    ///
402
    /// [`Uuid`]: ../struct.Uuid.html
403
    /// [`Braced`]: struct.Braced.html
404
0
    pub const fn from_uuid(uuid: Uuid) -> Self {
405
0
        Braced(uuid)
406
0
    }
407
408
    /// Writes the [`Uuid`] as a lower-case hyphenated string surrounded by
409
    /// braces to `buffer`, and returns the subslice of the buffer that contains
410
    /// the encoded UUID.
411
    ///
412
    /// This is slightly more efficient than using the formatting
413
    /// infrastructure as it avoids virtual calls, and may avoid
414
    /// double buffering.
415
    ///
416
    /// [`Uuid`]: ../struct.Uuid.html
417
    ///
418
    /// # Panics
419
    ///
420
    /// Panics if the buffer is not large enough: it must have length at least
421
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
422
    /// sufficiently-large temporary buffer.
423
    ///
424
    /// [`LENGTH`]: #associatedconstant.LENGTH
425
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
426
    ///
427
    /// # Examples
428
    ///
429
    /// ```rust
430
    /// use uuid::Uuid;
431
    ///
432
    /// fn main() -> Result<(), uuid::Error> {
433
    ///     let uuid = Uuid::parse_str("936DA01f9abd4d9d80c702af85c822a8")?;
434
    ///
435
    ///     // the encoded portion is returned
436
    ///     assert_eq!(
437
    ///         uuid.braced()
438
    ///             .encode_lower(&mut Uuid::encode_buffer()),
439
    ///         "{936da01f-9abd-4d9d-80c7-02af85c822a8}"
440
    ///     );
441
    ///
442
    ///     // the buffer is mutated directly, and trailing contents remains
443
    ///     let mut buf = [b'!'; 40];
444
    ///     uuid.braced().encode_lower(&mut buf);
445
    ///     assert_eq!(
446
    ///         &buf as &[_],
447
    ///         b"{936da01f-9abd-4d9d-80c7-02af85c822a8}!!" as &[_]
448
    ///     );
449
    ///
450
    ///     Ok(())
451
    /// }
452
    /// ```
453
    /// */
454
    #[inline]
455
0
    pub fn encode_lower<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
456
0
        encode_braced(self.0.as_bytes(), buffer, false)
457
0
    }
458
459
    /// Writes the [`Uuid`] as an upper-case hyphenated string surrounded by
460
    /// braces to `buffer`, and returns the subslice of the buffer that contains
461
    /// the encoded UUID.
462
    ///
463
    /// This is slightly more efficient than using the formatting
464
    /// infrastructure as it avoids virtual calls, and may avoid
465
    /// double buffering.
466
    ///
467
    /// [`Uuid`]: ../struct.Uuid.html
468
    ///
469
    /// # Panics
470
    ///
471
    /// Panics if the buffer is not large enough: it must have length at least
472
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
473
    /// sufficiently-large temporary buffer.
474
    ///
475
    /// [`LENGTH`]: #associatedconstant.LENGTH
476
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
477
    ///
478
    /// # Examples
479
    ///
480
    /// ```rust
481
    /// use uuid::Uuid;
482
    ///
483
    /// fn main() -> Result<(), uuid::Error> {
484
    ///     let uuid = Uuid::parse_str("936da01f9abd4d9d80c702af85c822a8")?;
485
    ///
486
    ///     // the encoded portion is returned
487
    ///     assert_eq!(
488
    ///         uuid.braced()
489
    ///             .encode_upper(&mut Uuid::encode_buffer()),
490
    ///         "{936DA01F-9ABD-4D9D-80C7-02AF85C822A8}"
491
    ///     );
492
    ///
493
    ///     // the buffer is mutated directly, and trailing contents remains
494
    ///     let mut buf = [b'!'; 40];
495
    ///     uuid.braced().encode_upper(&mut buf);
496
    ///     assert_eq!(
497
    ///         &buf as &[_],
498
    ///         b"{936DA01F-9ABD-4D9D-80C7-02AF85C822A8}!!" as &[_]
499
    ///     );
500
    ///
501
    ///     Ok(())
502
    /// }
503
    /// ```
504
    /// */
505
    #[inline]
506
0
    pub fn encode_upper<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
507
0
        encode_braced(self.0.as_bytes(), buffer, true)
508
0
    }
509
510
    /// Get a reference to the underlying [`Uuid`].
511
    ///
512
    /// # Examples
513
    ///
514
    /// ```rust
515
    /// use uuid::Uuid;
516
    ///
517
    /// let braced = Uuid::nil().braced();
518
    /// assert_eq!(*braced.as_uuid(), Uuid::nil());
519
    /// ```
520
0
    pub const fn as_uuid(&self) -> &Uuid {
521
0
        &self.0
522
0
    }
523
524
    /// Consumes the [`Braced`], returning the underlying [`Uuid`].
525
    ///
526
    /// # Examples
527
    ///
528
    /// ```rust
529
    /// use uuid::Uuid;
530
    ///
531
    /// let braced = Uuid::nil().braced();
532
    /// assert_eq!(braced.into_uuid(), Uuid::nil());
533
    /// ```
534
0
    pub const fn into_uuid(self) -> Uuid {
535
0
        self.0
536
0
    }
537
}
538
539
impl Simple {
540
    /// The length of a simple [`Uuid`] string.
541
    ///
542
    /// [`Uuid`]: ../struct.Uuid.html
543
    pub const LENGTH: usize = 32;
544
545
    /// Creates a [`Simple`] from a [`Uuid`].
546
    ///
547
    /// [`Uuid`]: ../struct.Uuid.html
548
    /// [`Simple`]: struct.Simple.html
549
0
    pub const fn from_uuid(uuid: Uuid) -> Self {
550
0
        Simple(uuid)
551
0
    }
552
553
    /// Writes the [`Uuid`] as a lower-case simple string to `buffer`,
554
    /// and returns the subslice of the buffer that contains the encoded UUID.
555
    ///
556
    /// This is slightly more efficient than using the formatting
557
    /// infrastructure as it avoids virtual calls, and may avoid
558
    /// double buffering.
559
    ///
560
    /// [`Uuid`]: ../struct.Uuid.html
561
    ///
562
    /// # Panics
563
    ///
564
    /// Panics if the buffer is not large enough: it must have length at least
565
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
566
    /// sufficiently-large temporary buffer.
567
    ///
568
    /// [`LENGTH`]: #associatedconstant.LENGTH
569
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
570
    ///
571
    /// # Examples
572
    ///
573
    /// ```rust
574
    /// use uuid::Uuid;
575
    ///
576
    /// fn main() -> Result<(), uuid::Error> {
577
    ///     let uuid = Uuid::parse_str("936DA01f9abd4d9d80c702af85c822a8")?;
578
    ///
579
    ///     // the encoded portion is returned
580
    ///     assert_eq!(
581
    ///         uuid.simple().encode_lower(&mut Uuid::encode_buffer()),
582
    ///         "936da01f9abd4d9d80c702af85c822a8"
583
    ///     );
584
    ///
585
    ///     // the buffer is mutated directly, and trailing contents remains
586
    ///     let mut buf = [b'!'; 36];
587
    ///     assert_eq!(
588
    ///         uuid.simple().encode_lower(&mut buf),
589
    ///         "936da01f9abd4d9d80c702af85c822a8"
590
    ///     );
591
    ///     assert_eq!(
592
    ///         &buf as &[_],
593
    ///         b"936da01f9abd4d9d80c702af85c822a8!!!!" as &[_]
594
    ///     );
595
    ///
596
    ///     Ok(())
597
    /// }
598
    /// ```
599
    /// */
600
    #[inline]
601
0
    pub fn encode_lower<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
602
0
        encode_simple(self.0.as_bytes(), buffer, false)
603
0
    }
604
605
    /// Writes the [`Uuid`] as an upper-case simple string to `buffer`,
606
    /// and returns the subslice of the buffer that contains the encoded UUID.
607
    ///
608
    /// [`Uuid`]: ../struct.Uuid.html
609
    ///
610
    /// # Panics
611
    ///
612
    /// Panics if the buffer is not large enough: it must have length at least
613
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
614
    /// sufficiently-large temporary buffer.
615
    ///
616
    /// [`LENGTH`]: #associatedconstant.LENGTH
617
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
618
    ///
619
    /// # Examples
620
    ///
621
    /// ```rust
622
    /// use uuid::Uuid;
623
    ///
624
    /// fn main() -> Result<(), uuid::Error> {
625
    ///     let uuid = Uuid::parse_str("936da01f9abd4d9d80c702af85c822a8")?;
626
    ///
627
    ///     // the encoded portion is returned
628
    ///     assert_eq!(
629
    ///         uuid.simple().encode_upper(&mut Uuid::encode_buffer()),
630
    ///         "936DA01F9ABD4D9D80C702AF85C822A8"
631
    ///     );
632
    ///
633
    ///     // the buffer is mutated directly, and trailing contents remains
634
    ///     let mut buf = [b'!'; 36];
635
    ///     assert_eq!(
636
    ///         uuid.simple().encode_upper(&mut buf),
637
    ///         "936DA01F9ABD4D9D80C702AF85C822A8"
638
    ///     );
639
    ///     assert_eq!(
640
    ///         &buf as &[_],
641
    ///         b"936DA01F9ABD4D9D80C702AF85C822A8!!!!" as &[_]
642
    ///     );
643
    ///
644
    ///     Ok(())
645
    /// }
646
    /// ```
647
    /// */
648
    #[inline]
649
0
    pub fn encode_upper<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
650
0
        encode_simple(self.0.as_bytes(), buffer, true)
651
0
    }
652
653
    /// Get a reference to the underlying [`Uuid`].
654
    ///
655
    /// # Examples
656
    ///
657
    /// ```rust
658
    /// use uuid::Uuid;
659
    ///
660
    /// let simple = Uuid::nil().simple();
661
    /// assert_eq!(*simple.as_uuid(), Uuid::nil());
662
    /// ```
663
0
    pub const fn as_uuid(&self) -> &Uuid {
664
0
        &self.0
665
0
    }
666
667
    /// Consumes the [`Simple`], returning the underlying [`Uuid`].
668
    ///
669
    /// # Examples
670
    ///
671
    /// ```rust
672
    /// use uuid::Uuid;
673
    ///
674
    /// let simple = Uuid::nil().simple();
675
    /// assert_eq!(simple.into_uuid(), Uuid::nil());
676
    /// ```
677
0
    pub const fn into_uuid(self) -> Uuid {
678
0
        self.0
679
0
    }
680
}
681
682
impl Urn {
683
    /// The length of a URN [`Uuid`] string.
684
    ///
685
    /// [`Uuid`]: ../struct.Uuid.html
686
    pub const LENGTH: usize = 45;
687
688
    /// Creates a [`Urn`] from a [`Uuid`].
689
    ///
690
    /// [`Uuid`]: ../struct.Uuid.html
691
    /// [`Urn`]: struct.Urn.html
692
0
    pub const fn from_uuid(uuid: Uuid) -> Self {
693
0
        Urn(uuid)
694
0
    }
695
696
    /// Writes the [`Uuid`] as a lower-case URN string to
697
    /// `buffer`, and returns the subslice of the buffer that contains the
698
    /// encoded UUID.
699
    ///
700
    /// This is slightly more efficient than using the formatting
701
    /// infrastructure as it avoids virtual calls, and may avoid
702
    /// double buffering.
703
    ///
704
    /// [`Uuid`]: ../struct.Uuid.html
705
    ///
706
    /// # Panics
707
    ///
708
    /// Panics if the buffer is not large enough: it must have length at least
709
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
710
    /// sufficiently-large temporary buffer.
711
    ///
712
    /// [`LENGTH`]: #associatedconstant.LENGTH
713
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
714
    ///
715
    /// # Examples
716
    ///
717
    /// ```rust
718
    /// use uuid::Uuid;
719
    ///
720
    /// fn main() -> Result<(), uuid::Error> {
721
    ///     let uuid = Uuid::parse_str("936DA01f9abd4d9d80c702af85c822a8")?;
722
    ///
723
    ///     // the encoded portion is returned
724
    ///     assert_eq!(
725
    ///         uuid.urn().encode_lower(&mut Uuid::encode_buffer()),
726
    ///         "urn:uuid:936da01f-9abd-4d9d-80c7-02af85c822a8"
727
    ///     );
728
    ///
729
    ///     // the buffer is mutated directly, and trailing contents remains
730
    ///     let mut buf = [b'!'; 49];
731
    ///     uuid.urn().encode_lower(&mut buf);
732
    ///     assert_eq!(
733
    ///         uuid.urn().encode_lower(&mut buf),
734
    ///         "urn:uuid:936da01f-9abd-4d9d-80c7-02af85c822a8"
735
    ///     );
736
    ///     assert_eq!(
737
    ///         &buf as &[_],
738
    ///         b"urn:uuid:936da01f-9abd-4d9d-80c7-02af85c822a8!!!!" as &[_]
739
    ///     );
740
    ///     
741
    ///     Ok(())
742
    /// }
743
    /// ```
744
    /// */
745
    #[inline]
746
0
    pub fn encode_lower<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
747
0
        encode_urn(self.0.as_bytes(), buffer, false)
748
0
    }
749
750
    /// Writes the [`Uuid`] as an upper-case URN string to
751
    /// `buffer`, and returns the subslice of the buffer that contains the
752
    /// encoded UUID.
753
    ///
754
    /// This is slightly more efficient than using the formatting
755
    /// infrastructure as it avoids virtual calls, and may avoid
756
    /// double buffering.
757
    ///
758
    /// [`Uuid`]: ../struct.Uuid.html
759
    ///
760
    /// # Panics
761
    ///
762
    /// Panics if the buffer is not large enough: it must have length at least
763
    /// [`LENGTH`]. [`Uuid::encode_buffer`] can be used to get a
764
    /// sufficiently-large temporary buffer.
765
    ///
766
    /// [`LENGTH`]: #associatedconstant.LENGTH
767
    /// [`Uuid::encode_buffer`]: ../struct.Uuid.html#method.encode_buffer
768
    ///
769
    /// # Examples
770
    ///
771
    /// ```rust
772
    /// use uuid::Uuid;
773
    ///
774
    /// fn main() -> Result<(), uuid::Error> {
775
    ///     let uuid = Uuid::parse_str("936da01f9abd4d9d80c702af85c822a8")?;
776
    ///
777
    ///     // the encoded portion is returned
778
    ///     assert_eq!(
779
    ///         uuid.urn().encode_upper(&mut Uuid::encode_buffer()),
780
    ///         "urn:uuid:936DA01F-9ABD-4D9D-80C7-02AF85C822A8"
781
    ///     );
782
    ///
783
    ///     // the buffer is mutated directly, and trailing contents remains
784
    ///     let mut buf = [b'!'; 49];
785
    ///     assert_eq!(
786
    ///         uuid.urn().encode_upper(&mut buf),
787
    ///         "urn:uuid:936DA01F-9ABD-4D9D-80C7-02AF85C822A8"
788
    ///     );
789
    ///     assert_eq!(
790
    ///         &buf as &[_],
791
    ///         b"urn:uuid:936DA01F-9ABD-4D9D-80C7-02AF85C822A8!!!!" as &[_]
792
    ///     );
793
    ///
794
    ///     Ok(())
795
    /// }
796
    /// ```
797
    /// */
798
    #[inline]
799
0
    pub fn encode_upper<'buf>(&self, buffer: &'buf mut [u8]) -> &'buf mut str {
800
0
        encode_urn(self.0.as_bytes(), buffer, true)
801
0
    }
802
803
    /// Get a reference to the underlying [`Uuid`].
804
    ///
805
    /// # Examples
806
    ///
807
    /// ```rust
808
    /// use uuid::Uuid;
809
    ///
810
    /// let urn = Uuid::nil().urn();
811
    /// assert_eq!(*urn.as_uuid(), Uuid::nil());
812
    /// ```
813
0
    pub const fn as_uuid(&self) -> &Uuid {
814
0
        &self.0
815
0
    }
816
817
    /// Consumes the [`Urn`], returning the underlying [`Uuid`].
818
    ///
819
    /// # Examples
820
    ///
821
    /// ```rust
822
    /// use uuid::Uuid;
823
    ///
824
    /// let urn = Uuid::nil().urn();
825
    /// assert_eq!(urn.into_uuid(), Uuid::nil());
826
    /// ```
827
0
    pub const fn into_uuid(self) -> Uuid {
828
0
        self.0
829
0
    }
830
}
831
832
macro_rules! impl_fmt_traits {
833
    ($($T:ident<$($a:lifetime),*>),+) => {$(
834
        impl<$($a),*> fmt::Display for $T<$($a),*> {
835
            #[inline]
836
0
            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
837
0
                fmt::LowerHex::fmt(self, f)
838
0
            }
Unexecuted instantiation: <uuid::fmt::Hyphenated as core::fmt::Display>::fmt
Unexecuted instantiation: <uuid::fmt::Simple as core::fmt::Display>::fmt
Unexecuted instantiation: <uuid::fmt::Urn as core::fmt::Display>::fmt
Unexecuted instantiation: <uuid::fmt::Braced as core::fmt::Display>::fmt
839
        }
840
841
        impl<$($a),*> fmt::LowerHex for $T<$($a),*> {
842
0
            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
843
0
                f.write_str(self.encode_lower(&mut [0; Self::LENGTH]))
844
0
            }
Unexecuted instantiation: <uuid::fmt::Hyphenated as core::fmt::LowerHex>::fmt
Unexecuted instantiation: <uuid::fmt::Simple as core::fmt::LowerHex>::fmt
Unexecuted instantiation: <uuid::fmt::Urn as core::fmt::LowerHex>::fmt
Unexecuted instantiation: <uuid::fmt::Braced as core::fmt::LowerHex>::fmt
845
        }
846
847
        impl<$($a),*> fmt::UpperHex for $T<$($a),*> {
848
0
            fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
849
0
                f.write_str(self.encode_upper(&mut [0; Self::LENGTH]))
850
0
            }
Unexecuted instantiation: <uuid::fmt::Hyphenated as core::fmt::UpperHex>::fmt
Unexecuted instantiation: <uuid::fmt::Simple as core::fmt::UpperHex>::fmt
Unexecuted instantiation: <uuid::fmt::Urn as core::fmt::UpperHex>::fmt
Unexecuted instantiation: <uuid::fmt::Braced as core::fmt::UpperHex>::fmt
851
        }
852
853
        impl_fmt_from!($T<$($a),*>);
854
    )+}
855
}
856
857
macro_rules! impl_fmt_from {
858
    ($T:ident<>) => {
859
        impl From<Uuid> for $T {
860
            #[inline]
861
0
            fn from(f: Uuid) -> Self {
862
0
                $T(f)
863
0
            }
Unexecuted instantiation: <uuid::fmt::Simple as core::convert::From<uuid::Uuid>>::from
Unexecuted instantiation: <uuid::fmt::Urn as core::convert::From<uuid::Uuid>>::from
Unexecuted instantiation: <uuid::fmt::Braced as core::convert::From<uuid::Uuid>>::from
Unexecuted instantiation: <uuid::fmt::Hyphenated as core::convert::From<uuid::Uuid>>::from
864
        }
865
866
        impl From<$T> for Uuid {
867
            #[inline]
868
0
            fn from(f: $T) -> Self {
869
0
                f.into_uuid()
870
0
            }
Unexecuted instantiation: <uuid::Uuid as core::convert::From<uuid::fmt::Hyphenated>>::from
Unexecuted instantiation: <uuid::Uuid as core::convert::From<uuid::fmt::Simple>>::from
Unexecuted instantiation: <uuid::Uuid as core::convert::From<uuid::fmt::Urn>>::from
Unexecuted instantiation: <uuid::Uuid as core::convert::From<uuid::fmt::Braced>>::from
871
        }
872
873
        impl AsRef<Uuid> for $T {
874
            #[inline]
875
0
            fn as_ref(&self) -> &Uuid {
876
0
                &self.0
877
0
            }
Unexecuted instantiation: <uuid::fmt::Hyphenated as core::convert::AsRef<uuid::Uuid>>::as_ref
Unexecuted instantiation: <uuid::fmt::Simple as core::convert::AsRef<uuid::Uuid>>::as_ref
Unexecuted instantiation: <uuid::fmt::Urn as core::convert::AsRef<uuid::Uuid>>::as_ref
Unexecuted instantiation: <uuid::fmt::Braced as core::convert::AsRef<uuid::Uuid>>::as_ref
878
        }
879
880
        impl Borrow<Uuid> for $T {
881
            #[inline]
882
0
            fn borrow(&self) -> &Uuid {
883
0
                &self.0
884
0
            }
Unexecuted instantiation: <uuid::fmt::Hyphenated as core::borrow::Borrow<uuid::Uuid>>::borrow
Unexecuted instantiation: <uuid::fmt::Simple as core::borrow::Borrow<uuid::Uuid>>::borrow
Unexecuted instantiation: <uuid::fmt::Urn as core::borrow::Borrow<uuid::Uuid>>::borrow
Unexecuted instantiation: <uuid::fmt::Braced as core::borrow::Borrow<uuid::Uuid>>::borrow
885
        }
886
    };
887
    ($T:ident<$a:lifetime>) => {
888
        impl<$a> From<&$a Uuid> for $T<$a> {
889
            #[inline]
890
            fn from(f: &$a Uuid) -> Self {
891
                $T::from_uuid_ref(f)
892
            }
893
        }
894
895
        impl<$a> From<$T<$a>> for &$a Uuid {
896
            #[inline]
897
            fn from(f: $T<$a>) -> &$a Uuid {
898
                f.0
899
            }
900
        }
901
902
        impl<$a> AsRef<Uuid> for $T<$a> {
903
            #[inline]
904
            fn as_ref(&self) -> &Uuid {
905
                self.0
906
            }
907
        }
908
909
        impl<$a> Borrow<Uuid> for $T<$a> {
910
            #[inline]
911
            fn borrow(&self) -> &Uuid {
912
                self.0
913
            }
914
        }
915
    };
916
}
917
918
impl_fmt_traits! {
919
    Hyphenated<>,
920
    Simple<>,
921
    Urn<>,
922
    Braced<>
923
}
924
925
#[cfg(test)]
926
mod tests {
927
    use super::*;
928
929
    #[test]
930
    fn hyphenated_trailing() {
931
        let mut buf = [b'x'; 100];
932
        let len = Uuid::nil().hyphenated().encode_lower(&mut buf).len();
933
        assert_eq!(len, super::Hyphenated::LENGTH);
934
        assert!(buf[len..].iter().all(|x| *x == b'x'));
935
    }
936
937
    #[test]
938
    fn hyphenated_ref_trailing() {
939
        let mut buf = [b'x'; 100];
940
        let len = Uuid::nil().as_hyphenated().encode_lower(&mut buf).len();
941
        assert_eq!(len, super::Hyphenated::LENGTH);
942
        assert!(buf[len..].iter().all(|x| *x == b'x'));
943
    }
944
945
    #[test]
946
    fn simple_trailing() {
947
        let mut buf = [b'x'; 100];
948
        let len = Uuid::nil().simple().encode_lower(&mut buf).len();
949
        assert_eq!(len, super::Simple::LENGTH);
950
        assert!(buf[len..].iter().all(|x| *x == b'x'));
951
    }
952
953
    #[test]
954
    fn simple_ref_trailing() {
955
        let mut buf = [b'x'; 100];
956
        let len = Uuid::nil().as_simple().encode_lower(&mut buf).len();
957
        assert_eq!(len, super::Simple::LENGTH);
958
        assert!(buf[len..].iter().all(|x| *x == b'x'));
959
    }
960
961
    #[test]
962
    fn urn_trailing() {
963
        let mut buf = [b'x'; 100];
964
        let len = Uuid::nil().urn().encode_lower(&mut buf).len();
965
        assert_eq!(len, super::Urn::LENGTH);
966
        assert!(buf[len..].iter().all(|x| *x == b'x'));
967
    }
968
969
    #[test]
970
    fn urn_ref_trailing() {
971
        let mut buf = [b'x'; 100];
972
        let len = Uuid::nil().as_urn().encode_lower(&mut buf).len();
973
        assert_eq!(len, super::Urn::LENGTH);
974
        assert!(buf[len..].iter().all(|x| *x == b'x'));
975
    }
976
977
    #[test]
978
    fn braced_trailing() {
979
        let mut buf = [b'x'; 100];
980
        let len = Uuid::nil().braced().encode_lower(&mut buf).len();
981
        assert_eq!(len, super::Braced::LENGTH);
982
        assert!(buf[len..].iter().all(|x| *x == b'x'));
983
    }
984
985
    #[test]
986
    fn braced_ref_trailing() {
987
        let mut buf = [b'x'; 100];
988
        let len = Uuid::nil().as_braced().encode_lower(&mut buf).len();
989
        assert_eq!(len, super::Braced::LENGTH);
990
        assert!(buf[len..].iter().all(|x| *x == b'x'));
991
    }
992
993
    #[test]
994
    #[should_panic]
995
    fn hyphenated_too_small() {
996
        Uuid::nil().hyphenated().encode_lower(&mut [0; 35]);
997
    }
998
999
    #[test]
1000
    #[should_panic]
1001
    fn simple_too_small() {
1002
        Uuid::nil().simple().encode_lower(&mut [0; 31]);
1003
    }
1004
1005
    #[test]
1006
    #[should_panic]
1007
    fn urn_too_small() {
1008
        Uuid::nil().urn().encode_lower(&mut [0; 44]);
1009
    }
1010
1011
    #[test]
1012
    #[should_panic]
1013
    fn braced_too_small() {
1014
        Uuid::nil().braced().encode_lower(&mut [0; 37]);
1015
    }
1016
1017
    #[test]
1018
    fn hyphenated_to_inner() {
1019
        let hyphenated = Uuid::nil().hyphenated();
1020
        assert_eq!(Uuid::from(hyphenated), Uuid::nil());
1021
    }
1022
1023
    #[test]
1024
    fn simple_to_inner() {
1025
        let simple = Uuid::nil().simple();
1026
        assert_eq!(Uuid::from(simple), Uuid::nil());
1027
    }
1028
1029
    #[test]
1030
    fn urn_to_inner() {
1031
        let urn = Uuid::nil().urn();
1032
        assert_eq!(Uuid::from(urn), Uuid::nil());
1033
    }
1034
1035
    #[test]
1036
    fn braced_to_inner() {
1037
        let braced = Uuid::nil().braced();
1038
        assert_eq!(Uuid::from(braced), Uuid::nil());
1039
    }
1040
}