{"record":{"id":"bea2afb2239b3490","repo":"netdata/netdata","slug":"use-normal-urllib3-poolmanager-instead-of-appengin","errorCode":null,"errorMessage":"Use normal urllib3.PoolManager instead of AppEngineManageron Managed VMs, as using URLFetch is not necessary in this environment.","messagePattern":"Use normal urllib3\\.PoolManager instead of AppEngineManageron Managed VMs, as using URLFetch is not necessary in this environment\\.","errorType":"exception","errorClass":"AppEnginePlatformError","httpStatus":null,"severity":"error","filePath":"src/collectors/python.d.plugin/python_modules/urllib3/contrib/appengine.py","lineNumber":107,"sourceCode":"    Notably it will raise an :class:`AppEnginePlatformError` if:\n        * URLFetch is not available.\n        * If you attempt to use this on App Engine Flexible, as full socket\n          support is available.\n        * If a request size is more than 10 megabytes.\n        * If a response size is more than 32 megabtyes.\n        * If you use an unsupported request method such as OPTIONS.\n\n    Beyond those cases, it will raise normal urllib3 errors.\n    \"\"\"\n\n    def __init__(self, headers=None, retries=None, validate_certificate=True,\n                 urlfetch_retries=True):\n        if not urlfetch:\n            raise AppEnginePlatformError(\n                \"URLFetch is not available in this environment.\")\n\n        if is_prod_appengine_mvms():\n            raise AppEnginePlatformError(\n                \"Use normal urllib3.PoolManager instead of AppEngineManager\"\n                \"on Managed VMs, as using URLFetch is not necessary in \"\n                \"this environment.\")\n\n        warnings.warn(\n            \"urllib3 is using URLFetch on Google App Engine sandbox instead \"\n            \"of sockets. To use sockets directly instead of URLFetch see \"\n            \"https://urllib3.readthedocs.io/en/latest/reference/urllib3.contrib.html.\",\n            AppEnginePlatformWarning)\n\n        RequestMethods.__init__(self, headers)\n        self.validate_certificate = validate_certificate\n        self.urlfetch_retries = urlfetch_retries\n\n        self.retries = retries or Retry.DEFAULT\n\n    def __enter__(self):\n        return self","sourceCodeStart":89,"sourceCodeEnd":125,"githubUrl":"https://github.com/netdata/netdata/blob/4864de85e26f6734d92cfc27ccbeff5921f49938/src/collectors/python.d.plugin/python_modules/urllib3/contrib/appengine.py#L89-L125","documentation":"AppEnginePlatformError raised by AppEngineManager.__init__ when is_prod_appengine_mvms() is true - the code is running on Google App Engine Managed VMs (the precursor of the Flexible Environment). There, full socket access is available, so URLFetch (and its limits) is unnecessary; urllib3 explicitly tells you to use the normal PoolManager instead.","triggerScenarios":"Deploying code that constructs AppEngineManager to App Engine Managed VMs / Flexible Environment instead of the standard sandbox. Detection triggers on the GAE environment variables that identify VM-based runtimes.","commonSituations":"Migrating an app from GAE standard to Flexible/Managed VMs while keeping the AppEngineManager selection logic; shared libraries that picked the manager based on 'am I on GAE' without distinguishing standard vs flexible.","solutions":["Replace AppEngineManager() with urllib3.PoolManager() in that environment - sockets work normally there.","Make the selection conditional: AppEngineManager only when is_prod_appengine() and not is_prod_appengine_mvms(); otherwise PoolManager.","Move off the deprecated Managed VM/URLFetch stack entirely to the modern flexible runtimes."],"exampleFix":"# before\nfrom urllib3.contrib.appengine import AppEngineManager\nhttp = AppEngineManager()  # on Managed VMs -> AppEnginePlatformError\n\n# after\nfrom urllib3.contrib.appengine import AppEngineManager, is_prod_appengine, is_prod_appengine_mvms\nimport urllib3\nif is_prod_appengine() and not is_prod_appengine_mvms():\n    http = AppEngineManager()\nelse:\n    http = urllib3.PoolManager()","handlingStrategy":"validation","validationCode":"from urllib3.contrib.appengine import is_prod_appengine, is_prod_appengine_mvms\n\ndef pick_manager():\n    if is_prod_appengine() and not is_prod_appengine_mvms():\n        from urllib3.contrib.appengine import AppEngineManager\n        return AppEngineManager()\n    import urllib3\n    return urllib3.PoolManager()  # Managed VMs / Flexible / anywhere else","typeGuard":null,"tryCatchPattern":"from urllib3.contrib.appengine import AppEngineManager, AppEnginePlatformError\n\ntry:\n    http = AppEngineManager()\nexcept AppEnginePlatformError as e:\n    if 'Managed VMs' in str(e):\n        import urllib3\n        http = urllib3.PoolManager()  # sockets are fine here\n    else:\n        raise","preventionTips":["Distinguish GAE standard from Flexible/Managed VMs before choosing a manager: is_prod_appengine_mvms() must be False.","Centralize transport selection in one factory so migrating runtimes flips behavior in one place."],"tags":["appengine","gae","managed-vms","flexible-environment","urlfetch","urllib3"],"backgroundTag":null,"analyzedSha":"4864de85e26f6734d92cfc27ccbeff5921f49938","analyzedAt":"2026-08-15T09:12:38.226Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}