Browse Source

Improving memory performance in case with multiple hosts per line

master
anthony restaino 8 years ago
parent
commit
638220efc6
  1. 65
      app/src/main/java/acr/browser/lightning/utils/AdBlock.java
  2. 19
      app/src/main/java/acr/browser/lightning/utils/StringBuilderUtils.java

65
app/src/main/java/acr/browser/lightning/utils/AdBlock.java

@ -1,11 +1,15 @@
package acr.browser.lightning.utils; package acr.browser.lightning.utils;
import android.content.Context;
import android.content.res.AssetManager; import android.content.res.AssetManager;
import android.support.annotation.NonNull; import android.support.annotation.NonNull;
import android.support.annotation.Nullable; import android.support.annotation.Nullable;
import android.util.Log; import android.util.Log;
import com.anthonycr.bonsai.Completable;
import com.anthonycr.bonsai.CompletableAction;
import com.anthonycr.bonsai.CompletableSubscriber;
import com.anthonycr.bonsai.Schedulers;
import java.io.BufferedReader; import java.io.BufferedReader;
import java.io.IOException; import java.io.IOException;
import java.io.InputStreamReader; import java.io.InputStreamReader;
@ -40,10 +44,10 @@ public class AdBlock {
@Inject PreferenceManager mPreferenceManager; @Inject PreferenceManager mPreferenceManager;
@Inject @Inject
public AdBlock(@NonNull Context context) { public AdBlock() {
BrowserApp.getAppComponent().inject(this); BrowserApp.getAppComponent().inject(this);
if (mBlockedDomainsList.isEmpty() && Constants.FULL_VERSION) { if (mBlockedDomainsList.isEmpty() && Constants.FULL_VERSION) {
loadHostsFile(context); loadHostsFile().subscribeOn(Schedulers.io()).subscribe();
} }
mBlockAds = mPreferenceManager.getAdBlockEnabled(); mBlockAds = mPreferenceManager.getAdBlockEnabled();
} }
@ -52,31 +56,6 @@ public class AdBlock {
mBlockAds = mPreferenceManager.getAdBlockEnabled(); mBlockAds = mPreferenceManager.getAdBlockEnabled();
} }
private void loadBlockedDomainsList(@NonNull final Context context) {
BrowserApp.getIOThread().execute(new Runnable() {
@Override
public void run() {
AssetManager asset = context.getAssets();
BufferedReader reader = null;
try {
//noinspection IOResourceOpenedButNotSafelyClosed
reader = new BufferedReader(new InputStreamReader(
asset.open(BLOCKED_DOMAINS_LIST_FILE_NAME)));
String line;
while ((line = reader.readLine()) != null) {
mBlockedDomainsList.add(line.trim());
}
} catch (IOException e) {
Log.wtf(TAG, "Reading blocked domains list from file '"
+ BLOCKED_DOMAINS_LIST_FILE_NAME + "' failed.", e);
} finally {
Utils.close(reader);
}
}
});
}
/** /**
* a method that determines if the given URL is an ad or not. It performs * a method that determines if the given URL is an ad or not. It performs
* a search of the URL's domain on the blocked domain hash set. * a search of the URL's domain on the blocked domain hash set.
@ -128,20 +107,20 @@ public class AdBlock {
} }
/** /**
* This method reads through a hosts file and extracts the domains that should * This Completable reads through a hosts file and extracts the domains that should
* be redirected to localhost (a.k.a. IP address 127.0.0.1). It can handle files that * be redirected to localhost (a.k.a. IP address 127.0.0.1). It can handle files that
* simply have a list of hostnames to block, or it can handle a full blown hosts file. * simply have a list of host names to block, or it can handle a full blown hosts file.
* It will strip out comments, references to the base IP address and just extract the * It will strip out comments, references to the base IP address and just extract the
* domains to be used * domains to be used.
* *
* @param context the context needed to read the file * @return a Completable that will load the hosts file into memory.
*/ */
private void loadHostsFile(@NonNull final Context context) { @NonNull
BrowserApp.getIOThread().execute(new Runnable() { private Completable loadHostsFile() {
return Completable.create(new CompletableAction() {
@Override @Override
public void run() { public void onSubscribe(@NonNull CompletableSubscriber subscriber) {
AssetManager asset = context.getAssets(); AssetManager asset = BrowserApp.getApplication().getAssets();
BufferedReader reader = null; BufferedReader reader = null;
try { try {
//noinspection IOResourceOpenedButNotSafelyClosed //noinspection IOResourceOpenedButNotSafelyClosed
@ -150,7 +129,7 @@ public class AdBlock {
StringBuilder lineBuilder = new StringBuilder(); StringBuilder lineBuilder = new StringBuilder();
String line; String line;
long time = System.currentTimeMillis(); long time = System.currentTimeMillis();
// TODO: 4/23/17 Improve performance by reading in on IO thread and then processing on worker thread
while ((line = reader.readLine()) != null) { while ((line = reader.readLine()) != null) {
lineBuilder.append(line); lineBuilder.append(line);
@ -172,9 +151,13 @@ public class AdBlock {
!StringBuilderUtils.equals(lineBuilder, LOCALHOST)) { !StringBuilderUtils.equals(lineBuilder, LOCALHOST)) {
while (StringBuilderUtils.contains(lineBuilder, SPACE)) { while (StringBuilderUtils.contains(lineBuilder, SPACE)) {
int space = lineBuilder.indexOf(SPACE); int space = lineBuilder.indexOf(SPACE);
String host = lineBuilder.substring(0, space); StringBuilder partial = StringBuilderUtils.substring(lineBuilder, 0, space);
StringBuilderUtils.replace(lineBuilder, host, EMPTY); StringBuilderUtils.trim(partial);
mBlockedDomainsList.add(host.trim());
String partialLine = partial.toString();
mBlockedDomainsList.add(partialLine);
StringBuilderUtils.replace(lineBuilder, partialLine, EMPTY);
StringBuilderUtils.trim(lineBuilder);
} }
if (lineBuilder.length() > 0) { if (lineBuilder.length() > 0) {
mBlockedDomainsList.add(lineBuilder.toString()); mBlockedDomainsList.add(lineBuilder.toString());

19
app/src/main/java/acr/browser/lightning/utils/StringBuilderUtils.java

@ -96,4 +96,23 @@ public class StringBuilderUtils {
int index = stringBuilder.indexOf(equal); int index = stringBuilder.indexOf(equal);
return index >= 0 && stringBuilder.length() == equal.length(); return index >= 0 && stringBuilder.length() == equal.length();
} }
/**
* Creates a sub-string builder from the
* current string builder.
*
* @param stringBuilder the string builder.
* @param start the starting index.
* @param end the ending index.
* @return a string builder that contains the
* characters between the indices.
*/
@NonNull
public static StringBuilder substring(@NonNull StringBuilder stringBuilder, int start, int end) {
StringBuilder newStringBuilder = new StringBuilder(stringBuilder);
newStringBuilder.replace(end, stringBuilder.length(), EMPTY);
newStringBuilder.replace(0, start, EMPTY);
return newStringBuilder;
}
} }

Loading…
Cancel
Save