Examples
Mobile Development Environment
Complete mobile app development setup for React Native, Flutter, and native iOS/Android development
Mobile Development Environment
This example provides a comprehensive mobile development environment supporting React Native, Flutter, native iOS, and Android development with proper tooling, emulators, and testing capabilities.
Quick Start
Download Configuration
# Download the mobile development configuration
curl -fsSL https://raw.githubusercontent.com/jameswlane/devex/main/examples/mobile-development.yaml > ~/.devex/mobile-dev.yaml
# Preview what will be installed
devex config apply --file ~/.devex/mobile-dev.yaml --dry-runApply Configuration
# Apply the configuration
devex config apply --file ~/.devex/mobile-dev.yaml
# Install all tools
devex installVerify Installation
# Check installed tools
node --version
react-native --version
flutter --version # if Flutter was selected
adb versionComplete Configuration
# ~/.devex/mobile-development.yaml
# Complete Mobile Development Environment
applications:
development:
# Version Control
- name: git
description: "Distributed version control system"
category: "Version Control"
default: true
priority: 10
- name: git-lfs
description: "Git Large File Storage for assets"
category: "Version Control"
default: true
dependencies: ["git"]
# Code Editors and IDEs
- name: vscode
description: "Visual Studio Code with mobile development extensions"
category: "Editors"
default: true
post_install:
# Mobile development extensions
- shell: "code --install-extension ms-vscode.vscode-typescript-next"
- shell: "code --install-extension ms-vscode.vscode-eslint"
- shell: "code --install-extension esbenp.prettier-vscode"
- shell: "code --install-extension bradlc.vscode-tailwindcss"
- shell: "code --install-extension ms-vscode.vscode-json"
- shell: "code --install-extension redhat.vscode-yaml"
- shell: "code --install-extension ms-vscode-remote.remote-containers"
# React Native specific
- shell: "code --install-extension msjsdiag.vscode-react-native"
- shell: "code --install-extension ms-vscode.vscode-react-native"
# Flutter specific (if using Flutter)
- shell: "code --install-extension Dart-Code.dart-code"
- shell: "code --install-extension Dart-Code.flutter"
# Android development
- shell: "code --install-extension vscjava.vscode-java-pack"
- shell: "code --install-extension redhat.java"
config_files:
- source: "~/.devex/assets/vscode/mobile-dev-settings.json"
destination: "~/.config/Code/User/settings.json"
- name: android-studio
description: "Android Studio IDE"
category: "IDEs"
default: true
linux:
install_method: flatpak
install_command: com.google.AndroidStudio
macos:
install_method: brew
install_command: android-studio
cask: true
windows:
install_method: winget
install_command: Google.AndroidStudio
post_install:
- shell: "echo 'export ANDROID_HOME=$HOME/Android/Sdk' >> ~/.bashrc"
- shell: "echo 'export PATH=$PATH:$ANDROID_HOME/emulator' >> ~/.bashrc"
- shell: "echo 'export PATH=$PATH:$ANDROID_HOME/tools' >> ~/.bashrc"
- shell: "echo 'export PATH=$PATH:$ANDROID_HOME/tools/bin' >> ~/.bashrc"
- shell: "echo 'export PATH=$PATH:$ANDROID_HOME/platform-tools' >> ~/.bashrc"
# macOS only - Xcode for iOS development
- name: xcode
description: "Xcode for iOS development"
category: "IDEs"
default: true
condition:
platform: "darwin"
macos:
install_method: mas
install_command: "497799835"
post_install:
- shell: "sudo xcode-select --switch /Applications/Xcode.app/Contents/Developer"
- shell: "sudo xcodebuild -license accept"
# Android Development Tools
- name: android-sdk
description: "Android SDK and tools"
category: "Mobile Development"
default: true
dependencies: ["android-studio"]
- name: adb
description: "Android Debug Bridge"
category: "Mobile Development"
default: true
linux:
install_method: apt
install_command: adb
macos:
install_method: brew
install_command: android-platform-tools
windows:
install_method: winget
install_command: Google.PlatformTools
# React Native Development
- name: react-native-cli
description: "React Native CLI"
category: "Mobile Development"
default: true
dependencies: ["node"]
install_method: npm
install_command: "@react-native-community/cli"
global: true
- name: expo-cli
description: "Expo CLI for React Native"
category: "Mobile Development"
default: true
dependencies: ["node"]
install_method: npm
install_command: "@expo/cli"
global: true
# Flutter Development (optional)
- name: flutter
description: "Flutter SDK"
category: "Mobile Development"
default: false
linux:
install_method: curlpipe
install_command: "https://storage.googleapis.com/flutter_infra_release/releases/stable/linux/flutter_linux_3.13.0-stable.tar.xz"
macos:
install_method: brew
install_command: flutter
windows:
install_method: winget
install_command: Google.Flutter
post_install:
- shell: "echo 'export PATH=$PATH:$HOME/flutter/bin' >> ~/.bashrc"
- shell: "flutter doctor"
- shell: "flutter config --enable-web"
# iOS Development Tools (macOS only)
- name: ios-simulator
description: "iOS Simulator"
category: "Mobile Development"
default: true
condition:
platform: "darwin"
dependencies: ["xcode"]
- name: cocoapods
description: "CocoaPods dependency manager"
category: "Mobile Development"
default: true
condition:
platform: "darwin"
install_method: gem
install_command: cocoapods
# Cross-platform tools
- name: node
description: "Node.js for React Native development"
category: "Programming Languages"
install_method: mise
install_command: node@lts
default: true
priority: 20
shell_updates:
- "export NODE_OPTIONS='--max-old-space-size=4096'"
post_install:
- shell: "npm install -g npm@latest"
- shell: "npm install -g yarn pnpm"
# Java (required for Android development)
- name: java
description: "Java JDK for Android development"
category: "Programming Languages"
install_method: mise
install_command: java@openjdk-17
default: true
post_install:
- shell: "echo 'export JAVA_HOME=$(dirname $(dirname $(readlink -f $(which java))))' >> ~/.bashrc"
# Testing and Debugging Tools
- name: flipper
description: "Mobile app debugging platform"
category: "Debugging"
default: false
linux:
install_method: flatpak
install_command: com.facebook.flipper
macos:
install_method: brew
install_command: flipper
cask: true
windows:
install_method: winget
install_command: Facebook.Flipper
- name: reactotron
description: "React Native debugging tool"
category: "Debugging"
default: false
install_method: npm
install_command: reactotron-cli
global: true
# Design and Prototyping
- name: figma-linux
description: "Figma design tool"
category: "Design"
default: false
desktop_environments: ["gnome", "kde", "xfce"]
linux:
install_method: flatpak
install_command: io.github.Figma_Linux.figma_linux
# Version Control for Mobile Assets
- name: fastlane
description: "Mobile app automation"
category: "Deployment"
default: false
install_method: gem
install_command: fastlane
# Container Support
- name: docker
description: "Container platform for CI/CD"
category: "Containers"
default: true
post_install:
- shell: "docker pull reactnativecommunity/react-native-android"
# Terminal and Shell Tools
- name: zsh
description: "Zsh shell with mobile development plugins"
category: "Shell"
default: true
post_install:
- shell: "sh -c '$(curl -fsSL https://raw.github.com/ohmyzsh/ohmyzsh/master/tools/install.sh)'"
- name: watchman
description: "File watching service"
category: "Development Tools"
default: true
linux:
install_method: apt
install_command: watchman
macos:
install_method: brew
install_command: watchman
windows:
# Watchman for Windows is more complex to install
install_method: manual
# Programming Languages
programming_languages:
- name: Node.js
description: "JavaScript runtime for React Native"
category: "Programming Languages"
install_method: mise
install_command: node@lts
default: true
shell_updates:
- "export NODE_OPTIONS='--max-old-space-size=4096'"
post_install:
# React Native development packages
- shell: "npm install -g react-native-cli @react-native-community/cli"
- shell: "npm install -g expo-cli @expo/cli"
- shell: "npm install -g react-devtools"
- shell: "npm install -g metro-bundler"
# Testing tools
- shell: "npm install -g detox-cli"
- shell: "npm install -g appium"
# Development utilities
- shell: "npm install -g react-native-rename"
- shell: "npm install -g react-native-version"
- name: Java
description: "Java JDK for Android development"
category: "Programming Languages"
install_method: mise
install_command: java@openjdk-17
default: true
shell_updates:
- "export JAVA_HOME=$(dirname $(dirname $(readlink -f $(which java))))"
- name: Dart
description: "Dart language for Flutter"
category: "Programming Languages"
install_method: mise
install_command: dart@latest
default: false
condition:
flutter_enabled: true
dependencies: ["flutter"]
- name: Python
description: "Python for mobile automation scripts"
category: "Programming Languages"
install_method: mise
install_command: python@3.11
default: false
post_install:
- shell: "pip install appium-python-client"
- shell: "pip install pytest pytest-xdist"
- name: Ruby
description: "Ruby for Fastlane and iOS automation"
category: "Programming Languages"
install_method: mise
install_command: ruby@latest
default: false
condition:
platform: "darwin"
post_install:
- shell: "gem install fastlane"
- shell: "gem install cocoapods"
# Mobile Databases and Backend Services
databases:
- name: sqlite
description: "SQLite for local mobile database"
category: "Mobile Databases"
default: true
- name: realm-studio
description: "Realm database browser"
category: "Mobile Databases"
default: false
macos:
install_method: brew
install_command: realm-studio
cask: true
windows:
install_method: winget
install_command: Realm.RealmStudio
- name: firebase-cli
description: "Firebase CLI for backend services"
category: "Backend Services"
default: false
install_method: npm
install_command: firebase-tools
global: true
# Environment Configuration
environment:
shell:
default_shell: "zsh"
oh_my_zsh: true
plugins:
- "git"
- "node"
- "npm"
- "react-native"
- "android"
- "flutter" # if Flutter enabled
theme: "agnoster"
fonts:
- name: "JetBrains Mono"
description: "Programming font for mobile development"
method: "url"
url: "https://download.jetbrains.com/fonts/JetBrainsMono-2.304.zip"
destination: "~/.local/share/fonts/"
post_install:
- shell: "fc-cache -fv"
# System Configuration
system:
git:
settings:
- key: "core.editor"
value: "code --wait"
- key: "init.defaultBranch"
value: "main"
- key: "pull.rebase"
value: "false"
- key: "lfs.track"
value: "*.png *.jpg *.jpeg *.gif *.svg *.mp4 *.mov *.avi"
android:
sdk_path: "$HOME/Android/Sdk"
ndk_version: "25.1.8937393"
build_tools_version: "33.0.0"
emulator_config:
avd_name: "DevEx_Pixel_6_API_33"
system_image: "system-images;android-33;google_apis;x86_64"
node:
global_packages:
- "@react-native-community/cli"
- "@expo/cli"
- "react-devtools"
- "metro-bundler"
- "flipper-pkg"
environment_variables:
ANDROID_HOME: "$HOME/Android/Sdk"
ANDROID_SDK_ROOT: "$HOME/Android/Sdk"
JAVA_HOME: "$JAVA_HOME"
FLUTTER_ROOT: "$HOME/flutter" # if Flutter enabled
REACT_EDITOR: "code"
EXPO_EDITOR: "code"React Native Development
Project Setup and Configuration
# Create new React Native project
npx react-native@latest init MyAwesomeApp
cd MyAwesomeApp
# Install additional dependencies
npm install react-navigation/native react-navigation/stack
npm install react-native-screens react-native-safe-area-context
npm install @reduxjs/toolkit react-redux
npm install react-native-vector-icons
npm install react-native-async-storage/async-storage
# Development dependencies
npm install --save-dev @types/react @types/react-native
npm install --save-dev eslint @typescript-eslint/parser
npm install --save-dev prettier eslint-config-prettier
npm install --save-dev jest @testing-library/react-native
npm install --save-dev detox
# iOS dependencies (macOS only)
cd ios && pod install && cd ..
# Start Metro bundler
npx react-native start
# Run on Android
npx react-native run-android
# Run on iOS (macOS only)
npx react-native run-iosReact Native Project Structure
MyReactNativeApp/
├── android/ # Android native code
├── ios/ # iOS native code
├── src/
│ ├── components/ # Reusable UI components
│ │ ├── common/
│ │ └── forms/
│ ├── screens/ # Screen components
│ │ ├── auth/
│ │ ├── home/
│ │ └── profile/
│ ├── navigation/ # Navigation configuration
│ ├── services/ # API and external services
│ ├── store/ # State management (Redux/Zustand)
│ ├── utils/ # Utility functions
│ ├── hooks/ # Custom React hooks
│ ├── types/ # TypeScript type definitions
│ └── assets/ # Images, fonts, etc.
├── __tests__/ # Test files
├── e2e/ # End-to-end tests
├── package.json
├── tsconfig.json # TypeScript configuration
├── babel.config.js # Babel configuration
├── metro.config.js # Metro bundler configuration
└── react-native.config.js # React Native configurationFlutter Development
Flutter Project Setup
# Create new Flutter project
flutter create my_flutter_app
cd my_flutter_app
# Add common dependencies
flutter pub add http
flutter pub add shared_preferences
flutter pub add provider
flutter pub add flutter_bloc
flutter pub add go_router
flutter pub add cached_network_image
flutter pub add sqflite
# Add development dependencies
flutter pub add --dev flutter_test
flutter pub add --dev integration_test
flutter pub add --dev flutter_lints
flutter pub add --dev mockito
flutter pub add --dev build_runner
# Get dependencies
flutter pub get
# Run the app
flutter run
# Run on specific device
flutter devices
flutter run -d android
flutter run -d ios
flutter run -d chromeAndroid Development
Native Android Setup
# Create new Android project using Android Studio
# Or use command line with Android SDK
# Project structure for modern Android development
MyAndroidApp/
├── app/
│ ├── src/
│ │ ├── main/
│ │ │ ├── java/com/example/myapp/
│ │ │ │ ├── ui/
│ │ │ │ │ ├── activities/
│ │ │ │ │ ├── fragments/
│ │ │ │ │ └── adapters/
│ │ │ │ ├── data/
│ │ │ │ │ ├── repositories/
│ │ │ │ │ ├── models/
│ │ │ │ │ └── network/
│ │ │ │ ├── viewmodels/
│ │ │ │ └── utils/
│ │ │ ├── res/
│ │ │ └── AndroidManifest.xml
│ │ ├── test/ # Unit tests
│ │ └── androidTest/ # Instrumented tests
│ ├── build.gradle
│ └── proguard-rules.pro
├── build.gradle
└── gradle.propertiesiOS Development (macOS only)
iOS Project Setup
// iOS Project Structure
MyiOSApp/
├── MyiOSApp/
│ ├── Models/ # Data models
│ ├── Views/ # UI components
│ ├── ViewModels/ # MVVM pattern
│ ├── Services/ # API and data services
│ ├── Utilities/ # Helper functions
│ ├── Resources/ # Assets, strings, etc.
│ ├── AppDelegate.swift
│ ├── SceneDelegate.swift
│ └── Info.plist
├── MyiOSAppTests/ # Unit tests
├── MyiOSAppUITests/ # UI tests
└── MyiOSApp.xcodeproj
// Podfile for CocoaPods dependencies
platform :ios, '14.0'
use_frameworks!
target 'MyiOSApp' do
# Networking
pod 'Alamofire', '~> 5.7'
pod 'SDWebImage', '~> 5.17'
# UI
pod 'SnapKit', '~> 5.6'
# Database
pod 'RealmSwift', '~> 10.40'
# Testing
target 'MyiOSAppTests' do
inherit! :search_paths
pod 'Quick', '~> 6.1'
pod 'Nimble', '~> 11.2'
end
endTesting and Debugging
Mobile Testing Setup
// Jest configuration for React Native
// jest.config.js
module.exports = {
preset: 'react-native',
setupFilesAfterEnv: ['<rootDir>/jest.setup.js'],
transformIgnorePatterns: [
'node_modules/(?!(react-native|@react-native|@react-navigation)/)',
],
collectCoverageFrom: [
'src/**/*.{js,jsx,ts,tsx}',
'!src/**/*.d.ts',
'!src/**/*.stories.{js,jsx,ts,tsx}',
],
coverageThreshold: {
global: {
branches: 80,
functions: 80,
lines: 80,
statements: 80,
},
},
};
// jest.setup.js
import 'react-native-gesture-handler/jestSetup';
import mockAsyncStorage from '@react-native-async-storage/async-storage/jest/async-storage-mock';
jest.mock('@react-native-async-storage/async-storage', () => mockAsyncStorage);
// Component test example
// __tests__/components/UserList.test.tsx
import React from 'react';
import { render, fireEvent, waitFor } from '@testing-library/react-native';
import { UserList } from '../src/components/UserList';
const mockUsers = [
{ id: 1, name: 'John Doe', email: 'john@example.com' },
{ id: 2, name: 'Jane Smith', email: 'jane@example.com' },
];
describe('UserList', () => {
it('renders user list correctly', async () => {
const { getByText, getByTestId } = render(
<UserList users={mockUsers} onUserPress={jest.fn()} />
);
await waitFor(() => {
expect(getByText('John Doe')).toBeTruthy();
expect(getByText('Jane Smith')).toBeTruthy();
});
});
it('calls onUserPress when user is tapped', () => {
const onUserPress = jest.fn();
const { getByText } = render(
<UserList users={mockUsers} onUserPress={onUserPress} />
);
fireEvent.press(getByText('John Doe'));
expect(onUserPress).toHaveBeenCalledWith(mockUsers[0]);
});
});
// E2E testing with Detox
// e2e/firstTest.e2e.js
describe('User List Screen', () => {
beforeAll(async () => {
await device.launchApp();
});
beforeEach(async () => {
await device.reloadReactNative();
});
it('should display user list', async () => {
await expect(element(by.text('Users'))).toBeVisible();
await expect(element(by.id('userList'))).toBeVisible();
});
it('should navigate to user detail', async () => {
await element(by.text('John Doe')).tap();
await expect(element(by.text('User Details'))).toBeVisible();
});
});Development Automation
Mobile Development Scripts
#!/bin/bash
# scripts/mobile-dev-setup.sh
# Mobile development environment automation
set -e
PLATFORM="${1:-all}" # react-native, flutter, android, ios, all
echo "📱 Setting up mobile development environment for: $PLATFORM"
setup_react_native() {
echo "⚛️ Setting up React Native environment..."
# Install React Native CLI
npm install -g @react-native-community/cli
npm install -g @expo/cli
# Install development tools
npm install -g react-devtools
npm install -g flipper-pkg
npm install -g reactotron-cli
echo "✅ React Native setup complete"
}
setup_flutter() {
echo "🐦 Setting up Flutter environment..."
# Verify Flutter installation
if command -v flutter &> /dev/null; then
flutter doctor
flutter config --enable-web
flutter config --enable-linux-desktop
flutter config --enable-macos-desktop
flutter config --enable-windows-desktop
else
echo "❌ Flutter not found. Please install Flutter first."
exit 1
fi
echo "✅ Flutter setup complete"
}
setup_android() {
echo "🤖 Setting up Android development..."
# Set Android environment variables
export ANDROID_HOME="$HOME/Android/Sdk"
export PATH="$PATH:$ANDROID_HOME/emulator"
export PATH="$PATH:$ANDROID_HOME/tools"
export PATH="$PATH:$ANDROID_HOME/tools/bin"
export PATH="$PATH:$ANDROID_HOME/platform-tools"
# Create AVD if it doesn't exist
if ! avdmanager list avd | grep -q "DevEx_Pixel_6_API_33"; then
echo "📱 Creating Android Virtual Device..."
avdmanager create avd -n "DevEx_Pixel_6_API_33" \
-k "system-images;android-33;google_apis;x86_64" \
--device "pixel_6"
fi
echo "✅ Android setup complete"
}
setup_ios() {
if [[ "$OSTYPE" == "darwin"* ]]; then
echo "🍎 Setting up iOS development..."
# Install CocoaPods
if ! command -v pod &> /dev/null; then
sudo gem install cocoapods
fi
# Setup pod repo
pod setup
echo "✅ iOS setup complete"
else
echo "ℹ️ iOS development only available on macOS"
fi
}
case $PLATFORM in
"react-native")
setup_react_native
setup_android
setup_ios
;;
"flutter")
setup_flutter
setup_android
setup_ios
;;
"android")
setup_android
;;
"ios")
setup_ios
;;
"all")
setup_react_native
setup_flutter
setup_android
setup_ios
;;
*)
echo "❌ Unknown platform: $PLATFORM"
echo "Usage: $0 [react-native|flutter|android|ios|all]"
exit 1
;;
esac
echo "🎉 Mobile development environment setup complete for $PLATFORM!"Build and Deployment Automation
#!/bin/bash
# scripts/mobile-build.sh
# Automated mobile app building and deployment
set -e
PROJECT_TYPE="${1:-react-native}" # react-native, flutter, android, ios
BUILD_TYPE="${2:-debug}" # debug, release
PLATFORM="${3:-both}" # android, ios, both
echo "🏗️ Building $PROJECT_TYPE app ($BUILD_TYPE) for $PLATFORM"
build_react_native() {
echo "⚛️ Building React Native app..."
if [[ "$PLATFORM" == "android" || "$PLATFORM" == "both" ]]; then
echo "🤖 Building Android..."
if [[ "$BUILD_TYPE" == "release" ]]; then
cd android && ./gradlew assembleRelease && cd ..
else
cd android && ./gradlew assembleDebug && cd ..
fi
fi
if [[ "$PLATFORM" == "ios" || "$PLATFORM" == "both" ]]; then
if [[ "$OSTYPE" == "darwin"* ]]; then
echo "🍎 Building iOS..."
cd ios && pod install && cd ..
if [[ "$BUILD_TYPE" == "release" ]]; then
npx react-native run-ios --configuration Release
else
npx react-native run-ios
fi
else
echo "ℹ️ iOS build skipped (not on macOS)"
fi
fi
}
build_flutter() {
echo "🐦 Building Flutter app..."
if [[ "$PLATFORM" == "android" || "$PLATFORM" == "both" ]]; then
echo "🤖 Building Android..."
if [[ "$BUILD_TYPE" == "release" ]]; then
flutter build apk --release
flutter build appbundle --release
else
flutter build apk --debug
fi
fi
if [[ "$PLATFORM" == "ios" || "$PLATFORM" == "both" ]]; then
if [[ "$OSTYPE" == "darwin"* ]]; then
echo "🍎 Building iOS..."
if [[ "$BUILD_TYPE" == "release" ]]; then
flutter build ios --release
else
flutter build ios --debug
fi
else
echo "ℹ️ iOS build skipped (not on macOS)"
fi
fi
}
case $PROJECT_TYPE in
"react-native")
build_react_native
;;
"flutter")
build_flutter
;;
*)
echo "❌ Unknown project type: $PROJECT_TYPE"
exit 1
;;
esac
echo "✅ Build complete!"Mobile Development Best Practices:
- Cross-Platform Consistency: Use shared business logic and platform-specific UI
- Performance Optimization: Profile and optimize for mobile constraints
- Testing Strategy: Implement unit, integration, and E2E tests
- State Management: Use proper state management solutions (Redux, Riverpod, etc.)
- Security: Implement proper authentication and data encryption
- Offline Support: Design for offline-first functionality
- App Store Guidelines: Follow platform-specific guidelines and policies
- CI/CD: Automate builds, tests, and deployments
This mobile development environment provides comprehensive tooling for building modern mobile applications across React Native, Flutter, and native platforms with proper testing, debugging, and deployment capabilities.