package org.sorz.lab.smallcloudemoji.parsers;
import android.util.Xml;
import org.sorz.lab.smallcloudemoji.db.DaoSession;
import org.sorz.lab.smallcloudemoji.db.RepositoryDao;
import org.sorz.lab.smallcloudemoji.db.Source;
import org.sorz.lab.smallcloudemoji.db.SourceDao;
import org.sorz.lab.smallcloudemoji.exceptions.PullParserException;
import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
import java.io.IOException;
import java.io.Reader;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.List;
/**
* Read store xml and store sources into database.
*/
public class StoreSourceLoader {
private final DaoSession daoSession;
private final SourceDao sourceDao;
private final RepositoryDao repositoryDao;
private static final String NAME_SPACE = null;
private static final String ROOT_TAG = "cloudemoticonstore";
private static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyyMMdd");
public StoreSourceLoader(DaoSession daoSession) {
this.daoSession = daoSession;
sourceDao = daoSession.getSourceDao();
repositoryDao = daoSession.getRepositoryDao();
}
/**
* Parse source from XML reader to databases.
*
* @param reader Reader of XML file.
* @param lastUpdateTime Latest update time of store.
* @return Update time of current store (may be not changed if it's already updated so that
* parsing is canceled.
*/
public String loadToDatabase(Reader reader, String lastUpdateTime)
throws IOException, PullParserException {
XmlPullParser parser = Xml.newPullParser();
String updateTime;
try {
parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, false);
parser.setInput(reader);
parser.nextTag();
parser.require(XmlPullParser.START_TAG, NAME_SPACE, ROOT_TAG);
// Continue parser only when newer version exists.
updateTime = parser.getAttributeValue(NAME_SPACE, "updatetime");
if (lastUpdateTime != null && updateTime != null) {
if (lastUpdateTime.equals(updateTime))
return updateTime;
}
// Check whether already installed for each.
final List<Source> sources = loadStore(parser);
for (Source source : sources) {
long count = repositoryDao.queryBuilder()
.where(RepositoryDao.Properties.Url.eq(source.getCodeUrl()))
.limit(1)
.count();
source.setInstalled(count != 0);
}
daoSession.runInTx(new Runnable() {
@Override
public void run() {
sourceDao.deleteAll();
sourceDao.insertInTx(sources);
}
});
} catch (XmlPullParserException e) {
e.printStackTrace();
throw new PullParserException(e);
}
if (updateTime == null)
return "0";
else
return updateTime;
}
private static List<Source> loadStore(XmlPullParser parser)
throws IOException, XmlPullParserException {
parser.require(XmlPullParser.START_TAG, NAME_SPACE, ROOT_TAG);
ArrayList<Source> sources = new ArrayList<Source>();
while (parser.next() != XmlPullParser.END_TAG) {
if (parser.getEventType() != XmlPullParser.START_TAG) {
continue;
}
if (parser.getName().equals("source")) {
Source source = loadSource(parser);
if (source != null)
sources.add(source);
}
}
return sources;
}
private static Source loadSource(XmlPullParser parser)
throws IOException, XmlPullParserException {
parser.require(XmlPullParser.START_TAG, NAME_SPACE, "source");
Source source = new Source();
while (parser.next() != XmlPullParser.END_TAG) {
if (parser.getEventType() != XmlPullParser.START_TAG) {
continue;
}
String tagName = parser.getName();
if (tagName.equals("name"))
source.setName(parser.nextText());
else if (tagName.equals("iconurl"))
source.setIconUrl(parser.nextText());
else if (tagName.equals("postedon"))
try {
source.setPostDate(DATE_FORMAT.parse(parser.nextText()));
} catch (ParseException e) {
e.printStackTrace(); // Ignore
}
else if (tagName.equals("introduction"))
source.setIntroduction(parser.nextText());
else if (tagName.equals("creator"))
source.setCreator(parser.nextText());
else if (tagName.equals("creatorurl"))
source.setCreatorUrl(parser.nextText());
else if (tagName.equals("server"))
source.setServer(parser.nextText());
else if (tagName.equals("serverurl"))
source.setServerUrl(parser.nextText());
else if (tagName.equals("dataformat"))
source.setDataFormat(parser.nextText());
else if (tagName.equals("installurl"))
source.setInstallUrl(parser.nextText());
else if (tagName.equals("codeurl"))
source.setCodeUrl(parser.nextText());
else if (tagName.equals("storeurl"))
source.setStoreUrl(parser.nextText());
}
if (source.getCodeUrl() == null || source.getName() == null)
return null;
return source;
}
}