Repository: acl-org/acl-anthology

Issue:
Wrong revision links
[P16-2078](https://www.aclweb.org/anthology/papers/P/P16/P16-2078/) is listed as having a revision, but the revision links to P16-1200v2 instead. The correct file [P16-2078v2](https://www.aclweb.org/anthology/P16-2078v2) does exist on the server, though. I have no idea if this is the only case or if there are more.

If we can assume that the file names for revisions and errata will always begin with the paper ID, I could add a check for this into the Python Anthology module that throws an error if they don't match—this way, the problem would show up on Travis CI.


Discussion:
I think this is worthwhile. While I don't see it explicitly stated anywhere, this is the convention that's been followed, and I'd like to see it made official. It matches the arXiv style decently well.
Yes, let’s check for this error. Strange. 
We should also document this convention, maybe in a wiki page. 
My guess is that because (a) P16-1200 also was revised and (b) revisions are done manually, this is a copy-and-paste error. Would be good to have protection against these in the future.

Resolving patch:
diff --git a/bin/anthology/papers.py b/bin/anthology/papers.py
--- a/bin/anthology/papers.py
+++ b/bin/anthology/papers.py
@@ -91,7 +91,7 @@ def _parse_element(self, paper_element):
                 value = {
                     "filename": element.text,
                     "type": element.get("type", "attachment"),
-                    "url": infer_attachment_url(element.text),
+                    "url": infer_attachment_url(element.text, self.full_id),
                 }
             elif tag in ("author", "editor"):
                 value = PersonName.from_element(element)
@@ -109,6 +109,12 @@ def _parse_element(self, paper_element):
                             ),
                         }
                     ]
+                if not element.text.startswith(self.full_id):
+                    log.error(
+                        "{} must begin with paper ID '{}', but is '{}'".format(
+                            tag, self.full_id, element.text
+                        )
+                    )
                 value = {
                     "value": element.text,
                     "id": element.get("id"),
@@ -122,13 +128,13 @@ def _parse_element(self, paper_element):
                 value = {
                     "filename": element.get("href"),
                     "type": element.get("tag", "video"),
-                    "url": infer_attachment_url(element.get("href")),
+                    "url": infer_attachment_url(element.get("href"), self.full_id),
                 }
             elif tag in ("dataset", "software"):
                 value = {
                     "filename": element.text,
                     "type": tag,
-                    "url": infer_attachment_url(element.text),
+                    "url": infer_attachment_url(element.text, self.full_id),
                 }
                 tag = "attachment"
             else:
diff --git a/bin/anthology/utils.py b/bin/anthology/utils.py
--- a/bin/anthology/utils.py
+++ b/bin/anthology/utils.py
@@ -72,11 +72,17 @@ def remove_extra_whitespace(text):
     return re.sub(" +", " ", text.replace("\n", "").strip())
 
 
-def infer_attachment_url(filename):
+def infer_attachment_url(filename, parent_id=None):
     # If filename has a network location, it's interpreted as a complete URL
     if urlparse(filename).netloc:
         return filename
     # Otherwise, treat it as an internal filename
+    if parent_id is not None and not filename.startswith(parent_id):
+        logging.error(
+            "attachment must begin with paper ID '{}', but is '{}'".format(
+                parent_id, filename
+            )
+        )
     return data.ATTACHMENT_URL.format(filename)
 
 


Test patch: