| Index: src/org/adblockplus/sbrowser/contentblocker/engine/Engine.java |
| =================================================================== |
| --- a/src/org/adblockplus/sbrowser/contentblocker/engine/Engine.java |
| +++ b/src/org/adblockplus/sbrowser/contentblocker/engine/Engine.java |
| @@ -21,22 +21,28 @@ import java.io.BufferedReader; |
| import java.io.BufferedWriter; |
| import java.io.File; |
| import java.io.FileOutputStream; |
| import java.io.IOException; |
| import java.io.InputStream; |
| import java.io.InputStreamReader; |
| import java.io.OutputStreamWriter; |
| import java.io.Writer; |
| +import java.net.URI; |
| +import java.net.URISyntaxException; |
| import java.net.URL; |
| import java.net.URLEncoder; |
| +import java.nio.charset.StandardCharsets; |
| import java.util.ArrayList; |
| +import java.util.Collections; |
| import java.util.HashMap; |
| import java.util.List; |
| import java.util.Map; |
| +import java.util.Set; |
| +import java.util.TreeSet; |
| import java.util.concurrent.LinkedBlockingQueue; |
| import java.util.concurrent.TimeUnit; |
| import java.util.concurrent.locks.ReentrantLock; |
| import java.util.regex.Pattern; |
| import org.adblockplus.adblockplussbrowser.R; |
| import android.content.Context; |
| @@ -148,30 +154,30 @@ public final class Engine |
| .queryIntentActivities(new Intent(ACTION_OPEN_SETTINGS), 0).size() > 0; |
| } |
| catch (final Throwable t) |
| { |
| return false; |
| } |
| } |
| - void requestUpdateBroadcast() |
| + public void requestUpdateBroadcast() |
| { |
| this.lock(); |
| try |
| { |
| this.nextUpdateBroadcast = System.currentTimeMillis() + BROADCAST_COMBINATION_DELAY_MILLIS; |
| } |
| finally |
| { |
| this.unlock(); |
| } |
| } |
| - private void sendUpdateBroadcast() |
| + private void writeFileAndSendUpdateBroadcast() |
| { |
| createAndWriteFile(); |
| runOnUiThread(new Runnable() |
| { |
| @Override |
| public void run() |
| { |
| @@ -237,23 +243,24 @@ public final class Engine |
| } |
| void downloadFinished(final String id, final int responseCode, final String response, |
| final Map<String, String> headers) |
| { |
| this.engineEvents.add(new DownloadFinishedEvent(id, responseCode, response, headers)); |
| } |
| - public void createAndWriteFile() |
| + private void createAndWriteFile() |
| { |
| this.lock(); |
| try |
| { |
| Log.d(TAG, "Writing filters..."); |
| final File filterFile = this.subscriptions.createAndWriteFile(); |
| + writeWhitelistedWebsites(this.serviceContext, filterFile); |
| final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this.serviceContext); |
| final String key = this.serviceContext.getString(R.string.key_cached_filter_path); |
| prefs.edit().putString(key, filterFile.getAbsolutePath()).commit(); |
| Log.d(TAG, "Cleaning up cache..."); |
| final File dummyFile = getDummyFilterFile(this.serviceContext); |
| final File[] cacheDirFiles = getFilterCacheDir(this.serviceContext).listFiles(); |
| @@ -420,17 +427,17 @@ public final class Engine |
| Log.d(TAG, "Added " + additional + " additional default/built-in subscriptions"); |
| engine.subscriptions.persistSubscriptions(); |
| } |
| final File cachedFilterFile = getCachedFilterFile(context); |
| if (cachedFilterFile == null || !cachedFilterFile.exists()) |
| { |
| - engine.sendUpdateBroadcast(); |
| + engine.writeFileAndSendUpdateBroadcast(); |
| } |
| engine.handlerThread = new Thread(new EventHandler(engine)); |
| engine.handlerThread.setDaemon(true); |
| engine.handlerThread.start(); |
| engine.downloader = Downloader.create(context, engine); |
| @@ -489,16 +496,47 @@ public final class Engine |
| } |
| public static void writeFilterHeaders(Writer writer) throws IOException |
| { |
| writer.write("[Adblock Plus 2.0]\n"); |
| writer.write("! This file was automatically created.\n"); |
| } |
| + private static void writeWhitelistedWebsites(Context context, File filterFile) throws IOException |
| + { |
| + Log.d(TAG, "Writing whitelisted websites..."); |
| + final SharedPreferences prefs = |
| + PreferenceManager.getDefaultSharedPreferences(context.getApplicationContext()); |
| + final String key = context.getString(R.string.key_whitelisted_websites); |
| + |
| + final Set<String> whitelistedWebsites = new TreeSet<>(); |
| + whitelistedWebsites.addAll(prefs.getStringSet(key, Collections.<String>emptySet())); |
| + |
| + try (final BufferedWriter w = new BufferedWriter( |
| + new OutputStreamWriter(new FileOutputStream(filterFile, true), StandardCharsets.UTF_8))) |
| + { |
| + for (final String url : whitelistedWebsites) |
| + { |
| + try |
| + { |
| + final URI uri = new URI(url); |
| + final String host = uri.getHost() != null ? uri.getHost() : uri.getPath(); |
| + w.write("@@||" + host + "^$document"); |
| + w.write('\n'); |
| + } |
| + catch (URISyntaxException e) |
| + { |
| + Log.w(TAG, "Failed to parse whitelisted website: " + url); |
| + continue; |
| + } |
| + } |
| + } |
| + } |
| + |
| private static File getCachedFilterFile(Context context) |
| { |
| final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context); |
| final String cachedFilterPath = prefs.getString(context.getString(R.string.key_cached_filter_path), null); |
| if (cachedFilterPath != null) |
| { |
| return new File(cachedFilterPath); |
| } |
| @@ -621,17 +659,17 @@ public final class Engine |
| this.engine.subscriptions.checkForUpdates(); |
| } |
| if (currentTime > this.engine.nextUpdateBroadcast) |
| { |
| this.engine.nextUpdateBroadcast = Long.MAX_VALUE; |
| Log.d(TAG, "Sending update broadcast"); |
| - this.engine.sendUpdateBroadcast(); |
| + this.engine.writeFileAndSendUpdateBroadcast(); |
| } |
| } |
| finally |
| { |
| engine.unlock(); |
| } |
| } |
| catch (final InterruptedException e) |