Многоцелевой артефакт / проект поколения Acceleo Maven
Я пытаюсь построить maven acceleo generator
, Генератор состоит из нескольких акселерационных проектов (артефакты в maven) с взаимозависимостями.
Я столкнулся с проблемой с зависимостями между файлами EMTL. Во время выполнения я получаю сообщения об ошибках компиляции в mtl (их нет). Я предполагаю, что это могут быть hrefs в скомпилированных файлах emtl.
Существует плагин компиляции Acceleo Maven, который позволяет:
а) абсолютные пути (заканчивающиеся через репозиторий maven)
б) 'platform:/plugin/...'
пути.
(a) работает, если проекты акселераторов (артефакты maven) создаются на той же машине, на которой мы выполняем генерацию, но если местоположение репозитория maven изменяется, у нас возникает проблема. Следовательно, развертывание артефактов maven оказывается бессмысленным.
(б) не работает, потому что работает изнутри Maven, 'platform:/plugin/'
не может быть решен.
Я пытался отменить 'createURIConverter'
метод в AbstractAcceleoGenerator
затем с помощью URLClassLoader
мы можем расшифровать 'platform:/plugin/'
hrefs и найдите правильный файл emtl. Я могу убедиться, что это работает, но я все еще получаю сообщение
"org.eclipse.acceleo.engine.AcceleoEvaluationException: Unresolved compilation error in generation module"
какие-либо предложения?
2 ответа
Исключение было вызвано hrefs в модели EMTL, разрешающей к нулю.
Проблема с разрешением hrefs заключалась лишь в отсутствии регистрации фабрики ресурсов (исключение, информирующее меня об этом, теряется в EcoreUtil.resolve, которое ловит исключение с помощью "// Неудачное решение игнорируется." - наиболее бесполезно).
Таким образом, кажется, что мой подход "переопределить метод createURIConverter и заставить его декодировать" platform:/plugin/.. "с помощью URLClassLoader" работает.
Сборка URLClassLoader с использованием того же метода, что и в AcceleoParserMojo.
Вот точные изменения, которые я внес в свой генератор.
Добавлен специальный преобразователь URI для преобразования URI-адресов Platform:/... в jar:file:/... URI:
@Override
protected URIConverter createURIConverter() {
if (EMFPlugin.IS_ECLIPSE_RUNNING) {
return super.createURIConverter();
}
// Converts platform:/... URIs to jar:file:/... URIs
// Required to load Acceleo templates from other projects
return new ExtensibleURIConverterImpl() {
@Override
public URI normalize(URI uri) {
if (uri.isPlatform()) {
URI normalized = getURIMap().get(uri);
if (normalized == null) {
String path = uri.segmentsList().stream().skip(2).collect(Collectors.joining("/"));
URL resource = getClass().getClassLoader().getResource(path);
if (resource != null) {
normalized = URI.createURI(resource.toString());
getURIMap().put(uri, normalized);
}
}
if (normalized != null) {
return normalized;
}
}
return super.normalize(uri);
}
};
}
Зарегистрировал фабрику ресурсов для emtl-файлов:
@Override
public void registerResourceFactories(ResourceSet resourceSet) {
super.registerResourceFactories(resourceSet);
// Your resource factories here
// ...
// Emtl resource factory, required to load Acceleo templates from other projects
resourceSet.getResourceFactoryRegistry().getExtensionToFactoryMap().put("emtl", new EMtlResourceFactoryImpl());
}
Если вы используете двоичный формат для emtl-файлов, я думаю, можно заменить фабрику наEMtlBinaryResourceFactoryImpl
.