prompt: You will be provided with a partial code base and an issue statement explaining a problem to resolve.
  <issue>
  SecureDrop backups from previous versions don't work if database migration has occurred
  ## Description
  
  Backup restore (https://github.com/freedomofpress/securedrop/blob/develop/install_files/ansible-base/roles/restore/files/restore.py) script does not apply database migrations, and as such breaks the application upon backup restore. Manual workaround that appears to have no side-effects is to run `sudo dpkg-reconfigure securedrop-app-code` on the app server.
  
  ## Steps to Reproduce
  
  1. Install SecureDrop 0.8.0
  2. `securedrop-admin backup`
  3. Upgrade to 0.9.0 (or higher)
  4. `securedrop-admin restore`
  5. Observe source and journalist interface return error 500
  
  ## Expected Behavior
  
  The application should be operational.
  
  ## Actual Behavior
  
  The source and journalist interfaces return error 500s.
  
  ## Comments
  
  Running `sudo dpkg-reconfigure securedrop-app-code` calls the postinst script which will apply migration. Based on my testing, this seems to work reliably.
  
  </issue>
  <code>
  [start of install_files/ansible-base/roles/restore/files/restore.py]
  1 #!/usr/bin/python2.7
  2 """
  3 This script and backup archive should be copied to the App server and run by
  4 the Ansible playbook. When run (as root), it restores the contents of the 0.3
  5 backup file to the machine it's run on.
  6 
  7 python restore.py sd-backup-TIMESTAMP.tar.gz
  8 """
  9 
  10 import os
  11 import subprocess
  12 import sys
  13 import tarfile
  14 
  15 
  16 def verify_args():
  17     usage = """
  18 Usage: restore.py <backup file>
  19 
  20     <backup file>  Path to a SecureDrop 0.3 backup created by backup.py"
  21     """
  22     if len(sys.argv) != 2:
  23         print(usage)
  24         sys.exit(1)
  25 
  26     if not os.path.exists(sys.argv[1]):
  27         print("<backup file> '{}' not found".format(sys.argv[1]))
  28         sys.exit(1)
  29 
  30     if os.geteuid() != 0:
  31         print("This program must be run as root!")
  32         sys.exit(1)
  33 
  34 
  35 def main():
  36     verify_args()
  37 
  38     with tarfile.open(sys.argv[1], 'r:*') as backup:
  39         # This assumes that both the old installation (source of the backup)
  40         # and the new installation (destination of the restore) used the
  41         # default paths for various locations.
  42         backup.extractall(path='/')
  43 
  44     # Reload Tor and the web server so they pick up the new configuration
  45     # If the process exits with a non-zero return code, raises an exception.
  46     subprocess.check_call(['service', 'apache2', 'restart'])
  47     subprocess.check_call(['service', 'tor', 'reload'])
  48 
  49 
  50 if __name__ == "__main__":
  51     main()
  52
  [end of install_files/ansible-base/roles/restore/files/restore.py]
  </code>
  
  I need you to solve this issue by generating a single patch file that I can apply directly to this repository using git apply. Please respond with a single patch file in the following format.
  <patch>
  diff --git a/file.py b/file.py
  --- a/file.py
  +++ b/file.py
  @@ -1,27 +1,35 @@
   def euclidean(a, b):
  -    while b:
  -        a, b = b, a % b
  -    return a
  +    if b == 0:
  +        return a
  +    return euclidean(b, a % b)
   
   
   def bresenham(x0, y0, x1, y1):
       points = []
       dx = abs(x1 - x0)
       dy = abs(y1 - y0)
  -    sx = 1 if x0 < x1 else -1
  -    sy = 1 if y0 < y1 else -1
  -    err = dx - dy
  +    x, y = x0, y0
  +    sx = -1 if x0 > x1 else 1
  +    sy = -1 if y0 > y1 else 1
   
  -    while True:
  -        points.append((x0, y0))
  -        if x0 == x1 and y0 == y1:
  -            break
  -        e2 = 2 * err
  -        if e2 > -dy:
  -            err -= dy
  -            x0 += sx
  -        if e2 < dx:
  -            err += dx
  -            y0 += sy
  +    if dx > dy:
  +        err = dx / 2.0
  +        while x != x1:
  +            points.append((x, y))
  +            err -= dy
  +            if err < 0:
  +                y += sy
  +                err += dx
  +            x += sx
  +    else:
  +        err = dy / 2.0
  +        while y != y1:
  +            points.append((x, y))
  +            err -= dx
  +            if err < 0:
  +                x += sx
  +                err += dy
  +            y += sy
  +
  +    points.append((x, y))
       return points
  
  </patch>
golden_diff: diff --git a/install_files/ansible-base/roles/restore/files/restore.py b/install_files/ansible-base/roles/restore/files/restore.py
  --- a/install_files/ansible-base/roles/restore/files/restore.py
  +++ b/install_files/ansible-base/roles/restore/files/restore.py
  @@ -45,6 +45,8 @@
       # If the process exits with a non-zero return code, raises an exception.
       subprocess.check_call(['service', 'apache2', 'restart'])
       subprocess.check_call(['service', 'tor', 'reload'])
  +    # Apply database migrations (if backed-up version < version to restore)
  +    subprocess.check_call(['dpkg-reconfigure', 'securedrop-app-code'])
   
   
   if __name__ == "__main__":
  
verification_info: {"golden_diff": "diff --git a/install_files/ansible-base/roles/restore/files/restore.py b/install_files/ansible-base/roles/restore/files/restore.py\n--- a/install_files/ansible-base/roles/restore/files/restore.py\n+++ b/install_files/ansible-base/roles/restore/files/restore.py\n@@ -45,6 +45,8 @@\n     # If the process exits with a non-zero return code, raises an exception.\n     subprocess.check_call(['service', 'apache2', 'restart'])\n     subprocess.check_call(['service', 'tor', 'reload'])\n+    # Apply database migrations (if backed-up version < version to restore)\n+    subprocess.check_call(['dpkg-reconfigure', 'securedrop-app-code'])\n \n \n if __name__ == \"__main__\":\n", "issue": "SecureDrop backups from previous versions don't work if database migration has occurred\n## Description\r\n\r\nBackup restore (https://github.com/freedomofpress/securedrop/blob/develop/install_files/ansible-base/roles/restore/files/restore.py) script does not apply database migrations, and as such breaks the application upon backup restore. Manual workaround that appears to have no side-effects is to run `sudo dpkg-reconfigure securedrop-app-code` on the app server.\r\n\r\n## Steps to Reproduce\r\n\r\n1. Install SecureDrop 0.8.0\r\n2. `securedrop-admin backup`\r\n3. Upgrade to 0.9.0 (or higher)\r\n4. `securedrop-admin restore`\r\n5. Observe source and journalist interface return error 500\r\n\r\n## Expected Behavior\r\n\r\nThe application should be operational.\r\n\r\n## Actual Behavior\r\n\r\nThe source and journalist interfaces return error 500s.\r\n\r\n## Comments\r\n\r\nRunning `sudo dpkg-reconfigure securedrop-app-code` calls the postinst script which will apply migration. Based on my testing, this seems to work reliably.\n", "before_files": [{"content": "#!/usr/bin/python2.7\n\"\"\"\nThis script and backup archive should be copied to the App server and run by\nthe Ansible playbook. When run (as root), it restores the contents of the 0.3\nbackup file to the machine it's run on.\n\npython restore.py sd-backup-TIMESTAMP.tar.gz\n\"\"\"\n\nimport os\nimport subprocess\nimport sys\nimport tarfile\n\n\ndef verify_args():\n    usage = \"\"\"\nUsage: restore.py <backup file>\n\n    <backup file>  Path to a SecureDrop 0.3 backup created by backup.py\"\n    \"\"\"\n    if len(sys.argv) != 2:\n        print(usage)\n        sys.exit(1)\n\n    if not os.path.exists(sys.argv[1]):\n        print(\"<backup file> '{}' not found\".format(sys.argv[1]))\n        sys.exit(1)\n\n    if os.geteuid() != 0:\n        print(\"This program must be run as root!\")\n        sys.exit(1)\n\n\ndef main():\n    verify_args()\n\n    with tarfile.open(sys.argv[1], 'r:*') as backup:\n        # This assumes that both the old installation (source of the backup)\n        # and the new installation (destination of the restore) used the\n        # default paths for various locations.\n        backup.extractall(path='/')\n\n    # Reload Tor and the web server so they pick up the new configuration\n    # If the process exits with a non-zero return code, raises an exception.\n    subprocess.check_call(['service', 'apache2', 'restart'])\n    subprocess.check_call(['service', 'tor', 'reload'])\n\n\nif __name__ == \"__main__\":\n    main()\n", "path": "install_files/ansible-base/roles/restore/files/restore.py"}]}