diff --git a/app/src/main/java/org/fdroid/fdroid/RepoUpdater.java b/app/src/main/java/org/fdroid/fdroid/RepoUpdater.java
index 3d6e85fcf..7abd9d7a2 100644
--- a/app/src/main/java/org/fdroid/fdroid/RepoUpdater.java
+++ b/app/src/main/java/org/fdroid/fdroid/RepoUpdater.java
@@ -1,18 +1,48 @@
+/*
+ * Copyright (C) 2016 Blue Jay Wireless
+ * Copyright (C) 2015-2016 Daniel Martí <mvdan@mvdan.cc>
+ * Copyright (C) 2014-2016 Hans-Christoph Steiner <hans@eds.org>
+ * Copyright (C) 2014-2016 Peter Serwylo <peter@serwylo.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
 package org.fdroid.fdroid;
 
+import android.content.ContentResolver;
 import android.content.ContentValues;
 import android.content.Context;
+import android.content.pm.PackageInfo;
+import android.content.pm.PackageManager;
 import android.support.annotation.NonNull;
 import android.support.annotation.Nullable;
 import android.text.TextUtils;
 import android.util.Log;
 
 import org.fdroid.fdroid.data.Apk;
+import org.fdroid.fdroid.data.ApkProvider;
 import org.fdroid.fdroid.data.App;
+import org.fdroid.fdroid.data.AppProvider;
 import org.fdroid.fdroid.data.Repo;
 import org.fdroid.fdroid.data.RepoPersister;
 import org.fdroid.fdroid.data.RepoProvider;
+import org.fdroid.fdroid.data.RepoPushRequest;
 import org.fdroid.fdroid.data.Schema.RepoTable;
+import org.fdroid.fdroid.installer.InstallManagerService;
+import org.fdroid.fdroid.installer.InstallerService;
 import org.fdroid.fdroid.net.Downloader;
 import org.fdroid.fdroid.net.DownloaderFactory;
 import org.xml.sax.InputSource;
@@ -27,6 +57,7 @@ import java.net.URL;
 import java.security.CodeSigner;
 import java.security.cert.Certificate;
 import java.security.cert.X509Certificate;
+import java.util.ArrayList;
 import java.util.Date;
 import java.util.List;
 import java.util.jar.JarEntry;
@@ -37,12 +68,15 @@ import javax.xml.parsers.SAXParser;
 import javax.xml.parsers.SAXParserFactory;
 
 /**
- * Responsible for updating an individual repository. This will:
- *  * Download the index.jar
- *  * Verify that it is signed correctly and by the correct certificate
- *  * Parse the index.xml from the .jar file
- *  * Save the resulting repo, apps, and apks to the database.
- *
+ * Updates the local database with a repository's app/apk metadata and verifying
+ * the JAR signature on the file received from the repository. As an overview:
+ * <ul>
+ * <li>Download the {@code index.jar}
+ * <li>Verify that it is signed correctly and by the correct certificate
+ * <li>Parse the {@code index.xml} that is in {@code index.jar}
+ * <li>Save the resulting repo, apps, and apks to the database.
+ * <li>Process any push install/uninstall requests included in the repository
+ * </ul>
  * <b>WARNING</b>: this class is the central piece of the entire security model of
  * FDroid!  Avoid modifying it when possible, if you absolutely must, be very,
  * very careful with the changes that you are making!
@@ -66,7 +100,10 @@ public class RepoUpdater {
     private String cacheTag;
     private X509Certificate signingCertFromJar;
 
-    @NonNull private final RepoPersister persister;
+    @NonNull
+    private final RepoPersister persister;
+
+    private final List<RepoPushRequest> repoPushRequestList = new ArrayList<>();
 
     /**
      * Updates an app repo as read out of the database into a {@link Repo} instance.
@@ -148,6 +185,7 @@ public class RepoUpdater {
             // successful download, then we will have a file ready to use:
             cacheTag = downloader.getCacheTag();
             processDownloadedFile(downloader.outputFile);
+            processRepoPushRequests();
         }
     }
 
@@ -170,6 +208,11 @@ public class RepoUpdater {
                     throw new RuntimeException("Error while saving repo details to database.", e);
                 }
             }
+
+            @Override
+            public void receiveRepoPushRequest(RepoPushRequest repoPushRequest) {
+                repoPushRequestList.add(repoPushRequest);
+            }
         };
     }
 
@@ -188,7 +231,7 @@ public class RepoUpdater {
             JarFile jarFile = new JarFile(downloadedFile, true);
             JarEntry indexEntry = (JarEntry) jarFile.getEntry("index.xml");
             indexInputStream = new ProgressBufferedInputStream(jarFile.getInputStream(indexEntry),
-                processXmlProgressListener, new URL(repo.address), (int) indexEntry.getSize());
+                    processXmlProgressListener, new URL(repo.address), (int) indexEntry.getSize());
 
             // Process the index...
             SAXParserFactory factory = SAXParserFactory.newInstance();
@@ -396,4 +439,52 @@ public class RepoUpdater {
         throw new SigningException(repo, "Signing certificate does not match!");
     }
 
+    /**
+     * Server index XML can include optional {@code install} and {@code uninstall}
+     * requests.  This processes those requests, figuring out whether the client
+     * should always accept, prompt the user, or ignore those requests on a
+     * per repo basis.
+     */
+    private void processRepoPushRequests() {
+        PackageManager pm = context.getPackageManager();
+
+        for (RepoPushRequest repoPushRequest : repoPushRequestList) {
+            String packageName = repoPushRequest.packageName;
+            PackageInfo packageInfo = null;
+            try {
+                packageInfo = pm.getPackageInfo(packageName, 0);
+            } catch (PackageManager.NameNotFoundException e) {
+                // ignored
+            }
+            if (RepoPushRequest.INSTALL.equals(repoPushRequest.request)) {
+                ContentResolver cr = context.getContentResolver();
+                App app = AppProvider.Helper.findByPackageName(cr, packageName);
+                int versionCode;
+                if (repoPushRequest.versionCode == null) {
+                    versionCode = app.suggestedVersionCode;
+                } else {
+                    versionCode = repoPushRequest.versionCode;
+                }
+                if (packageInfo != null && versionCode == packageInfo.versionCode) {
+                    Utils.debugLog(TAG, repoPushRequest + " already installed, ignoring");
+                } else {
+                    Apk apk = ApkProvider.Helper.find(context, packageName, versionCode);
+                    InstallManagerService.queue(context, app, apk);
+                }
+            } else if (RepoPushRequest.UNINSTALL.equals(repoPushRequest.request)) {
+                if (packageInfo == null) {
+                    Utils.debugLog(TAG, "ignoring request, not installed: " + repoPushRequest);
+                    continue;
+                }
+                if (repoPushRequest.versionCode == null
+                        || repoPushRequest.versionCode == packageInfo.versionCode) {
+                    InstallerService.uninstall(context, packageName);
+                } else {
+                    Utils.debugLog(TAG, "ignoring request based on versionCode:" + repoPushRequest);
+                }
+            } else {
+                Utils.debugLog(TAG, "Unknown Repo Push Request: " + repoPushRequest.request);
+            }
+        }
+    }
 }
diff --git a/app/src/main/java/org/fdroid/fdroid/RepoXMLHandler.java b/app/src/main/java/org/fdroid/fdroid/RepoXMLHandler.java
index 780d82f55..d58307c5e 100644
--- a/app/src/main/java/org/fdroid/fdroid/RepoXMLHandler.java
+++ b/app/src/main/java/org/fdroid/fdroid/RepoXMLHandler.java
@@ -25,6 +25,7 @@ import android.support.annotation.Nullable;
 import org.fdroid.fdroid.data.Apk;
 import org.fdroid.fdroid.data.App;
 import org.fdroid.fdroid.data.Repo;
+import org.fdroid.fdroid.data.RepoPushRequest;
 import org.xml.sax.Attributes;
 import org.xml.sax.SAXException;
 import org.xml.sax.helpers.DefaultHandler;
@@ -64,6 +65,8 @@ public class RepoXMLHandler extends DefaultHandler {
         void receiveRepo(String name, String description, String signingCert, int maxage, int version, long timestamp);
 
         void receiveApp(App app, List<Apk> packages);
+
+        void receiveRepoPushRequest(RepoPushRequest repoPushRequest);
     }
 
     private final IndexReceiver receiver;
@@ -250,6 +253,10 @@ public class RepoXMLHandler extends DefaultHandler {
         receiver.receiveRepo(repoName, repoDescription, repoSigningCert, repoMaxAge, repoVersion, repoTimestamp);
     }
 
+    private void onRepoPushRequestParsed(RepoPushRequest repoPushRequest) {
+        receiver.receiveRepoPushRequest(repoPushRequest);
+    }
+
     @Override
     public void startElement(String uri, String localName, String qName,
                              Attributes attributes) throws SAXException {
@@ -262,6 +269,15 @@ public class RepoXMLHandler extends DefaultHandler {
             repoName = cleanWhiteSpace(attributes.getValue("", "name"));
             repoDescription = cleanWhiteSpace(attributes.getValue("", "description"));
             repoTimestamp = parseLong(attributes.getValue("", "timestamp"), 0);
+        } else if (RepoPushRequest.INSTALL.equals(localName)
+                || RepoPushRequest.UNINSTALL.equals(localName)) {
+            if (repo.pushRequests == Repo.PUSH_REQUEST_ACCEPT_ALWAYS) {
+                RepoPushRequest r = new RepoPushRequest(
+                        localName,
+                        attributes.getValue("packageName"),
+                        attributes.getValue("versionCode"));
+                onRepoPushRequestParsed(r);
+            }
         } else if ("application".equals(localName) && curapp == null) {
             curapp = new App();
             curapp.packageName = attributes.getValue("", "id");
diff --git a/app/src/main/java/org/fdroid/fdroid/data/DBHelper.java b/app/src/main/java/org/fdroid/fdroid/data/DBHelper.java
index 680772bd8..bcf757446 100644
--- a/app/src/main/java/org/fdroid/fdroid/data/DBHelper.java
+++ b/app/src/main/java/org/fdroid/fdroid/data/DBHelper.java
@@ -1,3 +1,26 @@
+/*
+ * Copyright (C) 2016 Blue Jay Wireless
+ * Copyright (C) 2015-2016 Daniel Martí <mvdan@mvdan.cc>
+ * Copyright (C) 2015 Christian Morgner
+ * Copyright (C) 2014-2016 Hans-Christoph Steiner <hans@eds.org>
+ * Copyright (C) 2013-2016 Peter Serwylo <peter@serwylo.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
 package org.fdroid.fdroid.data;
 
 import android.content.ContentValues;
@@ -23,6 +46,8 @@ class DBHelper extends SQLiteOpenHelper {
 
     private static final String TAG = "DBHelper";
 
+    public static final int REPO_XML_ARG_COUNT = 8;
+
     private static final String DATABASE_NAME = "fdroid";
 
     private static final String CREATE_TABLE_REPO = "create table "
@@ -42,7 +67,8 @@ class DBHelper extends SQLiteOpenHelper {
             + RepoTable.Cols.IS_SWAP + " integer boolean default 0,"
             + RepoTable.Cols.USERNAME + " string, "
             + RepoTable.Cols.PASSWORD + " string,"
-            + RepoTable.Cols.TIMESTAMP + " integer not null default 0"
+            + RepoTable.Cols.TIMESTAMP + " integer not null default 0, "
+            + RepoTable.Cols.PUSH_REQUESTS + " integer not null default " + Repo.PUSH_REQUEST_IGNORE
             + ");";
 
     static final String CREATE_TABLE_APK =
@@ -120,7 +146,7 @@ class DBHelper extends SQLiteOpenHelper {
             + " );";
     private static final String DROP_TABLE_INSTALLED_APP = "DROP TABLE " + InstalledAppTable.NAME + ";";
 
-    private static final int DB_VERSION = 61;
+    private static final int DB_VERSION = 62;
 
     private final Context context;
 
@@ -244,14 +270,15 @@ class DBHelper extends SQLiteOpenHelper {
                     defaultRepos[offset + 3], // version
                     defaultRepos[offset + 4], // enabled
                     defaultRepos[offset + 5], // priority
-                    defaultRepos[offset + 6]  // pubkey
+                    defaultRepos[offset + 6], // pushRequests
+                    defaultRepos[offset + 7]  // pubkey
             );
         }
     }
 
     private void insertRepo(SQLiteDatabase db, String name, String address,
                             String description, String version, String enabled,
-                            String priority, String pubKey) {
+                            String priority, String pushRequests, String pubKey) {
         ContentValues values = new ContentValues();
         values.put(RepoTable.Cols.ADDRESS, address);
         values.put(RepoTable.Cols.NAME, name);
@@ -265,7 +292,21 @@ class DBHelper extends SQLiteOpenHelper {
         values.put(RepoTable.Cols.LAST_ETAG, (String) null);
         values.put(RepoTable.Cols.TIMESTAMP, 0);
 
-        Utils.debugLog(TAG, "Adding repository " + name);
+        switch (pushRequests) {
+            case "ignore":
+                values.put(RepoTable.Cols.PUSH_REQUESTS, Repo.PUSH_REQUEST_IGNORE);
+                break;
+            case "prompt":
+                values.put(RepoTable.Cols.PUSH_REQUESTS, Repo.PUSH_REQUEST_PROMPT);
+                break;
+            case "always":
+                values.put(RepoTable.Cols.PUSH_REQUESTS, Repo.PUSH_REQUEST_ACCEPT_ALWAYS);
+                break;
+            default:
+                throw new IllegalArgumentException(pushRequests + " is not a supported option!");
+        }
+
+        Utils.debugLog(TAG, "Adding repository " + name + " with push requests as " + pushRequests);
         db.insert(RepoTable.NAME, null, values);
     }
 
@@ -302,6 +343,7 @@ class DBHelper extends SQLiteOpenHelper {
         removeApkPackageNameColumn(db, oldVersion);
         addAppPrefsTable(db, oldVersion);
         lowerCaseApkHashes(db, oldVersion);
+        supportRepoPushRequests(db, oldVersion);
     }
 
     private void lowerCaseApkHashes(SQLiteDatabase db, int oldVersion) {
@@ -490,13 +532,13 @@ class DBHelper extends SQLiteOpenHelper {
     }
 
     private void insertNameAndDescription(SQLiteDatabase db,
-            int addressResId, int nameResId, int descriptionResId) {
+                                          String name, String address, String description) {
         ContentValues values = new ContentValues();
         values.clear();
-        values.put(RepoTable.Cols.NAME, context.getString(nameResId));
-        values.put(RepoTable.Cols.DESCRIPTION, context.getString(descriptionResId));
-        db.update(RepoTable.NAME, values, RepoTable.Cols.ADDRESS + " = ?", new String[] {
-                context.getString(addressResId),
+        values.put(RepoTable.Cols.NAME, name);
+        values.put(RepoTable.Cols.DESCRIPTION, description);
+        db.update(RepoTable.NAME, values, RepoTable.Cols.ADDRESS + " = ?", new String[]{
+                address,
         });
     }
 
@@ -770,6 +812,17 @@ class DBHelper extends SQLiteOpenHelper {
                 + ApkTable.Cols.TARGET_SDK_VERSION + " integer");
     }
 
+    private void supportRepoPushRequests(SQLiteDatabase db, int oldVersion) {
+        if (oldVersion >= 61) {
+            return;
+        }
+        Utils.debugLog(TAG, "Adding " + RepoTable.Cols.PUSH_REQUESTS
+                + " columns to " + RepoTable.NAME);
+        db.execSQL("alter table " + RepoTable.NAME + " add column "
+                + RepoTable.Cols.PUSH_REQUESTS + " integer not null default "
+                + Repo.PUSH_REQUEST_IGNORE);
+    }
+
     private static boolean columnExists(SQLiteDatabase db, String table, String column) {
         Cursor cursor = db.rawQuery("select * from " + table + " limit 0,1", null);
         boolean exists = cursor.getColumnIndex(column) != -1;
diff --git a/app/src/main/java/org/fdroid/fdroid/data/Repo.java b/app/src/main/java/org/fdroid/fdroid/data/Repo.java
index 62746de2b..fa8289bdf 100644
--- a/app/src/main/java/org/fdroid/fdroid/data/Repo.java
+++ b/app/src/main/java/org/fdroid/fdroid/data/Repo.java
@@ -1,3 +1,26 @@
+/*
+ * Copyright (C) 2016 Blue Jay Wireless
+ * Copyright (C) 2014-2016 Daniel Martí <mvdan@mvdan.cc>
+ * Copyright (C) 2014-2016 Hans-Christoph Steiner <hans@eds.org>
+ * Copyright (C) 2014-2016 Peter Serwylo <peter@serwylo.com>
+ * Copyright (C) 2015 Christian Morgner
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
 package org.fdroid.fdroid.data;
 
 import android.content.ContentValues;
@@ -15,6 +38,10 @@ public class Repo extends ValueObject {
 
     public static final int VERSION_DENSITY_SPECIFIC_ICONS = 11;
 
+    public static final int PUSH_REQUEST_IGNORE = 0;
+    public static final int PUSH_REQUEST_PROMPT = 1;
+    public static final int PUSH_REQUEST_ACCEPT_ALWAYS = 2;
+
     protected long id;
 
     public String address;
@@ -44,6 +71,9 @@ public class Repo extends ValueObject {
     /** When the signed repo index was generated, used to protect against replay attacks */
     public long timestamp;
 
+    /** How to treat push requests included in this repo's index XML */
+    public int pushRequests = PUSH_REQUEST_IGNORE;
+
     public Repo() {
     }
 
@@ -101,6 +131,9 @@ public class Repo extends ValueObject {
                 case Cols.TIMESTAMP:
                     timestamp = cursor.getLong(i);
                     break;
+                case Cols.PUSH_REQUESTS:
+                    pushRequests = cursor.getInt(i);
+                    break;
             }
         }
     }
@@ -223,5 +256,9 @@ public class Repo extends ValueObject {
         if (values.containsKey(Cols.TIMESTAMP)) {
             timestamp = toInt(values.getAsInteger(Cols.TIMESTAMP));
         }
+
+        if (values.containsKey(Cols.PUSH_REQUESTS)) {
+            pushRequests = toInt(values.getAsInteger(Cols.PUSH_REQUESTS));
+        }
     }
 }
diff --git a/app/src/main/java/org/fdroid/fdroid/data/RepoPushRequest.java b/app/src/main/java/org/fdroid/fdroid/data/RepoPushRequest.java
new file mode 100644
index 000000000..1c89b0884
--- /dev/null
+++ b/app/src/main/java/org/fdroid/fdroid/data/RepoPushRequest.java
@@ -0,0 +1,58 @@
+/*
+ * Copyright (C) 2016 Blue Jay Wireless
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
+package org.fdroid.fdroid.data;
+
+import android.support.annotation.Nullable;
+
+/**
+ * Represents action requests embedded in the index XML received from a repo.
+ * When {@link #versionCode} is {@code null}, that means that the
+ * {@code versionCode} was not specified by the server, and F-Droid should
+ * install the best available version.
+ */
+public class RepoPushRequest {
+    public static final String TAG = "RepoPushRequest";
+
+    public static final String INSTALL = "install";
+    public static final String UNINSTALL = "uninstall";
+
+    public final String request;
+    public final String packageName;
+    @Nullable
+    public final Integer versionCode;
+
+    public RepoPushRequest(String request, String packageName, String versionCode) {
+        this.request = request;
+        this.packageName = packageName;
+
+        Integer i;
+        try {
+            i = Integer.parseInt(versionCode);
+        } catch (NumberFormatException e) {
+            i = null;
+        }
+        this.versionCode = i;
+    }
+
+    @Override
+    public String toString() {
+        return request + " " + packageName + " " + versionCode;
+    }
+}
diff --git a/app/src/main/java/org/fdroid/fdroid/data/Schema.java b/app/src/main/java/org/fdroid/fdroid/data/Schema.java
index 88987b1de..dc5432958 100644
--- a/app/src/main/java/org/fdroid/fdroid/data/Schema.java
+++ b/app/src/main/java/org/fdroid/fdroid/data/Schema.java
@@ -196,11 +196,12 @@ public interface Schema {
             String USERNAME     = "username";
             String PASSWORD     = "password";
             String TIMESTAMP    = "timestamp";
+            String PUSH_REQUESTS = "pushRequests";
 
             String[] ALL = {
                     _ID, ADDRESS, NAME, DESCRIPTION, IN_USE, PRIORITY, SIGNING_CERT,
                     FINGERPRINT, MAX_AGE, LAST_UPDATED, LAST_ETAG, VERSION, IS_SWAP,
-                    USERNAME, PASSWORD, TIMESTAMP,
+                    USERNAME, PASSWORD, TIMESTAMP, PUSH_REQUESTS,
             };
         }
     }
diff --git a/app/src/main/res/values/default_repos.xml b/app/src/main/res/values/default_repos.xml
index 640364aa5..6a09a6920 100644
--- a/app/src/main/res/values/default_repos.xml
+++ b/app/src/main/res/values/default_repos.xml
@@ -18,6 +18,8 @@
         <item>1</item>
         <!-- priority -->
         <item>10</item>
+        <!-- push requests -->
+        <item>ignore</item>
         <!-- pubkey -->
         <item>
             3082035e30820246a00302010202044c49cd00300d06092a864886f70d01010505003071310b300906035504061302554b3110300e06035504081307556e6b6e6f776e3111300f0603550407130857657468657262793110300e060355040a1307556e6b6e6f776e3110300e060355040b1307556e6b6e6f776e311930170603550403131043696172616e2047756c746e69656b73301e170d3130303732333137313032345a170d3337313230383137313032345a3071310b300906035504061302554b3110300e06035504081307556e6b6e6f776e3111300f0603550407130857657468657262793110300e060355040a1307556e6b6e6f776e3110300e060355040b1307556e6b6e6f776e311930170603550403131043696172616e2047756c746e69656b7330820122300d06092a864886f70d01010105000382010f003082010a028201010096d075e47c014e7822c89fd67f795d23203e2a8843f53ba4e6b1bf5f2fd0e225938267cfcae7fbf4fe596346afbaf4070fdb91f66fbcdf2348a3d92430502824f80517b156fab00809bdc8e631bfa9afd42d9045ab5fd6d28d9e140afc1300917b19b7c6c4df4a494cf1f7cb4a63c80d734265d735af9e4f09455f427aa65a53563f87b336ca2c19d244fcbba617ba0b19e56ed34afe0b253ab91e2fdb1271f1b9e3c3232027ed8862a112f0706e234cf236914b939bcf959821ecb2a6c18057e070de3428046d94b175e1d89bd795e535499a091f5bc65a79d539a8d43891ec504058acb28c08393b5718b57600a211e803f4a634e5c57f25b9b8c4422c6fd90203010001300d06092a864886f70d0101050500038201010008e4ef699e9807677ff56753da73efb2390d5ae2c17e4db691d5df7a7b60fc071ae509c5414be7d5da74df2811e83d3668c4a0b1abc84b9fa7d96b4cdf30bba68517ad2a93e233b042972ac0553a4801c9ebe07bf57ebe9a3b3d6d663965260e50f3b8f46db0531761e60340a2bddc3426098397fda54044a17e5244549f9869b460ca5e6e216b6f6a2db0580b480ca2afe6ec6b46eedacfa4aa45038809ece0c5978653d6c85f678e7f5a2156d1bedd8117751e64a4b0dcd140f3040b021821a8d93aed8d01ba36db6c82372211fed714d9a32607038cdfd565bd529ffc637212aaa2c224ef22b603eccefb5bf1e085c191d4b24fe742b17ab3f55d4e6f05ef
@@ -37,6 +39,8 @@
         <item>0</item>
         <!-- priority -->
         <item>20</item>
+        <!-- push requests -->
+        <item>ignore</item>
         <!-- pubkey -->
         <item>
             3082035e30820246a00302010202044c49cd00300d06092a864886f70d01010505003071310b300906035504061302554b3110300e06035504081307556e6b6e6f776e3111300f0603550407130857657468657262793110300e060355040a1307556e6b6e6f776e3110300e060355040b1307556e6b6e6f776e311930170603550403131043696172616e2047756c746e69656b73301e170d3130303732333137313032345a170d3337313230383137313032345a3071310b300906035504061302554b3110300e06035504081307556e6b6e6f776e3111300f0603550407130857657468657262793110300e060355040a1307556e6b6e6f776e3110300e060355040b1307556e6b6e6f776e311930170603550403131043696172616e2047756c746e69656b7330820122300d06092a864886f70d01010105000382010f003082010a028201010096d075e47c014e7822c89fd67f795d23203e2a8843f53ba4e6b1bf5f2fd0e225938267cfcae7fbf4fe596346afbaf4070fdb91f66fbcdf2348a3d92430502824f80517b156fab00809bdc8e631bfa9afd42d9045ab5fd6d28d9e140afc1300917b19b7c6c4df4a494cf1f7cb4a63c80d734265d735af9e4f09455f427aa65a53563f87b336ca2c19d244fcbba617ba0b19e56ed34afe0b253ab91e2fdb1271f1b9e3c3232027ed8862a112f0706e234cf236914b939bcf959821ecb2a6c18057e070de3428046d94b175e1d89bd795e535499a091f5bc65a79d539a8d43891ec504058acb28c08393b5718b57600a211e803f4a634e5c57f25b9b8c4422c6fd90203010001300d06092a864886f70d0101050500038201010008e4ef699e9807677ff56753da73efb2390d5ae2c17e4db691d5df7a7b60fc071ae509c5414be7d5da74df2811e83d3668c4a0b1abc84b9fa7d96b4cdf30bba68517ad2a93e233b042972ac0553a4801c9ebe07bf57ebe9a3b3d6d663965260e50f3b8f46db0531761e60340a2bddc3426098397fda54044a17e5244549f9869b460ca5e6e216b6f6a2db0580b480ca2afe6ec6b46eedacfa4aa45038809ece0c5978653d6c85f678e7f5a2156d1bedd8117751e64a4b0dcd140f3040b021821a8d93aed8d01ba36db6c82372211fed714d9a32607038cdfd565bd529ffc637212aaa2c224ef22b603eccefb5bf1e085c191d4b24fe742b17ab3f55d4e6f05ef
@@ -57,6 +61,8 @@
         <item>0</item>
         <!-- priority -->
         <item>10</item>
+        <!-- push requests -->
+        <item>ignore</item>
         <!-- pubkey -->
         <item>
             308205d8308203c0020900a397b4da7ecda034300d06092a864886f70d01010505003081ad310b30090603550406130255533111300f06035504080c084e657720596f726b3111300f06035504070c084e657720596f726b31143012060355040b0c0b4644726f6964205265706f31193017060355040a0c10477561726469616e2050726f6a656374311d301b06035504030c14677561726469616e70726f6a6563742e696e666f3128302606092a864886f70d0109011619726f6f7440677561726469616e70726f6a6563742e696e666f301e170d3134303632363139333931385a170d3431313131303139333931385a3081ad310b30090603550406130255533111300f06035504080c084e657720596f726b3111300f06035504070c084e657720596f726b31143012060355040b0c0b4644726f6964205265706f31193017060355040a0c10477561726469616e2050726f6a656374311d301b06035504030c14677561726469616e70726f6a6563742e696e666f3128302606092a864886f70d0109011619726f6f7440677561726469616e70726f6a6563742e696e666f30820222300d06092a864886f70d01010105000382020f003082020a0282020100b3cd79121b9b883843be3c4482e320809106b0a23755f1dd3c7f46f7d315d7bb2e943486d61fc7c811b9294dcc6b5baac4340f8db2b0d5e14749e7f35e1fc211fdbc1071b38b4753db201c314811bef885bd8921ad86facd6cc3b8f74d30a0b6e2e6e576f906e9581ef23d9c03e926e06d1f033f28bd1e21cfa6a0e3ff5c9d8246cf108d82b488b9fdd55d7de7ebb6a7f64b19e0d6b2ab1380a6f9d42361770d1956701a7f80e2de568acd0bb4527324b1e0973e89595d91c8cc102d9248525ae092e2c9b69f7414f724195b81427f28b1d3d09a51acfe354387915fd9521e8c890c125fc41a12bf34d2a1b304067ab7251e0e9ef41833ce109e76963b0b256395b16b886bca21b831f1408f836146019e7908829e716e72b81006610a2af08301de5d067c9e114a1e5759db8a6be6a3cc2806bcfe6fafd41b5bc9ddddb3dc33d6f605b1ca7d8a9e0ecdd6390d38906649e68a90a717bea80fa220170eea0c86fc78a7e10dac7b74b8e62045a3ecca54e035281fdc9fe5920a855fde3c0be522e3aef0c087524f13d973dff3768158b01a5800a060c06b451ec98d627dd052eda804d0556f60dbc490d94e6e9dea62ffcafb5beffbd9fc38fb2f0d7050004fe56b4dda0a27bc47554e1e0a7d764e17622e71f83a475db286bc7862deee1327e2028955d978272ea76bf0b88e70a18621aba59ff0c5993ef5f0e5d6b6b98e68b70203010001300d06092a864886f70d0101050500038202010079c79c8ef408a20d243d8bd8249fb9a48350dc19663b5e0fce67a8dbcb7de296c5ae7bbf72e98a2020fb78f2db29b54b0e24b181aa1c1d333cc0303685d6120b03216a913f96b96eb838f9bff125306ae3120af838c9fc07ebb5100125436bd24ec6d994d0bff5d065221871f8410daf536766757239bf594e61c5432c9817281b985263bada8381292e543a49814061ae11c92a316e7dc100327b59e3da90302c5ada68c6a50201bda1fcce800b53f381059665dbabeeb0b50eb22b2d7d2d9b0aa7488ca70e67ac6c518adb8e78454a466501e89d81a45bf1ebc350896f2c3ae4b6679ecfbf9d32960d4f5b493125c7876ef36158562371193f600bc511000a67bdb7c664d018f99d9e589868d103d7e0994f166b2ba18ff7e67d8c4da749e44dfae1d930ae5397083a51675c409049dfb626a96246c0015ca696e94ebb767a20147834bf78b07fece3f0872b057c1c519ff882501995237d8206b0b3832f78753ebd8dcbd1d3d9f5ba733538113af6b407d960ec4353c50eb38ab29888238da843cd404ed8f4952f59e4bbc0035fc77a54846a9d419179c46af1b4a3b7fc98e4d312aaa29b9b7d79e739703dc0fa41c7280d5587709277ffa11c3620f5fba985b82c238ba19b17ebd027af9424be0941719919f620dd3bb3c3f11638363708aa11f858e153cf3a69bce69978b90e4a273836100aa1e617ba455cd00426847f
@@ -76,6 +82,8 @@
         <item>0</item>
         <!-- priority -->
         <item>20</item>
+        <!-- push requests -->
+        <item>ignore</item>
         <!-- pubkey -->
         <item>
             308205d8308203c0020900a397b4da7ecda034300d06092a864886f70d01010505003081ad310b30090603550406130255533111300f06035504080c084e657720596f726b3111300f06035504070c084e657720596f726b31143012060355040b0c0b4644726f6964205265706f31193017060355040a0c10477561726469616e2050726f6a656374311d301b06035504030c14677561726469616e70726f6a6563742e696e666f3128302606092a864886f70d0109011619726f6f7440677561726469616e70726f6a6563742e696e666f301e170d3134303632363139333931385a170d3431313131303139333931385a3081ad310b30090603550406130255533111300f06035504080c084e657720596f726b3111300f06035504070c084e657720596f726b31143012060355040b0c0b4644726f6964205265706f31193017060355040a0c10477561726469616e2050726f6a656374311d301b06035504030c14677561726469616e70726f6a6563742e696e666f3128302606092a864886f70d0109011619726f6f7440677561726469616e70726f6a6563742e696e666f30820222300d06092a864886f70d01010105000382020f003082020a0282020100b3cd79121b9b883843be3c4482e320809106b0a23755f1dd3c7f46f7d315d7bb2e943486d61fc7c811b9294dcc6b5baac4340f8db2b0d5e14749e7f35e1fc211fdbc1071b38b4753db201c314811bef885bd8921ad86facd6cc3b8f74d30a0b6e2e6e576f906e9581ef23d9c03e926e06d1f033f28bd1e21cfa6a0e3ff5c9d8246cf108d82b488b9fdd55d7de7ebb6a7f64b19e0d6b2ab1380a6f9d42361770d1956701a7f80e2de568acd0bb4527324b1e0973e89595d91c8cc102d9248525ae092e2c9b69f7414f724195b81427f28b1d3d09a51acfe354387915fd9521e8c890c125fc41a12bf34d2a1b304067ab7251e0e9ef41833ce109e76963b0b256395b16b886bca21b831f1408f836146019e7908829e716e72b81006610a2af08301de5d067c9e114a1e5759db8a6be6a3cc2806bcfe6fafd41b5bc9ddddb3dc33d6f605b1ca7d8a9e0ecdd6390d38906649e68a90a717bea80fa220170eea0c86fc78a7e10dac7b74b8e62045a3ecca54e035281fdc9fe5920a855fde3c0be522e3aef0c087524f13d973dff3768158b01a5800a060c06b451ec98d627dd052eda804d0556f60dbc490d94e6e9dea62ffcafb5beffbd9fc38fb2f0d7050004fe56b4dda0a27bc47554e1e0a7d764e17622e71f83a475db286bc7862deee1327e2028955d978272ea76bf0b88e70a18621aba59ff0c5993ef5f0e5d6b6b98e68b70203010001300d06092a864886f70d0101050500038202010079c79c8ef408a20d243d8bd8249fb9a48350dc19663b5e0fce67a8dbcb7de296c5ae7bbf72e98a2020fb78f2db29b54b0e24b181aa1c1d333cc0303685d6120b03216a913f96b96eb838f9bff125306ae3120af838c9fc07ebb5100125436bd24ec6d994d0bff5d065221871f8410daf536766757239bf594e61c5432c9817281b985263bada8381292e543a49814061ae11c92a316e7dc100327b59e3da90302c5ada68c6a50201bda1fcce800b53f381059665dbabeeb0b50eb22b2d7d2d9b0aa7488ca70e67ac6c518adb8e78454a466501e89d81a45bf1ebc350896f2c3ae4b6679ecfbf9d32960d4f5b493125c7876ef36158562371193f600bc511000a67bdb7c664d018f99d9e589868d103d7e0994f166b2ba18ff7e67d8c4da749e44dfae1d930ae5397083a51675c409049dfb626a96246c0015ca696e94ebb767a20147834bf78b07fece3f0872b057c1c519ff882501995237d8206b0b3832f78753ebd8dcbd1d3d9f5ba733538113af6b407d960ec4353c50eb38ab29888238da843cd404ed8f4952f59e4bbc0035fc77a54846a9d419179c46af1b4a3b7fc98e4d312aaa29b9b7d79e739703dc0fa41c7280d5587709277ffa11c3620f5fba985b82c238ba19b17ebd027af9424be0941719919f620dd3bb3c3f11638363708aa11f858e153cf3a69bce69978b90e4a273836100aa1e617ba455cd00426847f
diff --git a/app/src/test/java/org/fdroid/fdroid/RepoXMLHandlerTest.java b/app/src/test/java/org/fdroid/fdroid/RepoXMLHandlerTest.java
index ac1056331..2f40767db 100644
--- a/app/src/test/java/org/fdroid/fdroid/RepoXMLHandlerTest.java
+++ b/app/src/test/java/org/fdroid/fdroid/RepoXMLHandlerTest.java
@@ -1,3 +1,24 @@
+/*
+ * Copyright (C) 2016 Blue Jay Wireless
+ * Copyright (C) 2015 Daniel Martí <mvdan@mvdan.cc>
+ * Copyright (C) 2014-2016 Hans-Christoph Steiner <hans@eds.org>
+ * Copyright (C) 2014-2016 Peter Serwylo <peter@serwylo.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
 
 package org.fdroid.fdroid;
 
@@ -8,6 +29,7 @@ import android.util.Log;
 import org.fdroid.fdroid.data.Apk;
 import org.fdroid.fdroid.data.App;
 import org.fdroid.fdroid.data.Repo;
+import org.fdroid.fdroid.data.RepoPushRequest;
 import org.fdroid.fdroid.mock.MockRepo;
 import org.junit.Test;
 import org.junit.runner.RunWith;
@@ -82,6 +104,38 @@ public class RepoXMLHandlerTest {
         });
     }
 
+    @Test
+    public void testPushRequestsRepoIgnore() {
+        Repo expectedRepo = new Repo();
+        expectedRepo.name = "non-public test repo";
+        expectedRepo.signingCertificate = "308204e1308202c9a0030201020204483450fa300d06092a864886f70d01010b050030213110300e060355040b1307462d44726f6964310d300b06035504031304736f7661301e170d3136303832333133333131365a170d3434303130393133333131365a30213110300e060355040b1307462d44726f6964310d300b06035504031304736f766130820222300d06092a864886f70d01010105000382020f003082020a0282020100dfdcd120f3ab224999dddf4ea33ea588d295e4d7130bef48c143e9d76e5c0e0e9e5d45e64208e35feebc79a83f08939dd6a343b7d1e2179930a105a1249ccd36d88ff3feffc6e4dc53dae0163a7876dd45ecc1ddb0adf5099aa56c1a84b52affcd45d0711ffa4de864f35ac0333ebe61ea8673eeda35a88f6af678cc4d0f80b089338ac8f2a8279a64195c611d19445cab3fd1a020afed9bd739bb95142fb2c00a8f847db5ef3325c814f8eb741bacf86ed3907bfe6e4564d2de5895df0c263824e0b75407589bae2d3a4666c13b92102d8781a8ee9bb4a5a1a78c4a9c21efdaf5584da42e84418b28f5a81d0456a3dc5b420991801e6b21e38c99bbe018a5b2d690894a114bc860d35601416aa4dc52216aff8a288d4775cddf8b72d45fd2f87303a8e9c0d67e442530be28eaf139894337266e0b33d57f949256ab32083bcc545bc18a83c9ab8247c12aea037e2b68dee31c734cb1f04f241d3b94caa3a2b258ffaf8e6eae9fbbe029a934dc0a0859c5f120334812693a1c09352340a39f2a678dbc1afa2a978bfee43afefcb7e224a58af2f3d647e5745db59061236b8af6fcfd93b3602f9e456978534f3a7851e800071bf56da80401c81d91c45f82568373af0576b1cc5eef9b85654124b6319770be3cdba3fbebe3715e8918fb6c8966624f3d0e815effac3d2ee06dd34ab9c693218b2c7c06ba99d6b74d4f17b8c3cb0203010001a321301f301d0603551d0e04160414d62bee9f3798509546acc62eb1de14b08b954d4f300d06092a864886f70d01010b05000382020100743f7c5692085895f9d1fffad390fb4202c15f123ed094df259185960fd6dadf66cb19851070f180297bba4e6996a4434616573b375cfee94fee73a4505a7ec29136b7e6c22e6436290e3686fe4379d4e3140ec6a08e70cfd3ed5b634a5eb5136efaaabf5f38e0432d3d79568a556970b8cfba2972f5d23a3856d8a981b9e9bbbbb88f35e708bde9cbc5f681cbd974085b9da28911296fe2579fa64bbe9fa0b93475a7a8db051080b0c5fade0d1c018e7858cd4cbe95145b0620e2f632cbe0f8af9cbf22e2fdaa72245ae31b0877b07181cc69dd2df74454251d8de58d25e76354abe7eb690f22e59b08795a8f2c98c578e0599503d9085927634072c82c9f82abd50fd12b8fd1a9d1954eb5cc0b4cfb5796b5aaec0356643b4a65a368442d92ef94edd3ac6a2b7fe3571b8cf9f462729228aab023ef9183f73792f5379633ccac51079177d604c6bc1873ada6f07d8da6d68c897e88a5fa5d63fdb8df820f46090e0716e7562dd3c140ba279a65b996f60addb0abe29d4bf2f5abe89480771d492307b926d91f02f341b2148502903c43d40f3c6c86a811d060711f0698b384acdcc0add44eb54e42962d3d041accc715afd49407715adc09350cb55e8d9281a3b0b6b5fcd91726eede9b7c8b13afdebb2c2b377629595f1096ba62fb14946dbac5f3c5f0b4e5b712e7acc7dcf6c46cdc5e6d6dfdeee55a0c92c2d70f080ac6";
+        expectedRepo.description = "This is a repository of apps to be used with F-Droid. Applications in this repository are either official binaries built by the original application developers, or are binaries built from source by the admin of f-droid.org using the tools on https://gitlab.com/u/fdroid.";
+        expectedRepo.timestamp = 1472071347;
+        RepoDetails actualDetails = getFromFile("pushRequestsIndex.xml", Repo.PUSH_REQUEST_IGNORE);
+        handlerTestSuite(expectedRepo, actualDetails, 2, 14, -1, 17);
+        checkPushRequests(actualDetails);
+
+        List<RepoPushRequest> repoPushRequests = actualDetails.repoPushRequestList;
+        assertNotNull(repoPushRequests);
+        assertEquals(0, repoPushRequests.size());
+    }
+
+    @Test
+    public void testPushRequestsRepoAlways() {
+        Repo expectedRepo = new Repo();
+        expectedRepo.name = "non-public test repo";
+        expectedRepo.signingCertificate = "308204e1308202c9a0030201020204483450fa300d06092a864886f70d01010b050030213110300e060355040b1307462d44726f6964310d300b06035504031304736f7661301e170d3136303832333133333131365a170d3434303130393133333131365a30213110300e060355040b1307462d44726f6964310d300b06035504031304736f766130820222300d06092a864886f70d01010105000382020f003082020a0282020100dfdcd120f3ab224999dddf4ea33ea588d295e4d7130bef48c143e9d76e5c0e0e9e5d45e64208e35feebc79a83f08939dd6a343b7d1e2179930a105a1249ccd36d88ff3feffc6e4dc53dae0163a7876dd45ecc1ddb0adf5099aa56c1a84b52affcd45d0711ffa4de864f35ac0333ebe61ea8673eeda35a88f6af678cc4d0f80b089338ac8f2a8279a64195c611d19445cab3fd1a020afed9bd739bb95142fb2c00a8f847db5ef3325c814f8eb741bacf86ed3907bfe6e4564d2de5895df0c263824e0b75407589bae2d3a4666c13b92102d8781a8ee9bb4a5a1a78c4a9c21efdaf5584da42e84418b28f5a81d0456a3dc5b420991801e6b21e38c99bbe018a5b2d690894a114bc860d35601416aa4dc52216aff8a288d4775cddf8b72d45fd2f87303a8e9c0d67e442530be28eaf139894337266e0b33d57f949256ab32083bcc545bc18a83c9ab8247c12aea037e2b68dee31c734cb1f04f241d3b94caa3a2b258ffaf8e6eae9fbbe029a934dc0a0859c5f120334812693a1c09352340a39f2a678dbc1afa2a978bfee43afefcb7e224a58af2f3d647e5745db59061236b8af6fcfd93b3602f9e456978534f3a7851e800071bf56da80401c81d91c45f82568373af0576b1cc5eef9b85654124b6319770be3cdba3fbebe3715e8918fb6c8966624f3d0e815effac3d2ee06dd34ab9c693218b2c7c06ba99d6b74d4f17b8c3cb0203010001a321301f301d0603551d0e04160414d62bee9f3798509546acc62eb1de14b08b954d4f300d06092a864886f70d01010b05000382020100743f7c5692085895f9d1fffad390fb4202c15f123ed094df259185960fd6dadf66cb19851070f180297bba4e6996a4434616573b375cfee94fee73a4505a7ec29136b7e6c22e6436290e3686fe4379d4e3140ec6a08e70cfd3ed5b634a5eb5136efaaabf5f38e0432d3d79568a556970b8cfba2972f5d23a3856d8a981b9e9bbbbb88f35e708bde9cbc5f681cbd974085b9da28911296fe2579fa64bbe9fa0b93475a7a8db051080b0c5fade0d1c018e7858cd4cbe95145b0620e2f632cbe0f8af9cbf22e2fdaa72245ae31b0877b07181cc69dd2df74454251d8de58d25e76354abe7eb690f22e59b08795a8f2c98c578e0599503d9085927634072c82c9f82abd50fd12b8fd1a9d1954eb5cc0b4cfb5796b5aaec0356643b4a65a368442d92ef94edd3ac6a2b7fe3571b8cf9f462729228aab023ef9183f73792f5379633ccac51079177d604c6bc1873ada6f07d8da6d68c897e88a5fa5d63fdb8df820f46090e0716e7562dd3c140ba279a65b996f60addb0abe29d4bf2f5abe89480771d492307b926d91f02f341b2148502903c43d40f3c6c86a811d060711f0698b384acdcc0add44eb54e42962d3d041accc715afd49407715adc09350cb55e8d9281a3b0b6b5fcd91726eede9b7c8b13afdebb2c2b377629595f1096ba62fb14946dbac5f3c5f0b4e5b712e7acc7dcf6c46cdc5e6d6dfdeee55a0c92c2d70f080ac6";
+        expectedRepo.description = "This is a repository of apps to be used with F-Droid. Applications in this repository are either official binaries built by the original application developers, or are binaries built from source by the admin of f-droid.org using the tools on https://gitlab.com/u/fdroid.";
+        expectedRepo.timestamp = 1472071347;
+        RepoDetails actualDetails = getFromFile("pushRequestsIndex.xml", Repo.PUSH_REQUEST_ACCEPT_ALWAYS);
+        handlerTestSuite(expectedRepo, actualDetails, 2, 14, -1, 17);
+        checkPushRequests(actualDetails);
+
+        List<RepoPushRequest> repoPushRequests = actualDetails.repoPushRequestList;
+        assertNotNull(repoPushRequests);
+        assertEquals(6, repoPushRequests.size());
+    }
+
     @Test
     public void testMediumRepo() {
         Repo expectedRepo = new Repo();
@@ -697,6 +751,30 @@ public class RepoXMLHandlerTest {
         }
     }
 
+    private void checkPushRequests(RepoDetails actualDetails) {
+        final Object[] expectedPushRequestsIndex = new Object[]{
+                "install", "org.fdroid.fdroid", 101002,
+                "install", "org.fdroid.fdroid.privileged", null,
+                "uninstall", "com.android.vending", null,
+                "uninstall", "com.facebook.orca", -12345,
+                "uninstall", null, null,  // request with no data
+                "install", "asdfasdfasdf", null, // non-existent app
+        };
+
+        checkIncludedApps(actualDetails.apps, new String[]{
+                "org.fdroid.fdroid", "org.fdroid.fdroid.privileged",
+        });
+
+        List<RepoPushRequest> repoPushRequestList = actualDetails.repoPushRequestList;
+        int i = 0;
+        for (RepoPushRequest repoPushRequest : repoPushRequestList) {
+            assertEquals(repoPushRequest.request, expectedPushRequestsIndex[i]);
+            assertEquals(repoPushRequest.packageName, expectedPushRequestsIndex[i + 1]);
+            assertEquals(repoPushRequest.versionCode, expectedPushRequestsIndex[i + 2]);
+            i += 3;
+        }
+    }
+
     private void handlerTestSuite(Repo expectedRepo, RepoDetails actualDetails, int appCount, int apkCount, int maxAge, int version) {
         assertNotNull(actualDetails);
         assertFalse(TextUtils.isEmpty(actualDetails.signingCert));
@@ -736,6 +814,7 @@ public class RepoXMLHandlerTest {
 
         public List<Apk> apks = new ArrayList<>();
         public List<App> apps = new ArrayList<>();
+        public List<RepoPushRequest> repoPushRequestList = new ArrayList<>();
 
         @Override
         public void receiveRepo(String name, String description, String signingCert, int maxage, int version, long timestamp) {
@@ -753,17 +832,27 @@ public class RepoXMLHandlerTest {
             apps.add(app);
         }
 
+        @Override
+        public void receiveRepoPushRequest(RepoPushRequest repoPushRequest) {
+            repoPushRequestList.add(repoPushRequest);
+        }
     }
 
     @NonNull
     private RepoDetails getFromFile(String indexFilename) {
+        return getFromFile(indexFilename, Repo.PUSH_REQUEST_IGNORE);
+    }
+
+    @NonNull
+    private RepoDetails getFromFile(String indexFilename, int pushRequests) {
         try {
             SAXParserFactory factory = SAXParserFactory.newInstance();
             factory.setNamespaceAware(true);
             SAXParser parser = factory.newSAXParser();
             XMLReader reader = parser.getXMLReader();
             RepoDetails repoDetails = new RepoDetails();
-            RepoXMLHandler handler = new RepoXMLHandler(new MockRepo(100), repoDetails);
+            MockRepo mockRepo = new MockRepo(100, pushRequests);
+            RepoXMLHandler handler = new RepoXMLHandler(mockRepo, repoDetails);
             reader.setContentHandler(handler);
             Log.i(TAG, "test file: " + getClass().getClassLoader().getResource(indexFilename));
             InputStream input = getClass().getClassLoader().getResourceAsStream(indexFilename);
diff --git a/app/src/test/java/org/fdroid/fdroid/data/RepoProviderTest.java b/app/src/test/java/org/fdroid/fdroid/data/RepoProviderTest.java
index a7ea0b36b..c9553c83c 100644
--- a/app/src/test/java/org/fdroid/fdroid/data/RepoProviderTest.java
+++ b/app/src/test/java/org/fdroid/fdroid/data/RepoProviderTest.java
@@ -1,3 +1,24 @@
+/*
+ * Copyright (C) 2016 Blue Jay Wireless
+ * Copyright (C) 2014-2016 Hans-Christoph Steiner <hans@eds.org>
+ * Copyright (C) 2014-2016 Peter Serwylo <peter@serwylo.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
 package org.fdroid.fdroid.data;
 
 import android.app.Application;
@@ -93,7 +114,7 @@ public class RepoProviderTest extends FDroidProviderTest {
                     defaultRepos.get(i),
                     reposFromXml[offset + 1], // address
                     reposFromXml[offset + 2], // description
-                    Utils.calcFingerprint(reposFromXml[offset + 6]), // pubkey
+                    Utils.calcFingerprint(reposFromXml[offset + 7]), // pubkey
                     reposFromXml[offset]      // name
             );
         }
diff --git a/app/src/test/java/org/fdroid/fdroid/mock/MockRepo.java b/app/src/test/java/org/fdroid/fdroid/mock/MockRepo.java
index 3b3fce976..5926c7b88 100644
--- a/app/src/test/java/org/fdroid/fdroid/mock/MockRepo.java
+++ b/app/src/test/java/org/fdroid/fdroid/mock/MockRepo.java
@@ -4,8 +4,13 @@ import org.fdroid.fdroid.data.Repo;
 
 public class MockRepo extends Repo {
 
-    public MockRepo(long repoId) {
-        id = repoId;
+    public MockRepo(long id) {
+        this.id = id;
+    }
+
+    public MockRepo(long id, int pushRequests) {
+        this.id = id;
+        this.pushRequests = pushRequests;
     }
 
 }
diff --git a/app/src/test/resources/pushRequestsIndex.xml b/app/src/test/resources/pushRequestsIndex.xml
new file mode 100644
index 000000000..7a9d88d0e
--- /dev/null
+++ b/app/src/test/resources/pushRequestsIndex.xml
@@ -0,0 +1 @@
+<?xml version="1.0" encoding="utf-8"?><fdroid><repo icon="fdroid-icon.png" name="non-public test repo" pubkey="308204e1308202c9a0030201020204483450fa300d06092a864886f70d01010b050030213110300e060355040b1307462d44726f6964310d300b06035504031304736f7661301e170d3136303832333133333131365a170d3434303130393133333131365a30213110300e060355040b1307462d44726f6964310d300b06035504031304736f766130820222300d06092a864886f70d01010105000382020f003082020a0282020100dfdcd120f3ab224999dddf4ea33ea588d295e4d7130bef48c143e9d76e5c0e0e9e5d45e64208e35feebc79a83f08939dd6a343b7d1e2179930a105a1249ccd36d88ff3feffc6e4dc53dae0163a7876dd45ecc1ddb0adf5099aa56c1a84b52affcd45d0711ffa4de864f35ac0333ebe61ea8673eeda35a88f6af678cc4d0f80b089338ac8f2a8279a64195c611d19445cab3fd1a020afed9bd739bb95142fb2c00a8f847db5ef3325c814f8eb741bacf86ed3907bfe6e4564d2de5895df0c263824e0b75407589bae2d3a4666c13b92102d8781a8ee9bb4a5a1a78c4a9c21efdaf5584da42e84418b28f5a81d0456a3dc5b420991801e6b21e38c99bbe018a5b2d690894a114bc860d35601416aa4dc52216aff8a288d4775cddf8b72d45fd2f87303a8e9c0d67e442530be28eaf139894337266e0b33d57f949256ab32083bcc545bc18a83c9ab8247c12aea037e2b68dee31c734cb1f04f241d3b94caa3a2b258ffaf8e6eae9fbbe029a934dc0a0859c5f120334812693a1c09352340a39f2a678dbc1afa2a978bfee43afefcb7e224a58af2f3d647e5745db59061236b8af6fcfd93b3602f9e456978534f3a7851e800071bf56da80401c81d91c45f82568373af0576b1cc5eef9b85654124b6319770be3cdba3fbebe3715e8918fb6c8966624f3d0e815effac3d2ee06dd34ab9c693218b2c7c06ba99d6b74d4f17b8c3cb0203010001a321301f301d0603551d0e04160414d62bee9f3798509546acc62eb1de14b08b954d4f300d06092a864886f70d01010b05000382020100743f7c5692085895f9d1fffad390fb4202c15f123ed094df259185960fd6dadf66cb19851070f180297bba4e6996a4434616573b375cfee94fee73a4505a7ec29136b7e6c22e6436290e3686fe4379d4e3140ec6a08e70cfd3ed5b634a5eb5136efaaabf5f38e0432d3d79568a556970b8cfba2972f5d23a3856d8a981b9e9bbbbb88f35e708bde9cbc5f681cbd974085b9da28911296fe2579fa64bbe9fa0b93475a7a8db051080b0c5fade0d1c018e7858cd4cbe95145b0620e2f632cbe0f8af9cbf22e2fdaa72245ae31b0877b07181cc69dd2df74454251d8de58d25e76354abe7eb690f22e59b08795a8f2c98c578e0599503d9085927634072c82c9f82abd50fd12b8fd1a9d1954eb5cc0b4cfb5796b5aaec0356643b4a65a368442d92ef94edd3ac6a2b7fe3571b8cf9f462729228aab023ef9183f73792f5379633ccac51079177d604c6bc1873ada6f07d8da6d68c897e88a5fa5d63fdb8df820f46090e0716e7562dd3c140ba279a65b996f60addb0abe29d4bf2f5abe89480771d492307b926d91f02f341b2148502903c43d40f3c6c86a811d060711f0698b384acdcc0add44eb54e42962d3d041accc715afd49407715adc09350cb55e8d9281a3b0b6b5fcd91726eede9b7c8b13afdebb2c2b377629595f1096ba62fb14946dbac5f3c5f0b4e5b712e7acc7dcf6c46cdc5e6d6dfdeee55a0c92c2d70f080ac6" timestamp="1472071347" url="http://testy.at.or.at/fdroid/repo" version="17"><description>This is a repository of apps to be used with F-Droid. Applications in this repository are either official binaries built by the original application developers, or are binaries built from source by the admin of f-droid.org using the tools on https://gitlab.com/u/fdroid. </description><mirror>https://testy.at.or.at/fdroid/repo</mirror><mirror>http://frkcchxlcvnb4m5a.onion/fdroid/repo</mirror></repo><install packageName="org.fdroid.fdroid" versionCode="101002"/><install packageName="org.fdroid.fdroid.privileged"/><uninstall packageName="com.android.vending"/><uninstall packageName="com.facebook.orca" versionCode="-12345"/><uninstall/><install packageName="asdfasdfasdf"/><application id="org.fdroid.fdroid"><id>org.fdroid.fdroid</id><added>2011-01-17</added><lastupdated>2016-08-21</lastupdated><name>F-Droid</name><summary>Application manager</summary><icon>org.fdroid.fdroid.101005.png</icon><desc>&lt;p&gt;Connects to F-Droid compatible repositories. The default repo is hosted at f-droid.org, which contains only bona fide FOSS.&lt;/p&gt;&lt;p&gt;Android is open in the sense that you are free to install apks from anywhere you wish, but there are many good reasons for using a client/repository setup:&lt;/p&gt;&lt;ul&gt;&lt;li&gt; Be notified when updates are available&lt;/li&gt;&lt;li&gt; Keep track of older and beta versions&lt;/li&gt;&lt;li&gt; Filter apps that aren't compatible with the device&lt;/li&gt;&lt;li&gt; Find apps via categories and searchable descriptions&lt;/li&gt;&lt;li&gt; Access associated urls for donations, source code etc.&lt;/li&gt;&lt;li&gt; Stay safe by checking repo index signatures and apk hashes&lt;/li&gt;&lt;/ul&gt;</desc><license>GPLv3+</license><categories>System</categories><category>System</category><web>https://f-droid.org</web><source>https://gitlab.com/fdroid/fdroidclient</source><tracker>https://gitlab.com/fdroid/fdroidclient/issues</tracker><changelog>https://gitlab.com/fdroid/fdroidclient/raw/HEAD/CHANGELOG.md</changelog><donate>https://f-droid.org/about</donate><bitcoin>15u8aAPK4jJ5N8wpWJ5gutAyyeHtKX5i18</bitcoin><flattr>343053</flattr><marketversion>0.100.1</marketversion><marketvercode>100150</marketvercode><package><version>0.101-alpha5</version><versioncode>101005</versioncode><apkname>org.fdroid.fdroid_101005.apk</apkname><srcname>org.fdroid.fdroid_101005_src.tar.gz</srcname><hash type="sha256">981b5f02c8dbaefc0426576250808d1f5f28bb0595055fa3812bb716d09aefb5</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4672154</size><sdkver>10</sdkver><targetSdkVersion>24</targetSdkVersion><added>2016-08-21</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.101-alpha4</version><versioncode>101004</versioncode><apkname>org.fdroid.fdroid_101004.apk</apkname><srcname>org.fdroid.fdroid_101004_src.tar.gz</srcname><hash type="sha256">f8fafc7a1fc2520bd27149a14c61a8a8edcbca8819ce50d3ee4e1c65d9395f95</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4659390</size><sdkver>10</sdkver><targetSdkVersion>24</targetSdkVersion><added>2016-08-04</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.101-alpha3</version><versioncode>101003</versioncode><apkname>org.fdroid.fdroid_101003.apk</apkname><srcname>org.fdroid.fdroid_101003_src.tar.gz</srcname><hash type="sha256">8b8617a2725be617ae12c3471fb067bba15026f08b3590e29d41ff20f8bb934a</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4673287</size><sdkver>10</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-07-27</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.101-alpha2</version><versioncode>101002</versioncode><apkname>org.fdroid.fdroid_101002.apk</apkname><srcname>org.fdroid.fdroid_101002_src.tar.gz</srcname><hash type="sha256">04487136c5d4c0b9ad5bb549b041ca7b9bac99490c03a5c2cfafc95efc20f59e</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4654706</size><sdkver>10</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-07-07</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.101-alpha1</version><versioncode>101001</versioncode><apkname>org.fdroid.fdroid_101001.apk</apkname><srcname>org.fdroid.fdroid_101001_src.tar.gz</srcname><hash type="sha256">e34929048a664bc6cd7af8e8fce90edb8c4dcf648d1db0ccc4472e96ae30aa5b</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4632826</size><sdkver>10</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-06-21</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.100.1</version><versioncode>100150</versioncode><apkname>org.fdroid.fdroid_100150.apk</apkname><srcname>org.fdroid.fdroid_100150_src.tar.gz</srcname><hash type="sha256">105c6ebbc78c8919ed1d659e091156db12a9fb07a2e8a39c2e22ddb00b96f780</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4577097</size><sdkver>8</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-06-22</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.100</version><versioncode>100050</versioncode><apkname>org.fdroid.fdroid_100050.apk</apkname><srcname>org.fdroid.fdroid_100050_src.tar.gz</srcname><hash type="sha256">9870531d4ae60201eb045ed7b8dcba2999406b07477881ac1a2de5e731b773fe</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4577210</size><sdkver>8</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-06-08</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.100-alpha8</version><versioncode>100008</versioncode><apkname>org.fdroid.fdroid_100008.apk</apkname><srcname>org.fdroid.fdroid_100008_src.tar.gz</srcname><hash type="sha256">fe733f9f592f294a230d1465b86285ff22c868c27399bfd6718eead5f7f66aac</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4577009</size><sdkver>8</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-05-24</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.100-alpha7</version><versioncode>100007</versioncode><apkname>org.fdroid.fdroid_100007.apk</apkname><srcname>org.fdroid.fdroid_100007_src.tar.gz</srcname><hash type="sha256">e741c3c5413ed63ae6fb3616fd199f394c93ca3188a26a233d9034ca2b807497</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4571260</size><sdkver>8</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-05-13</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,WRITE_SETTINGS,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,INTERNET,ACCESS_SUPERUSER,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.100-alpha6</version><versioncode>100006</versioncode><apkname>org.fdroid.fdroid_100006.apk</apkname><srcname>org.fdroid.fdroid_100006_src.tar.gz</srcname><hash type="sha256">70dfb60b5b16debbcdecddddae4c7a013843a8cf269979fd1e5effa3132f9fe4</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4570003</size><sdkver>8</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-05-03</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,ACCESS_SUPERUSER,INTERNET,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.100-alpha5</version><versioncode>100005</versioncode><apkname>org.fdroid.fdroid_100005.apk</apkname><srcname>org.fdroid.fdroid_100005_src.tar.gz</srcname><hash type="sha256">d5fc82ab6050a9649a8fe995eb53a168dd8987df409857626778671286c9d2f7</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4547520</size><sdkver>8</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-04-23</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,ACCESS_SUPERUSER,INTERNET,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package><package><version>0.100-alpha4</version><versioncode>100004</versioncode><apkname>org.fdroid.fdroid_100004.apk</apkname><srcname>org.fdroid.fdroid_100004_src.tar.gz</srcname><hash type="sha256">417e0cb16e7e7d95e6bf2d797d87b0ecce9711e693e1a93c678805e35363b7c7</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>4536877</size><sdkver>8</sdkver><targetSdkVersion>23</targetSdkVersion><added>2016-04-17</added><permissions>RECEIVE_BOOT_COMPLETED,BLUETOOTH_ADMIN,ACCESS_NETWORK_STATE,ACCESS_WIFI_STATE,WRITE_EXTERNAL_STORAGE,READ_EXTERNAL_STORAGE,BLUETOOTH,org.fdroid.fdroid.privileged.USE_SERVICE,CHANGE_NETWORK_STATE,ACCESS_SUPERUSER,INTERNET,CHANGE_WIFI_MULTICAST_STATE,CHANGE_WIFI_STATE,NFC</permissions><uses-permission maxSdkVersion="18" name="android.permission.WRITE_EXTERNAL_STORAGE"/></package></application><application id="org.fdroid.fdroid.privileged"><id>org.fdroid.fdroid.privileged</id><added>2015-09-10</added><lastupdated>2016-01-20</lastupdated><name>F-Droid Privileged Extension</name><summary>Help F-Droid acquire system privileges</summary><icon>org.fdroid.fdroid.privileged.1050.png</icon><desc>&lt;p&gt;&lt;b&gt;Note:&lt;/b&gt; F-Droid will need root privileges to install this app as a system app.&lt;/p&gt;&lt;p&gt;&lt;a href=&quot;fdroid.app:org.fdroid.fdroid&quot;&gt;F-Droid&lt;/a&gt; can make use of system privileges or permissions to install, update and remove applications on its own. The only way to obtain those privileges is to become a system app.&lt;/p&gt;&lt;p&gt;This is where the Privileged Extension comes in - being a separate app and much smaller, it can be installed as a system app and communicate with the main app via AIDL IPC.&lt;/p&gt;&lt;p&gt;This has several advantages:&lt;/p&gt;&lt;ul&gt;&lt;li&gt; Reduced disk usage in the system partition&lt;/li&gt;&lt;li&gt; System updates don't remove F-Droid&lt;/li&gt;&lt;li&gt; The process of installing into system via root is safer&lt;/li&gt;&lt;/ul&gt;</desc><license>GPLv3+</license><categories>System</categories><category>System</category><web>https://f-droid.org</web><source>https://gitlab.com/fdroid/fdroidclient</source><tracker>https://gitlab.com/fdroid/fdroidclient/issues</tracker><donate>https://f-droid.org/about</donate><bitcoin>15u8aAPK4jJ5N8wpWJ5gutAyyeHtKX5i18</bitcoin><flattr>343053</flattr><marketversion>0.1</marketversion><marketvercode>1050</marketvercode><package><version>0.1</version><versioncode>1050</versioncode><apkname>org.fdroid.fdroid.privileged_1050.apk</apkname><srcname>org.fdroid.fdroid.privileged_1050_src.tar.gz</srcname><hash type="sha256">a0b19494f1a065d477807a49693456c2a305f947cfdb4f54ecfb3c4ce1511c1a</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>33663</size><sdkver>8</sdkver><targetSdkVersion>22</targetSdkVersion><added>2016-01-20</added><permissions>INSTALL_PACKAGES,DELETE_PACKAGES</permissions></package><package><version>0.1-alpha0</version><versioncode>1000</versioncode><apkname>org.fdroid.fdroid.privileged_1000.apk</apkname><srcname>org.fdroid.fdroid.privileged_1000_src.tar.gz</srcname><hash type="sha256">4d2251bbf1468ca69cead98b190ceab1f74bd2901e18ed22b237797098ce36e6</hash><sig>9063aaadfff9cfd811a9c72fb5012f28</sig><size>45605</size><sdkver>8</sdkver><targetSdkVersion>22</targetSdkVersion><added>2015-09-10</added><permissions>INSTALL_PACKAGES,DELETE_PACKAGES</permissions></package></application></fdroid>