/// <summary>
/// Perform one increment migration step.
/// </summary>
/// <param name="domainObjectDtoRepository">Repository of all CmObject DTOs available for one migration step.</param>
/// <remarks>
/// The method must add/remove/update the DTOs to the repository,
/// as it adds/removes objects as part of it work.
/// Implementors of this interface should ensure the Repository's
/// starting model version number is correct for the step.
/// Implementors must also increment the Repository's model version number
/// at the end of its migration work.
/// The method also should normally modify the xml string(s)
/// of relevant DTOs, since that string will be used by the main
/// data migration calling client (ie. BEP).
/// </remarks>
public void PerformMigration(IDomainObjectDTORepository domainObjectDtoRepository)
{
DataMigrationServices.CheckVersionNumber(domainObjectDtoRepository, 7000018);
// collect all writing system info
var guidToWsInfo = new Dictionary<string, Tuple<string, DomainObjectDTO, XElement>>();
foreach (DomainObjectDTO wsDto in domainObjectDtoRepository.AllInstancesSansSubclasses("LgWritingSystem").ToArray())
{
XElement wsElem = XElement.Parse(wsDto.Xml);
XElement icuLocaleElem = wsElem.Element("ICULocale");
var icuLocale = icuLocaleElem.Element("Uni").Value;
string langTag = Version19LangTagUtils.ToLangTag(icuLocale);
guidToWsInfo[wsDto.Guid.ToLowerInvariant()] = Tuple.Create(langTag, wsDto, wsElem);
}
// remove all CmSortSpec objects
foreach (DomainObjectDTO sortSpecDto in domainObjectDtoRepository.AllInstancesSansSubclasses("CmSortSpec").ToArray())
domainObjectDtoRepository.Remove(sortSpecDto);
// remove SortSpecs property from LangProject
DomainObjectDTO lpDto = domainObjectDtoRepository.AllInstancesSansSubclasses("LangProject").First();
XElement lpElem = XElement.Parse(lpDto.Xml);
XElement sortSpecsElem = lpElem.Element("SortSpecs");
bool lpModified = false;
if (sortSpecsElem != null)
{
sortSpecsElem.Remove();
lpModified = true;
}
var referencedWsIds = new HashSet<string>();
// convert all LangProject writing system references to strings
if (ConvertRefToString(lpElem.Element("AnalysisWss"), guidToWsInfo, referencedWsIds))
lpModified = true;
if (ConvertRefToString(lpElem.Element("VernWss"), guidToWsInfo, referencedWsIds))
lpModified = true;
if (ConvertRefToString(lpElem.Element("CurAnalysisWss"), guidToWsInfo, referencedWsIds))
lpModified = true;
if (ConvertRefToString(lpElem.Element("CurPronunWss"), guidToWsInfo, referencedWsIds))
lpModified = true;
if (ConvertRefToString(lpElem.Element("CurVernWss"), guidToWsInfo, referencedWsIds))
lpModified = true;
if (lpModified)
DataMigrationServices.UpdateDTO(domainObjectDtoRepository, lpDto, lpElem.ToString());
// convert all ReversalIndex writing system references to strings
ConvertAllRefsToStrings(domainObjectDtoRepository, "ReversalIndex", guidToWsInfo, referencedWsIds);
// convert all WordformLookupList writing system references to strings
ConvertAllRefsToStrings(domainObjectDtoRepository, "WordformLookupList", guidToWsInfo, referencedWsIds);
// convert all CmPossibilityList writing system references to strings
ConvertAllRefsToStrings(domainObjectDtoRepository, "CmPossibilityList", guidToWsInfo, referencedWsIds);
// convert all UserViewField writing system references to strings
ConvertAllRefsToStrings(domainObjectDtoRepository, "UserViewField", guidToWsInfo, referencedWsIds);
// convert all CmBaseAnnotation writing system references to strings
ConvertAllRefsToStrings(domainObjectDtoRepository, "CmBaseAnnotation", guidToWsInfo, referencedWsIds);
// convert all FsOpenFeature writing system references to strings
ConvertAllRefsToStrings(domainObjectDtoRepository, "FsOpenFeature", guidToWsInfo, referencedWsIds);
// convert all ScrMarkerMapping ICU locales to lang tags
ConvertAllIcuLocalesToLangTags(domainObjectDtoRepository, "ScrMarkerMapping", referencedWsIds);
// convert all ScrImportSource ICU locales to lang tags
ConvertAllIcuLocalesToLangTags(domainObjectDtoRepository, "ScrImportSource", referencedWsIds);
// convert all ICU locales to Language Tags and remove legacy magic font names
foreach (DomainObjectDTO dto in domainObjectDtoRepository.AllInstances())
UpdateStringsAndProps(domainObjectDtoRepository, dto, referencedWsIds);
var localStoreFolder = Path.Combine(domainObjectDtoRepository.ProjectFolder, FdoFileHelper.ksWritingSystemsDir);
// If any writing systems that project needs don't already exist as LDML files,
// create them, either by copying relevant data from a shipping LDML file, or by
// extracting data from the obsolete writing system object's XML.
if (!string.IsNullOrEmpty(domainObjectDtoRepository.ProjectFolder))
{
foreach (Tuple<string, DomainObjectDTO, XElement> wsInfo in guidToWsInfo.Values)
{
if (referencedWsIds.Contains(wsInfo.Item1))
{
var ws = new Version19WritingSystemDefn();
var langTag = wsInfo.Item1;
ws.LangTag = langTag;
var ldmlFileName = Path.ChangeExtension(langTag, "ldml");
string localPath = Path.Combine(localStoreFolder, ldmlFileName);
if (File.Exists(localPath))
continue; // already have one.
string globalPath = Path.Combine(DirectoryFinder.GlobalWritingSystemStoreDirectory, ldmlFileName);
if (File.Exists(globalPath))
continue; // already have one.
// Need to make one.
// Code similar to this was in the old migrator (prior to 7000043). It does not work
// because the XML files it is looking for are in the Languages subdirectory of the
// FieldWorks 6 data directory, and this is looking in the FW 7 one. No one has complained
// so we decided not to try to fix it for the new implementation of the migration.
//string langDefPath = Path.Combine(FwDirectoryFinder.GetDataSubDirectory("Languages"),
// Path.ChangeExtension(langTag, "xml"));
//if (File.Exists(langDefPath))
// FillWritingSystemFromLangDef(XElement.Load(langDefPath), ws);
//else
FillWritingSystemFromFDO(domainObjectDtoRepository, wsInfo.Item3, ws);
ws.Save(localPath);
}
}
}
foreach (Tuple<string, DomainObjectDTO, XElement> wsInfo in guidToWsInfo.Values)
{
// this should also remove all LgCollations as well
DataMigrationServices.RemoveIncludingOwnedObjects(domainObjectDtoRepository, wsInfo.Item2, false);
}
DataMigrationServices.IncrementVersionNumber(domainObjectDtoRepository);
}