nxext / nx-extensions

Nx Extensions for Stencil, Svelte, SolidJS, Preact, Ionic, and Capacitor
MIT License
463 stars 102 forks source link

React: Capacitor live reload not working #773

Open johnnyBira opened 2 years ago

johnnyBira commented 2 years ago

I have setup Ionic React in my NX workspace using the @nxext/ionic-react generator and have successfully added iOS as one of my target platforms. What is not clear to from the docs of @nxext/ionic-react is how to get a development environment with livereload in the iOS Simulator working.

I have tried the following command which does start the simulator as expected

nx run client:cap --cmd="run ios -l --external"

however the process exists immediately after the project is built and the simulator is started.

I have setup Ionic with Capacitor in a non NX environment before, and from this experience the expected behaviour is for the process to stay alive and livereload the app which is running in the simulator.

What am I missing

johnnyBira commented 2 years ago

I guess it's related to this issue in the old repository? https://github.com/nxtend-team/nxtend/issues/304

Is this still the suggested workaround still relevant or is there another solution?

DominikPieper commented 2 years ago

@johnnyBira they’re technically the same plugins but for Nx 14. We migrated them over and continue here together. But no further bug fixing here until now so probably the same bug. Sorry I can’t help more for now 😅

johnnyBira commented 2 years ago

@DominikPieper that's too bad 😓 This means there's pretty much no viable development environment at the moment.

johnnyBira commented 2 years ago

I was finally able to follow the steps in the workaround above. React configs was slightly different from the suggested Angular recipe. Will post my workaround for React later tonight

johnnyBira commented 2 years ago

My current recipe is sceptic to iOS, but I'm sure it can be extended to include other platforms:

  1. Your current IP and add to capacitor-config.ts. packages/{package-name}/capacitor-config.ts
    
    import { CapacitorConfig } from '@capacitor/cli';

const config: CapacitorConfig = { appId: '{app-id}', appName: '{app-name}', webDir: '../../dist/packages/{package-name}', bundledWebRuntime: false, server: { url: '{your-current-ip}:4200', cleartext: true, }, };

export default config;

2. Update `project.json` with the following config:
`/package/{package-name}/project.json`
``` json
}
    "serve": {
      "executor": "@nrwl/web:dev-server",
      "defaultConfiguration": "development",
      "options": {
        "buildTarget": "client:build",
        "hmr": true,
        "browserTarget": "project:build",
        "host": "0.0.0.0"
      }
}
  1. Start the dev server:
    nx run {package-name}:serve
  2. Start simulator:

    Using Capacitor

    nx run {package-name}:cap -cmd "run ios -l --external" Or do what I did and create a shorthand in project.json:

    {
    "cap": {
      "executor": "@nxext/capacitor:cap",
      "options": {
        "cmd": "--help"
      },
      "configurations": {
        "ios": {
          "cmd": "run ios -l --external"
        }
      }
    }

    Now you can run this to start the iOS simulator instead:

    nx run {project-name}:cap:ios

    Using XCode

    Run:

    nx run {project-name}:open:ios

    This will open Xcode, where you can click the play button to start the app in your selected simulator

b3h3m0th commented 2 years ago

@johnnyBira Thank you so much, finally a solution that worked for me! For anybody else wondering how to configure the server.url: I used the ip package which helps you dynamically setting that value like so:

import { CapacitorConfig } from '@capacitor/cli';
import ip from 'ip';

const config: CapacitorConfig = {
  appId: '{app-id}',
  appName: '{app-name}',
  webDir: '../../dist/apps/{app-name}',
  bundledWebRuntime: false,
  server: {
    url: `http://${ip.address()}:4200`,
    cleartext: true,
  },
};

export default config;
mvaljento commented 1 year ago

My run command (@nxext/capacitor:ca) exits immediately. I'm trying to integrate a Capacitor Angular app to my monorepo. Do I need to be running also the "serve" command in the background?

deving1995 commented 1 year ago

I was able to do this for android, albeit it's weird, and I'm not sure if it's really reliable for how an app would actually behave on android. I did it slightly different than @johnnyBira along with the ip plugin mentioned by @b3h3m0th

My capacitor.config.ts file (remember to replace fieldpak and fieldclient with your app):

import { CapacitorConfig } from '@capacitor/cli';
import ip from 'ip';

const config: CapacitorConfig = {
  appId: 'com.fieldpak.fieldclient',
  appName: 'field-client',
  webDir: '../../dist/apps/field-client',
  bundledWebRuntime: false,
  server: {
    androidScheme: 'https',
    url: `http://${ip.address()}:4200`,
    cleartext: true
  },
};

export default config;

I did not use the @nrwl/web:dev-server as an executor for serve in project.json, I left it with the @angular-devkit/build-angular:dev-server that was already there as the @nrwl/web:dev-server or @nx/web:dev-server executors were being weird.

And I simply added the options with hmr and host

"serve": {
  "executor": "@angular-devkit/build-angular:dev-server",
  "configurations": {
    "production": {
      "browserTarget": "field-client:build:production"
     },
     "development": {
       "browserTarget": "field-client:build:development"
     }
  },
  "defaultConfiguration": "development",
  "options": {
    "hmr": true,
     "host": "0.0.0.0"
  }
},

As for actually having this run with live reload.... this is where it gets weird

I serve the app with nx run {package-name}:serve, and then I run the capacitor android app. The app came up blank on my device, so I went and inspected it in chrome://inspect/devices#devices and eventually the blank screen turned into an error page, and there were no console logs.

But then, I realized I could try typing into the url bar at the top of the device inspection window. I thought maybe "localhost:4200", or "0.0.0.0:4200" but neither worked, so then I did an ipconfig to get my ip address and put that in with port 4200 and well ah, when I make changes to the source code the app is reloaded on the device with the changes.

image