Змінні середовища: що це, використання та налаштування в мобільних проектах

Автор: IT Sectr Опубліковано: 2026-05-31 Час читання: 8 хв

Змінні середовища — динамічні значення, які передаються додатку на етапі запуску для налаштування поведінки без зміни коду. Вони дозволяють розділяти конфігурації розробки, тестування та продакшну. За даними Twelve-Factor App, 2025, конфігурація повинна зберігатися в змінних середовища, а не в коді. Змінні середовища забезпечують безпечне управління API-ключами, URL бекенду та прапорцями функціональності.

Головне

  • Змінні середовища відокремлюють конфігурацію додатка від вихідного коду для різних середовищ запуску
  • .env файли зберігають змінні у форматі KEY=VALUE і виключаються з репозиторію через .gitignore
  • iOS використовує xcconfig і Build Settings для передачі змінних на етапі компіляції
  • Android використовує BuildConfig і gradle.properties для генерації конфігураційних полів
  • Безпека: ключі та токени повинні завантажуватися через CI/CD, а не зберігатися в коді чи репозиторії

Що таке змінні середовища

Змінні середовища — це пара ключ-значення, доступна процесу додатка через API операційної системи. Вони передаються процесу при його створенні та існують тільки під час його роботи. На відміну від параметрів конфігурації, вбудованих у вихідний код, змінні середовища не вимагають перекомпіляції для зміни значень. Це фундаментальний принцип Twelve-Factor App, який забезпечує чітке розділення між кодом і конфігурацією.

У мобільній розробці змінні середовища вирішують проблему різних конфігурацій для середовищ: розробник використовує локальний сервер, тестувальник — staging, користувачі — production. Замість того щоб зберігати три URL бекенду в коді з умовними операторами if-else, розробник передає один URL через змінну середовища на етапі збірки. Це спрощує код і виключає ризик випадкового використання продакшн-сервера в тестовому середовищі.

Основна перевага — безпека: чутливі дані не потрапляють до репозиторію коду. API-ключі, секрети Firebase, токени доступу до бекенду та сертифікати завантажуються через CI/CD безпосередньо в середовище збірки. Якщо зловмисник отримає доступ до репозиторію коду, він не знайде там секретів, оскільки вони зберігаються в захищених сховищах CI-системи та передаються тільки на етапі збірки бінарного файлу.

Навіщо потрібні змінні середовища в мобільній розробці

Мобільні проекти мають мінімум три середовища: development, staging та production. Кожне середовище вимагає свого набору конфігурацій: URL сервера, ім'я пакета, схема підпису та сертифікати push-сповіщень. Без змінних середовища розробнику доводиться вручну змінювати конфігурацію перед кожною збіркою, що призводить до помилок: забутий продакшн-ключ у тестовій збірці може викликати відправку сповіщень реальним користувачам або витрату платного API.

Розділення середовищ

Змінні середовища дозволяють перемикати бекенд без зміни коду: достатньо замінити значення в змінній API_BASE_URL. Прапорці функціональності (feature flags) керуються через змінні типу FEATURE_CHAT_ENABLED=true, що дозволяє включати нові можливості в staging без впливу на продакшн. Для кожного середовища створюється свій .env файл, який завантажується на етапі збірки.

dart
class AppConfig {
  static final String apiBaseUrl =
    const String.fromEnvironment('API_BASE_URL',
      defaultValue: 'http://localhost:8080');
}

Безпека ключів

Жорстко закодовані ключі — поширена вразливість мобільних додатків. Зловмисник декомпілює APK або IPA за допомогою інструментів типу jadx або Hopper та витягує секрети з бінарного файлу. Навіть обфускація не захищає строкові літерали — вони легко знаходяться в коді після декомпіляції. Змінні середовища вирішують цю проблему, передаючи ключі на етапі збірки через CI/CD, де вони маскуються в логах.

kotlin
object Config {
    val apiKey: String =
        System.getenv("API_KEY") ?: throw
            IllegalStateException("API_KEY not set")
}

CI/CD інтеграція

Змінні середовища інтегруються з пайплайнами збірки: GitHub Actions, GitLab CI, Bitrise та CircleCI підтримують секретні змінні, які не відображаються в логах. На етапі збірки CI підставляє потрібні значення залежно від гілки або тега: для гілки develop використовується staging, для тега v* — production. Це автоматизує процес та виключає людський фактор, гарантуючи, що кожна збірка отримує правильний набір конфігурації.

.env файли та бібліотеки для управління

Файл .env — стандартний спосіб зберігання змінних середовища у форматі KEY=VALUE. Він не включається в репозиторій, а натомість до репозиторію додається .env.example з шаблоном усіх змінних і порожніми значеннями. Кожен розробник створює свій .env файл з локальними налаштуваннями, не зачіпаючи конфігурацію інших членів команди. Для різних середовищ використовуються окремі файли: .env.dev, .env.stage, .env.prod.

bash
# .env.example — шаблон для розробників
API_BASE_URL=http://localhost:8080
FEATURE_CHAT_ENABLED=true
SENTRY_DSN=

Для мобільних проектів існують спеціалізовані бібліотеки для роботи з .env файлами:

  • flutter_dotenv (Flutter) — завантажує змінні з .env у runtime через dotenv.load()
  • BuildConfig (Android) — генерує типізовані поля зі значень build.gradle
  • xcconfig (iOS) — підключає файли конфігурації до різних схем збірки Xcode
  • react-native-config (React Native) — управління змінними через .env файли

Налаштування гілкування в CI/CD дозволяють підставляти різні .env файли: .env.dev для тестових серверів, .env.stage для передрелізу та .env.prod для публікації в магазини додатків. Файли з секретами завантажуються із безпечного сховища (Vault, AWS Secrets Manager) і не зберігаються в репозиторії. Це гарантує, що навіть при компрометації системи контролю версій секрети залишаються захищеними.

Змінні середовища в iOS проектах

iOS екосистема використовує xcconfig файли для управління змінними на рівні збірки. Вони підключаються до схем Xcode та дозволяють перевизначати значення для Debug та Release конфігурацій. xcconfig файли підтримують успадкування: можна створити базовий файл зі спільними налаштуваннями та специфічні файли для кожного середовища.

Налаштування xcconfig файлів

Файли xcconfig зберігають змінні у форматі KEY = VALUE та підключаються до схеми збірки в Xcode через налаштування Configuration. Змінні з xcconfig доступні в Info.plist через синтаксис $(VARIABLE_NAME), що дозволяє використовувати різні ідентифікатори бандла та назви додатка для різних схем. Для швидкої ідентифікації середовища до назви додатка додається суфікс Dev або Staging.

bash
# Config/Dev.xcconfig — конфігурація розробки
API_BASE_URL = http://localhost:3000
BUNDLE_ID_SUFFIX = .dev
APP_DISPLAY_NAME = MyApp Dev

Swift код для читання змінних

Для runtime-доступу до змінних в iOS використовується файл Configuration.swift, який читає значення з Info.plist через Bundle.main.object(forInfoDictionaryKey:). Цей підхід гарантує, що змінні визначаються на етапі збірки та доступні додатку одразу після запуску. Значення читаються один раз при ініціалізації модуля та кешуються для швидкого доступу протягом життєвого циклу додатка.

swift
enum AppEnvironment {
    static var apiBaseURL: URL {
        guard let urlString = Bundle.main
            .object(forInfoDictionaryKey: "API_BASE_URL"),
              let url = URL(string: urlString as! String)
        else { fatalError("API_BASE_URL is not configured") }
        return url
    }

    static var isChatEnabled: Bool {
        Bundle.main.object(
            forInfoDictionaryKey: "FEATURE_CHAT_ENABLED"
        ) as? Bool ?? false
    }
}

Змінні середовища в Android проектах

Android підтримує змінні середовища через BuildConfig — автоматично генерований клас, поля якого визначаються в build.gradle файлі модуля. BuildConfig створюється на етапі компіляції для кожного флейвору та типу збірки окремо. Це дозволяє мати різні значення для debug та release без використання умовних операторів у коді, що підвищує продуктивність та безпеку.

Налаштування BuildConfig полів

Поля BuildConfig задаються через buildConfigField в defaultConfig або в конкретних buildTypes. Для кожного середовища створюється окремий buildType або productFlavor. Це забезпечує строгу ізоляцію конфігурацій: debug використовує локальний сервер, release — продакшн. Поля BuildConfig статично типізовані, що виключає помилки при зверненні до них у коді.

groovy
// build.gradle (Module: app)
android {
    defaultConfig {
        buildConfigField "String", "API_BASE_URL",
            "\"http://localhost:8080\""
    }
    buildTypes {
        debug {
            buildConfigField "String", "API_BASE_URL",
                "\"http://dev.api.itsectr.com\""
        }
        release {
            buildConfigField "String", "API_BASE_URL",
                "\"https://api.itsectr.com\""
        }
    }
}

gradle.properties для спільних значень

Файл gradle.properties в корені проекту зберігає глобальні змінні Gradle. Вони доступні у всіх модулях через синтаксис $variableName та використовуються для вказівки версій залежностей, прапорців збірки та ключів API. На відміну від BuildConfig, gradle.properties працює тільки на етапі конфігурації Gradle, а не в runtime додатка. Тому паролі та ключі API, вказані в gradle.properties, не видно в декомпільованому коді, оскільки вони використовуються тільки для генерації BuildConfig на етапі компіляції.

groovy
# gradle.properties
SENTRY_DSN=https://key@sentry.io/project
MAPS_API_KEY=AIzaSy...

Для безпечної передачі секретів в Android проектах рекомендується використовувати local.properties (виключений з VCS) або завантажувати значення з CI/CD змінних в build.gradle через System.getenv(). Це гарантує, що ключі не потраплять до репозиторію. При публікації в Google Play Console переконайтеся, що всі відлагоджувальні ключі замінені на продакшн-версії через різні buildTypes або productFlavors з відповідними значеннями BuildConfig.

Часті запитання

Чи можна використовувати змінні середовища в Flutter?

Так, Flutter підтримує змінні середовища через пакет flutter_dotenv для runtime-доступу або через нативні канали для платформених змінних. У Dart також доступний конструктор String.fromEnvironment для передачі значень на етапі компіляції через --dart-define, що є кращим способом для Flutter проектів.

У чому різниця між BuildConfig та gradle.properties?

BuildConfig — це Java-клас із типізованими полями, згенерований на етапі компіляції для кожного buildType та flavor. gradle.properties — текстовий файл із парами ключ-значення, доступний усім модулям Gradle на етапі конфігурації збірки. BuildConfig працює в runtime додатка, gradle.properties — тільки в скриптах Gradle.

Як не допустити витоку .env файлу в репозиторій?

Додайте .env до файлу .gitignore вашого репозиторію. До репозиторію комітьте тільки .env.example з порожніми значеннями та описом кожної змінної. Для CI/CD використовуйте зашифровані секрети в налаштуваннях GitHub Actions, GitLab CI або Bitrise, які маскуються в логах та недоступні для читання після завершення збірки.

Як передати змінні середовища через CI/CD?

Більшість CI-систем підтримують секретні змінні середовища. В GitHub Actions це Secrets, в GitLab CI — CI/CD Variables, в Bitrise — Secrets. На етапі збірки вони передаються в білд-скрипт через process.env або System.getenv(). Секретні змінні не відображаються в логах збірки та недоступні в форках репозиторію.

Що таке feature flags через змінні середовища?

Feature flags — це булеві змінні, які керують включенням або вимкненням функціональності без перекомпіляції коду. Приклад: FEATURE_NEW_PAYMENT=true включає нову платіжну систему в staging для тестування. В production той самий прапорець встановлений в false до повного розгортання бекенду. Це дозволяє безпечно впроваджувати зміни поетапно та відкочувати їх при проблемах.

Підсумки

  • Змінні середовища відокремлюють конфігурацію від вихідного коду для різних середовищ розробки
  • .env файли з шаблоном .env.example — стандарт управління змінними в командах з розмежуванням середовищ
  • iOS xcconfig підключає файли конфігурації до схем Xcode з підтримкою успадкування та Info.plist інтеграції
  • Android BuildConfig генерує типізовані поля з build.gradle для кожного buildType окремо
  • CI/CD секрети передають чутливі дані на етапі збірки без зберігання їх в репозиторії
  • Feature flags через змінні дозволяють включати функціональність у конкретному середовищі без перекомпіляції
  • Безпека: ключі шифруються в CI та не потрапляють у декомпільований бінарний файл додатка

Ми розробимо мобільний застосунок під ключ

IT Sectr створює застосунки для iOS та Android для стартапів і бізнесу з 2017 року. Ми проконсультуємо вас і запропонуємо найкраще рішення.

Обговорити проект

Читайте також