Replace CommaSeparatedList with String[].

This is a combination of:
 * `String[].split(",")` and
 * `TextUtils.join(",", values)`

It seems a bit wastefull to have our own implementation of these two things
which lightly wrap this code, and produce a datastructure which is non standard
and foreign to Java developers.
This commit is contained in:
Peter Serwylo 2016-06-20 22:24:52 +10:00
parent 57c63a8e2a
commit d99b357a1f
9 changed files with 51 additions and 96 deletions

View File

@ -266,7 +266,7 @@ public class AppDetails extends AppCompatActivity {
}
if (Preferences.get().expertMode() && apk.nativecode != null) {
holder.nativecode.setText(apk.nativecode.toString().replaceAll(",", " "));
holder.nativecode.setText(TextUtils.join(" ", apk.nativecode));
holder.nativecode.setVisibility(View.VISIBLE);
} else {
holder.nativecode.setVisibility(View.GONE);
@ -276,7 +276,7 @@ public class AppDetails extends AppCompatActivity {
holder.incompatibleReasons.setText(
getResources().getString(
R.string.requires_features,
apk.incompatibleReasons.toPrettyString()));
TextUtils.join(", ", apk.incompatibleReasons)));
holder.incompatibleReasons.setVisibility(View.VISIBLE);
} else {
holder.incompatibleReasons.setVisibility(View.GONE);
@ -1323,7 +1323,7 @@ public class AppDetails extends AppCompatActivity {
// Categories TextView
final TextView categories = (TextView) view.findViewById(R.id.categories);
if (prefs.expertMode() && app.categories != null) {
categories.setText(app.categories.toString().replaceAll(",", ", "));
categories.setText(TextUtils.join(", ", app.categories));
} else {
categories.setVisibility(View.GONE);
}

View File

@ -25,12 +25,15 @@ public class AppFilter {
// Return true if the given app should be filtered out based on user
// preferences, and false otherwise.
public boolean filter(App app) {
if (app.requirements == null) {
if (app.requirements != null && !Preferences.get().filterAppsRequiringRoot()) {
for (String requirement : app.requirements) {
if (requirement.equals("root")) {
return true;
}
}
}
return false;
}
return !Preferences.get().filterAppsRequiringRoot()
&& app.requirements.contains("root");
}
}

View File

@ -6,6 +6,7 @@ import android.content.pm.FeatureInfo;
import android.content.pm.PackageManager;
import android.os.Build;
import android.preference.PreferenceManager;
import android.support.annotation.Nullable;
import org.fdroid.fdroid.compat.SupportedArchitectures;
import org.fdroid.fdroid.data.Apk;
@ -69,15 +70,18 @@ public class CompatibilityChecker {
cpuAbisDesc = builder.toString();
}
private boolean compatibleApi(Utils.CommaSeparatedList nativecode) {
private boolean compatibleApi(@Nullable String[] nativecode) {
if (nativecode == null) {
return true;
}
for (final String cpuAbi : cpuAbis) {
if (nativecode.contains(cpuAbi)) {
for (String code : nativecode) {
if (code.equals(cpuAbi)) {
return true;
}
}
}
return false;
}
@ -108,9 +112,7 @@ public class CompatibilityChecker {
}
}
if (!compatibleApi(apk.nativecode)) {
for (final String code : apk.nativecode) {
incompatibleReasons.add(code);
}
Collections.addAll(incompatibleReasons, apk.nativecode);
Utils.debugLog(TAG, apk.packageName + " vercode " + apk.versionCode
+ " only supports " + Utils.CommaSeparatedList.str(apk.nativecode)
+ " while your architectures are " + cpuAbisDesc);

View File

@ -58,6 +58,7 @@ import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.Formatter;
import java.util.Iterator;
@ -402,84 +403,33 @@ public final class Utils {
return new Locale(languageTag);
}
public static final class CommaSeparatedList implements Iterable<String> {
private final String value;
private CommaSeparatedList(String list) {
value = list;
}
public static CommaSeparatedList make(List<String> list) {
public static final class CommaSeparatedList {
@Nullable
public static String[] make(List<String> list) {
if (list == null || list.isEmpty()) {
return null;
}
StringBuilder sb = new StringBuilder();
for (int i = 0; i < list.size(); i++) {
if (i > 0) {
sb.append(',');
}
sb.append(list.get(i));
}
return new CommaSeparatedList(sb.toString());
}
public static CommaSeparatedList make(String[] list) {
if (list == null || list.length == 0) {
return null;
}
StringBuilder sb = new StringBuilder();
for (int i = 0; i < list.length; i++) {
if (i > 0) {
sb.append(',');
}
sb.append(list[i]);
}
return new CommaSeparatedList(sb.toString());
return list.toArray(new String[list.size()]);
}
@Nullable
public static CommaSeparatedList make(@Nullable String list) {
public static String[] make(String[] list) {
if (list == null || list.length == 0) {
return null;
}
return list;
}
@Nullable
public static String[] make(@Nullable String list) {
if (TextUtils.isEmpty(list)) {
return null;
}
return new CommaSeparatedList(list);
return list.split(",");
}
public static String str(CommaSeparatedList instance) {
return instance == null ? null : instance.toString();
}
@Override
public String toString() {
return value;
}
public String toPrettyString() {
return value.replaceAll(",", ", ");
}
@Override
public Iterator<String> iterator() {
TextUtils.SimpleStringSplitter splitter = new TextUtils.SimpleStringSplitter(',');
splitter.setString(value);
return splitter.iterator();
}
public ArrayList<String> toArrayList() {
ArrayList<String> out = new ArrayList<>();
for (String element : this) {
out.add(element);
}
return out;
}
public boolean contains(String v) {
for (final String s : this) {
if (s.equals(v)) {
return true;
}
}
return false;
public static String str(@Nullable String[] values) {
return values == null ? null : TextUtils.join(",", values);
}
}

View File

@ -29,11 +29,11 @@ public class Apk extends ValueObject implements Comparable<Apk> {
public int targetSdkVersion = SDK_VERSION_MIN_VALUE; // 0 if unknown
public int maxSdkVersion = SDK_VERSION_MAX_VALUE; // "infinity" if not set
public Date added;
public Utils.CommaSeparatedList permissions; // null if empty or
public String[] permissions; // null if empty or
// unknown
public Utils.CommaSeparatedList features; // null if empty or unknown
public String[] features; // null if empty or unknown
public Utils.CommaSeparatedList nativecode; // null if empty or unknown
public String[] nativecode; // null if empty or unknown
/**
* ID (md5 sum of public key) of signature. Might be null, in the
@ -58,7 +58,7 @@ public class Apk extends ValueObject implements Comparable<Apk> {
public int repoVersion;
public String repoAddress;
public Utils.CommaSeparatedList incompatibleReasons;
public String[] incompatibleReasons;
public Apk() {
}

View File

@ -88,17 +88,17 @@ public class App extends ValueObject implements Comparable<App> {
/**
* List of categories (as defined in the metadata documentation) or null if there aren't any.
*/
public Utils.CommaSeparatedList categories;
public String[] categories;
/**
* List of anti-features (as defined in the metadata documentation) or null if there aren't any.
*/
public Utils.CommaSeparatedList antiFeatures;
public String[] antiFeatures;
/**
* List of special requirements (such as root privileges) or null if there aren't any.
*/
public Utils.CommaSeparatedList requirements;
public String[] requirements;
/**
* True if all updates for this app are to be ignored

View File

@ -98,11 +98,9 @@ public class AppProvider extends FDroidProvider {
cursor.moveToFirst();
while (!cursor.isAfterLast()) {
final String categoriesString = cursor.getString(0);
Utils.CommaSeparatedList categoriesList = Utils.CommaSeparatedList.make(categoriesString);
String[] categoriesList = Utils.CommaSeparatedList.make(categoriesString);
if (categoriesList != null) {
for (final String s : categoriesList) {
categorySet.add(s);
}
Collections.addAll(categorySet, categoriesList);
}
cursor.moveToNext();
}

View File

@ -672,9 +672,7 @@ public class RepoXMLHandlerTest {
assertNull(app.antiFeatures);
} else {
List<String> actualAntiFeatures = new ArrayList<>();
for (String antiFeature : app.antiFeatures) {
actualAntiFeatures.add(antiFeature);
}
Collections.addAll(actualAntiFeatures, app.antiFeatures);
assertTrue(actualAntiFeatures.containsAll(antiFeatures));
assertTrue(antiFeatures.containsAll(actualAntiFeatures));
}

View File

@ -289,7 +289,8 @@ public class ApkProviderTest extends FDroidProviderTest {
assertEquals(0, apk.repoVersion);
// But this should have saved correctly...
assertEquals("Some features", apk.features.toString());
assertEquals(1, apk.features.length);
assertEquals("Some features", apk.features[0]);
assertEquals("com.example.com", apk.packageName);
assertEquals(1, apk.versionCode);
assertEquals(10, apk.repo);
@ -435,7 +436,10 @@ public class ApkProviderTest extends FDroidProviderTest {
assertNotNull(updatedApk.added);
assertNotNull(updatedApk.hashType);
assertEquals("one,two,three", updatedApk.features.toString());
assertEquals(3, updatedApk.features.length);
assertEquals("one", updatedApk.features[0]);
assertEquals("two", updatedApk.features[1]);
assertEquals("three", updatedApk.features[2]);
assertEquals(new Date(dateTimestamp).getYear(), updatedApk.added.getYear());
assertEquals(new Date(dateTimestamp).getMonth(), updatedApk.added.getMonth());
assertEquals(new Date(dateTimestamp).getDay(), updatedApk.added.getDay());