Есть ли способ решить проблему компилятора / сериализатора / компоновщика GWT? - PullRequest
0 голосов
/ 16 марта 2011

Допустим, у меня есть класс ...

com.mycom.app.AbstractMessage

В

* 1009 есть еще один класс* com.mycom.model.QueryResponse

QueryResponse расширяет AbstractMessage и замечает, что они находятся в разных пакетах

com.mycom.model является модулем GWT и вмодуль XML

Когда я компилирую модель, возникают ошибки.Однако, когда я пытаюсь использовать QueryReponse в другом модуле GWT, я получаю ошибки времени выполнения

«Исходный код для типа com.mycom.app.AbstractMessage недоступен; вы забыли унаследовать требуемый модуль»

Это позволяет мне полагать, что AbstractMessage не был скомпилирован / скомпилирован правильно, чтобы начать понятно, потому что я НЕ ХОЧУ, чтобы пакет "app" был модулем GWT

Другими словами,Я только хочу собрать все классы в «модель», а не суперклассы.Как я могу сказать компилятору GWT / rpc / linker / serializer и т. Д. Не делать этого?

т.е. есть ли способ сказать GWT не выходить за определенные классы при сериализации / компиляции

Я делаю это в исходной среде, где у нас много пакетов, большинство из нихзависит только от МОДЕЛИ, и я НЕ хочу делать модуль GWT из каждого пакета, просто так он компилируется.

Кто-нибудь думает?

Ответы [ 3 ]

0 голосов
/ 16 марта 2011

Есть еще один вариант: если, как я подозреваю, вы используете шаблон команды - я видел, что все абстрактные интерфейсы, суперклассы для команд, ответов и т. Д. Всегда идут в пакетах на стороне клиента - то есть в пакетах, скомпилированных GWT. , Они являются референтными, пригодными для использования и инстанцируемыми для серверной части приложения - поэтому эти исходные файлы компилируются дважды: один раз GWT в javascript для использования в браузере и один раз в javac в байт-код для разрешения ссылки со стороны сервера. Таким образом, во всех модулях GWT, включая gwt-user.jar, если вы откроете их с помощью 7Zip или WinZip, вы увидите файлы JAR с исходным кодом и классом.

0 голосов
/ 21 марта 2011

Я провел небольшое исследование по этому вопросу, вы правы, GWT будет искать все реализации абстрактного класса, если и только если на AbstractClass ссылаются в интерфейсе RPC GWTAsync, даже если некоторые находятся в Пакеты GWT.

Допустим, объект типа AbstractClass входит в сеть, и десериализатору GWT теперь поручено скрыть сетевые данные в конкретном экземпляре. Он должен знать обо всех реализациях AbstractClass, чтобы найти, что происходит по сети прямо сейчас! - Таким образом, для достижения этого во время компиляции генерируется файл .rpc для каждого интерфейса службы GWT, в котором перечислены все возможные конкретные типы, которые могут возвращать методы службы.

Рэй Райан (сотрудник Google) однажды упомянул, что плохая идея - использовать аргументы интерфейсов или возвращаемые типы в любом интерфейсе RPC. - потому что десериализатору трудно узнать точный тип.

Вы можете вручную отредактировать созданный RPC-файл и удалить ошибочные типы или пометить другие реализации как не сериализуемые, не реализовав Serializable в этих реализациях в других пакетах.

Лучший способ может быть - я подозреваю, что вы написали код: "реализует java.io.Serializable" на верхнем уровне (для самого AbstractClass), возможно, сейчас пришло время перенести его в каждую реализацию.

Теперь задача десериализатора GWT RPC ясна и понятна - он знает, что только определенные реализации (которые можно сериализировать) в AbstractClass будут проходить по сети и достигать и компилировать только их. Поэтому он не будет компилировать другие не сериализуемые подклассы вашего AbstractClass - поскольку он знает, что они не сериализуемы.

0 голосов
/ 16 марта 2011

Я рекомендую Переместить AbstractMessage в пакет моделей - так как это суперкласс модели QueryResponse .

А также наследование в моделях является хорошей идеей, если у вас есть 0 полей и только методы (поведение) в суперклассе.

Наконец, если GWT хочет сделать ваш QueryResponse в javascript - ему нужны ВСЕ типы, указанные в исходном файле, для правильной компиляции. Поэтому не упоминайте никакие серверные классы в исходном файле, который должен стать javascript.

Иметь регион, в котором есть все классы java на стороне сервера, которые будут запускаться в JVM на сервере, и другой регион, полный исходных файлов, которые будут компилироваться в javascript компилятором GWT. Код / классы регионов на стороне сервера МОГУТ ссылаться на код / ​​классы регионов клиента, но ОБЯЗАТЕЛЬНО НЕ наоборот . Убедитесь, что ни один код, который станет javascript, не ссылается (даже неиспользуемый оператор import) на класс на стороне сервера.

Компилятор GWT работает только с исходными файлами, однако вам необходимо скомпилировать код клиента в файлы .class, чтобы ваши серверные классы могли ссылаться на них.

НОВОЕ РЕДАКТИРОВАНИЕ:

Я провел небольшое исследование по этому вопросу, вы правы, GWT будет искать все реализации абстрактного класса, если и только если на AbstractClass ссылаются в интерфейсе RPC GWTAsync, даже если некоторые находятся в Пакеты GWT.

Допустим, по сети поступает объект типа AbstractClass, и теперь десериализатору GWT поручено скрыть сетевые данные в конкретном экземпляре. Он должен знать обо всех реализациях AbstractClass, чтобы найти, что происходит по сети прямо сейчас! - Таким образом, для достижения этой цели во время компиляции генерируется файл .rpc для каждого интерфейса службы GWT, в котором перечислены все возможные конкретные типы, которые могут возвращать методы службы.

Рэй Райан (сотрудник Google) однажды упомянул, что плохая идея - использовать аргументы интерфейсов или возвращаемые типы в любом интерфейсе RPC. - потому что десериализатору трудно узнать точный тип.

Вы можете вручную отредактировать сгенерированный RPC-файл и удалить ошибочные типы или пометить другие реализации как не сериализуемые, не реализовав Serializable в этих реализациях в других пакетах.

Лучше может быть ... Я подозреваю, что вы написали код: «реализует java.io.Serializable» на верхнем уровне (для самого AbstractClass), возможно, сейчас пришло время перенести его в каждую реализацию.

Теперь задача десериализатора GWT RPC ясна и понятна - он знает, что только определенные реализации (которые можно сериализировать) в AbstractClass будут проходить по сети и достигать и компилировать только их. Поэтому он не будет компилировать другие не сериализуемые подклассы вашего AbstractClass - поскольку он знает, что они не сериализуемы.

...