Java - Как уменьшить размер сторонних jar-файлов, чтобы уменьшить размер вашего приложения - PullRequest
11 голосов
/ 07 апреля 2011

Я разрабатываю Java-приложение , которое включает апплет .Этот апплет зависит от двух файлов JAR:

  • JFreeChart (для построения графиков на стороне клиента) - 1,7 мб (размер файла JAR)
  • MySqlJdbcConnector (для хранения данных, собранных на стороне клиента, в удаленной базе данных) - .7 МБ (размер файла JAR)

Теперьпроблема заключается в размере выше двух файлов JAR.Общий размер моего апплета jar (myApplet.jar) составляет 2,5 МБ , из которых 2,4 МБ из-за двух вышеуказанных файлов JAR.

Я не использую все классы в этих jar-файлах.В частности, для jfreechart я использую очень небольшое количество классов из этой библиотеки.

===================================== Вопросы ======================================

Q1. Для создания файла myApplet.jar я выполнил распаковку обоих файлов jar (jfreechartи mySQLJdbcConnector), а затем упаковал разархивированную версию файлов JAR с исходным кодом моего кода апплета для создания одного файла JAR ( т.е. myApplet.jar). Это правильный способ упаковки сторонних файлов JARфайлы с кодом вашего апплета?Есть ли способ, которым я могу оптимизировать это?

Q2. Я попытался найти зависимости классов библиотеки jfreechart, которые я использую в своем приложении, чтобы упаковать только тезависимости в myApplet.jar. Для этой цели я использовал DependencyAnalyzer , чтобы найти зависимости всех классов.Но позже мне было трудно сделать это вручную, потому что каждый класс (класс jfreechart, который я использую в своем приложении) имеет много зависимостей, и я использую около 15 классов jfreechart, поэтому сделать это для каждого класса будет очень сложно.Итак, какие-либо предложения по этому поводу?

Q3. Является ли эта ситуация очень распространенной, с которой сталкиваются разработчики, или я что-то упускаю, из-за чего я должен это сделать?

Ответы [ 3 ]

11 голосов
/ 07 апреля 2011

Я бы предложил попробовать ProGuard . Вы можете исключить части файлов JAR, которые вы не используете.

8 голосов
/ 07 апреля 2011

Да, вы можете сэкономить место, создав JAR, содержащий только те классы, которые требуются вашему апплету.(Я видел, что это называется Uber-JAR.)

Существуют различные инструменты для этого;например, ProGuard, Zelix ClassMaster, плагин Maven, имя которого я забыл и т. д.

Однако есть пара проблем, по крайней мере, в общем случае:

  • Если ваш код использует динамическую загрузку (например, путем вызова Class.forName(className)), эти инструменты обычно не могут обнаружить зависимость.Таким образом, чтобы динамически загружаемые классы не попадали в финальный JAR-файл, необходимо сообщить инструменту имена всех классов, которые ваше приложение может явно загрузить таким образом.

  • Вам нужновзглянуть на лицензию сторонней библиотеки.IIRC, некоторые лицензии требуют, чтобы вы включали библиотеку в свои распределенные артефакты таким образом, чтобы люди могли заменить другую версию библиотеки.Можно утверждать, что Uber-JAR делает это трудно, и, следовательно, может быть проблематичным.

JFreeChart - это LGPL, а LGPL - это лицензия, требования которой указаны выше.Однако MySQL - это GPL, что превосходит LGPL, а это означает, что ваш апплет должен быть под GPL ... если вы распространяете его.


Наконец, если вы хотите минимизировать размер JAR апплета, вам НЕ следует включать исходный код в JAR.Исходный код должен быть в отдельном файле JAR (или ZIP, TAR или где-либо еще).

4 голосов
/ 07 апреля 2011

A1:

Вы можете создать скрипт ant или использовать Eclipse или любую другую IDE для автоматической упаковки вашего апплета. Но ваш путь тоже верен

A2:

Я бы не стал делать это вручную. Найти транзитивные зависимости очень сложно. Возможно, ответ darioo - лучший способ сделать это.

A3:

Это действительно очень часто. Пара подсказок:

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

С другой стороны, возможно, у вас не должно быть прямого подключения вашего апплета к базе данных. Вы можете создать интерфейс RMI (или что-то подобное) для передачи вашего SQL и данных результатов на сервер приложений, который фактически выполняет ваш SQL. Это важный аспект безопасности для вашего апплета, если вы не запускаете его в безопасной внутренней сети.

...