Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[NoQA][CP STAGING][HybridApp] Add Mobile-Expensify submodule and build HybridApp on both platforms #52629

Merged
merged 45 commits into from
Dec 11, 2024
Merged
Show file tree
Hide file tree
Changes from 40 commits
Commits
Show all changes
45 commits
Select commit Hold shift + click to select a range
aa1423d
Add Mobile-Expensify submodule and build HybridApp on both platforms
staszekscp Nov 15, 2024
9a7ec44
Merge main
staszekscp Nov 17, 2024
8d83853
Add bash scripts for HybridApp
staszekscp Nov 18, 2024
0062442
Remove HybridApp-specific patches from Expensify/App
staszekscp Nov 18, 2024
8cdf9fb
Distinguish HybridApp in the applyPatches.sh script
staszekscp Nov 18, 2024
72edef4
Fix postInstall.sh when Mobile-Expensify directory doesn't exist
staszekscp Nov 18, 2024
886d227
Update README.md
staszekscp Nov 18, 2024
e9d89da
Add additional last lines to run-build.shand is-hybrid-app.sh files
staszekscp Nov 19, 2024
10466a5
Update Mobile-Expensify submodule
staszekscp Nov 19, 2024
be40697
Update submodule url
staszekscp Nov 19, 2024
f5c210a
Add bundle install command to pod-install.sh to simplify the initial …
staszekscp Nov 19, 2024
de68ceb
Update submodule commit
staszekscp Nov 19, 2024
ea1dd0e
Fix 'npm run ios' command
staszekscp Nov 20, 2024
51015f5
Update submodule commit
staszekscp Nov 20, 2024
83e3e38
Add improvements to pod-install.sh and run-build.sh scripts
staszekscp Nov 20, 2024
2d88e98
Update submodule commit
staszekscp Nov 20, 2024
03b25ca
Update submodule path to https
staszekscp Nov 20, 2024
3f1068b
Update submodule commit
staszekscp Nov 21, 2024
13c3b1b
Add info where to find correct workspace for AS and XCode
staszekscp Nov 21, 2024
fcbd7b4
Fix the clean.sh script
staszekscp Nov 21, 2024
947e970
Update submodule commit
staszekscp Nov 21, 2024
a17f39c
Add HybridApp troubleshooting section in README.md
staszekscp Nov 21, 2024
158de25
Adjust HybridApp deployment to the added submodule
staszekscp Nov 21, 2024
8244b48
Update submodule commit
staszekscp Nov 21, 2024
56b8924
Merge pull request #141 from software-mansion-labs/feat/hybridapp-dep…
staszekscp Nov 21, 2024
0fdf7c4
Merge branch 'main' into feat/old-dot-submodule
staszekscp Nov 22, 2024
6b631b5
Merge branch 'main' into feat/old-dot-submodule
staszekscp Nov 26, 2024
bbd6009
Fix npm run clean-standalone script
staszekscp Nov 26, 2024
43e9dfb
Update submodule commit
staszekscp Nov 26, 2024
b218c1e
Remove -rostruct flag from deploy.yml
staszekscp Nov 26, 2024
e71007d
Update README.md
staszekscp Nov 26, 2024
9a31329
Fix npm run pod-install-standalone script
staszekscp Nov 28, 2024
d371d3a
Improve logic for pod install command
staszekscp Nov 28, 2024
d0cae08
Update README.md with info how to solve problems with git submodule u…
staszekscp Nov 28, 2024
b92f567
Add relative paths to better explain where the native code lies in Hy…
staszekscp Nov 28, 2024
d026fb3
Remove 'pod repo remove trunk' command from pod-install.sh
staszekscp Nov 28, 2024
bb95e91
Fix standalone NewDot installation step
staszekscp Nov 28, 2024
d2fbff3
Merge branch 'main' into feat/old-dot-submodule
staszekscp Nov 28, 2024
51b54ca
Merge branch 'main' into feat/old-dot-submodule
staszekscp Dec 4, 2024
49183bc
Update submodule commit
staszekscp Dec 5, 2024
793d495
Update submodule and README.md
staszekscp Dec 11, 2024
6479a6d
Merge branch 'main' into feat/old-dot-submodule
staszekscp Dec 11, 2024
621cb78
Update submodule commit
staszekscp Dec 11, 2024
255b634
Remove --repo-update flag from the pod-install script
staszekscp Dec 11, 2024
791dbee
Fix deploy.yml
staszekscp Dec 11, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
43 changes: 7 additions & 36 deletions .github/workflows/deploy.yml
Original file line number Diff line number Diff line change
Expand Up @@ -163,16 +163,11 @@ jobs:
name: Build and deploy Android HybridApp
needs: prep
runs-on: ubuntu-latest-xl
defaults:
run:
working-directory: Mobile-Expensify/react-native
steps:
- name: Checkout
uses: actions/checkout@v4
with:
repository: 'Expensify/Mobile-Expensify'
submodules: true
path: 'Mobile-Expensify'
token: ${{ secrets.OS_BOTIFY_TOKEN }}
# fetch-depth: 0 is required in order to fetch the correct submodule branch
fetch-depth: 0
Expand All @@ -187,19 +182,9 @@ jobs:
- name: Configure MapBox SDK
run: ./scripts/setup-mapbox-sdk.sh ${{ secrets.MAPBOX_SDK_DOWNLOAD_TOKEN }}

- uses: actions/setup-node@v4
with:
node-version-file: 'Mobile-Expensify/react-native/.nvmrc'
cache: npm
cache-dependency-path: 'Mobile-Expensify/react-native'

- name: Install node modules
run: |
npm install
cd .. && npm install

# Fixes https://github.com/Expensify/App/issues/51682
npm run grunt:build:shared
- name: Setup Node
id: setup-node
uses: ./.github/actions/composite/setupNode

- name: Setup Java
uses: actions/setup-java@v4
Expand All @@ -211,7 +196,6 @@ jobs:
uses: ruby/[email protected]
with:
bundler-cache: true
working-directory: 'Mobile-Expensify/react-native'

- name: Install New Expensify Gems
run: bundle install
Expand All @@ -226,7 +210,7 @@ jobs:
op document get --output ./upload-key.keystore upload-key.keystore
op document get --output ./android-fastlane-json-key.json android-fastlane-json-key.json
# Copy the keystore to the Android directory for Fullstory
cp ./upload-key.keystore ../Android
cp ./upload-key.keystore Mobile-Expensify/Android

- name: Load Android upload keystore credentials from 1Password
id: load-credentials
Expand Down Expand Up @@ -481,16 +465,11 @@ jobs:
runs-on: macos-13-xlarge
env:
DEVELOPER_DIR: /Applications/Xcode_15.2.0.app/Contents/Developer
defaults:
run:
working-directory: Mobile-Expensify/react-native
steps:
- name: Checkout
uses: actions/checkout@v4
with:
repository: 'Expensify/Mobile-Expensify'
submodules: true
path: 'Mobile-Expensify'
token: ${{ secrets.OS_BOTIFY_TOKEN }}
# fetch-depth: 0 is required in order to fetch the correct submodule branch
fetch-depth: 0
Expand All @@ -506,22 +485,14 @@ jobs:
run: |
./scripts/setup-mapbox-sdk.sh ${{ secrets.MAPBOX_SDK_DOWNLOAD_TOKEN }}

- uses: actions/setup-node@v4
- name: Setup Node
id: setup-node
with:
node-version-file: 'Mobile-Expensify/react-native/.nvmrc'
cache-dependency-path: 'Mobile-Expensify/react-native'

- name: Install node modules
run: |
npm install
cd .. && npm install
uses: ./.github/actions/composite/setupNode

- name: Setup Ruby
uses: ruby/[email protected]
with:
bundler-cache: true
working-directory: 'Mobile-Expensify/react-native'

- name: Install New Expensify Gems
run: bundle install
Expand All @@ -543,7 +514,7 @@ jobs:
with:
timeout_minutes: 10
max_attempts: 5
command: cd Mobile-Expensify/iOS && pod install
command: npm run pod-install

- name: Install 1Password CLI
uses: 1password/install-cli-action@v1
Expand Down
3 changes: 3 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[submodule "Mobile-Expensify"]
Julesssss marked this conversation as resolved.
Show resolved Hide resolved
path = Mobile-Expensify
url = https://github.com/Expensify/Mobile-Expensify.git
1 change: 1 addition & 0 deletions Mobile-Expensify
Submodule Mobile-Expensify added at 887782
96 changes: 96 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -437,6 +437,102 @@ export default withOnyx({
1. The application uses [`react-navigation`](https://reactnavigation.org/) for navigating between parts of the app.
1. [Higher Order Components](https://reactjs.org/docs/higher-order-components.html) are used to connect React components to persistent storage via [`react-native-onyx`](https://github.com/Expensify/react-native-onyx).

----
# HybridApp

Currently, the production Expensify app contains both "Expensify Classic" and "New Expensify". The file structure is as follows:

- 📂 [**App**](https://github.com/Expensify/App)
- 📂 [**android**](https://github.com/Expensify/App/tree/main/android): New Expensify Android specific code (not a part of HybridApp native code)
- 📂 [**ios**](https://github.com/Expensify/App/tree/main/ios): New Expensify iOS specific code (not a part of HybridApp native code)
- 📂 [**src**](https://github.com/Expensify/App/tree/main/src): New Expensify TypeScript logic
- 📂 [**Mobile-Expensify**](https://github.com/Expensify/Mobile-Expensify): `git` submodule that is pointed to [Mobile-Expensify](https://github.com/Expensify/Mobile-Expensify)
- 📂 [**Android**](https://github.com/Expensify/Mobile-Expensify/tree/main/Android): Expensify Classic Android specific code
- 📂 [**iOS**](https://github.com/Expensify/Mobile-Expensify/tree/main/iOS): Expensify Classic iOS specific code
- 📂 [**app**](https://github.com/Expensify/Mobile-Expensify/tree/main/app): Expensify Classic JavaScript logic (aka YAPL)

You can only build HybridApp if you have been granted access to [`Mobile-Expensify`](https://github.com/Expensify/Mobile-Expensify). For most contributors, you will be working on the standalone NewDot application.

## Getting started with HybridApp

1. If you haven't, please follow [these instructions](https://github.com/Expensify/App?tab=readme-ov-file#getting-started) to setup the NewDot local environment.
2. Run `git submodule update --init` to download the `Mobile-Expensify` sourcecode.
- If you have access to `Mobile-Expensify` and the command fails with a https-related error add this to your `~/.gitconfig` file:

```
[url "ssh://[email protected]/"]
insteadOf = https://github.com/
```

At this point, the default behavior of some `npm` scripts will change to target HybridApp:
- `npm run android` - build HybridApp for Android
- `npm run ios` - build HybridApp for iOS
- `npm run ipad` - build HybridApp for iPad
- `npm run ipad-sm` - build HybridApp for small iPad
- `npm run pod-install` - install pods for HybridApp
- `npm run clean` - clean native code of HybridApp

If for some reason, you need to target the standalone NewDot application, you can append `*-standalone` to each of these scripts (eg. `npm run ios-standalone` will build NewDot instead of HybridApp).

## Working with HybridApp
Day-to-day work with HybridApp shouldn't differ much from the work on the standalone NewDot repo.

The main difference is that the native code which runs React Native is located in `./Mobile-Expensify/Android` and `./Mobile-Expensify/iOS` directories. It means, that changes in `./android` and `./ios` folders in the root **won't affect the HybridApp build**.

In that case, if you'd like to eg. remove `Pods`, you need to do it in `./Mobile-Expensify/iOS`. The same rule applies to Android builds - if you'd like to delete `.cxx`, `build` or `.gradle` directories, you need to go to `./Mobile-Expensify/android` first.

Additionally, If you'd like to open the HybridApp project in Android Studio or XCode, you **must choose a workspace located in the `Mobile-Expensify`** directory:

- Android: `./Mobile-Expensify/Android`
- iOS: `./Mobile-Expensify/iOS/Expensify.xcworkspace`

### Updating the Mobile-Expensify submodule

`Mobile-Expensify` directory is a git submodule. It means, that it points to a specific commit on the `Mobile-Expensify` repository. If you'd like to download the most recent changes from `main`, please use the following command:

`git submodule update --remote`

### Modifying Mobile-Expensify code

It's important to emphasise that a git submodule is just a **regular git repository** after all. It means that you can switch branches, pull the newest changes, and execute all regular git commands within the `Mobile-Expensify` directory.

> [!Note]
> #### For external contributors
>
> If you'd like to modify the `Mobile-Expensify` source code, it is best that you create your own fork. Then, you can swap origin of the remote repository by executing this command:
>
Comment on lines +502 to +503
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we are ready to merge this, are we making the OldApp repo public too now?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Mobile-Expensify will remain private for now

> `cd Mobile-Expensify && git remote set-url origin <YOUR_FORK_URL>`
>
> This way, you'll attach the submodule to your fork repository.

### Adding HybridApp-related patches

Applying patches from the `patches` directory is performed automatically with the `npm install` command executed in `Expensify/App`.

If you'd like to add HybridApp-specific patches, use the `--patch-dir` flag:

`npx patch-package <PACKAGE_NAME> --patch-dir Mobile-Expensify/patches`

### HybridApp troubleshooting

#### Cleaning the repo
- `npm run clean` - deep clean of all HybridApp artifacts (including NewDot's `node_modules`)
- `npm run clean -- --ios` - clean only iOS HybridApp artifacts (`Pods`, `build` folder, `DerivedData`)
- `npm run clean -- --android` - clean only Android HybridApp artifacts (`.cxx`, `build`, and `.gradle` folders, execute `./gradlew clean`)

If you'd like to do it manually, remember to `cd Mobile-Expensify` first!

#### Common errors
1. **Please check your internet connection** - set `_isOnDev` in `api.js` to always return `false`
2. **CDN: trunk URL couldn't be downloaded** - `cd Mobile-Expensify && pod repo remove trunk`

3. **Task :validateSigningRelease FAILED** - open `Mobile-Expensify/Android/build.gradle` and do the following:
```
- signingConfig signingConfigs.release
+ signingConfig signingConfigs.debug
```
4. **Build service could not create build operation: unknown error while handling message: MsgHandlingError(message: "unable to initiate PIF transfer session (operation in progress?)")** - reopen XCode

----

# Philosophy
Expand Down
16 changes: 8 additions & 8 deletions fastlane/Fastfile
Original file line number Diff line number Diff line change
Expand Up @@ -71,9 +71,9 @@ platform :android do

desc "Generate a production HybridApp AAB"
lane :build_hybrid do
ENV["ENVFILE"]="../.env.production.hybridapp"
ENV["ENVFILE"]="Mobile-Expensify/.env.production.hybridapp"
gradle(
project_dir: '../Android',
project_dir: 'Mobile-Expensify/Android',
task: "bundleRelease",
flags: "--refresh-dependencies",
properties: {
Expand Down Expand Up @@ -118,7 +118,7 @@ platform :android do
lane :build_local_hybrid do
ENV["ENVFILE"]=".env.production"
gradle(
project_dir: '../Android',
project_dir: 'Mobile-Expensify/Android',
task: 'assemble',
flavor: 'Production',
build_type: 'Release',
Expand Down Expand Up @@ -377,7 +377,7 @@ platform :ios do

desc "Build an iOS HybridApp production build"
lane :build_hybrid do
ENV["ENVFILE"]="../.env.production.hybridapp"
ENV["ENVFILE"]="Mobile-Expensify/.env.production.hybridapp"

setupIOSSigningCertificate()

Expand All @@ -394,7 +394,7 @@ platform :ios do
)

build_app(
workspace: "../iOS/Expensify.xcworkspace",
workspace: "Mobile-Expensify/iOS/Expensify.xcworkspace",
scheme: "Expensify",
output_name: "Expensify.ipa",
export_method: "app-store",
Expand Down Expand Up @@ -423,9 +423,9 @@ platform :ios do

desc "Build an unsigned iOS HybridApp production build"
lane :build_unsigned_hybrid do
ENV["ENVFILE"]="../Mobile-Expensify/.env.production.hybridapp"
ENV["ENVFILE"]="./Mobile-Expensify/.env.production.hybridapp"
build_app(
workspace: "../Mobile-Expensify/iOS/Expensify.xcworkspace",
workspace: "./Mobile-Expensify/iOS/Expensify.xcworkspace",
scheme: "Expensify"
)
setIOSBuildOutputsInEnv()
Expand Down Expand Up @@ -542,7 +542,7 @@ platform :ios do
dsym_path: ENV[KEY_DSYM_PATH],
gsp_path: "./ios/GoogleService-Info.plist",
# Assuming we are running this from the react-native submodule directory for HybridApp
binary_path: "../iOS/Pods/FirebaseCrashlytics/upload-symbols"
binary_path: "./Mobile-Expensify/iOS/Pods/FirebaseCrashlytics/upload-symbols"
)
end

Expand Down
2 changes: 2 additions & 0 deletions ios/Podfile
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ require File.join(File.dirname(`node --print "require.resolve('expo/package.json
# This value is used by $RNMapboxMaps
$RNMapboxMapsImpl = 'mapbox'
$VCDisableFrameProcessors = true
ENV['PROJECT_ROOT_PATH'] = "./";

def node_require(script)
# Resolve script with node to allow for hoisting
Expand Down Expand Up @@ -82,6 +83,7 @@ target 'NewExpensify' do
# ENV Variable enables/disables TurboModules
ENV['RCT_NEW_ARCH_ENABLED'] = '1';


use_react_native!(
:path => config[:reactNativePath],
# An absolute path to your application root.
Expand Down
2 changes: 1 addition & 1 deletion ios/Podfile.lock
Original file line number Diff line number Diff line change
Expand Up @@ -3290,6 +3290,6 @@ SPEC CHECKSUMS:
VisionCamera: c95a8ad535f527562be1fb05fb2fd324578e769c
Yoga: a1d7895431387402a674fd0d1c04ec85e87909b8

PODFILE CHECKSUM: 15e2f095b9c80d658459723edf84005a6867debf
PODFILE CHECKSUM: 615266329434ea4a994dccf622008a2197313c88

COCOAPODS: 1.15.2
16 changes: 11 additions & 5 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,18 @@
"setupNewDotWebForEmulators": "./scripts/setup-newdot-web-emulators.sh",
"startAndroidEmulator": "./scripts/start-android.sh",
"postinstall": "./scripts/postInstall.sh",
"clean": "npx react-native clean-project-auto",
"android": "./scripts/set-pusher-suffix.sh && npx react-native run-android --mode=developmentDebug --appId=com.expensify.chat.dev --active-arch-only",
"ios": "./scripts/set-pusher-suffix.sh && npx react-native run-ios --list-devices --mode=\"DebugDevelopment\" --scheme=\"New Expensify Dev\"",
"clean": "./scripts/clean.sh",
"clean-standalone": "./scripts/clean.sh --new-dot",
"android": "./scripts/set-pusher-suffix.sh && ./scripts/run-build.sh --android",
"android-standalone": "./scripts/set-pusher-suffix.sh && ./scripts/run-build.sh --android --new-dot",
"ios": "./scripts/set-pusher-suffix.sh && ./scripts/run-build.sh --ios",
"ios-standalone": "./scripts/set-pusher-suffix.sh && ./scripts/run-build.sh --ios --new-dot",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we do isHybridApp ? ios : ios-standalone? So users don't have to choose manually? Or does run-build handle this already?

Copy link
Contributor Author

@staszekscp staszekscp Nov 19, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If someone has access to Mobile-Expensify, the run-build command builds HybridApp by default - for Expesnify/App contributors nothing changes, the command will build a standalone NewDot.

I added the npm run ios-standalone for HybridApp devs that would need to build the "original", greenfield version of NewDot. I consider it a bit simpler than invoking the command with some additional flags. I don't think it'll be used frequently, but I wanted to add this option for anyone that wants to do that 😄

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm just checking in here. This seems reasonable, but I want to confirm where the switch logic is for future reference before marking this thread resolved.

"pod-install": "./scripts/pod-install.sh",
"ipad": "concurrently \"npx react-native run-ios --simulator=\\\"iPad Pro (12.9-inch) (6th generation)\\\" --mode=\\\"DebugDevelopment\\\" --scheme=\\\"New Expensify Dev\\\"\"",
"ipad-sm": "concurrently \"npx react-native run-ios --simulator=\\\"iPad Pro (11-inch) (4th generation)\\\" --mode=\\\"DebugDevelopment\\\" --scheme=\\\"New Expensify Dev\\\"\"",
"pod-install-standalone": "./scripts/pod-install.sh --new-dot",
"ipad": "concurrently \"./scripts/run-build.sh --ipad\"",
"ipad-standalone": "concurrently \"./scripts/run-build.sh --ipad --new-dot\"",
"ipad-sm": "concurrently \"./scripts/run-build.sh --ipad-sm\"",
"ipad-sm-standalone": "concurrently \"./scripts/run-build.sh --ipad-sm --new-dot\"",
"start": "npx react-native start",
"web": "./scripts/set-pusher-suffix.sh && concurrently npm:web-proxy npm:web-server",
"web-proxy": "ts-node web/proxy.ts",
Expand Down
2 changes: 1 addition & 1 deletion patches/@onfido+react-native-sdk+10.6.0.patch
Original file line number Diff line number Diff line change
Expand Up @@ -1252,7 +1252,7 @@ index a9de0d0..da83d9f 100644
- s.dependency "Onfido", "~> 29.6.0"
+ s.dependency "Onfido", "~> 29.7.0"
+
+ if ENV['USE_FRAMEWORKS'] == '1'
+ if ENV['USE_FRAMEWORKS'] != nil
+ s.pod_target_xcconfig = {
+ "OTHER_CFLAGS" => "$(inherited) -DUSE_FRAMEWORKS",
+ "OTHER_CPLUSPLUSFLAGS" => "$(inherited) -DUSE_FRAMEWORKS",
Expand Down

This file was deleted.

Loading
Loading