Skip to content

Instantly share code, notes, and snippets.

@Mozilla9
Last active October 24, 2016 22:05
Show Gist options
  • Save Mozilla9/8c0770ac4104f5fa49ae to your computer and use it in GitHub Desktop.
Save Mozilla9/8c0770ac4104f5fa49ae to your computer and use it in GitHub Desktop.
Structure of product-extension iOS project
  • Базовое самостоятельное приложение (продукт)
  • Приложение для vendor-a на основе базового (экстеншен)

Что позволяет:

  • переопределение локализации
  • переопределение графических ресурсов
  • переопределение сторибордов/ксибов/реализаций сервисов-классов

Работа с кодом в продукте:

  • Локализация. Через обычные макросы NSLocalizedString или NSLocalizedStringFromTable. Локализацию желательно разбивать на логические модули, не держать все в одном огромном Localizable.strings. В экстеншене потом будет проще.

  • Графика. Обычный способ [UIImage imageWithName:], без указаний бандлов. В IB также, просто имена ресурсов.

  • Сториборды/ксибы/реализации сервисов-классов. Есть специальный plist с сконфигом (аля spring), там указаны явные реализации для сервисов/классов, константы, переопределения сторибордов/ксибов. При старте приложения грузим конфиг, если это экстеншен, то базовый конфиг мержится с конфигом экстеншена. Потом инстанцируются глобальные сервисы/провайдеры. Сториборды бъются логически по сценам (1-3 контроллера), чтобы в экстеншенах можно было заменить часть функционала. Все названия должны быть с префиксом проекта. При инстанцировании контроллеров/вьюх/классов с бизнес логикой используются специальные провайдеры, которые по имени класса(или протокола) отдадут нужную реализацию.

  • Файл проекта. Настройки вынесены в *.xcconfig файлы. Они позволяют при создании экстеншена упростить перенос настроек, сделать переопределения.

Структура проектов в репозитории (у нас svn, а не git - уж простите):

  • отдельная папка для кода modules - на диск выгружается с именем app
  • отдельная папка для файла проекта (файл проекта не в папке с кодом)
  • папка project-all - там скрипт для выгрузки исходников над диск + подтягивание зависимостей.
  • папка thirdparties. которая на картинке - она не под svn. Там зависимости (фрамеворки/либы), которые мы не будем сами менять. От применения CocoaPods отказались по своим причинам (сперва использовали активно). Структура продукта на диске Структура проекта в xcode

Требование к экстеншену:

  • чтобы работал дебаг по коду продукта
  • чтобы можно было из экстеншена вносить изменения в продукт (добавлять-удалять файлы, управлять таргетами). Не держать два проекта открытыми, типа вначале вносишь изменения в продукт, коммитишь, а в экстеншене подтягиваешь изменения из репозитория и потом вручную удаляешь-добавляешь файлы, назначаешь таргеты (кто использовал mogenerator, тот поймет).

Структура экстеншена:

  • в репозитории структура идентична продукту. Папка modules выгружается на диск с именем экстеншена.
  • Классы, файлы UI и прочее, создаются с префиксом экстеншена. Структура экстеншена на диске
  • файл проекта для экстеншена и продукта находятся на одном уровне. В итоге у них единый $(SRCROOT) - для скриптов это очень полезно (ради этого и исключили их из папки исходников)
  • при выгрузке экстеншена создается папка build(не под svn) и в ней localizations.bundle (не включается в таргет) и resources.xcassets (включается в таргет). Они добавлены в проекта экстеншена и используются для сборки.
  • на картинке ниже показан проект экстеншена в xcode. Продукт вложен в экстеншен - так получаем доступ с таргетам продукта и можем менять продукт. Структура экстеншена в xcode

Сборка экстеншена:

  • код продукта собирается как статическая либа и линкуется с экстеншеном (в либу не включаются зависимости, они напрямую включены в таргет экстеншена)
  • сториборды/ксибы продукта собираются в отдельный бандл (плюс в том, что xcode их сам компилирует в *.nib и *.storyboardc) и потом скриптом копируются в корень ExtName.app.
  • НЕ графические ресурсы (например, всякие *.plist файлы) и файлы coredata из продукта собираются в свой бандл и копируются в ExtName.app.
  • Графические ресурсы из продукта, перед Compile sources-фазой, копируются во вспомогательный resources.xcassets. Потом туда же копируются ресурсы из экстеншена. Файлы с одинаковыми именами заменяют друг друга. Так достигается цель переопределение графики.
  • Локализация из продукта копируется во вспомогательный бандл localizations.bundle, затем скрипт ищет совпадающие имена файлов в экстеншене и продукте и делает мерж файлов локализации (скрипт простейший - стандартная osx утилита join вам в помощь). Не совпадающие файлы из экстеншена добавляет в бандл без мержа. Затем компилит локализацию через plutil -convert binary1 -- "<path_to_file>". Далее все из этого бандла копируется в ExtName.app
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment