Merge OPMLMatcher code into OPMLParser

This commit is contained in:
Shinokuni 2020-08-02 15:16:05 +02:00
parent 90fd810d08
commit f014284316
4 changed files with 74 additions and 95 deletions

View File

@ -2,39 +2,87 @@ package com.readrops.api.opml
import android.content.Context
import android.net.Uri
import com.readrops.api.opml.model.Body
import com.readrops.api.opml.model.Head
import com.readrops.api.opml.model.OPML
import com.readrops.api.opml.model.Outline
import com.readrops.api.utils.LibUtils
import com.readrops.db.entities.Feed
import com.readrops.db.entities.Folder
import io.reactivex.Completable
import io.reactivex.Single
import org.simpleframework.xml.Serializer
import org.simpleframework.xml.core.Persister
import java.io.OutputStream
class OPMLParser {
object OPMLParser {
companion object {
@JvmStatic
fun read(uri: Uri, context: Context): Single<OPML> {
fun read(uri: Uri, context: Context): Single<Map<Folder, List<Feed>>> {
return Single.create { emitter ->
val fileString = LibUtils.fileToString(uri, context)
val serializer: Serializer = Persister()
val opml: OPML = serializer.read(OPML::class.java, fileString)
emitter.onSuccess(opml)
emitter.onSuccess(opmltoFoldersAndFeeds(opml))
}
}
@JvmStatic
fun write(opml: OPML, outputStream: OutputStream): Completable {
fun write(foldersAndFeeds: Map<Folder, List<Feed>>, outputStream: OutputStream): Completable {
return Completable.create { emitter ->
val serializer: Serializer = Persister()
serializer.write(opml, outputStream)
serializer.write(foldersAndFeedsToOPML(foldersAndFeeds), outputStream)
emitter.onComplete()
}
}
private fun opmltoFoldersAndFeeds(opml: OPML): Map<Folder, List<Feed>> {
val foldersAndFeeds: MutableMap<Folder, List<Feed>> = HashMap()
val body = opml.body!!
body.outlines?.forEach { outline ->
val folder = Folder(outline.title)
val feeds = arrayListOf<Feed>()
outline.outlines?.forEach { feedOutline ->
val feed = Feed().apply {
name = feedOutline.title
url = feedOutline.xmlUrl
siteUrl = feedOutline.htmlUrl
}
feeds.add(feed)
}
foldersAndFeeds[folder] = feeds
}
return foldersAndFeeds
}
private fun foldersAndFeedsToOPML(foldersAndFeeds: Map<Folder, List<Feed>>): OPML {
val outlines = arrayListOf<Outline>()
for (folderAndFeeds in foldersAndFeeds) {
val outline = Outline(folderAndFeeds.key.name)
val feedOutlines = arrayListOf<Outline>()
folderAndFeeds.value.forEach { feed ->
val feedOutline = Outline(feed.name, feed.url, feed.siteUrl)
feedOutlines.add(feedOutline)
}
outline.outlines = feedOutlines
outlines.add(outline)
}
val head = Head("Subscriptions")
val body = Body(outlines)
return OPML("2.0", head, body)
}
}

View File

@ -22,6 +22,7 @@ import androidx.preference.Preference;
import androidx.preference.PreferenceFragmentCompat;
import com.afollestad.materialdialogs.MaterialDialog;
import com.readrops.api.opml.OPMLParser;
import com.readrops.app.R;
import com.readrops.app.ReadropsApp;
import com.readrops.app.activities.AddAccountActivity;
@ -30,12 +31,9 @@ import com.readrops.app.activities.NotificationPermissionActivity;
import com.readrops.app.utils.PermissionManager;
import com.readrops.app.utils.SharedPreferencesManager;
import com.readrops.app.utils.Utils;
import com.readrops.app.utils.matchers.OPMLMatcher;
import com.readrops.app.viewmodels.AccountViewModel;
import com.readrops.db.entities.account.Account;
import com.readrops.db.entities.account.AccountType;
import com.readrops.api.opml.OPMLParser;
import com.readrops.api.opml.model.OPML;
import java.io.File;
import java.io.FileOutputStream;
@ -247,11 +245,8 @@ public class AccountSettingsFragment extends PreferenceFragmentCompat {
final OutputStream outputStream = new FileOutputStream(file);
viewModel.getFoldersWithFeeds()
.flatMapCompletable(folderListMap -> {
OPML opml = OPMLMatcher.INSTANCE.foldersAndFeedsToOPML(folderListMap, getContext());
return OPMLParser.write(opml, outputStream);
}).subscribeOn(Schedulers.io())
.flatMapCompletable(folderListMap -> OPMLParser.write(folderListMap, outputStream))
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.doAfterTerminate(() -> {
try {

View File

@ -1,59 +0,0 @@
package com.readrops.app.utils.matchers
import android.content.Context
import com.readrops.app.R
import com.readrops.db.entities.Feed
import com.readrops.db.entities.Folder
import com.readrops.api.opml.model.Body
import com.readrops.api.opml.model.Head
import com.readrops.api.opml.model.OPML
import com.readrops.api.opml.model.Outline
object OPMLMatcher {
fun opmltoFoldersAndFeeds(opml: OPML): Map<Folder, List<Feed>> {
val foldersAndFeeds: MutableMap<Folder, List<Feed>> = HashMap()
val body = opml.body!!
body.outlines?.forEach { outline ->
val folder = Folder(outline.title)
val feeds = arrayListOf<Feed>()
outline.outlines?.forEach { feedOutline ->
val feed = Feed().apply {
name = feedOutline.title
url = feedOutline.xmlUrl
siteUrl = feedOutline.htmlUrl
}
feeds.add(feed)
}
foldersAndFeeds[folder] = feeds
}
return foldersAndFeeds
}
fun foldersAndFeedsToOPML(foldersAndFeeds: Map<Folder, List<Feed>>, context: Context): OPML {
val outlines = arrayListOf<Outline>()
for (folderAndFeeds in foldersAndFeeds) {
val outline = Outline(folderAndFeeds.key.name)
val feedOutlines = arrayListOf<Outline>()
folderAndFeeds.value.forEach { feed ->
val feedOutline = Outline(feed.name, feed.url, feed.siteUrl)
feedOutlines.add(feedOutline)
}
outline.outlines = feedOutlines
outlines.add(outline)
}
val head = Head(context.getString(R.string.subscriptions))
val body = Body(outlines)
return OPML("2.0", head, body)
}
}

View File

@ -7,14 +7,13 @@ import android.util.Log;
import androidx.annotation.NonNull;
import androidx.lifecycle.AndroidViewModel;
import com.readrops.api.opml.OPMLParser;
import com.readrops.app.repositories.ARepository;
import com.readrops.db.Database;
import com.readrops.db.entities.Feed;
import com.readrops.db.entities.Folder;
import com.readrops.db.entities.account.Account;
import com.readrops.db.entities.account.AccountType;
import com.readrops.app.repositories.ARepository;
import com.readrops.app.utils.matchers.OPMLMatcher;
import com.readrops.api.opml.OPMLParser;
import java.util.List;
import java.util.Map;
@ -73,10 +72,6 @@ public class AccountViewModel extends AndroidViewModel {
public Completable parseOPMLFile(Uri uri) {
return OPMLParser.read(uri, getApplication())
.flatMapCompletable(opml -> {
Map<Folder, List<Feed>> foldersAndFeeds = OPMLMatcher.INSTANCE.opmltoFoldersAndFeeds(opml);
return repository.insertOPMLFoldersAndFeeds(foldersAndFeeds);
});
.flatMapCompletable(foldersAndFeeds -> repository.insertOPMLFoldersAndFeeds(foldersAndFeeds));
}
}