1+ import os
2+ import subprocess
13import sys
24
35from sentry_sdk .hub import Hub
46from sentry_sdk .integrations import Integration
5- from sentry_sdk .tracing import record_http_request
7+ from sentry_sdk .tracing import EnvironHeaders , record_http_request
68
79
810try :
@@ -17,10 +19,11 @@ class StdlibIntegration(Integration):
1719 @staticmethod
1820 def setup_once ():
1921 # type: () -> None
20- install_httplib ()
22+ _install_httplib ()
23+ _install_subprocess ()
2124
2225
23- def install_httplib ():
26+ def _install_httplib ():
2427 # type: () -> None
2528 real_putrequest = HTTPConnection .putrequest
2629 real_getresponse = HTTPConnection .getresponse
@@ -90,3 +93,47 @@ def getresponse(self, *args, **kwargs):
9093
9194 HTTPConnection .putrequest = putrequest
9295 HTTPConnection .getresponse = getresponse
96+
97+
98+ def _get_argument (args , kwargs , name , position , setdefault = None ):
99+ if name in kwargs :
100+ rv = kwargs [name ]
101+ if rv is None and setdefault is not None :
102+ rv = kwargs [name ] = setdefault
103+ elif position < len (args ):
104+ rv = args [position ]
105+ if rv is None and setdefault is not None :
106+ rv = args [position ] = setdefault
107+ else :
108+ rv = kwargs [name ] = setdefault
109+
110+ return rv
111+
112+
113+ def _install_subprocess ():
114+ old_popen_init = subprocess .Popen .__init__
115+
116+ def sentry_patched_popen_init (self , * a , ** kw ):
117+ hub = Hub .current
118+ if hub .get_integration (StdlibIntegration ) is None :
119+ return old_popen_init (self , * a , ** kw )
120+
121+ # do not setdefault! args is required by Popen, doing setdefault would
122+ # make invalid calls valid
123+ args = _get_argument (a , kw , "args" , 0 ) or []
124+ cwd = _get_argument (a , kw , "cwd" , 10 )
125+
126+ for k , v in hub .iter_trace_propagation_headers ():
127+ env = _get_argument (a , kw , "env" , 11 , {})
128+ env ["SUBPROCESS_" + k .upper ().replace ("-" , "_" )] = v
129+
130+ with hub .span (op = "subprocess" , description = " " .join (map (str , args ))) as span :
131+ span .set_tag ("subprocess.cwd" , cwd )
132+
133+ return old_popen_init (self , * a , ** kw )
134+
135+ subprocess .Popen .__init__ = sentry_patched_popen_init
136+
137+
138+ def get_subprocess_traceparent_headers ():
139+ return EnvironHeaders (os .environ , prefix = "SUBPROCESS_" )
0 commit comments