diff --git a/docs/en/docs-nav.json b/docs/en/docs-nav.json index d9e3fee2f8..bbb1e53eaa 100644 --- a/docs/en/docs-nav.json +++ b/docs/en/docs-nav.json @@ -1966,6 +1966,22 @@ "path": "framework/ui/react-native", "isIndex": true }, + { + "text": "Running on Web", + "path": "framework/ui/react-native/running-on-web.md" + }, + { + "text": "Running on Device", + "path": "framework/ui/react-native/running-on-device.md" + }, + { + "text": "Manual Backend Configuration", + "path": "framework/ui/react-native/manual-backend-configuration.md" + }, + { + "text": "Android Emulator Setup", + "path": "framework/ui/react-native/setting-up-android-emulator.md" + }, { "text": "Styling with NativeWind", "path": "framework/ui/react-native/styling-with-nativewind.md" diff --git a/docs/en/framework/ui/react-native/index.md b/docs/en/framework/ui/react-native/index.md index c0957d5426..def2ac125c 100644 --- a/docs/en/framework/ui/react-native/index.md +++ b/docs/en/framework/ui/react-native/index.md @@ -1,25 +1,30 @@ ```json //[doc-seo] { - "Description": "Learn how to set up your development environment for React Native with ABP Framework, enabling seamless mobile app integration!" + "Description": "Learn how to set up your development environment for React Native with ABP Framework, enabling seamless mobile app integration!" } ``` ```json -//[doc-params] +//[doc-nav] { - "Architecture": ["Monolith", "Tiered", "Microservice"] + "Next": { + "Name": "Running on Web", + "Path": "framework/ui/react-native/running-on-web" + } } ``` # Getting Started with React Native -> The React Native mobile option is *available for* ***Team*** *or higher licenses* +> The React Native mobile option is _available for_ **_Team_** _or higher licenses_ The ABP platform provides a basic [React Native](https://reactnative.dev/) startup template to develop mobile applications **integrated with your ABP-based backends**. > The startup template UI is built with **[NativeWind v4](https://www.nativewind.dev/)** (Tailwind CSS for React Native) on top of a shadcn-inspired neutral palette, with full **light/dark mode** support. See [Styling with NativeWind](styling-with-nativewind.md) for the styling system reference. +React Native startup template running on a mobile emulator + ## How to Prepare Development Environment Please follow the steps below to prepare your development environment for React Native. @@ -27,10 +32,8 @@ Please follow the steps below to prepare your development environment for React 1. **Install Node.js:** Visit the [Node.js downloads page](https://nodejs.org/en/download/) and download the appropriate Node.js v20.11+ installer for your operating system. Alternatively, you can install [NVM](https://github.com/nvm-sh/nvm) to manage multiple versions of Node.js on your system. 2. **[Optional] Install Yarn:** You can install Yarn v1 (not v2) by following the instructions on [the installation page](https://classic.yarnpkg.com/en/docs/install). Yarn v1 provides a better developer experience compared to npm v6 and below. You can skip this step and use npm, which is built into Node.js. 3. **[Optional] Install VS Code:** [VS Code](https://code.visualstudio.com/) is a free, open-source IDE that works seamlessly with TypeScript. While you can use any IDE, including Visual Studio or Rider, VS Code typically provides the best developer experience for React Native projects. -4. **[Optional] Install an Emulator/Simulator:** If you want to test on Android emulators or iOS simulators (instead of using the Web View method), you'll need to install one of the following: - - **Android Studio & Emulator:** Install [Android Studio](https://developer.android.com/studio) and set up an Android Virtual Device (AVD) through the AVD Manager. You can follow the [Android Studio Emulator guide](https://docs.expo.dev/workflow/android-studio-emulator/) on expo.io documentation. - - **Xcode & iOS Simulator:** On macOS, install [Xcode](https://developer.apple.com/xcode/) from the App Store, which includes the iOS Simulator. You can follow the [iOS Simulator guide](https://docs.expo.dev/workflow/ios-simulator/) on expo.io documentation. - > **Note:** The Web View method (recommended for quick testing) doesn't require an emulator or simulator. If you prefer a CLI-based approach for Android, you can check the [setting up android emulator without android studio](setting-up-android-emulator.md) guide as an alternative. + +Additional tools depend on how you plan to run the app — see the [Run the application](#run-the-application) section below. ## How to Start a New React Native Project @@ -38,9 +41,21 @@ You have multiple options to initiate a new React Native project that works with ### 1. Using ABP Studio -ABP Studio is the most convenient and flexible way to create a React Native application based on the ABP framework. Follow the [tool documentation](../../../studio) and select the option below: +ABP Studio is the most convenient and flexible way to create a React Native application based on the ABP framework. Follow the [tool documentation](../../../studio) and select the mobile option in the solution wizard: + +
+ +
+ABP Studio modern template — Mobile Application on Application Type step +

Modern template — on the Application Type step, enable Mobile Application (React Native with Expo).

+
+ +
+ABP Studio classic template — React Native on Mobile Framework step +

Classic template — on the Mobile Framework step, select React Native.

+
-React Native option +
### 2. Using ABP CLI @@ -54,106 +69,48 @@ abp new MyCompanyName.MyProjectName -csf -u -m react-native This command creates a solution containing an **Angular** or **MVC** project (depending on your choice), a **.NET Core** project, and a **React Native** project. -## Running the React Native Application - -> **Recommended:** For faster development and testing, we recommend using the **Web View** option first, as it requires fewer backend modifications. The backend configuration described in the next section is only needed if you want to test on Android emulators or iOS simulators. - -Before running the React Native application, install the dependencies by running `yarn install` or `npm install` in the `react-native` directory. - -### Web View (Recommended - Quickest Method) - -The quickest way to test the application is by using the web view. While testing on a physical device is also supported, we recommend using [local HTTPS development](https://docs.expo.dev/guides/local-https-development/) as it requires fewer backend modifications. - -Follow these steps to set up the web view: - -1. Navigate to the `react-native` directory and start the application by running: - ```bash - yarn web - ``` -2. Generate SSL certificates by running the following command in a separate directory: - ```bash - mkcert localhost - ``` -3. Set up the local proxy by running: - ```bash - yarn create:local-proxy - ``` - The default port is `443`. To use a different port, specify the `SOURCE_PORT` environment variable: -4. If you changed the port in the previous step, update the `apiUrl` in `Environment.ts` accordingly. -5. Update the mobile application settings in the database and re-run the migrations. If you specified a custom port, ensure the port is updated in the configuration as well: - ```json - "OpenIddict": { - "Applications": { - "MyApplication_Mobile": { - "ClientId": "MyApplication_Mobile", - "RootUrl": "https://localhost" - } - } - } - ``` - -### Running on Emulator/Simulator - -If you prefer to test on an Android emulator or iOS simulator, you'll need to configure the backend as described in the section below. Follow these steps: - -1. Make sure the [database migration is complete](../../../get-started?UI=NG&DB=EF&Tiered=No#create-the-database) and the [API is up and running](../../../get-started?UI=NG&DB=EF&Tiered=No#run-the-application). -2. Open `react-native` folder and run `yarn install` or `npm install` if you have not already. -3. Open the `Environment.ts` file in the `react-native` folder and replace the `localhost` address in the `apiUrl` and `issuer` properties with your local IP address as shown below: - -{{ if Architecture == "Monolith" }} - -react native monolith environment local IP - -{{ else if Architecture == "Tiered" }} - -react native tiered environment local IP - -> Make sure that `issuer` matches the running address of the `.AuthServer` project, `apiUrl` matches the running address of the `.HttpApi.Host` or `.Web` project. - -{{ else }} - -react native microservice environment local IP +## Run the Application -> Make sure that `issuer` matches the running address of the `.AuthServer` project, `apiUrl` matches the running address of the `.AuthServer` project. +You can choose how you want to run the mobile app: -{{ end }} +| Goal | Documentation | +| ------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| **Browser testing (fastest)** | [Running on Web](./running-on-web.md) — ABP Studio **Default** profile or Expo Web + HTTPS proxy at `https://localhost:8443` | +| **Emulator, simulator, or physical device** | [Running on Device](./running-on-device.md) — **Pro, non-tiered Monolith:** **MobileEmulator** profile or `yarn tunnel:api`; **Tiered / Microservice:** manual backend setup | -1. Run `yarn start` or `npm start`. Wait for the Expo CLI to print the options. +> **Before device testing (Monolith):** Install **cloudflared** using Cloudflare's [Download and install cloudflared](https://developers.cloudflare.com/cloudflare-one/networks/connectors/cloudflare-tunnel/downloads/) guide. The template's Quick Tunnel workflow does not require a Cloudflare account or the remaining steps in that document. -> The React Native application was generated with [Expo](https://expo.io/). Expo is a set of tools built around React Native to help you quickly start an app, and it includes many features. +Before running, you may need to install dependencies in the React Native project folder: -expo-cli-options +- **Monolith / Tiered / app-nolayers:** `react-native/` +- **Microservice:** `apps/mobile/react-native/` -In the image above, you can start the application on an Android emulator, an iOS simulator, or a physical phone by scanning the QR code with the [Expo Client](https://expo.io/tools#client) or by choosing the corresponding option. +Run `yarn install` or `npm install` in that folder. -### Expo +> **Recommended:** We suggest starting with [Running on Web](./running-on-web.md). Because it requires the fewest setup steps and provides faster development and hot-reload options compared to the physical device tests. -Press **i** to open the iOS simulator, or scan the QR code from the Expo CLI with your phone to run on a physical device. +### Related guides -### Android Studio +- [Manual Backend Configuration](./manual-backend-configuration.md): This includes a fallback HTTP/local IP setup for Tiered or Microservice architectures (or when Cloudflare tunnels are unavailable). +- [Setting Up Android Emulator Without Android Studio](./setting-up-android-emulator.md): This covers the CLI-based Android emulator setup based on your preference. -1. Start the emulator in **Android Studio** before running the `yarn start` or `npm start` command. -2. Press **a** to open in Android Studio. +The default login credentials, if not changed, are: -React Native login screen - -Enter **admin** as the username and **1q2w3E** as the password to log in to the application. - -The application is up and running. You can continue to develop your application based on this startup template. +- User name: **admin** +- Password: **1q2w3E\*** ## Navigation The startup template ships with **two navigation styles**, switchable when the project is created: -- **Bottom Tab** — *the default* — three tabs at the bottom of the screen: **Home**, **Settings** and **Account**. +- **Bottom Tab** — _the default_ — three tabs at the bottom of the screen: **Home**, **Settings** and **Account**. - **Drawer** — a side menu (hamburger) with two items: **Home** and **Settings**. Bottom Tab vs Drawer navigation comparison - Every main tab or drawer item is wired to **its own** native stack (`@react-navigation/native-stack`). Pushing more screens stays on that branch: the Back stack belongs to that tab or drawer route and does not mix with others. Bottom Tab and Drawer use the **same screen components**; they differ in how those screens are grouped and opened from the outer shell (and where the sign‑in/sign‑up flow lives in Bottom Tab versus Drawer). -> **How to choose:** The mode is selected in **ABP Studio** during the *Mobile Framework* step. Switching modes after the project is generated is not a one-line change — you would need to add the missing navigator (and its `@react-navigation/drawer` or `@react-navigation/bottom-tabs` dependency) manually, then update `src/AppContainer.tsx` and `src/navigators/types.ts` to match. Pick the mode upfront when possible. +> **How to choose:** The mode is selected in **ABP Studio** during the _Mobile Framework_ step. Switching modes after the project is generated is not a one-line change — you would need to add the missing navigator (and its `@react-navigation/drawer` or `@react-navigation/bottom-tabs` dependency) manually, then update `src/AppContainer.tsx` and `src/navigators/types.ts` to match. Pick the mode upfront when possible. ### Bottom Tab Navigation (default) @@ -161,7 +118,7 @@ The root navigator is `BottomTabNavigator` (`src/navigators/BottomTabNavigator.t - **HomeTab** → `HomeNavigator` → `HomeScreen` (hero greeting + feature cards). - **SettingsTab** → `SettingsNavigator` → `SettingsScreen` (language, theme, profile/password shortcuts). -- **AccountTab** → `AccountNavigator` — *conditional stack* based on the authentication state read from Redux: +- **AccountTab** → `AccountNavigator` — _conditional stack_ based on the authentication state read from Redux: - **Authenticated:** `AccountScreen` → `ChangePasswordScreen`, `ProfilePictureScreen`. - **Guest:** `LoginScreen` → `RegisterScreen`, `ForgotPasswordScreen`, `ResetPasswordScreen`. @@ -205,213 +162,6 @@ To add a screen to either navigation mode: 2. Register it as a `Stack.Screen` inside the appropriate navigator (e.g. `HomeNavigator`, `SettingsNavigator`, or `AccountNavigator`). 3. Add the route to the matching `*ParamList` in `src/navigators/types.ts` so the screen props stay typed. -If the new screen needs to appear at the *root* level (a new tab or drawer item rather than a child of an existing stack), edit `BottomTabNavigator.tsx` or `DrawerNavigator.tsx` and update the corresponding `BottomTabParamList` / `RootDrawerParamList` type. - -## How to Configure & Run the Backend (Required for Emulator/Simulator Testing) - -> React Native application does not trust the auto-generated .NET HTTPS certificate. You should use **HTTP** during the development. - -To disable the HTTPS-only settings of OpenIddict, open the {{ if Architecture == "Monolith" }}`MyProjectNameHttpApiHostModule`{{ else if Architecture == "Tiered" }}`MyProjectNameAuthServerModule`{{ end }} project and add the following code block to the `PreConfigureServices` method: - -```csharp -#if DEBUG - PreConfigure(options => - { - options.UseAspNetCore() - .DisableTransportSecurityRequirement(); - }); -#endif -``` - -> **Important:** Before running the backend application, make sure you have completed the [database migration](../../../get-started?UI=NG&DB=EF&Tiered=No#create-the-database) if you are starting with a fresh database. The backend application requires the database to be properly initialized. - -A React Native application running on an Android emulator or a physical phone **cannot connect to the backend** on `localhost`. To resolve this, you need to run the backend application using the `Kestrel` configuration. - -{{ if Architecture == "Monolith" }} - -React Native monolith host project configuration - -- Open the `appsettings.json` file in the `.DbMigrator` folder. Replace the `localhost` address in the `RootUrl` property with your local IP address. Then, run the database migrator. -- Open the `appsettings.Development.json` file in the `.HttpApi.Host` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. - ```json - { - "Kestrel": { - "Endpoints": { - "Http": { - "Url": "http://0.0.0.0:44323" //replace with your host port - } - } - } - } - ``` - -{{ else if Architecture == "Tiered" }} - -React Native tiered project configuration - -- Open the `appsettings.json` file in the `.DbMigrator` folder. Replace the `localhost` address in the `RootUrl` property with your local IP address. Then, run the database migrator. -- Open the `appsettings.Development.json` file in the `.AuthServer` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. - ```json - { - "Kestrel": { - "Endpoints": { - "Http": { - "Url": "http://0.0.0.0:44337" - } - } - } - } - ``` -- Open the `appsettings.Development.json` file in the `.HttpApi.Host` folder. Add this configuration to accept global requests. Additionally, you need to configure the authentication server as mentioned above. - ```json - { - "Kestrel": { - "Endpoints": { - "Http": { - "Url": "http://0.0.0.0:44389" //replace with your host port - } - } - }, - "AuthServer": { - "Authority": "http://192.168.1.37:44337/", //replace with your IP and authentication port - "MetaAddress": "http://192.168.1.37:44337/", - "RequireHttpsMetadata": false, - "Audience": "MyTieredProject" //replace with your application name - } - } - ``` - -{{ else if Architecture == "Microservice" }} - -React Native microservice project configuration - -- Open the `appsettings.Development.json` file in the `.AuthServer` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. - ```json - { - "App": { - "EnablePII": true - }, - "Kestrel": { - "Endpoints": { - "Http": { - "Url": "http://0.0.0.0:44319" - } - } - } - } - ``` -- Open the `appsettings.Development.json` file in the `.AdministrationService` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. You should also provide the authentication server configuration. Additionally, you need to apply the same process for all services you will use in the React Native application. - ```json - { - "App": { - "EnablePII": true - }, - "Kestrel": { - "Endpoints": { - "Http": { - "Url": "http://0.0.0.0:44357" - } - } - }, - "AuthServer": { - "Authority": "http://192.168.1.36:44319/", - "MetaAddress": "http://192.168.1.36:44319/", - "RequireHttpsMetadata": false, - "Audience": "AdministrationService" - } - } - ``` -- Update the `appsettings.json` file in the `.IdentityService` folder. Replace the `localhost` configuration with your local IP address for the React Native application. - ```json - { - //... - "OpenIddict": { - "Applications": { - //... - "ReactNative": { - "RootUrl": "exp://192.168.1.36:19000" - }, - "MobileGateway": { - "RootUrl": "http://192.168.1.36:44347/" - } - //... - } - //... - } - } - ``` -- Finally, update the mobile gateway configurations as follows: - ```json - //gateways/mobile/MyMicroserviceProject.MobileGateway/Properties/launchSettings.json - { - "iisSettings": { - "windowsAuthentication": false, - "anonymousAuthentication": true, - "iisExpress": { - "applicationUrl": "http://192.168.1.36:44347" //update with your IP address - } - }, - "profiles": { - //... - "MyMicroserviceProject.MobileGateway": { - "commandName": "Project", - "dotnetRunMessages": "true", - "launchBrowser": true, - "applicationUrl": "http://192.168.1.36:44347", - "environmentVariables": { - "ASPNETCORE_ENVIRONMENT": "Development" - } - } - } - } - ``` - ```json - //gateways/mobile/MyMicroserviceProject.MobileGateway/appsettings.json - { - //Update clusters with your IP address - //... - "ReverseProxy": { - //... - "Clusters": { - "AuthServer": { - "Destinations": { - "AuthServer": { - "Address": "http://192.168.1.36:44319/" - } - } - }, - "Administration": { - "Destinations": { - "Administration": { - "Address": "http://192.168.1.36:44357/" - } - } - }, - "Saas": { - "Destinations": { - "Saas": { - "Address": "http://192.168.1.36:44330/" - } - } - }, - "Identity": { - "Destinations": { - "Identity": { - "Address": "http://192.168.1.36:44397/" - } - } - }, - "Language": { - "Destinations": { - "Identity": { - "Address": "http://192.168.1.36:44310/" - } - } - } - } - } - } - ``` - {{ end }} +If the new screen needs to appear at the _root_ level (a new tab or drawer item rather than a child of an existing stack), edit `BottomTabNavigator.tsx` or `DrawerNavigator.tsx` and update the corresponding `BottomTabParamList` / `RootDrawerParamList` type. -Run the backend application(s) as described in the [getting started document](../../../get-started). \ No newline at end of file +The application is up and running. You can continue to develop your application based on this startup template, or follow the [Book Store mobile tutorial](../../../tutorials/mobile/react-native/index.md). diff --git a/docs/en/framework/ui/react-native/manual-backend-configuration.md b/docs/en/framework/ui/react-native/manual-backend-configuration.md new file mode 100644 index 0000000000..0285aa3423 --- /dev/null +++ b/docs/en/framework/ui/react-native/manual-backend-configuration.md @@ -0,0 +1,258 @@ +```json +//[doc-seo] +{ + "Description": "Configure your ABP backend for React Native emulator and device testing using local IP addresses and HTTP when Cloudflare tunnels are unavailable." +} +``` + +```json +//[doc-params] +{ + "Architecture": ["Monolith", "Tiered", "Microservice"] +} +``` + +```json +//[doc-nav] +{ + "Previous": { + "Name": "Running on Device", + "Path": "framework/ui/react-native/running-on-device" + } +} +``` + +# Manual Backend Configuration + +> **When to use this guide:** We recommend this fallback when you cannot use the [Cloudflare tunnel](./running-on-device.md#cloudflare-tunnel-manual-cli) workflow — for example, on **Tiered** or **Microservice** templates (which do not include `tunnel.js`), when corporate firewalls block `cloudflared`, or when developing fully offline. + +> **Prefer simpler options first:** +> +> - Browser testing → [Running on Web](./running-on-web.md) (no backend changes) +> - Pro, non-tiered Monolith on emulator/device → [Running on Device](./running-on-device.md) with `yarn tunnel:api` or the **MobileEmulator** profile + +> React Native does not trust the auto-generated .NET HTTPS certificate. Use **HTTP** during this manual workflow. + +{{ if Architecture == "Monolith" }} + +To disable the HTTPS-only settings of OpenIddict, open the `MyProjectNameHttpApiHostModule` project and add the following code block to the `PreConfigureServices` method: + +```csharp +#if DEBUG + PreConfigure(options => + { + options.UseAspNetCore() + .DisableTransportSecurityRequirement(); + }); +#endif +``` + +{{ else if Architecture == "Tiered" }} + +To disable the HTTPS-only settings of OpenIddict, open the `MyProjectNameAuthServerModule` project and add the following code block to the `PreConfigureServices` method: + +```csharp +#if DEBUG + PreConfigure(options => + { + options.UseAspNetCore() + .DisableTransportSecurityRequirement(); + }); +#endif +``` + +{{ end }} + +> **Important:** Before running the backend application, make sure you have completed the [database migration](../../../get-started?UI=NG&DB=EF&Tiered=No#create-the-database) if you are starting with a fresh database. + +A React Native application running on an Android emulator or a physical phone **cannot connect to the backend** on `localhost`. Bind the backend to `0.0.0.0` so it accepts requests from your local network, then update `Environment.ts` with your local IP address. + +{{ if Architecture == "Monolith" }} + +- Open the `appsettings.json` file in the `.DbMigrator` folder. Replace the `localhost` address in the `RootUrl` property with your local IP address. Then, run the database migrator. +- Open the `appsettings.Development.json` file in the `.HttpApi.Host` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. + ```json + { + "Kestrel": { + "Endpoints": { + "Http": { + "Url": "http://0.0.0.0:44323" //replace with your host port + } + } + } + } + ``` + +Update `react-native/Environment.ts` with your local IP address instead of `localhost`, then start Expo as described in [Running on Device](./running-on-device.md). + +{{ else if Architecture == "Tiered" }} + +- Open the `appsettings.json` file in the `.DbMigrator` folder. Replace the `localhost` address in the `RootUrl` property with your local IP address. Then, run the database migrator. +- Open the `appsettings.Development.json` file in the `.AuthServer` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. + ```json + { + "Kestrel": { + "Endpoints": { + "Http": { + "Url": "http://0.0.0.0:44337" + } + } + } + } + ``` +- Open the `appsettings.Development.json` file in the `.HttpApi.Host` folder. Add this configuration to accept global requests. Additionally, configure the authentication server as mentioned above. + ```json + { + "Kestrel": { + "Endpoints": { + "Http": { + "Url": "http://0.0.0.0:44389" //replace with your host port + } + } + }, + "AuthServer": { + "Authority": "http://192.168.1.37:44337/", //replace with your IP and authentication port + "MetaAddress": "http://192.168.1.37:44337/", + "RequireHttpsMetadata": false, + "Audience": "MyTieredProject" //replace with your application name + } + } + ``` + +Update `react-native/Environment.ts` with your local IP address, then start Expo as described in [Running on Device](./running-on-device.md). + +{{ else if Architecture == "Microservice" }} + +- Open the `appsettings.Development.json` file in the `.AuthServer` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. + ```json + { + "App": { + "EnablePII": true + }, + "Kestrel": { + "Endpoints": { + "Http": { + "Url": "http://0.0.0.0:44319" + } + } + } + } + ``` +- Open the `appsettings.Development.json` file in the `.AdministrationService` folder. Add this configuration to accept global requests for testing the React Native application in the development environment. You should also provide the authentication server configuration. Additionally, apply the same process for all services you will use in the React Native application. + ```json + { + "App": { + "EnablePII": true + }, + "Kestrel": { + "Endpoints": { + "Http": { + "Url": "http://0.0.0.0:44357" + } + } + }, + "AuthServer": { + "Authority": "http://192.168.1.36:44319/", + "MetaAddress": "http://192.168.1.36:44319/", + "RequireHttpsMetadata": false, + "Audience": "AdministrationService" + } + } + ``` +- Update the `appsettings.json` file in the `.IdentityService` folder. Replace the `localhost` configuration with your local IP address for the React Native application. + ```json + { + //... + "OpenIddict": { + "Applications": { + //... + "ReactNative": { + "RootUrl": "exp://192.168.1.36:19000" + }, + "MobileGateway": { + "RootUrl": "http://192.168.1.36:44347/" + } + //... + } + //... + } + } + ``` +- Finally, update the mobile gateway configurations as follows: + ```json + //gateways/mobile/MyMicroserviceProject.MobileGateway/Properties/launchSettings.json + { + "iisSettings": { + "windowsAuthentication": false, + "anonymousAuthentication": true, + "iisExpress": { + "applicationUrl": "http://192.168.1.36:44347" //update with your IP address + } + }, + "profiles": { + //... + "MyMicroserviceProject.MobileGateway": { + "commandName": "Project", + "dotnetRunMessages": "true", + "launchBrowser": true, + "applicationUrl": "http://192.168.1.36:44347", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "Development" + } + } + } + } + ``` + ```json + //gateways/mobile/MyMicroserviceProject.MobileGateway/appsettings.json + { + //Update clusters with your IP address + //... + "ReverseProxy": { + //... + "Clusters": { + "AuthServer": { + "Destinations": { + "AuthServer": { + "Address": "http://192.168.1.36:44319/" + } + } + }, + "Administration": { + "Destinations": { + "Administration": { + "Address": "http://192.168.1.36:44357/" + } + } + }, + "Saas": { + "Destinations": { + "Saas": { + "Address": "http://192.168.1.36:44330/" + } + } + }, + "Identity": { + "Destinations": { + "Identity": { + "Address": "http://192.168.1.36:44397/" + } + } + }, + "Language": { + "Destinations": { + "Language": { + "Address": "http://192.168.1.36:44310/" + } + } + } + } + } + } + ``` + +Update `apps/mobile/react-native/Environment.ts` with your local IP address, then start Expo as described in [Running on Device](./running-on-device.md). + +{{ end }} + +Run the backend application(s) as described in the [getting started document](../../../get-started). diff --git a/docs/en/framework/ui/react-native/running-on-device.md b/docs/en/framework/ui/react-native/running-on-device.md new file mode 100644 index 0000000000..0b45f7a4a4 --- /dev/null +++ b/docs/en/framework/ui/react-native/running-on-device.md @@ -0,0 +1,201 @@ +```json +//[doc-seo] +{ + "Description": "Run your ABP React Native application on an Android emulator, iOS simulator, or physical device using ABP Studio or Cloudflare tunnel." +} +``` + +```json +//[doc-nav] +{ + "Previous": { + "Name": "Running on Web", + "Path": "framework/ui/react-native/running-on-web" + }, + "Next": { + "Name": "Manual Backend Configuration", + "Path": "framework/ui/react-native/manual-backend-configuration" + } +} +``` + +```json +//[doc-params] +{ + "Architecture": ["Monolith", "Tiered", "Microservice"] +} +``` + +# Running on a Device + +You can use this guide when you want to run the app on an **Android emulator**, **iOS simulator**, or **physical device** instead of in the browser. + +For browser testing, see [Running on Web](./running-on-web.md). + +## Prerequisites + +1. Install dependencies in the React Native project folder: + +{{ if Architecture == "Microservice" }} + +- `apps/mobile/react-native/` + +{{ else }} + +- `react-native/` + +{{ end }} + +2. Complete the [database migration](../../../get-started?UI=NG&DB=EF&Tiered=No#create-the-database) and ensure the backend host is running. +3. Set up an emulator or simulator if needed: + - **Android:** [Android Studio Emulator guide](https://docs.expo.dev/workflow/android-studio-emulator/) or [Setting Up Android Emulator Without Android Studio](./setting-up-android-emulator.md) + - **iOS (macOS):** [iOS Simulator guide](https://docs.expo.dev/workflow/ios-simulator/) + +{{ if Architecture == "Monolith" }} + +1. Install **cloudflared** before using the **MobileEmulator** profile or `yarn tunnel:api`. Follow Cloudflare's [Download and install cloudflared](https://developers.cloudflare.com/cloudflare-one/networks/connectors/cloudflare-tunnel/downloads/) guide. The template uses free Quick Tunnels (`*.trycloudflare.com`) and does not require a Cloudflare account or the remaining locally-managed tunnel steps in that document. + +{{ end }} + +## Using ABP Studio + +{{ if Architecture == "Monolith" }} + +### MobileEmulator profile (Recommended) + +**Pro, non-tiered Monolith** solutions include a **MobileEmulator** run profile in the [Solution Runner](../../../studio/running-applications). When you start it, ABP Studio specifically runs: + +1. The backend host +2. **ReactNativeTunnel** — runs `node scripts/tunnel.js` to expose your local backend through a Cloudflare tunnel +3. **ReactNative** — runs `npx expo start --android` (change the `--android` flag to `--ios` in `MobileEmulator.abprun.json` or via the profile edit option in Solution Runner) + +Before the first run: + +1. [Install cloudflared](https://developers.cloudflare.com/cloudflare-one/networks/connectors/cloudflare-tunnel/downloads/) if you have not already (see [Prerequisites](#prerequisites)). +2. Switch to the **MobileEmulator** profile in the Solution Runner. +3. Open `react-native/Environment.ts` and follow the inline comments: **uncomment the tunnel configuration block** and **comment out the localhost constants**. + +Start an Android emulator (or connect a device), then start the **MobileEmulator** profile. + +ABP Studio Solution Runner with MobileEmulator profile selected + +See [Cloudflare tunnel (manual CLI)](#cloudflare-tunnel-manual-cli) below for what the tunnel script does, and [Automate Localhost Access for Expo](https://abp.io/community/articles/automate-localhost-access-for-expo-a-guide-to-dynamic-7cblqtj3) for architecture details and troubleshooting. + +{{ else if Architecture == "Tiered" }} + +> **Note:** The **MobileEmulator** run profile is available only for **Pro, non-tiered** solutions. For tiered architectures, follow [Manual Backend Configuration](./manual-backend-configuration.md) and the [manual CLI steps](#manual-cli-without-mobileemulator-profile) below. + +{{ else }} + +> **Note:** The **MobileEmulator** run profile is not included in the microservice template. Follow [Manual Backend Configuration](./manual-backend-configuration.md) and the [manual CLI steps](#manual-cli-without-mobileemulator-profile) below. + +{{ end }} + +## Cloudflare tunnel (manual CLI) + +{{ if Architecture == "Monolith" }} + +Non-tiered React Native templates ship with a Cloudflare tunnel automation script. The tunnel gives your mobile app a temporary **HTTPS** URL (for example `https://example.trycloudflare.com`) that forwards to your local backend — without reconfiguring Kestrel or OpenIddict over HTTP. + +> **Prerequisite:** Install **cloudflared** on your machine using Cloudflare's [Download and install cloudflared](https://developers.cloudflare.com/cloudflare-one/networks/connectors/cloudflare-tunnel/downloads/) guide before running `yarn tunnel:api` or the **MobileEmulator** profile. + +The template includes: + +| Item | Location | +| ------------------ | ------------------------------------------------------ | +| Tunnel script | `react-native/scripts/tunnel.js` | +| npm script | `yarn tunnel:api` (runs `node scripts/tunnel.js`) | +| Generated config | `react-native/tunnel-config.json` (created at runtime) | +| Environment switch | Inline comments in `react-native/Environment.ts` | + +When `tunnel.js` runs, it: + +1. Starts `cloudflared tunnel --url https://localhost:{api-port}` (port matches your backend host). +2. Captures the generated `*.trycloudflare.com` domain from the `cloudflared` output. +3. Writes `tunnel-config.json` and updates the fallback value in `Environment.ts`. + +### Steps + +1. **Switch `Environment.ts` to tunnel mode.** Open `react-native/Environment.ts` and follow the inline comments: + - **Uncomment** the tunnel configuration block (the block that reads `tunnel-config.json`). + - **Comment out** the localhost `apiUrl` / `appUrl` constants. +2. **Start the backend host** if it is not already running. +3. **Start the tunnel** from the `react-native` folder: + +```bash +yarn tunnel:api +``` + +Or: + +```bash +npm run tunnel:api +``` + +Wait until the script prints `✓ Tunnel domain saved`. + +4. **Start Expo** in a separate terminal: + +```bash +yarn start +``` + +5. Start your Android emulator, iOS simulator, or connect a physical device. + +> **With ABP Studio:** The **MobileEmulator** run profile performs steps 2–4 for you after you update `Environment.ts`. + +See [Automate Localhost Access for Expo](https://abp.io/community/articles/automate-localhost-access-for-expo-a-guide-to-dynamic-7cblqtj3) for OAuth redirect considerations, troubleshooting, and development-build guidance. + +If Cloudflare tunnels are unavailable, use [Manual Backend Configuration](./manual-backend-configuration.md) as a fallback. + +{{ else if Architecture == "Tiered" }} + +Tiered templates do not include `tunnel.js` or the `tunnel:api` script. Configure the backend using [Manual Backend Configuration](./manual-backend-configuration.md), or adapt the [Cloudflare tunnel guide](https://abp.io/community/articles/automate-localhost-access-for-expo-a-guide-to-dynamic-7cblqtj3) for your auth server and API host ports. + +{{ else }} + +Microservice templates do not include `tunnel.js` or the `tunnel:api` script. Configure the backend using [Manual Backend Configuration](./manual-backend-configuration.md), or adapt the [Cloudflare tunnel guide](https://abp.io/community/articles/automate-localhost-access-for-expo-a-guide-to-dynamic-7cblqtj3) for your auth server and mobile gateway ports. + +{{ end }} + +## Manual CLI (without MobileEmulator profile) + +{{ if Architecture == "Monolith" }} + +If you are not using the **MobileEmulator** profile, prefer the [Cloudflare tunnel workflow](#cloudflare-tunnel-manual-cli) above. Only use [Manual Backend Configuration](./manual-backend-configuration.md) when tunnels are unavailable. + +{{ else }} + +1. Configure the backend as described in [Manual Backend Configuration](./manual-backend-configuration.md). +2. Open the `Environment.ts` file in the React Native folder and replace the `localhost` address in the `apiUrl` and `issuer` properties with your local IP address: + +{{ if Architecture == "Tiered" }} + +> Make sure that `issuer` matches the running address of the `.AuthServer` project, and `apiUrl` matches the running address of the `.HttpApi.Host` or `.Web` project. + +{{ else }} + +> Make sure that `issuer` matches the running address of the `.AuthServer` project, and `apiUrl` matches the running address of the mobile gateway. + +{{ end }} + +1. Run `yarn start`, `yarn android`, or `yarn ios`. + +{{ end }} + +> The React Native application was generated with [Expo](https://expo.io/). Expo is a set of tools built around React Native to help you quickly start an app, and it includes many features. + +Expo CLI showing QR code and platform launch options + +You can start the application on an Android emulator, an iOS simulator, or a physical phone by scanning the QR code or by choosing the corresponding option in the Expo CLI. + +Enter **admin** as the username and **1q2w3E\*** as the password to log in to the application. + +### Android Studio + +1. Start the emulator in **Android Studio** before running `yarn start`, `yarn android`, or `npm start`. +2. Press **a** in the Expo CLI to open on Android. + +### iOS Simulator + +1. Press **i** in the Expo CLI to open the iOS simulator (macOS only). diff --git a/docs/en/framework/ui/react-native/running-on-web.md b/docs/en/framework/ui/react-native/running-on-web.md new file mode 100644 index 0000000000..60286f51af --- /dev/null +++ b/docs/en/framework/ui/react-native/running-on-web.md @@ -0,0 +1,116 @@ +```json +//[doc-seo] +{ + "Description": "Run your ABP React Native application in the browser using ABP Studio or Expo Web with local HTTPS." +} +``` + +```json +//[doc-params] +{ + "Architecture": ["Monolith", "Tiered", "Microservice"] +} +``` + +```json +//[doc-nav] +{ + "Previous": { + "Name": "Overview", + "Path": "framework/ui/react-native" + }, + "Next": { + "Name": "Running on Device", + "Path": "framework/ui/react-native/running-on-device" + } +} +``` + +# Running on Web + +Running the React Native app in a browser is the **fastest way to test** login, navigation, and API integrations. No emulator, Cloudflare tunnel, or manual backend configuration is required. + +## React Native project folder + +{{ if Architecture == "Microservice" }} + +- `apps/mobile/react-native/` + +{{ else }} + +- `react-native/` + +{{ end }} + +Install dependencies once with `yarn install` or `npm install` in that folder. + +## Using ABP Studio (Recommended) + +Solutions created with ABP Studio include a **Default** run profile in the [Solution Runner](../../../studio/running-applications). + +{{ if Architecture == "Monolith" }} + +React Native Default Profile + +{{ else if Architecture == "Tiered" }} + +React Native Default Profile + +{{ else }} + +React Native Default Profile + +{{ end }} + +### One-time setup: Initialize Solution + +Run the **Initialize Solution** task from the **Tasks** tab if you have not already. For React Native solutions, this task also creates local SSL certificates (`localhost.pem` and `localhost-key.pem`) in the React Native folder using [mkcert](https://github.com/FiloSottile/mkcert). These certificates are required by the **Default** profile's local SSL proxy. + +### Start the Default profile + +When you start the **Default** profile, ABP Studio runs these main applications: + +1. The backend host +2. **ReactNative.LocalSslProxy** — terminates HTTPS on **`https://localhost:8443`** and forwards to Expo Web on port `8081` +3. **ReactNative** — runs `npx expo start --web` and opens **`https://localhost:8443`** in your browser + +The solution template already adds `https://localhost:8443` to backend **CorsOrigins** and **RedirectAllowedUrls**, so no manual backend configuration is required. + +{{ if Architecture != "Microservice" }} + +React Native Web ABP Studio + +{{ end }} + +You can enter **admin** as the username and **1q2w3E\*** as the password to log in. + +## Manual setup (without ABP Studio) + +If you are not using ABP Studio, use Expo Web with a local HTTPS proxy as described in the [Expo local HTTPS development guide](https://docs.expo.dev/guides/local-https-development/). + +1. Navigate to the React Native folder and install dependencies if you have not already. +2. Generate SSL certificates in the React Native folder: + +```bash +mkcert localhost +``` + +3. Start Expo Web: + +```bash +yarn web +``` + +4. In a separate terminal, start the local SSL proxy (port `8443` matches the ABP Studio Default profile): + +```bash +npx local-ssl-proxy --source 8443 --target 8081 --cert localhost.pem --key localhost-key.pem +``` + +Alternatively, run `yarn create:local-proxy` and set `SOURCE_PORT=8443` if your template uses a different default port. + +1. Open **`https://localhost:8443`** in your browser. + +## Next steps + +To test on an Android emulator, iOS simulator, or physical device, continue with [Running on Device](./running-on-device.md). diff --git a/docs/en/framework/ui/react-native/setting-up-android-emulator.md b/docs/en/framework/ui/react-native/setting-up-android-emulator.md index 495197a0da..963c6d5b92 100644 --- a/docs/en/framework/ui/react-native/setting-up-android-emulator.md +++ b/docs/en/framework/ui/react-native/setting-up-android-emulator.md @@ -5,6 +5,16 @@ } ``` +````json +//[doc-nav] +{ + "Previous": { + "Name": "Running on Device", + "Path": "framework/ui/react-native/running-on-device" + } +} +```` + # Setting Up Android Emulator Without Android Studio (Windows, macOS, Linux) This guide walks you through installing and running an Android emulator **without Android Studio**, using only the **Android Command Line Tools**. diff --git a/docs/en/images/react-native-app.gif b/docs/en/images/react-native-app.gif new file mode 100644 index 0000000000..7cf95f932d Binary files /dev/null and b/docs/en/images/react-native-app.gif differ diff --git a/docs/en/images/rn-default-profile.png b/docs/en/images/rn-default-profile.png new file mode 100644 index 0000000000..eda9871dfc Binary files /dev/null and b/docs/en/images/rn-default-profile.png differ diff --git a/docs/en/images/rn-expo-qr.png b/docs/en/images/rn-expo-qr.png new file mode 100644 index 0000000000..e651d73888 Binary files /dev/null and b/docs/en/images/rn-expo-qr.png differ diff --git a/docs/en/images/rn-microservice-default-profile.png b/docs/en/images/rn-microservice-default-profile.png new file mode 100644 index 0000000000..e5859c3971 Binary files /dev/null and b/docs/en/images/rn-microservice-default-profile.png differ diff --git a/docs/en/images/rn-mobileEmulator-profile.png b/docs/en/images/rn-mobileEmulator-profile.png new file mode 100644 index 0000000000..2824413950 Binary files /dev/null and b/docs/en/images/rn-mobileEmulator-profile.png differ diff --git a/docs/en/images/rn-select-legacy.png b/docs/en/images/rn-select-legacy.png new file mode 100644 index 0000000000..d50b7f396b Binary files /dev/null and b/docs/en/images/rn-select-legacy.png differ diff --git a/docs/en/images/rn-select-modern.png b/docs/en/images/rn-select-modern.png new file mode 100644 index 0000000000..1b301fadde Binary files /dev/null and b/docs/en/images/rn-select-modern.png differ diff --git a/docs/en/images/rn-tiered-default-profile.png b/docs/en/images/rn-tiered-default-profile.png new file mode 100644 index 0000000000..54e63f81ca Binary files /dev/null and b/docs/en/images/rn-tiered-default-profile.png differ diff --git a/docs/en/images/rn-web-studio.png b/docs/en/images/rn-web-studio.png new file mode 100644 index 0000000000..81561a92ec Binary files /dev/null and b/docs/en/images/rn-web-studio.png differ diff --git a/docs/en/tutorials/mobile/react-native/index.md b/docs/en/tutorials/mobile/react-native/index.md index 5e97b6274a..db41615d98 100644 --- a/docs/en/tutorials/mobile/react-native/index.md +++ b/docs/en/tutorials/mobile/react-native/index.md @@ -1,13 +1,13 @@ ```json //[doc-seo] { - "Description": "Learn how to develop a mobile application using React Native with the ABP Framework. Build the Acme.BookStore mobile UI on top of the modernized ABP React Native template (NativeWind v4 + Bottom Tab navigation)." + "Description": "Learn how to develop a mobile application using React Native with the ABP Framework. Build the Acme.BookStore mobile UI on top of the modernized ABP React Native template (NativeWind v4 + Bottom Tab navigation)." } ``` # Mobile Application Development Tutorial - React Native -The React Native mobile option is *available for* ***Team*** *or higher licenses*. If you don't have a commercial license, follow this article by downloading the source code of the sample application linked below. +The React Native mobile option is _available for_ **_Team_** _or higher licenses_. If you don't have a commercial license, follow this article by downloading the source code of the sample application linked below. ## About This Tutorial @@ -18,6 +18,16 @@ The React Native mobile option is *available for* ***Team*** *or higher licenses - The mobile template was modernized in 2026: it now uses **NativeWind v4** (Tailwind CSS for React Native) for styling, **Bottom Tab navigation** by default, and the **Redux Toolkit** store with hook-based access (`useSelector` / `useDispatch`). The `connectToRedux` HOC, the `DrawerNavigator`, and the legacy `DataList`/`AbpSelect` components from earlier versions no longer ship with the template — this tutorial walks through building the new equivalents. - Before starting, please make sure that the [React Native Development Environment](../../../framework/ui/react-native/index.md) is ready on your machine. +## Running the Application + +Before implementing UI changes, run the `Acme.BookStore` mobile application and verify that login works: + +1. Open the solution in **ABP Studio** and run the **Initialize Solution** task once (creates SSL certificates and other one-time setup). +2. For browser testing, follow [Running on Web](../../../framework/ui/react-native/running-on-web.md) — start the **Default** run profile; ABP Studio opens the app at **`https://localhost:8443`**. +3. For an Android emulator or iOS simulator, follow [Running on Device](../../../framework/ui/react-native/running-on-device.md). The sample is a **Pro, non-tiered Monolith** solution — switch to the **MobileEmulator** run profile, update `react-native/Environment.ts`, and start the profile (or run `yarn tunnel:api` manually). For **Tiered** or **Microservice** solutions, use the manual backend steps in that guide instead. + +See the [React Native overview](../../../framework/ui/react-native/index.md) for environment setup and project creation. + ## Download the Source Code You can use the following link to download the source code of the application described in this article: @@ -1059,6 +1069,7 @@ function CreateUpdateBookForm({ submit, book, authors }: CreateUpdateBookFormPro }} /> + {/* Publish date modal */} setDateModalVisible(false)}> setDateModalVisible(false)} className="flex-1 bg-black/50 items-center justify-center px-6"> @@ -1239,7 +1250,6 @@ function CreateUpdateAuthorScreen({ navigation, route }: CreateUpdateAuthorScree })(); return () => { cancelled = true; }; }, [authorId, dispatch]); - const submit = async (data: AuthorFormValues) => { dispatch(LoadingActions.start({ key: 'save' })); try {