16
16
17
17
import math
18
18
import json
19
+ import re
19
20
20
21
try :
21
22
import flask
@@ -55,12 +56,13 @@ def get_request_data_from_flask():
55
56
"""Get http_request and trace data from flask request headers.
56
57
57
58
Returns:
58
- Tuple[Optional[dict], Optional[str]]:
59
- Data related to the current http request and the trace_id for the
60
- request. Both fields will be None if a flask request isn't found.
59
+ Tuple[Optional[dict], Optional[str], Optional[str]]:
60
+ Data related to the current http request, trace_id, and span_id for
61
+ the request. All fields will be None if a django request isn't
62
+ found.
61
63
"""
62
64
if flask is None or not flask .request :
63
- return None , None
65
+ return None , None , None
64
66
65
67
# build http_request
66
68
http_request = {
@@ -73,27 +75,26 @@ def get_request_data_from_flask():
73
75
"protocol" : flask .request .environ .get (_PROTOCOL_HEADER ),
74
76
}
75
77
76
- # find trace id
77
- trace_id = None
78
+ # find trace id and span id
78
79
header = flask .request .headers .get (_FLASK_TRACE_HEADER )
79
- if header :
80
- trace_id = header .split ("/" , 1 )[0 ]
80
+ trace_id , span_id = _parse_trace_span (header )
81
81
82
- return http_request , trace_id
82
+ return http_request , trace_id , span_id
83
83
84
84
85
85
def get_request_data_from_django ():
86
86
"""Get http_request and trace data from django request headers.
87
87
88
88
Returns:
89
- Tuple[Optional[dict], Optional[str]]:
90
- Data related to the current http request and the trace_id for the
91
- request. Both fields will be None if a django request isn't found.
89
+ Tuple[Optional[dict], Optional[str], Optional[str]]:
90
+ Data related to the current http request, trace_id, and span_id for
91
+ the request. All fields will be None if a django request isn't
92
+ found.
92
93
"""
93
94
request = _get_django_request ()
94
95
95
96
if request is None :
96
- return None , None
97
+ return None , None , None
97
98
98
99
# convert content_length to int if it exists
99
100
content_length = None
@@ -112,32 +113,55 @@ def get_request_data_from_django():
112
113
"protocol" : request .META .get (_PROTOCOL_HEADER ),
113
114
}
114
115
115
- # find trace id
116
- trace_id = None
116
+ # find trace id and span id
117
117
header = request .META .get (_DJANGO_TRACE_HEADER )
118
- if header :
119
- trace_id = header .split ("/" , 1 )[0 ]
118
+ trace_id , span_id = _parse_trace_span (header )
120
119
121
- return http_request , trace_id
120
+ return http_request , trace_id , span_id
121
+
122
+
123
+ def _parse_trace_span (header ):
124
+ """Given an X_CLOUD_TRACE header, extract the trace and span ids.
125
+
126
+ Args:
127
+ header (str): the string extracted from the X_CLOUD_TRACE header
128
+ Returns:
129
+ Tuple[Optional[dict], Optional[str]]:
130
+ The trace_id and span_id extracted from the header
131
+ Each field will be None if not found.
132
+ """
133
+ trace_id = None
134
+ span_id = None
135
+ if header :
136
+ try :
137
+ split_header = header .split ("/" , 1 )
138
+ trace_id = split_header [0 ]
139
+ header_suffix = split_header [1 ]
140
+ # the span is the set of alphanumeric characters after the /
141
+ span_id = re .findall (r"^\w+" , header_suffix )[0 ]
142
+ except IndexError :
143
+ pass
144
+ return trace_id , span_id
122
145
123
146
124
147
def get_request_data ():
125
148
"""Helper to get http_request and trace data from supported web
126
149
frameworks (currently supported: Flask and Django).
127
150
128
151
Returns:
129
- Tuple[Optional[dict], Optional[str]]:
130
- Data related to the current http request and the trace_id for the
131
- request. Both fields will be None if a supported web request isn't found.
152
+ Tuple[Optional[dict], Optional[str], Optional[str]]:
153
+ Data related to the current http request, trace_id, and span_id for
154
+ the request. All fields will be None if a django request isn't
155
+ found.
132
156
"""
133
157
checkers = (
134
158
get_request_data_from_django ,
135
159
get_request_data_from_flask ,
136
160
)
137
161
138
162
for checker in checkers :
139
- http_request , trace_id = checker ()
163
+ http_request , trace_id , span_id = checker ()
140
164
if http_request is not None :
141
- return http_request , trace_id
165
+ return http_request , trace_id , span_id
142
166
143
- return None , None
167
+ return None , None , None
0 commit comments