Repository: civisanalytics/civis-python

Issue:
Add `ignore_deprecated` flag to `APIClient`
The API client currently ignores any endpoints with a deprecation warning. This means that endpoints effectively cannot be deprecated-- once they are tagged deprecated, they are inaccessible from the client.

One option would be to automatically pull in these endpoints, which would allow for deprecation, but would make deprecated endpoints visible to new users, which may not be desirable. 

The alternative I'd propose is to add an `ignore_deprecated` flag when instantiating the client, which defaults to `True`. This means that existing code based on newly deprecated endpoints would still break, but could be updated to work until the endpoint is removed entirely.

Discussion:
elsander: @stephen-hoover Wanted to flag this for you, since you might have more context on the original decision here.

@salilgupta1 , can you note in the description that this closes #345 ?
stephen-hoover: > @stephen-hoover Wanted to flag this for you, since you might have more context on the original decision here.

Thanks for the flag, but I don't recall being involved in any discussions around the initial implementation of this part of the code.



Patch:
diff --git a/civis/resources/_resources.py b/civis/resources/_resources.py
index 0a10aa3..cbe0ec5 100644
--- a/civis/resources/_resources.py
+++ b/civis/resources/_resources.py
@@ -132,6 +132,16 @@ def docs_from_properties(properties, level=0):
     return docs
 
 
+def deprecated_notice(deprecation_warning):
+    """ Return a doc string element for the deprecation notice. The
+    doc string can be an empty string if the warning is None
+    """
+    if deprecation_warning is None:
+        return ""
+
+    return "Deprecation warning!\n------------------\n" + deprecation_warning
+
+
 def doc_from_responses(responses):
     """ Return a doc string element from a responses object. The
     doc string describes the returned objects of a function.
@@ -411,13 +421,14 @@ def parse_method(verb, operation, path):
     summary = operation["summary"]
     params = operation.get("parameters", [])
     responses = operation["responses"]
-    deprecated = operation.get('deprecated', False)
-    if 'deprecated' in summary.lower() or deprecated:
+    deprecation_warning = operation.get("x-deprecation-warning", None)
+    if 'deprecated' in summary.lower():
         return None
 
     args, param_doc = parse_params(params, summary, verb)
     response_doc = doc_from_responses(responses)
-    docs = join_doc_elements(param_doc, response_doc)
+    deprecation_notice = deprecated_notice(deprecation_warning)
+    docs = join_doc_elements(deprecation_notice, param_doc, response_doc)
     name = parse_method_name(verb, path)
 
     method = create_method(args, verb, name, path, docs)


Test patch:
diff --git a/civis/tests/test_resources.py b/civis/tests/test_resources.py
index 4c46091..2ce2d59 100644
--- a/civis/tests/test_resources.py
+++ b/civis/tests/test_resources.py
@@ -126,6 +126,18 @@ def test_docs_from_properties():
     assert sorted(y) == sorted(['    - a : string', '    - b : integer'])
 
 
+def test_deprecated_notice():
+    deprecation_warning = "This endpoint is no longer supported"
+    notice = _resources.deprecated_notice(deprecation_warning)
+
+    assert "Deprecation warning!" in notice
+    assert deprecation_warning in notice
+
+
+def test_deprecated_notice_handles_none():
+    assert _resources.deprecated_notice(None) == ""
+
+
 def test_doc_from_responses():
     responses = OrderedDict([('200', OrderedDict([('description', 'success'), ('schema', OrderedDict([('type', 'array'), ('items', OrderedDict([('type', 'object'), ('properties', OrderedDict([('id', OrderedDict([('description', 'The ID of the credential.'), ('type', 'integer')])), ('name', OrderedDict([('description', 'The name identifying the credential'), ('type', 'string')])), ('type', OrderedDict([('description', "The credential's type."), ('type', 'string')])), ('username', OrderedDict([('description', 'The username for the credential.'), ('type', 'string')])), ('description', OrderedDict([('description', 'A long description of the credential.'), ('type', 'string')])), ('owner', OrderedDict([('description', 'The name of the user who this credential belongs to.'), ('type', 'string')])), ('remoteHostId', OrderedDict([('description', 'The ID of the remote host associated with this credential.'), ('type', 'integer')])), ('remoteHostName', OrderedDict([('description', 'The name of the remote host associated with this credential.'), ('type', 'string')])), ('createdAt', OrderedDict([('description', 'The creation time for this credential.'), ('type', 'string'), ('format', 'time')])), ('updatedAt', OrderedDict([('description', 'The last modification time for this credential.'), ('type', 'string'), ('format', 'time')]))]))]))]))]))])  # noqa: E501
     x = _resources.doc_from_responses(responses)