Package org.rssowl.core.internal.persist.migration

Source Code of org.rssowl.core.internal.persist.migration.Migration0To1

/*   **********************************************************************  **
**   Copyright notice                                                       **
**                                                                          **
**   (c) 2005-2006 RSSOwl Development Team                                  **
**   http://www.rssowl.org/                                                 **
**                                                                          **
**   All rights reserved                                                    **
**                                                                          **
**   This program and the accompanying materials are made available under   **
**   the terms of the Eclipse Public License v1.0 which accompanies this    **
**   distribution, and is available at:                                     **
**   http://www.rssowl.org/legal/epl-v10.html                               **
**                                                                          **
**   A copy is found in the file epl-v10.html and important notices to the  **
**   license from the team is found in the textfile LICENSE.txt distributed **
**   in this package.                                                       **
**                                                                          **
**   This copyright notice MUST APPEAR in all copies of the file!           **
**                                                                          **
**   Contributors:                                                          **
**     RSSOwl Development Team - initial API and implementation             **
**                                                                          **
**  **********************************************************************  */
package org.rssowl.core.internal.persist.migration;

import org.eclipse.core.runtime.IProgressMonitor;
import org.rssowl.core.internal.InternalOwl;
import org.rssowl.core.internal.persist.service.ConfigurationFactory;
import org.rssowl.core.internal.persist.service.Migration;
import org.rssowl.core.model.internal.db4o.Counter;
import org.rssowl.core.model.internal.preferences.Preference;
import org.rssowl.core.model.internal.search.SearchCondition;
import org.rssowl.core.model.internal.search.SearchField;
import org.rssowl.core.model.internal.search.SearchValueType;
import org.rssowl.core.model.internal.types.AbstractEntity;
import org.rssowl.core.model.internal.types.Attachment;
import org.rssowl.core.model.internal.types.BookMark;
import org.rssowl.core.model.internal.types.Category;
import org.rssowl.core.model.internal.types.ConditionalGet;
import org.rssowl.core.model.internal.types.ExtendableType;
import org.rssowl.core.model.internal.types.Feed;
import org.rssowl.core.model.internal.types.Folder;
import org.rssowl.core.model.internal.types.Guid;
import org.rssowl.core.model.internal.types.Image;
import org.rssowl.core.model.internal.types.Label;
import org.rssowl.core.model.internal.types.Mark;
import org.rssowl.core.model.internal.types.News;
import org.rssowl.core.model.internal.types.Person;
import org.rssowl.core.model.internal.types.SearchMark;
import org.rssowl.core.model.internal.types.Source;
import org.rssowl.core.model.search.ISearchField;
import org.rssowl.core.model.search.SearchSpecifier;
import org.rssowl.core.model.types.IAttachment;
import org.rssowl.core.model.types.IBookMark;
import org.rssowl.core.model.types.ICategory;
import org.rssowl.core.model.types.IFeed;
import org.rssowl.core.model.types.IFolder;
import org.rssowl.core.model.types.IImage;
import org.rssowl.core.model.types.ILabel;
import org.rssowl.core.model.types.IMark;
import org.rssowl.core.model.types.INews;
import org.rssowl.core.model.types.IPerson;
import org.rssowl.core.model.types.ISearchMark;
import org.rssowl.core.model.types.ISource;
import org.rssowl.core.persist.IFolderChild;
import org.rssowl.core.persist.IModelFactory;
import org.rssowl.core.persist.IPreference;
import org.rssowl.core.persist.ISearchCondition;

import com.db4o.Db4o;
import com.db4o.ObjectContainer;
import com.db4o.ObjectSet;
import com.db4o.config.Configuration;
import com.db4o.query.Query;

import java.util.ArrayList;
import java.util.EnumSet;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
* Migration from version 0 to version 1.
*
* @inheritDoc
*/
public class Migration0To1 implements Migration   {

  /*
   * TODO Cleanup after tagging:
   *
   * 0) Delete core.model.types package.
   * 1) Delete core.model.internal.types package.
   * 2) Delete core.model.search package.
   * 3) Delete core.model.internal.search package.
   * 4) Delete core.model.internal.preferences package.
   * 5) Delete core.model.internal.db4o package.
   */

  /**
   * Creates an instance of this class.
   */
  public Migration0To1()  {
    super();
  }

  @SuppressWarnings("unchecked")
  private List<IFolderChild> getFolderChildren(org.rssowl.core.persist.IFolder folder, String fieldName)    {
    return (List<IFolderChild>) MigrationHelper.getFieldValue(folder, fieldName);
  }

  private IPreference convertPref(Preference oldPref) {
    String[] values = oldPref.getValues().toArray(new String[oldPref.getValues().size()]);
    IPreference.Type type = null;
    switch (oldPref.getType()) {
      case BOOLEAN:
        type = IPreference.Type.BOOLEAN;
        break;
      case INTEGER:
      case INTEGER_ARRAY:
        type = IPreference.Type.INTEGER;
        break;
      case LONG:
      case LONG_ARRAY:
        type = IPreference.Type.LONG;
        break;
      case STRING:
      case STRING_ARRAY:
        type = IPreference.Type.STRING;
        break;
      default:
        throw new IllegalArgumentException(oldPref.getType().toString());
    }
    IPreference newPref = new org.rssowl.core.internal.persist.Preference(oldPref.getKey());
    MigrationHelper.setField(newPref, "fValues", values);
    MigrationHelper.setField(newPref, "fType", type);
    return newPref;
  }

  public int getDestinationFormat() {
    return 1;
  }

  public int getOriginFormat() {
    return 0;
  }

  //TODO Report progress
  public boolean migrate(ConfigurationFactory configFactory, String dbFileName, IProgressMonitor progressMonitor) {
    progressMonitor.beginTask("Migrating data", 100);

    ObjectContainer oc = Db4o.openFile(configFactory.createConfiguration(), dbFileName);

    /* Copy all folder and mark properties to map */
    Map<Long, Map<String, ?>> idPropertiesMap = new HashMap<Long, Map<String, ?>>();
    for (Folder folder : oc.query(Folder.class)) {
      idPropertiesMap.put(folder.getId(), folder.getProperties());
    }

    for (Mark mark : oc.query(Mark.class)) {
      idPropertiesMap.put(mark.getId(), mark.getProperties());
    }

    oc.close();

    Configuration c = Db4o.newConfiguration();

    /* core.model.types to core.persist */
    c.objectClass(IAttachment.class).rename(org.rssowl.core.persist.IAttachment.class.getName());
    c.objectClass(IBookMark.class).rename(org.rssowl.core.persist.IBookMark.class.getName());
    c.objectClass(ICategory.class).rename(org.rssowl.core.persist.ICategory.class.getName());
    c.objectClass(IFeed.class).rename(org.rssowl.core.persist.IFeed.class.getName());
    c.objectClass(IFolder.class).rename(org.rssowl.core.persist.IFolder.class.getName());
    c.objectClass(IImage.class).rename(org.rssowl.core.persist.IImage.class.getName());
    c.objectClass(ILabel.class).rename(org.rssowl.core.persist.ILabel.class.getName());
    c.objectClass(IMark.class).rename(org.rssowl.core.persist.IMark.class.getName());
    c.objectClass(INews.class).rename(org.rssowl.core.persist.INews.class.getName());
    c.objectClass(INews.State.class).rename(org.rssowl.core.persist.INews.State.class.getName());
    c.objectClass(IPerson.class).rename(org.rssowl.core.persist.IPerson.class.getName());
    c.objectClass(ISearchMark.class).rename(org.rssowl.core.persist.ISearchMark.class.getName());
    c.objectClass(ISource.class).rename(org.rssowl.core.persist.ISource.class.getName());

    /* core.model.internal.types to core.internal.persist */
    c.objectClass(AbstractEntity.class).rename(org.rssowl.core.internal.persist.AbstractEntity.class.getName());
    c.objectClass(Attachment.class).rename(org.rssowl.core.internal.persist.Attachment.class.getName());
    c.objectClass(BookMark.class).rename(org.rssowl.core.internal.persist.BookMark.class.getName());
    c.objectClass(Category.class).rename(org.rssowl.core.internal.persist.Category.class.getName());
    c.objectClass(ConditionalGet.class).rename(org.rssowl.core.internal.persist.ConditionalGet.class.getName());
    c.objectClass(Feed.class).rename(org.rssowl.core.internal.persist.Feed.class.getName());
    c.objectClass(Folder.class).rename(org.rssowl.core.internal.persist.Folder.class.getName());
    c.objectClass(Guid.class).rename(org.rssowl.core.internal.persist.Guid.class.getName());
    c.objectClass(Image.class).rename(org.rssowl.core.internal.persist.Image.class.getName());
    c.objectClass(Label.class).rename(org.rssowl.core.internal.persist.Label.class.getName());
    c.objectClass(Mark.class).rename(org.rssowl.core.internal.persist.Mark.class.getName());
    c.objectClass(News.class).rename(org.rssowl.core.internal.persist.News.class.getName());
    c.objectClass(ExtendableType.class).rename(org.rssowl.core.internal.persist.AbstractEntity.class.getName());
    c.objectClass(Person.class).rename(org.rssowl.core.internal.persist.Person.class.getName());
    c.objectClass(SearchMark.class).rename(org.rssowl.core.internal.persist.SearchMark.class.getName());
    c.objectClass(Source.class).rename(org.rssowl.core.internal.persist.Source.class.getName());

    /* Search-related classes*/
    c.objectClass(SearchSpecifier.class).rename(org.rssowl.core.persist.SearchSpecifier.class.getName());
    c.objectClass(SearchCondition.class).rename(org.rssowl.core.internal.persist.SearchCondition.class.getName());
    c.objectClass(ISearchField.class).rename(org.rssowl.core.persist.ISearchField.class.getName());
    c.objectClass(SearchField.class).rename(org.rssowl.core.internal.persist.SearchField.class.getName());
    c.objectClass(SearchValueType.class).rename(org.rssowl.core.internal.persist.SearchValueType.class.getName());

    /* Counter */
    c.objectClass(Counter.class).rename(org.rssowl.core.internal.persist.service.Counter.class.getName());

    oc = Db4o.openFile(c, dbFileName);
    oc.close();
    /* 10 */
    progressMonitor.worked(10);

    oc = Db4o.openFile(configFactory.createConfiguration(), dbFileName);

    /* Preference */
    for (Preference pref : oc.query(Preference.class)) {
      oc.activate(pref, Integer.MAX_VALUE);
      oc.ext().set(convertPref(pref), Integer.MAX_VALUE);
      oc.delete(pref);
    }
    oc.commit();
    /* 20 */
    progressMonitor.worked(10);

    for (org.rssowl.core.persist.ISearchField searchField : oc.query(org.rssowl.core.internal.persist.SearchField.class))   {
      oc.activate(searchField, Integer.MAX_VALUE);
      String entityName = searchField.getEntityName();
      entityName = entityName.replace("core.model.types", "core.persist");
      MigrationHelper.setField(searchField, "fEntityName", entityName);
      oc.ext().set(searchField, Integer.MAX_VALUE);
    }
    oc.commit();
    /* 30 */
    progressMonitor.worked(10);

    for (org.rssowl.core.persist.ISearchCondition searchCond : oc.query(org.rssowl.core.internal.persist.SearchCondition.class))   {
      oc.activate(searchCond, Integer.MAX_VALUE);
      int searchSpecOrdinal = searchCond.getSpecifier().ordinal();
      org.rssowl.core.persist.SearchSpecifier searchSpec = org.rssowl.core.persist.SearchSpecifier.values()[searchSpecOrdinal];
      MigrationHelper.setField(searchCond, "fSpecifier", searchSpec);
      oc.ext().set(searchCond, Integer.MAX_VALUE);
    }
    oc.commit();
    /* 40 */
    progressMonitor.worked(10);

    List<org.rssowl.core.persist.IFolder> folders = new ArrayList<org.rssowl.core.persist.IFolder>();
    for (org.rssowl.core.persist.IFolder folder : oc.query(org.rssowl.core.internal.persist.Folder.class))   {
      oc.activate(folder, Integer.MAX_VALUE);
      List<IFolderChild> children = new ArrayList<IFolderChild>(getFolderChildren(folder, "fFolders"));
      MigrationHelper.setField(folder, "fFolders", null);
      children.addAll(getFolderChildren(folder, "fMarks"));
      MigrationHelper.setField(folder, "fMarks", null);
      MigrationHelper.setField(folder, "fChildren", children);
      folders.add(folder);
    }
    /* Only save folders once they have all been updated */
    for (org.rssowl.core.persist.IFolder folder : folders)   {
      oc.ext().set(folder, Integer.MAX_VALUE);
    }

    List<org.rssowl.core.persist.IMark> marks = new ArrayList<org.rssowl.core.persist.IMark>();
    for (org.rssowl.core.persist.IMark mark : oc.query(org.rssowl.core.internal.persist.Mark.class))   {
      oc.activate(mark, Integer.MAX_VALUE);
      org.rssowl.core.persist.IFolder parent = (org.rssowl.core.persist.IFolder) MigrationHelper.getFieldValue(mark, "fFolder");
      MigrationHelper.setField(mark, "fFolder", null);
      MigrationHelper.setField(mark, "fParent", parent);

      /*
       * If ISearchMark contains a search condition with INews.State, replace
       * it with an EnumSet<INews.State>.
       */
      if (mark instanceof org.rssowl.core.persist.ISearchMark) {
        org.rssowl.core.persist.ISearchMark searchMark = (org.rssowl.core.persist.ISearchMark) mark;
        EnumSet<org.rssowl.core.persist.INews.State> states = EnumSet.noneOf(org.rssowl.core.persist.INews.State.class);
        List<ISearchCondition> searchConds = new ArrayList<ISearchCondition>();
        for (ISearchCondition searchCond : searchMark.getSearchConditions()) {
          org.rssowl.core.persist.ISearchField searchField = searchCond.getField();
          if (searchField.getEntityName().equals(org.rssowl.core.persist.INews.class.getName()) && searchField.getId() == INews.STATE)  {
            states.add((org.rssowl.core.persist.INews.State) searchCond.getValue());
          }
          else {
            searchConds.add(searchCond);
          }
        }
        if (!states.isEmpty()) {
          IModelFactory factory = InternalOwl.getDefault().getModelFactory();
          org.rssowl.core.persist.ISearchField field = factory.createSearchField(INews.STATE, org.rssowl.core.persist.INews.class.getName());
          searchConds.add(factory.createSearchCondition(field, org.rssowl.core.persist.SearchSpecifier.IS, states));
          MigrationHelper.setField(mark, "fSearchConditions", searchConds);
        }
      }

      marks.add(mark);
    }
    /* Only save folders once they have all been updated */
    for (org.rssowl.core.persist.IMark mark : marks)   {
      oc.ext().set(mark, Integer.MAX_VALUE);
    }

    oc.commit();
    /* 80 */
    progressMonitor.worked(40);

    for (Map.Entry<Long, Map<String, ?>> entry : idPropertiesMap.entrySet()) {
      Query query = oc.query();
      query.constrain(org.rssowl.core.internal.persist.AbstractEntity.class);
      query.descend("fId").constrain(entry.getKey()); //$NON-NLS-1$
      List<?> list = query.execute();
      org.rssowl.core.internal.persist.AbstractEntity entity = (org.rssowl.core.internal.persist.AbstractEntity) list.get(0);
      oc.activate(entity, Integer.MAX_VALUE);
      for (Map.Entry<String, ?> valueEntry : entry.getValue().entrySet()) {
        entity.setProperty(valueEntry.getKey(), valueEntry.getValue());
      }
      oc.ext().set(entity, Integer.MAX_VALUE);
    }
    /* 90 */
    progressMonitor.worked(10);
    oc.close();

    /* Disable indices to force them to be re-created */
    Configuration config = configFactory.createConfiguration();
    config.objectClass(org.rssowl.core.internal.persist.BookMark.class).objectField("fFeedLink").indexed(false); //$NON-NLS-1$
    config.objectClass(org.rssowl.core.internal.persist.ConditionalGet.class).objectField("fLink").indexed(false); //$NON-NLS-1$
    config.objectClass(org.rssowl.core.internal.persist.Preference.class).objectField("fKey").indexed(false); //$NON-NLS-1$
    config.objectClass(org.rssowl.core.internal.persist.Feed.class).objectField("fLinkText").indexed(false);
    config.objectClass(org.rssowl.core.internal.persist.News.class).objectField("fLinkText").indexed(false); //$NON-NLS-1$
    config.objectClass(org.rssowl.core.internal.persist.News.class).objectField("fGuidValue").indexed(false);
    config.objectClass(org.rssowl.core.internal.persist.News.class).objectField("fFeedLink").indexed(false); //$NON-NLS-1$
    config.objectClass(org.rssowl.core.internal.persist.News.class).objectField("fStateOrdinal").indexed(false); //$NON-NLS-1$
    oc = Db4o.openFile(config, dbFileName);

    /* Access classes with index */
    ObjectSet<org.rssowl.core.internal.persist.BookMark> markSet = oc.query(org.rssowl.core.internal.persist.BookMark.class);
    if (markSet.hasNext())
      markSet.next().getName();

    ObjectSet<org.rssowl.core.internal.persist.ConditionalGet> condGetSet = oc.query(org.rssowl.core.internal.persist.ConditionalGet.class);
    if (condGetSet.hasNext())
      condGetSet.next().getLink();

    ObjectSet<org.rssowl.core.internal.persist.Preference> prefSet = oc.query(org.rssowl.core.internal.persist.Preference.class);
    if (prefSet.hasNext())
      prefSet.next().getKey();

    ObjectSet<org.rssowl.core.internal.persist.Feed> feedSet = oc.query(org.rssowl.core.internal.persist.Feed.class);
    if (feedSet.hasNext())
      feedSet.next().getLink();

    ObjectSet<org.rssowl.core.internal.persist.News> newsSet = oc.query(org.rssowl.core.internal.persist.News.class);
    if (newsSet.hasNext())
      newsSet.next().getLink();

    oc.close();
    /* 100 */
    progressMonitor.worked(10);

    return true;
  }
}
TOP

Related Classes of org.rssowl.core.internal.persist.migration.Migration0To1

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.