/******************************************************************************* * Copyright (C) 2012 Robert Munteanu <robert.munteanu@gmail.com> * * 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.eclipse.org/legal/epl-v10.html *******************************************************************************/ package com.itsolut.mantis.core; import java.util.ArrayList; import java.util.Collections; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; import org.eclipse.core.runtime.NullProgressMonitor; import org.eclipse.mylyn.tasks.core.TaskRepository; import org.eclipse.mylyn.tasks.core.data.TaskAttribute; import org.eclipse.mylyn.tasks.core.data.TaskData; import com.google.common.base.Joiner; import com.itsolut.mantis.core.MantisAttributeMapper.Attribute; import com.itsolut.mantis.core.exception.MantisException; import com.itsolut.mantis.core.model.MantisUser; import com.itsolut.mantis.core.util.MantisUtils; public class MantisTaskDataMigrator { public enum TaskDataVersion { Version_Zero(0) { @Override public void migrateTaskData(TaskRepository repository, TaskData taskData, IMantisClient mantisClient) { } }, /** * Person attributes move from userId key to userName key -> displayName value */ Version_3_9(3.9) { @Override public void migrateTaskData(TaskRepository repository, TaskData taskData, IMantisClient mantisClient) { try { migratePersonAttribute(taskData, MantisAttributeMapper.Attribute.REPORTER, mantisClient); migratePersonAttribute(taskData, MantisAttributeMapper.Attribute.ASSIGNED_TO, mantisClient); migratePersonAttribute(taskData, MantisAttributeMapper.Attribute.MONITORS, mantisClient); refreshOldMonitors(taskData, mantisClient); } catch (MantisException e) { MantisCorePlugin.warn("Failed migrating TaskData " + taskData.getTaskId() + " for repository " + taskData.getRepositoryUrl(), e); } } private void refreshOldMonitors(TaskData taskData, IMantisClient mantisClient) throws MantisException { TaskAttribute attribute = taskData.getRoot().getAttribute(MantisAttributeMapper.Attribute.MONITORS.getKey()); if ( attribute == null ) return; if (attribute.getValue().length() == 0) return; String oldValue = attribute.getMetaData().getValue(MantisAttributeMapper.TASK_ATTRIBUTE_ORIGINAL_MONITORS); List<String> monitorNames = userIdsToUserNames(mantisClient, new NullProgressMonitor(), MantisUtils.fromCsvString(oldValue)); String originalValues = Joiner.on(',').join(monitorNames); attribute.getMetaData().putValue(MantisAttributeMapper.TASK_ATTRIBUTE_ORIGINAL_MONITORS, originalValues); } private void migratePersonAttribute(TaskData taskData, Attribute attributeKey, IMantisClient mantisClient) throws MantisException { TaskAttribute attribute = taskData.getRoot().getAttribute(attributeKey.getKey()); if ( attribute == null ) return; // recreate metadata attribute.getMetaData() .setKind(attributeKey.getKind()).setLabel(attributeKey.toString()).setType(attributeKey.getType()); // at this point the configuration should not be stale so no I/O should be performed NullProgressMonitor progressMonitor = new NullProgressMonitor(); List<String> newValues = getNewValues(mantisClient, attribute, progressMonitor); Map<String, String> newOptions = getNewOptions(mantisClient, attribute, progressMonitor); if ( newValues.size() > 0 ) attribute.setValues(newValues); if ( newOptions.size() > 0 ) { attribute.clearOptions(); for ( Map.Entry<String, String> optionEntry : newOptions.entrySet() ) attribute.putOption(optionEntry.getKey(), optionEntry.getValue()); } } private Map<String, String> getNewOptions( IMantisClient mantisClient, TaskAttribute attribute, NullProgressMonitor progressMonitor) throws MantisException { // migrate options Map<String, String> newOptions = new LinkedHashMap<String, String>(attribute.getOptions().size()); for ( Map.Entry<String,String> optionEntry : attribute.getOptions().entrySet()) { // do not convert the empty option if ( optionEntry.getKey().length() == 0 ) continue; Integer userId; try { userId = Integer.valueOf(optionEntry.getKey()); } catch (NumberFormatException e) { // invalid format or already converted return Collections.emptyMap(); } String userName = mantisClient.getCache(progressMonitor).getUserNameById(userId); if ( userName == null ) continue; MantisUser user = mantisClient.getCache(progressMonitor).getUserByUsername(userName); newOptions.put(user.getKey(), user.getName()); } return newOptions; } private List<String> getNewValues(IMantisClient mantisClient, TaskAttribute attribute, NullProgressMonitor progressMonitor) throws MantisException { return userIdsToUserNames(mantisClient, progressMonitor, attribute.getValues()); } private List<String> userIdsToUserNames(IMantisClient mantisClient, NullProgressMonitor progressMonitor, List<String> userIds) throws MantisException { // no values if ( userIds == null || userIds.isEmpty() ) return Collections.emptyList(); if ( userIds.size() == 1 && userIds.get(0).length() == 0 ) return Collections.emptyList(); // migrate value List<String> newValues = new ArrayList<String>(userIds.size()); for ( String oldValue : userIds ) { Integer userId; try { userId = Integer.valueOf(oldValue); } catch (NumberFormatException e) { // invalid format or already converted return Collections.emptyList(); } String userName = mantisClient.getCache(progressMonitor).getUserNameById(userId); if ( userName == null ) continue; newValues.add(userName); } return newValues; } }; private final double value; private TaskDataVersion(double value) { this.value = value; } public double getValue() { return value; } public abstract void migrateTaskData(TaskRepository repository, TaskData taskData, IMantisClient mantisClient); } public TaskDataVersion getCurrent() { return TaskDataVersion.Version_3_9; } public void migrateTaskData(TaskRepository repository, TaskData taskData, IMantisClient mantisClient) { double taskDataVersion = 0; String taskDataVersionValue = taskData.getVersion(); if (taskDataVersionValue != null) { try { taskDataVersion = Double.parseDouble(taskDataVersionValue); } catch (NumberFormatException e) { taskDataVersion = 0; } } for (TaskDataVersion version : TaskDataVersion.values()) if (version.getValue() > taskDataVersion) version.migrateTaskData(repository, taskData, mantisClient); taskData.setVersion(String.valueOf(getCurrent().getValue())); } }