diff --git a/docassemble/EFSPIntegration/efm_client.py b/docassemble/EFSPIntegration/efm_client.py index 70b3999..f1c913b 100644 --- a/docassemble/EFSPIntegration/efm_client.py +++ b/docassemble/EFSPIntegration/efm_client.py @@ -20,7 +20,12 @@ ) from docassemble.AssemblyLine.al_document import ALDocumentBundle from docassemble.AssemblyLine.al_general import ALIndividual -from .py_efsp_client import ApiResponse, EfspConnection, _user_visible_resp +from .py_efsp_client import ( + ApiResponse, + LoggerWithContext, + EfspConnection, + _user_visible_resp, +) __all__ = ["ApiResponse", "ProxyConnection", "state_name_to_code"] @@ -187,6 +192,16 @@ def _call_proxy(self, req: PreparedRequest) -> ApiResponse: return _user_visible_resp(f"Url {self.base_url} is not valid: {ex}") return _user_visible_resp(resp) + def get_logger(self): + if not hasattr(self, "logger"): + # Copying what we do in `EfspConnection.get_logger` because it needs to + # wrap the logger we're trying to make here. + self.logger = LoggerWithContext( + DALogger(logging.getLogger("docassemble")), + {"session_id": self.get_session_id()}, + ) + return self.logger + def authenticate_user( self, tyler_email: str = None, diff --git a/docassemble/EFSPIntegration/py_efsp_client.py b/docassemble/EFSPIntegration/py_efsp_client.py index 68724ee..963ee8d 100644 --- a/docassemble/EFSPIntegration/py_efsp_client.py +++ b/docassemble/EFSPIntegration/py_efsp_client.py @@ -64,10 +64,10 @@ def __str__(self): else: err_str = "" msg = f"response_code: {self.response_code}, {err_str}data: {self.data}" - if self.session_id: - msg += f", session_id: {self.session_id}" - if self.req_id: - msg += f", req_id: {self.req_id}" + if self.get_session_id(): + msg += f", session_id: {self.get_session_id()}" + if self.get_req_id(): + msg += f", req_id: {self.get_req_id()}" return msg def __repr__(self): @@ -76,6 +76,16 @@ def __repr__(self): def is_ok(self): return self.response_code in [200, 201, 202, 203, 204, 205] + def get_session_id(self): + if not hasattr(self, "session_id"): + self.session_id = None + return self.session_id + + def get_req_id(self): + if not hasattr(self, "req_id"): + self.req_id = None + return self.req_id + def _user_visible_resp(resp: Union[Response, str, None]) -> ApiResponse: """This function takes the essentials of a response and puts in into @@ -159,12 +169,25 @@ def _send(self, to_send: Request, *, req_id: Optional[UUID] = None) -> ApiRespon if req_id is None: req_id = uuid4() to_send.headers["efsp-request-id"] = str(req_id) - to_send.headers["efsp-session-id"] = self.session_id - self.logger.info( + to_send.headers["efsp-session-id"] = self.get_session_id() + self.get_logger().info( f"Calling {to_send.method} on {to_send.url}", extra={"req-id": str(req_id)} ) return self._call_proxy(self.proxy_client.prepare_request(to_send)) + def get_session_id(self): + if not hasattr(self, "session_id"): + # Migration from older interviews, to start passing observability headers + self.session_id = str(uuid4()) + return self.session_id + + def get_logger(self): + if not hasattr(self, "logger"): + self.logger = LoggerWithContext( + logging.getLogger(), {"session_id": self.get_session_id()} + ) + return self.logger + @staticmethod def verbose_logging(turn_on: bool) -> None: if turn_on: @@ -222,7 +245,7 @@ def authenticate_user( if jurisdiction is None: jurisdiction = self.default_jurisdiction - self.logger.info( + self.get_logger().info( f"authenticating with jurisdiction: {jurisdiction}", extra={"req-id": str(req_id)}, ) @@ -274,7 +297,7 @@ def register_user( If it's FIRM_ADMINISTRATOR or FIRM_ADMIN_NEW_MEMBER, you need a firm_name_or_id """ req_id = uuid4() - self.logger.info("Attempting to register user", extra={"req-id": req_id}) + self.get_logger().info("Attempting to register user", extra={"req-id": req_id}) registration_type = registration_type.upper() if "phone_number" in person: phone_number = person["phone_number"] @@ -319,7 +342,7 @@ def is_valid_password(self, password: str) -> Optional[bool]: if results.data: password_regex = results.data.get("regularexpression", ".*") else: - self.logger.warning(f"No password rules found: {results}") + self.get_logger().warning(f"No password rules found: {results}") password_regex = ".*" try: @@ -778,12 +801,12 @@ def reserve_court_date( range_after_str = range_after.isoformat() else: range_after_str = range_after or "" - self.logger.debug(f"after: {range_after}", extra={"req-id": req_id}) + self.get_logger().debug(f"after: {range_after}", extra={"req-id": req_id}) if range_before is not None and not isinstance(range_before, str): range_before_str = range_before.isoformat() else: range_before_str = range_before or "" - self.logger.debug(f"before: {range_before}", extra={"req-id": req_id}) + self.get_logger().debug(f"before: {range_before}", extra={"req-id": req_id}) if estimated_duration is not None: estimated_duration = int(estimated_duration) * 60 * 60 req = Request(