GCC Code Coverage Report


Directory: libs/http_proto/
File: include/boost/http_proto/fields_view_base.hpp
Date: 2025-09-21 18:08:15
Exec Total Coverage
Lines: 10 10 100.0%
Functions: 4 4 100.0%
Branches: 0 0 -%

Line Branch Exec Source
1 //
2 // Copyright (c) 2021 Vinnie Falco (vinnie.falco@gmail.com)
3 // Copyright (c) 2025 Mohammad Nejati
4 //
5 // Distributed under the Boost Software License, Version 1.0. (See accompanying
6 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
7 //
8 // Official repository: https://github.com/cppalliance/http_proto
9 //
10
11 #ifndef BOOST_HTTP_PROTO_FIELDS_VIEW_BASE_HPP
12 #define BOOST_HTTP_PROTO_FIELDS_VIEW_BASE_HPP
13
14 #include <boost/http_proto/detail/config.hpp>
15 #include <boost/http_proto/detail/header.hpp>
16
17 #include <boost/core/detail/string_view.hpp>
18 #include <boost/url/grammar/recycled.hpp>
19 #include <boost/url/grammar/type_traits.hpp>
20
21 #include <iosfwd>
22 #include <string>
23
24 namespace boost {
25 namespace http_proto {
26
27 /** A read-only, bidirectional range of HTTP fields.
28
29 This is a mix-in used to add common
30 functionality to derived classes.
31 */
32 class fields_view_base
33 {
34 detail::header const* ph_;
35
36 friend class fields;
37 template<std::size_t>
38 friend class static_fields;
39 friend class fields_base;
40 friend class fields_view;
41 friend class message_base;
42 friend class message_view_base;
43 friend class request_base;
44 friend class request;
45 template<std::size_t>
46 friend class static_request;
47 friend class request_view;
48 friend class response_base;
49 friend class response;
50 template<std::size_t>
51 friend class static_response;
52 friend class response_view;
53 friend class serializer;
54
55 explicit
56 1289 fields_view_base(
57 detail::header const* ph) noexcept
58 1289 : ph_(ph)
59 {
60 1289 }
61
62 fields_view_base(
63 fields_view_base const&) = default;
64 fields_view_base&
65 operator=(fields_view_base const&) = default;
66
67 public:
68 //--------------------------------------------
69 //
70 // Types
71 //
72 //--------------------------------------------
73
74 /** A view to an HTTP field.
75
76 The view will be invalidated when the
77 underlying container is modified.
78
79 The caller is responsible for ensuring
80 that the lifetime of the container extends
81 until it is no longer referenced.
82 */
83 struct reference
84 {
85 /** Field name constant.
86
87 Set to `boost::none` if the constant
88 does not exist in @ref field.
89 */
90 boost::optional<field> const id;
91
92 /// A view to the field name.
93 core::string_view const name;
94
95 /// A view to the field value.
96 core::string_view const value;
97
98 reference const*
99 2063 operator->() const noexcept
100 {
101 2063 return this;
102 }
103 };
104
105 /// @copydoc reference
106 typedef reference const_reference;
107
108 /** A value type which represent an HTTP field.
109
110 This type allows for making a copy of
111 a field where ownership is retained
112 in the copy.
113 */
114 struct value_type
115 {
116 /** Field name constant.
117
118 Set to `boost::none` if the
119 constant does not exist in @ref field.
120 */
121 boost::optional<field> id;
122
123 /// Field name.
124 std::string name;
125
126 /// Field value.
127 std::string value;
128
129 /// Constructor.
130 BOOST_HTTP_PROTO_DECL
131 value_type(
132 reference const& other);
133
134 /** Conversion.
135
136 @see
137 @ref reference.
138
139 @return A view to the fields.
140 */
141 operator reference() const noexcept;
142 };
143
144 /** A bidirectional iterator to HTTP fields.
145 */
146 class iterator;
147
148 /// @copydoc iterator
149 using const_iterator = iterator;
150
151 /** A bidirectional reverse iterator to HTTP fields.
152 */
153 class reverse_iterator;
154
155 /// @copydoc iterator
156 using const_reverse_iterator = reverse_iterator;
157
158 /** A forward range of matching fields.
159
160 Objects of this type are returned by
161 the function @ref find_all.
162 */
163 class subrange;
164
165 //--------------------------------------------
166 //
167 // Observers
168 //
169 //--------------------------------------------
170
171 /** Return the largest possible serialized message.
172 */
173 static
174 constexpr
175 std::size_t
176 max_size() noexcept
177 {
178 // TODO: this doesn't take into account
179 // the start-line
180 return detail::header::max_offset;
181 }
182
183 /** Return an iterator to the beginning.
184 */
185 iterator
186 begin() const noexcept;
187
188 /** Return an iterator to the end.
189 */
190 iterator
191 end() const noexcept;
192
193 /** Return a reverse iterator to the beginning.
194 */
195 reverse_iterator
196 rbegin() const noexcept;
197
198 /** Return a reverse iterator to the end.
199 */
200 reverse_iterator
201 rend() const noexcept;
202
203 /** Return a string view representing the serialized data.
204 */
205 core::string_view
206 766 buffer() const noexcept
207 {
208 1532 return core::string_view(
209 766 ph_->cbuf, ph_->size);
210 }
211
212 /** Return the number of fields in the container.
213 */
214 std::size_t
215 215 size() const noexcept
216 {
217 215 return ph_->count;
218 }
219
220 /** Return the value of a field, or throws an exception.
221
222 If more than one field with the specified
223 name exists, the first field defined by
224 insertion order is returned.
225
226 @par Exception Safety
227 Strong guarantee.
228
229 @throw std::out_of_range
230 Field is not found.
231
232 @param id The field name constant.
233 */
234 BOOST_HTTP_PROTO_DECL
235 core::string_view
236 at(field id) const;
237
238 /** Return the value of a field, or throws an exception.
239
240 If more than one field with the specified
241 name exists, the first field defined by
242 insertion order is returned.
243
244 If `name` refers to a known field, it is
245 faster to call @ref at with a field id
246 instead of a string.
247
248 @par Exception Safety
249 Strong guarantee.
250
251 @throw std::out_of_range
252 Field is not found.
253
254 @param name The field name.
255 */
256 BOOST_HTTP_PROTO_DECL
257 core::string_view
258 at(core::string_view name) const;
259
260 /** Return true if a field exists.
261 */
262 BOOST_HTTP_PROTO_DECL
263 bool
264 exists(field id) const noexcept;
265
266 /** Return true if a field exists.
267
268 If `name` refers to a known field,
269 it is faster to call @ref exists
270 with a field id instead of a string.
271
272 @param name The field name.
273 */
274 BOOST_HTTP_PROTO_DECL
275 bool
276 exists(
277 core::string_view name) const noexcept;
278
279 /** Return the number of matching fields.
280
281 @param id The field name constant.
282 */
283 BOOST_HTTP_PROTO_DECL
284 std::size_t
285 count(field id) const noexcept;
286
287 /** Return the number of matching fields.
288
289 If `name` refers to a known field,
290 it is faster to call @ref count
291 with a field id instead of a string.
292
293 @param name The field name.
294 */
295 BOOST_HTTP_PROTO_DECL
296 std::size_t
297 count(
298 core::string_view name) const noexcept;
299
300 /** Return an iterator to the matching element if it exists.
301
302 @param id The field name constant.
303 */
304 BOOST_HTTP_PROTO_DECL
305 iterator
306 find(field id) const noexcept;
307
308 /** Return an iterator to the matching element if it exists.
309
310 If `name` refers to a known field,
311 it is faster to call @ref find
312 with a field id instead of a string.
313
314 @param name The field name.
315 */
316 BOOST_HTTP_PROTO_DECL
317 iterator
318 find(
319 core::string_view name) const noexcept;
320
321 /** Return an iterator to the matching element if it exists.
322
323 @param from The position to begin the
324 search from. This can be `end()`.
325
326 @param id The field name constant.
327 */
328 BOOST_HTTP_PROTO_DECL
329 iterator
330 find(
331 iterator from,
332 field id) const noexcept;
333
334 /** Return an iterator to the matching element if it exists.
335
336 If `name` refers to a known field,
337 it is faster to call @ref find
338 with a field id instead of a string.
339
340 @param from The position to begin the
341 search from. This can be `end()`.
342
343 @param name The field name.
344 */
345 BOOST_HTTP_PROTO_DECL
346 iterator
347 find(
348 iterator from,
349 core::string_view name) const noexcept;
350
351 /** Return an iterator to the matching element if it exists.
352
353 @param before One past the position
354 to begin the search from. This can
355 be `end()`.
356
357 @param id The field name constant.
358 */
359 BOOST_HTTP_PROTO_DECL
360 iterator
361 find_last(
362 iterator before,
363 field id) const noexcept;
364
365 /** Return an iterator to the matching element if it exists.
366
367 If `name` refers to a known field,
368 it is faster to call @ref find_last
369 with a field id instead of a string.
370
371 @param before One past the position
372 to begin the search from. This can
373 be `end()`.
374
375 @param name The field name.
376 */
377 BOOST_HTTP_PROTO_DECL
378 iterator
379 find_last(
380 iterator before,
381 core::string_view name) const noexcept;
382
383 /** Return the value of a field or a default if missing.
384
385 @param id The field name constant.
386
387 @param s The value to be returned if
388 field does not exist.
389 */
390 BOOST_HTTP_PROTO_DECL
391 core::string_view
392 value_or(
393 field id,
394 core::string_view s) const noexcept;
395
396 /** Return the value of a field or a default if missing.
397
398 If `name` refers to a known field,
399 it is faster to call @ref value_or
400 with a field id instead of a string.
401
402 @param name The field name.
403
404 @param s The value to be returned if
405 field does not exist.
406 */
407 BOOST_HTTP_PROTO_DECL
408 core::string_view
409 value_or(
410 core::string_view name,
411 core::string_view s) const noexcept;
412
413 /** Return a forward range containing values for all matching fields.
414
415 @param id The field name constant.
416 */
417 BOOST_HTTP_PROTO_DECL
418 subrange
419 find_all(field id) const noexcept;
420
421 /** Return a forward range containing values for all matching fields.
422
423 If `name` refers to a known field,
424 it is faster to call @ref find_all
425 with a field id instead of a string.
426
427 @param name The field name.
428 */
429 BOOST_HTTP_PROTO_DECL
430 subrange
431 find_all(
432 core::string_view name) const noexcept;
433 };
434
435 /** Format the container to the output stream
436
437 This function serializes the container to
438 the specified output stream.
439
440 @par Example
441 @code
442 request req;
443 std::stringstream ss;
444 ss << req;
445 assert( ss.str() == "GET / HTTP/1.1\r\n\r\n" );
446 @endcode
447
448 @par Effects
449 @code
450 return os << f.buffer();
451 @endcode
452
453 @par Complexity
454 Linear in `f.buffer().size()`
455
456 @par Exception Safety
457 Basic guarantee.
458
459 @return A reference to the output stream, for chaining
460
461 @param os The output stream to write to.
462
463 @param f The container to write.
464 */
465 BOOST_HTTP_PROTO_DECL
466 std::ostream&
467 operator<<(
468 std::ostream& os,
469 const fields_view_base& f);
470
471 } // http_proto
472 } // boost
473
474 #include <boost/http_proto/impl/fields_view_base.hpp>
475
476 #endif
477