From d029660d2e8cdbc5aa31a0ea4bb699a5e665fea1 Mon Sep 17 00:00:00 2001 From: Vasiliy Bout Date: Tue, 24 Aug 2010 14:05:58 +0000 Subject: [PATCH] Loading catalogs from network git-svn-id: https://only.mawhrin.net/repos/FBReaderJ/trunk@1674 6a642e6f-84f6-412e-ac94-c4a38d5a04b0 --- TODO.network | 3 +- data/network/catalogs.xml | 555 ------------------ data/resources/application/de.xml | 1 + data/resources/application/en.xml | 1 + data/resources/application/fr.xml | 1 + data/resources/application/hu.xml | 1 + data/resources/application/it.xml | 1 + data/resources/application/ru.xml | 1 + data/resources/application/vi.xml | 1 + data/resources/application/zh.xml | 1 + .../network/NetworkLibraryActivity.java | 89 ++- .../android/fbreader/network/NetworkView.java | 11 +- .../network/SQLiteNetworkDatabase.java | 8 +- .../fbreader/network/NetworkDatabase.java | 7 +- .../fbreader/network/NetworkLibrary.java | 129 ++-- .../fbreader/network/opds/OPDSLinkReader.java | 310 +--------- .../network/opds/OPDSLinkXMLReader.java | 20 +- 17 files changed, 183 insertions(+), 957 deletions(-) delete mode 100644 data/network/catalogs.xml diff --git a/TODO.network b/TODO.network index 728835573..1ec5cddca 100644 --- a/TODO.network +++ b/TODO.network @@ -14,7 +14,8 @@ NP: оповещение об изменениях в namespace'ах проис ** Загрузка не из xml, а из OPDS-каталога с расширениями DONE сделать DTD для xml-ей, как в OPDS, вместо существующего - ** перенести xml на сервер + DONE перенести xml на сервер + ** кэширование каталога ** сделать чтение информации о поиске напрямую из каталога ** Использовать default e-mail при регистрации новых пользователей в AuthenticationDialog (возможно только в Android 2.0+) diff --git a/data/network/catalogs.xml b/data/network/catalogs.xml deleted file mode 100644 index c295d05cf..000000000 --- a/data/network/catalogs.xml +++ /dev/null @@ -1,555 +0,0 @@ - - - http://data.fbreader.org/catalogs/generic-1.0.xml - FBReader catalogs list - 2010-07-28T16:34:00Z - - Geometer Plus - http://www.fbreader.org - contact@geometerplus.com - - - - urn:fbreader-org-catalog:feedbooks.com - 2010-07-28T12:00:00Z - Feedbooks OPDS Catalog - Feedbooks: Food for the mind. A place to discover and publish e-books. - - - - - - - - - - - - - - - - - - - urn:fbreader-org-catalog:litres.ru - 2010-07-28T12:15:00Z - Каталог LitRes - Продажа электронных книг. - - - - - - - - - - - - - - - - - - - - - urn:fbreader-org-catalog:manybooks.net - 2010-07-28T12:15:00Z - ManyBooks Catalog - ManyBooks.net: The best ebooks at the best price: free! - - - - - - - - - - urn:fbreader-org-catalog:shucang.com - 2010-07-28T13:40:00Z - Shucang Catalog - Shucang: a Chinese bookshelf. - - - - - - - - - - - - - - - - - - urn:fbreader-org-catalog:smashwords.com - 2010-07-28T13:40:00Z - Smashwords - Ebooks from independent authors and publishers - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/data/resources/application/de.xml b/data/resources/application/de.xml index 5620cd8b8..c39c5e8d5 100644 --- a/data/resources/application/de.xml +++ b/data/resources/application/de.xml @@ -139,6 +139,7 @@ + diff --git a/data/resources/application/en.xml b/data/resources/application/en.xml index c0e373d21..911b9f8b8 100644 --- a/data/resources/application/en.xml +++ b/data/resources/application/en.xml @@ -138,6 +138,7 @@ + diff --git a/data/resources/application/fr.xml b/data/resources/application/fr.xml index 9135d0498..f49a092fa 100644 --- a/data/resources/application/fr.xml +++ b/data/resources/application/fr.xml @@ -139,6 +139,7 @@ + diff --git a/data/resources/application/hu.xml b/data/resources/application/hu.xml index 0397ac655..ba0f0b2c2 100644 --- a/data/resources/application/hu.xml +++ b/data/resources/application/hu.xml @@ -139,6 +139,7 @@ + diff --git a/data/resources/application/it.xml b/data/resources/application/it.xml index f6b78c298..b8686edbf 100644 --- a/data/resources/application/it.xml +++ b/data/resources/application/it.xml @@ -139,6 +139,7 @@ + diff --git a/data/resources/application/ru.xml b/data/resources/application/ru.xml index 3677a6710..9f0a89213 100644 --- a/data/resources/application/ru.xml +++ b/data/resources/application/ru.xml @@ -138,6 +138,7 @@ + diff --git a/data/resources/application/vi.xml b/data/resources/application/vi.xml index ad3df03ee..8f1ac4fab 100644 --- a/data/resources/application/vi.xml +++ b/data/resources/application/vi.xml @@ -139,6 +139,7 @@ + diff --git a/data/resources/application/zh.xml b/data/resources/application/zh.xml index 7a28c6b21..202215126 100644 --- a/data/resources/application/zh.xml +++ b/data/resources/application/zh.xml @@ -139,6 +139,7 @@ + diff --git a/src/org/geometerplus/android/fbreader/network/NetworkLibraryActivity.java b/src/org/geometerplus/android/fbreader/network/NetworkLibraryActivity.java index 5ee2ff4cd..4ec9c7811 100644 --- a/src/org/geometerplus/android/fbreader/network/NetworkLibraryActivity.java +++ b/src/org/geometerplus/android/fbreader/network/NetworkLibraryActivity.java @@ -19,12 +19,15 @@ package org.geometerplus.android.fbreader.network; +import android.app.AlertDialog; +import android.content.DialogInterface; import android.os.Bundle; import android.os.Handler; import android.os.Message; import android.view.*; import android.widget.BaseAdapter; +import org.geometerplus.zlibrary.core.resources.ZLResource; import org.geometerplus.zlibrary.ui.android.R; import org.geometerplus.zlibrary.ui.android.dialogs.ZLAndroidDialogManager; @@ -35,8 +38,6 @@ import org.geometerplus.fbreader.network.NetworkLibrary; public class NetworkLibraryActivity extends NetworkBaseActivity { - private boolean myInitialized; - private NetworkTree myTree; @Override @@ -48,8 +49,7 @@ public class NetworkLibraryActivity extends NetworkBaseActivity { } private void prepareView() { - if (!myInitialized) { - myInitialized = true; + if (myTree == null) { myTree = NetworkLibrary.Instance().getTree(); setListAdapter(new LibraryAdapter()); getListView().invalidateViews(); @@ -59,28 +59,83 @@ public class NetworkLibraryActivity extends NetworkBaseActivity { @Override public void onResume() { super.onResume(); - final NetworkView networkView = NetworkView.Instance(); - if (!networkView.isInitialized()) { - final Handler handler = new Handler() { - public void handleMessage(Message message) { - prepareView(); - } - }; - ((ZLAndroidDialogManager)ZLAndroidDialogManager.Instance()).wait("loadingNetworkLibrary", new Runnable() { - public void run() { - networkView.initialize(); - handler.sendEmptyMessage(0); - } - }, this); + tryResume(); + } + + private void tryResume() { + if (!NetworkView.Instance().isInitialized()) { + new Initializator().start(); } else { prepareView(); } } + private class Initializator extends Handler { + + final DialogInterface.OnClickListener myListener = new DialogInterface.OnClickListener() { + public void onClick(DialogInterface dialog, int which) { + if (which == DialogInterface.BUTTON_POSITIVE) { + Initializator.this.start(); + } else { + NetworkLibraryActivity.this.finish(); + } + } + }; + + private void runInitialization() { + ((ZLAndroidDialogManager)ZLAndroidDialogManager.Instance()).wait("loadingNetworkLibrary", new Runnable() { + public void run() { + final String error = NetworkView.Instance().initialize(); + Initializator.this.end(error); + } + }, NetworkLibraryActivity.this); + } + + private void processResults(String error) { + final ZLResource dialogResource = ZLResource.resource("dialog"); + final ZLResource boxResource = dialogResource.getResource("networkError"); + final ZLResource buttonResource = dialogResource.getResource("button"); + new AlertDialog.Builder(NetworkLibraryActivity.this) + .setTitle(boxResource.getResource("title").getValue()) + .setMessage(error) + .setIcon(0) + .setPositiveButton(buttonResource.getResource("tryAgain").getValue(), myListener) + .setNegativeButton(buttonResource.getResource("cancel").getValue(), myListener) + .setOnCancelListener(new DialogInterface.OnCancelListener() { + public void onCancel(DialogInterface dialog) { + myListener.onClick(dialog, DialogInterface.BUTTON_NEGATIVE); + } + }) + .create().show(); + } + + @Override + public void handleMessage(Message message) { + if (message.what == 0) { + runInitialization(); // run initialization process + } else if (message.obj == null) { + prepareView(); // initialization is complete successfully + } else { + processResults((String) message.obj); // handle initialization error + } + } + + public void start() { + sendEmptyMessage(0); + } + + private void end(String error) { + sendMessage(obtainMessage(1, error)); + } + } + private final class LibraryAdapter extends BaseAdapter { public final int getCount() { + if (!NetworkView.Instance().isInitialized()) { + return 0; + } return myTree.subTrees().size() + 2; // subtrees + } diff --git a/src/org/geometerplus/android/fbreader/network/NetworkView.java b/src/org/geometerplus/android/fbreader/network/NetworkView.java index 3242c63d9..0876d629f 100644 --- a/src/org/geometerplus/android/fbreader/network/NetworkView.java +++ b/src/org/geometerplus/android/fbreader/network/NetworkView.java @@ -57,10 +57,16 @@ class NetworkView { return myInitialized; } - public void initialize() { + public String initialize() { new SQLiteNetworkDatabase(); - NetworkLibrary.Instance().synchronize(); + final NetworkLibrary library = NetworkLibrary.Instance(); + final String error = library.initialize(); + if (error != null) { + return error; + } + + library.synchronize(); myActions.add(new NetworkBookActions()); myActions.add(new NetworkCatalogActions()); @@ -70,6 +76,7 @@ class NetworkView { myActions.trimToSize(); myInitialized = true; + return null; } diff --git a/src/org/geometerplus/android/fbreader/network/SQLiteNetworkDatabase.java b/src/org/geometerplus/android/fbreader/network/SQLiteNetworkDatabase.java index 001a03f0e..cb277d333 100644 --- a/src/org/geometerplus/android/fbreader/network/SQLiteNetworkDatabase.java +++ b/src/org/geometerplus/android/fbreader/network/SQLiteNetworkDatabase.java @@ -20,7 +20,6 @@ package org.geometerplus.android.fbreader.network; import java.util.HashMap; -import java.util.List; import android.content.Context; import android.database.Cursor; @@ -77,7 +76,7 @@ class SQLiteNetworkDatabase extends NetworkDatabase { } @Override - protected void loadCustomLinks(List links, ICustomLinksFactory factory) { + protected void loadCustomLinks(ICustomLinksHandler handler) { final Cursor cursor = myDatabase.rawQuery("SELECT link_id,title,site_name,summary,icon FROM CustomLinks", null); final HashMap linksMap = new HashMap(); while (cursor.moveToNext()) { @@ -94,10 +93,7 @@ class SQLiteNetworkDatabase extends NetworkDatabase { } linksCursor.close(); - final ICustomNetworkLink newLink = factory.createCustomLink(id, siteName, title, summary, icon, linksMap); - if (newLink != null) { - links.add(newLink); - } + handler.handleCustomLinkData(id, siteName, title, summary, icon, linksMap); } cursor.close(); } diff --git a/src/org/geometerplus/fbreader/network/NetworkDatabase.java b/src/org/geometerplus/fbreader/network/NetworkDatabase.java index 07b78cfd5..256c24a2b 100644 --- a/src/org/geometerplus/fbreader/network/NetworkDatabase.java +++ b/src/org/geometerplus/fbreader/network/NetworkDatabase.java @@ -19,7 +19,6 @@ package org.geometerplus.fbreader.network; -import java.util.List; import java.util.Map; public abstract class NetworkDatabase { @@ -35,11 +34,11 @@ public abstract class NetworkDatabase { protected abstract void executeAsATransaction(Runnable actions); - public interface ICustomLinksFactory { - ICustomNetworkLink createCustomLink(int id, String siteName, String title, String summary, String icon, Map links); + public interface ICustomLinksHandler { + void handleCustomLinkData(int id, String siteName, String title, String summary, String icon, Map links); } - protected abstract void loadCustomLinks(List links, ICustomLinksFactory factory); + protected abstract void loadCustomLinks(ICustomLinksHandler handler); protected abstract void saveCustomLink(ICustomNetworkLink link); protected abstract void deleteCustomLink(ICustomNetworkLink link); } diff --git a/src/org/geometerplus/fbreader/network/NetworkLibrary.java b/src/org/geometerplus/fbreader/network/NetworkLibrary.java index 0754aff6a..c73218a9e 100644 --- a/src/org/geometerplus/fbreader/network/NetworkLibrary.java +++ b/src/org/geometerplus/fbreader/network/NetworkLibrary.java @@ -21,7 +21,6 @@ package org.geometerplus.fbreader.network; import java.util.*; -import org.geometerplus.zlibrary.core.filesystem.*; import org.geometerplus.zlibrary.core.util.ZLNetworkUtil; import org.geometerplus.zlibrary.core.options.ZLStringOption; import org.geometerplus.zlibrary.core.network.ZLNetworkRequest; @@ -30,7 +29,7 @@ import org.geometerplus.zlibrary.core.network.ZLNetworkManager; import org.geometerplus.fbreader.tree.FBTree; import org.geometerplus.fbreader.network.tree.*; import org.geometerplus.fbreader.network.opds.OPDSLinkReader; -import org.geometerplus.fbreader.network.opds.OPDSLinkXMLReader; + public class NetworkLibrary { private static NetworkLibrary ourInstance; @@ -206,6 +205,11 @@ public class NetworkLibrary { } } + + public interface OnNewLinkListener { + void onNewLink(INetworkLink link); + } + public final ZLStringOption NetworkSearchPatternOption = new ZLStringOption("NetworkSearch", "Pattern", ""); @@ -219,50 +223,48 @@ public class NetworkLibrary { private boolean myUpdateVisibility; private NetworkLibrary() { - final OPDSLinkXMLReader reader = new OPDSLinkXMLReader(myLoadedLinks); - reader.read(ZLResourceFile.createResourceFile("data/network/catalogs.xml")); + ArrayList> linksList = new ArrayList>(); + linksList.add(myLoadedLinks); + linksList.add(myCustomLinks); + myLinks = new CompositeList(linksList, new LinksComparator()); + } - NetworkDatabase.Instance().loadCustomLinks(myCustomLinks, - new NetworkDatabase.ICustomLinksFactory() { - public ICustomNetworkLink createCustomLink(int id, String siteName, + public String initialize() { + final LinksComparator comparator = new LinksComparator(); + + final String url = "http://data.fbreader.org/catalogs/generic-1.0.xml"; + + final String error = ZLNetworkManager.Instance().perform( + OPDSLinkReader.loadOPDSLinksRequest(url, new OnNewLinkListener() { + public void onNewLink(INetworkLink link) { + addLinkInternal(myLoadedLinks, link, comparator); + } + }) + ); + + if (error != null) { + synchronized (myLinks) { + myLoadedLinks.clear(); + } + return error; + } + + NetworkDatabase.Instance().loadCustomLinks( + new NetworkDatabase.ICustomLinksHandler() { + public void handleCustomLinkData(int id, String siteName, String title, String summary, String icon, Map links) { final ICustomNetworkLink link = OPDSLinkReader.createCustomLink(id, siteName, title, summary, icon, links); - link.setSaveLinkListener(myChangesListener); - return link; + if (link != null) { + addLinkInternal(myCustomLinks, link, comparator); + link.setSaveLinkListener(myChangesListener); + } } } ); - LinksComparator comparator = new LinksComparator(); - Collections.sort(myLoadedLinks, comparator); - Collections.sort(myCustomLinks, comparator); - - ArrayList> linksList = new ArrayList>(); - linksList.add(myLoadedLinks); - linksList.add(myCustomLinks); - myLinks = new CompositeList(linksList, comparator); + return null; } - /*private final LinkedList readCatalogFileNames() { - final LinkedList catalogs = new LinkedList(); - final ZLResourceFile catalogsFile = ZLResourceFile.createResourceFile("data/network/catalogs.txt"); - try { - InputStream stream = catalogsFile.getInputStream(); - if (stream != null) { - Scanner scanner = new Scanner(stream); - while (scanner.hasNextLine()) { - String line = scanner.nextLine().trim(); - if (line.length() > 0) { - catalogs.add(line); - } - } - scanner.close(); - } - } catch (IOException ex) { - } - return catalogs; - }*/ - public String rewriteUrl(String url, boolean externalUrl) { final String host = ZLNetworkUtil.hostFromUrl(url).toLowerCase(); synchronized (myLinks) { @@ -377,7 +379,6 @@ public class NetworkLibrary { } public NetworkTree getTree() { - synchronize(); return myRootTree; } @@ -441,48 +442,52 @@ public class NetworkLibrary { } }; - public void addCustomLink(ICustomNetworkLink link) { - final int index = Collections.binarySearch(myCustomLinks, link, new LinksComparator()); - if (index >= 0) { - throw new RuntimeException("Unable to add link with duplicated title to the library"); + private void addLinkInternal(ArrayList list, T link, LinksComparator comparator) { + synchronized (myLinks) { + final int index = Collections.binarySearch(list, link, comparator); + if (index >= 0) { + throw new RuntimeException("Unable to add link with duplicated title to the library"); + } + final int insertAt = -index - 1; + list.add(insertAt, link); } - final int insertAt = -index - 1; - myCustomLinks.add(insertAt, link); + } + + public void addCustomLink(ICustomNetworkLink link) { + addLinkInternal(myCustomLinks, link, new LinksComparator()); link.setSaveLinkListener(myChangesListener); link.saveLink(); } - /*public int getCustomLinksNumber() { - return myCustomLinks.size(); - } - - public ICustomNetworkLink getCustomLink(int index) { - return myCustomLinks.get(index); - }*/ - public void removeCustomLink(ICustomNetworkLink link) { - final int index = Collections.binarySearch(myCustomLinks, link, new LinksComparator()); - if (index < 0) { - return; + synchronized (myLinks) { + final int index = Collections.binarySearch(myCustomLinks, link, new LinksComparator()); + if (index < 0) { + return; + } + myCustomLinks.remove(index); } - myCustomLinks.remove(index); NetworkDatabase.Instance().deleteCustomLink(link); link.setSaveLinkListener(null); } public boolean hasCustomLinkTitle(String title, ICustomNetworkLink exeptFor) { - for (INetworkLink link: myLinks) { - if (link != exeptFor && link.getTitle().equals(title)) { - return true; + synchronized (myLinks) { + for (INetworkLink link: myLinks) { + if (link != exeptFor && link.getTitle().equals(title)) { + return true; + } } } return false; } public boolean hasCustomLinkSite(String siteName, ICustomNetworkLink exeptFor) { - for (INetworkLink link: myLinks) { - if (link != exeptFor && link.getSiteName().equals(siteName)) { - return true; + synchronized (myLinks) { + for (INetworkLink link: myLinks) { + if (link != exeptFor && link.getSiteName().equals(siteName)) { + return true; + } } } return false; diff --git a/src/org/geometerplus/fbreader/network/opds/OPDSLinkReader.java b/src/org/geometerplus/fbreader/network/opds/OPDSLinkReader.java index d3abeacb9..c18fa624d 100644 --- a/src/org/geometerplus/fbreader/network/opds/OPDSLinkReader.java +++ b/src/org/geometerplus/fbreader/network/opds/OPDSLinkReader.java @@ -19,87 +19,23 @@ package org.geometerplus.fbreader.network.opds; +import java.io.IOException; +import java.io.InputStream; +import java.net.URLConnection; import java.util.*; -//import org.geometerplus.zlibrary.core.xml.*; -//import org.geometerplus.zlibrary.core.filesystem.ZLFile; -//import org.geometerplus.zlibrary.core.filesystem.ZLResourceFile; +import org.geometerplus.zlibrary.core.network.ZLNetworkRequest; import org.geometerplus.fbreader.network.*; -//import org.geometerplus.fbreader.network.authentication.NetworkAuthenticationManager; -//import org.geometerplus.fbreader.network.authentication.litres.LitResAuthenticationManager; -public class OPDSLinkReader /*extends ZLXMLReaderAdapter*/ { - - /*private String mySiteName; - private String myTitle; - private String mySummary; - private String myIcon; - private boolean myHasStableIdentifiers; - - private final HashMap myLinks = new HashMap(); - - private HashMap myRelationAliases = new HashMap(); - - //private String mySearchType; - private final HashMap mySearchFields = new HashMap(); - - private final HashMap myUrlConditions = new HashMap(); - private String myAuthenticationType; - private final LinkedList myUrlRewritingRules = new LinkedList(); - - private String mySSLCertificate; - - private INetworkLink link() { - if (mySiteName == null || myTitle == null || myLinks.get(INetworkLink.URL_MAIN) == null) { - return null; - } - - OPDSLink opdsLink = new OPDSLink( - mySiteName, - myTitle, - mySummary, - myIcon, - myLinks, - myHasStableIdentifiers - ); - -// if (!mySearchType.empty()) { -// opdsLink.setupAdvancedSearch( -// mySearchType, -// mySearchFields["titleOrSeries"], -// mySearchFields["author"], -// mySearchFields["tag"], -// mySearchFields["annotation"] -// ); -// } - opdsLink.setRelationAliases(myRelationAliases); - opdsLink.setUrlConditions(myUrlConditions); - opdsLink.setUrlRewritingRules(myUrlRewritingRules); - - NetworkAuthenticationManager authManager = null; - if (myAuthenticationType == "basic") { - //authManager = new BasicAuthenticationManager(opdsLink, mySSLCertificate); - } else if (myAuthenticationType == "litres") { - authManager = new LitResAuthenticationManager(opdsLink, mySSLCertificate); - } - opdsLink.setAuthenticationManager(authManager); - - return opdsLink; - }*/ +public class OPDSLinkReader { public static ICustomNetworkLink createCustomLink(int id, String siteName, String title, String summary, String icon, Map links) { if (siteName == null || title == null || links.get(INetworkLink.URL_MAIN) == null) { return null; } - - OPDSCustomLink link = new OPDSCustomLink(id, siteName, title, summary, icon, links); - - // TODO: read common OPDSLink attributes from special custom.xml file - // Does this additional info have to override duplicated settings, received from user??? - - return link; + return new OPDSCustomLink(id, siteName, title, summary, icon, links); } public static ICustomNetworkLink createCustomLinkWithoutInfo(String siteName, String url) { @@ -108,233 +44,13 @@ public class OPDSLinkReader /*extends ZLXMLReaderAdapter*/ { return new OPDSCustomLink(ICustomNetworkLink.INVALID_ID, siteName, null, null, null, links); } - /*public INetworkLink readDocument(ZLFile file) { - mySiteName = myTitle = mySummary = myIcon = myAuthenticationType = mySSLCertificate = null; - //mySearchType = null; - myHasStableIdentifiers = false; - myLinks.clear(); - mySearchFields.clear(); - myUrlConditions.clear(); - myUrlRewritingRules.clear(); - myRelationAliases.clear(); - - String path = file.getPath(); - if (path.endsWith(".xml")) { - path = path.substring(0, path.length() - 4) + ".crt"; - if (ZLResourceFile.createResourceFile(path).exists()) { - mySSLCertificate = path; + public static ZLNetworkRequest loadOPDSLinksRequest(String url, final NetworkLibrary.OnNewLinkListener listener) { + return new ZLNetworkRequest(url) { + @Override + public String handleStream(URLConnection connection, InputStream inputStream) throws IOException { + new OPDSLinkXMLReader(listener).read(inputStream); + return null; } - } - - myState = READ_NOTHING; - - if (!ZLXMLProcessor.read(this, file)) { - return null; - } - - return link(); + }; } - - - private static final String TAG_CATALOG = "catalog"; - private static final String TAG_SITE = "site"; - private static final String TAG_LINK = "link"; - private static final String TAG_TITLE = "title"; - private static final String TAG_SUMMARY = "summary"; - private static final String TAG_ICON = "icon"; - private static final String TAG_RELATION_ALIASES = "relationAliases"; - private static final String TAG_ALIAS = "alias"; - private static final String TAG_SEARCH_DESCRIPTION = "advancedSearch"; - private static final String TAG_FEEDS = "feeds"; - private static final String TAG_AUTHENTICATION = "authentication"; - private static final String TAG_URL_REWRITING_RULES = "urlRewritingRules"; - private static final String TAG_FIELD = "field"; - private static final String TAG_CONDITION = "condition"; - private static final String TAG_RULE = "rule"; - - private static final int READ_NOTHING = 0; - private static final int READ_SITENAME = 1; - private static final int READ_TITLE = 2; - private static final int READ_SUMMARY = 3; - private static final int READ_ICON_NAME = 4; - private static final int READ_LINK = 5; - private static final int READ_SEARCH_DESCRIPTION = 6; - private static final int READ_SEARCH_FIELD = 7; - private static final int READ_FEEDS = 8; - private static final int READ_FEEDS_CONDITION = 9; - private static final int READ_URL_REWRITING_RULES = 10; - private static final int READ_RELATION_ALIASES = 11; - - private int myState; - - private String myAttrBuffer; - private final StringBuffer myBuffer = new StringBuffer(); - - - @Override - public boolean startElementHandler(String tag, ZLStringMap attributes) { - tag = tag.intern(); - if (TAG_CATALOG == tag) { - final String value = attributes.getValue("hasStableIdentifiers"); - myHasStableIdentifiers = value != null && value.equals("true"); - } else if (TAG_SITE == tag) { - myState = READ_SITENAME; - } else if (TAG_TITLE == tag) { - myState = READ_TITLE; - } else if (TAG_SUMMARY == tag) { - myState = READ_SUMMARY; - } else if (TAG_ICON == tag) { - myState = READ_ICON_NAME; - } else if (TAG_LINK == tag) { - String linkType = attributes.getValue("rel"); - if (linkType != null) { - myAttrBuffer = linkType; - myLinks.remove(myAttrBuffer); - myState = READ_LINK; - } - } else if (TAG_SEARCH_DESCRIPTION == tag) { - String searchType = attributes.getValue("style"); - if (searchType != null) { - //mySearchType = searchType; - myState = READ_SEARCH_DESCRIPTION; - } - } else if (myState == READ_SEARCH_DESCRIPTION && TAG_FIELD == tag) { - String name = attributes.getValue("name"); - if (name != null) { - myAttrBuffer = name; - mySearchFields.remove(myAttrBuffer); - myState = READ_SEARCH_FIELD; - } - } else if (TAG_FEEDS == tag) { - myState = READ_FEEDS; - } else if (myState == READ_FEEDS && TAG_CONDITION == tag) { - String show = attributes.getValue("show"); - if (show != null) { - myAttrBuffer = show; - myState = READ_FEEDS_CONDITION; - } - } else if (TAG_AUTHENTICATION == tag) { - String authenticationType = attributes.getValue("type"); - if (authenticationType != null) { - myAuthenticationType = authenticationType; - } - } else if (TAG_URL_REWRITING_RULES == tag) { - myState = READ_URL_REWRITING_RULES; - } else if (myState == READ_URL_REWRITING_RULES && TAG_RULE == tag) { - String type = attributes.getValue("type"); - String apply = attributes.getValue("apply"); - String name = attributes.getValue("name"); - String value = attributes.getValue("value"); - - int ruleApply = URLRewritingRule.APPLY_ALWAYS; - if (apply != null) { - apply = apply.intern(); - if (apply == "external") { - ruleApply = URLRewritingRule.APPLY_EXTERNAL; - } else if (apply == "internal") { - ruleApply = URLRewritingRule.APPLY_INTERNAL; - } else if (apply != "always") { - type = null; - } - } - - if (type != null && name != null && value != null) { - if (type == "addUrlParameter") { - myUrlRewritingRules.add(new URLRewritingRule(URLRewritingRule.ADD_URL_PARAMETER, ruleApply, name, value)); - } - } - } else if (TAG_RELATION_ALIASES == tag) { - myState = READ_RELATION_ALIASES; - } else if (myState == READ_RELATION_ALIASES && TAG_ALIAS == tag) { - String alias = attributes.getValue("alias"); - String name = attributes.getValue("name"); - String type = attributes.getValue("type"); - if (alias != null && name != null) { - if (alias.length() == 0) { - alias = null; - } - myRelationAliases.put(new RelationAlias(alias, type), name); - } - } - return false; - } - - @Override - public boolean endElementHandler(String tag) { - tag = tag.intern(); - - String bufferContent = myBuffer.toString().trim(); - myBuffer.delete(0, myBuffer.length()); - - if (bufferContent.length() != 0) { - switch (myState) { - case READ_NOTHING: - case READ_SEARCH_DESCRIPTION: - case READ_FEEDS: - case READ_URL_REWRITING_RULES: - case READ_RELATION_ALIASES: - break; - case READ_SITENAME: - mySiteName = bufferContent; - break; - case READ_TITLE: - myTitle = bufferContent; - break; - case READ_SUMMARY: - mySummary = bufferContent; - break; - case READ_ICON_NAME: - myIcon = bufferContent; - break; - case READ_LINK: - myLinks.put(myAttrBuffer, bufferContent); - break; - case READ_SEARCH_FIELD: - mySearchFields.put(myAttrBuffer, bufferContent); - break; - case READ_FEEDS_CONDITION: - myUrlConditions.put( - bufferContent, - myAttrBuffer.equals("signedIn") ? - OPDSLink.FeedCondition.SIGNED_IN : - OPDSLink.FeedCondition.NEVER - ); - break; - } - } - - if (myState == READ_SEARCH_FIELD) { - myState = READ_SEARCH_DESCRIPTION; - } else if (myState == READ_FEEDS_CONDITION) { - myState = READ_FEEDS; - } else if (myState == READ_URL_REWRITING_RULES && TAG_RULE == tag) { - //myState = myState; - } else if (myState == READ_RELATION_ALIASES && TAG_ALIAS == tag) { - //myState = myState; - } else { - myState = READ_NOTHING; - } - return false; - } - - @Override - public void characterDataHandler(char[] data, int start, int length) { - switch (myState) { - case READ_NOTHING: - case READ_SEARCH_DESCRIPTION: - case READ_FEEDS: - case READ_URL_REWRITING_RULES: - case READ_RELATION_ALIASES: - break; - case READ_SITENAME: - case READ_TITLE: - case READ_SUMMARY: - case READ_ICON_NAME: - case READ_LINK: - case READ_SEARCH_FIELD: - case READ_FEEDS_CONDITION: - myBuffer.append(data, start, length); - break; - } - }*/ } diff --git a/src/org/geometerplus/fbreader/network/opds/OPDSLinkXMLReader.java b/src/org/geometerplus/fbreader/network/opds/OPDSLinkXMLReader.java index 0a5123191..1b016c695 100644 --- a/src/org/geometerplus/fbreader/network/opds/OPDSLinkXMLReader.java +++ b/src/org/geometerplus/fbreader/network/opds/OPDSLinkXMLReader.java @@ -21,7 +21,6 @@ package org.geometerplus.fbreader.network.opds; import java.util.HashMap; import java.util.LinkedList; -import java.util.List; import java.util.Map; import org.geometerplus.zlibrary.core.filesystem.ZLResourceFile; @@ -30,6 +29,7 @@ import org.geometerplus.zlibrary.core.xml.ZLStringMap; import org.geometerplus.fbreader.constants.XMLNamespace; import org.geometerplus.fbreader.network.INetworkLink; import org.geometerplus.fbreader.network.NetworkImage; +import org.geometerplus.fbreader.network.NetworkLibrary; import org.geometerplus.fbreader.network.atom.ATOMLink; import org.geometerplus.fbreader.network.authentication.NetworkAuthenticationManager; import org.geometerplus.fbreader.network.authentication.litres.LitResAuthenticationManager; @@ -38,15 +38,15 @@ public class OPDSLinkXMLReader extends OPDSXMLReader { private static class LinkReader implements OPDSFeedReader { - private List myLinksBuffer; + private NetworkLibrary.OnNewLinkListener myListener; private String myAuthenticationType; private boolean myHasStableIdentifiers; private final LinkedList myUrlRewritingRules = new LinkedList(); private HashMap myRelationAliases = new HashMap(); - public LinkReader(List links) { - myLinksBuffer = links; + public LinkReader(NetworkLibrary.OnNewLinkListener listener) { + myListener = listener; } public void setAuthenticationType(String type) { @@ -141,7 +141,7 @@ public class OPDSLinkXMLReader extends OPDSXMLReader { INetworkLink result = link(siteName, title, summary, icon, links, urlConditions, sslCertificate); if (result != null) { - myLinksBuffer.add(result); + myListener.onNewLink(result); } return false; } @@ -190,8 +190,8 @@ public class OPDSLinkXMLReader extends OPDSXMLReader { public void processFeedEnd() {} } - public OPDSLinkXMLReader(List links) { - super(new LinkReader(links)); + public OPDSLinkXMLReader(NetworkLibrary.OnNewLinkListener listener) { + super(new LinkReader(listener)); } private String myFBReaderNamespaceId; @@ -275,10 +275,4 @@ public class OPDSLinkXMLReader extends OPDSXMLReader { } return super.startElementHandler(tagPrefix, tag, attributes, bufferContent); } - - @Override - public boolean endElementHandler(final String tagPrefix, final String tag, - final String bufferContent) { - return super.endElementHandler(tagPrefix, tag, bufferContent); - } }