Ошибка Guice при попытке использовать парсер Alf Xtext как автономный

Я пытаюсь написать плагин для Papyrus, который преобразует код Alf.

Я попытался использовать Alf-парсер, который уже включен в Papyrus (org.eclipse.papyrus.uml.alf.*). Поэтому я попытался создать экземпляр синтаксического анализатора, как написано здесь:

public class Activator extends Plugin {

    // default Activator code here ...

    public String ConvertAlfToSpecSharp(String alf)
    {
        new org.eclipse.emf.mwe.utils.StandaloneSetup().setPlatformUri("../");
        Injector injector = new AlfStandaloneSetup().createInjectorAndDoEMFRegistration();
        XtextResourceSet resourceSet = injector.getInstance(XtextResourceSet.class);
        resourceSet.addLoadOption(XtextResource.OPTION_RESOLVE_ALL, Boolean.TRUE);
        // ...
    }
}

Но первая строка (new org.eclipse.emf.mwe.utils.StandaloneSetup().setPlatformUri("../");) выдает следующее исключение:

com.google.inject.CreationException: Guice creation errors:

1) Error injecting method, java.lang.IllegalStateException: No EPackages were registered for the validator org.eclipse.papyrus.uml.alf.validation.CommonJavaValidator please override and implement getEPackages().
at org.eclipse.xtext.validation.AbstractInjectableValidator.register(Unknown Source)
at org.eclipse.xtext.service.MethodBasedModule.configure(MethodBasedModule.java:55)
while locating org.eclipse.papyrus.uml.alf.validation.CommonJavaValidator

1 error
    at com.google.inject.internal.Errors.throwCreationExceptionIfErrorsExist(Errors.java:435)
    at com.google.inject.internal.InternalInjectorCreator.injectDynamically(InternalInjectorCreator.java:183)
    at com.google.inject.internal.InternalInjectorCreator.build(InternalInjectorCreator.java:109)
    at com.google.inject.Guice.createInjector(Guice.java:95)
    at com.google.inject.Guice.createInjector(Guice.java:72)
    at com.google.inject.Guice.createInjector(Guice.java:62)
    at org.eclipse.papyrus.uml.alf.CommonStandaloneSetupGenerated.createInjector(CommonStandaloneSetupGenerated.java:28)
    at org.eclipse.papyrus.uml.alf.CommonStandaloneSetupGenerated.createInjectorAndDoEMFRegistration(CommonStandaloneSetupGenerated.java:22)
at org.eclipse.papyrus.uml.alf.CommonStandaloneSetup.doSetup(CommonStandaloneSetup.java:23)
    at org.eclipse.papyrus.uml.alf.AlfStandaloneSetupGenerated.createInjectorAndDoEMFRegistration(AlfStandaloneSetupGenerated.java:20)
    at <packagenamehere>.Activator.ConvertAlfToSpecSharp(Activator.java:113)

Я понятия не имею, как это решить, тем более что мне очень сложно отлаживать приложения eclipse...

Обновление: вот ссылки на некоторые соответствующие классы (все из плагина org.eclipse.papyrus.uml.alf.common плагинов Papyrus (ссылка)):


person jsf    schedule 29.07.2014    source источник
comment
Можете ли вы предоставить содержимое CommonStandaloneSetup.java, пожалуйста?   -  person Fabien Fleureau    schedule 30.07.2014
comment
Также можете ли вы предоставить содержимое CommonJavaValidator.java и AbstractCommonJavaValidator.java (его прямого родителя), пожалуйста? Как указано в сообщении об ошибке, метод getEPackages() возвращает пустой список.   -  person Fabien Fleureau    schedule 30.07.2014
comment
Все классы взяты из плагинов alf.common для Papyrus. Я добавил ссылки выше.   -  person jsf    schedule 30.07.2014


Ответы (1)


Как видите, метод getEPackages() класса AbstractCommonJavaValidator.java возвращает пустой список.

Если вы посмотрите на это AbstractAlfJavaValidator есть пакет EPackage, который добавляется в список.

В качестве решения, я думаю, вам следует отредактировать CommonJavaValidator.java и переопределить getEPackages(), чтобы добавить EPackage:

@Override
protected List<EPackage> getEPackages() {
    List<EPackage> result = super.getEPackages();
    // result.add(org.eclipse.papyrus.uml.alf.alf.AlfPackage.eINSTANCE);
    // Edit
    result.add(org.eclipse.emf.ecore.EcorePackage.eINSTANCE);
    return result;
}

Изменить

Если вы не можете редактировать плагины папируса, вам следует добавить следующее перед кодом:

if (!EPackage.Registry.INSTANCE.containsKey("http://www.eclipse.org/papyrus/alf/Alf")) { EPackage.Registry.INSTANCE.put("http://www.eclipse.org/papyrus/alf/Alf", org.eclipse.papyrus.uml.alf.alf.AlfPackage.eINSTANCE); }

Он добавит EPackage перед созданием guice, и исключение будет исключено.

person Fabien Fleureau    schedule 30.07.2014
comment
Если я редактирую CommonJavaValidator, как в вашем первом решении, я получаю циклическую ошибку зависимости, потому что AlfPackage находится в плагине org.eclipse.papyrus.uml.alf, который зависит от org.eclipse.papyrus.uml.alf.common, где находится CommonJavaValidator. Ваше второе решение ничего не делает для меня. Я вставил код прямо перед new org.eclipse.emf.mwe.utils.StandaloneSetup().setPlatformUri("../"); - person jsf; 30.07.2014
comment
Хорошо, тогда вы можете попробовать это вместо этого? result.add(org.eclipse.emf.ecore.EcorePackage.eINSTANCE); - person Fabien Fleureau; 30.07.2014
comment
Да, это сделало это. Большое спасибо. Вы должны обновить свой ответ на это решение. - person jsf; 30.07.2014