1717
1818import os
1919import configparser
20+ import shlex
21+ import subprocess
2022from typing import List , Optional , Union
23+ from os .path import expanduser , expandvars
2124
2225from gitlab .const import USER_AGENT
2326
@@ -33,6 +36,10 @@ def _env_config() -> List[str]:
3336 os .path .expanduser ("~/.python-gitlab.cfg" ),
3437]
3538
39+ HELPER_PREFIX = "helper:"
40+
41+ HELPER_ATTRIBUTES = ["job_token" , "http_password" , "private_token" , "oauth_token" ]
42+
3643
3744class ConfigError (Exception ):
3845 pass
@@ -50,6 +57,10 @@ class GitlabConfigMissingError(ConfigError):
5057 pass
5158
5259
60+ class GitlabConfigHelperError (ConfigError ):
61+ pass
62+
63+
5364class GitlabConfigParser (object ):
5465 def __init__ (
5566 self , gitlab_id : Optional [str ] = None , config_files : Optional [List [str ]] = None
@@ -150,6 +161,8 @@ def __init__(
150161 except Exception :
151162 pass
152163
164+ self ._get_values_from_helper ()
165+
153166 self .api_version = "4"
154167 try :
155168 self .api_version = self ._config .get ("global" , "api_version" )
@@ -192,3 +205,31 @@ def __init__(
192205 self .user_agent = self ._config .get (self .gitlab_id , "user_agent" )
193206 except Exception :
194207 pass
208+
209+ def _get_values_from_helper (self ):
210+ """Update attributes that may get values from an external helper program"""
211+ for attr in HELPER_ATTRIBUTES :
212+ value = getattr (self , attr )
213+ if not isinstance (value , str ):
214+ continue
215+
216+ if not value .lower ().strip ().startswith (HELPER_PREFIX ):
217+ continue
218+
219+ helper = value [len (HELPER_PREFIX ) :].strip ()
220+ commmand = [expanduser (expandvars (token )) for token in shlex .split (helper )]
221+
222+ try :
223+ value = (
224+ subprocess .check_output (commmand , stderr = subprocess .PIPE )
225+ .decode ("utf-8" )
226+ .strip ()
227+ )
228+ except subprocess .CalledProcessError as e :
229+ stderr = e .stderr .decode ().strip ()
230+ raise GitlabConfigHelperError (
231+ f"Failed to read { attr } value from helper "
232+ f"for { self .gitlab_id } :\n { stderr } "
233+ ) from e
234+
235+ setattr (self , attr , value )
0 commit comments