Appsilon / rhino

Build high quality, enterprise-grade Shiny apps at speed
https://appsilon.github.io/rhino
278 stars 24 forks source link

Auto-reload functionality when there are changes in R, JS, CSS/SCSS files #552

Open aswansyahputra opened 5 months ago

aswansyahputra commented 5 months ago

Motivation

I feel it quite cumbersome to have to manually restart the app when developing an app. Could be there any simple way?

Feature description

Perhaps a rhino::dev() function to run the app and watch for changes in R, JS, and SCSS/CSS files. Restart the app automatically to reflect any changes.

Implementation ideas

Utilize nodemon and npm-run-all nodejs package to achieve this goal. Lately I put this package.json snippet in app root directory:

{
  "private": true,
  "scripts": {
    "dev": "npm-run-all --parallel build-js:watch build-sass:watch run-rhino",
    "run-rhino": "nodemon --exec \"Rscript -e 'shiny::runApp(port = 3838)'\" --signal SIGTERM",
    "build-js:watch": "npm --prefix .rhino run build-js -- --watch",
    "build-sass:watch": "npm --prefix .rhino run build-sass -- --watch"
  },
  "nodemonConfig": {
    "watch": [
      "app/main.R",
      "app/logic/",
      "app/view/",
      "app/static/"
    ],
    "ext": "*"
  },
  "devDependencies": {
    "nodemon": "^3.0.3",
    "npm-run-all": "^4.1.5"
  }
}

Then run npm install once. Now I only need to run npm run install in terminal for my {rhino}-app development.

I think it's better to optionally put this config into .rhino directory instead and wrap the npm run dev into an R function to be accessible from R console.

Impact

This feature will undoubtedly revolutionize the daily work of Shiny developers.

Comments

No response

aswansyahputra commented 5 months ago

Perhaps these snippets would do:

{
  "scripts": {
    "dev": "npm-run-all --parallel build-js:watch build-sass:watch run-rhino",
    "run-rhino": "cd .. && nodemon --exec \"Rscript -e 'shiny::runApp(port = 3838)'\" --signal SIGTERM",
    "build-js:watch": "npm run build-js -- --watch",
    "build-sass:watch": "npm run build-sass -- --watch",
    "build-js": "webpack",
    "build-sass": "sass --no-source-map --style=compressed ../app/styles/main.scss:../app/static/css/app.min.css",
    "lint-js": "eslint --config .eslintrc.json ../app/js",
    "lint-sass": "stylelint ../app/styles",
    "run-app": "cd .. && Rscript -e \"shiny::runApp(port = 3333)\"",
    "run-cypress": "cypress run --project ../tests",
    "open-cypress": "cypress open --project ../tests",
    "test-e2e": "start-server-and-test run-app http://localhost:3333 run-cypress",
    "test-e2e-interactive": "start-server-and-test run-app http://localhost:3333 open-cypress"
  },
  "nodemonConfig": {
    "watch": [
      "../app/main.R",
      "../app/logic/",
      "../app/view/",
      "../app/static/"
    ],
    "ext": "*"
  },
  "devDependencies": {
    "nodemon": "^3.0.3",
    "npm-run-all": "^4.1.5",
    "@babel/core": "^7.15.5",
    "@babel/eslint-parser": "^7.15.4",
    "@babel/preset-env": "^7.15.4",
    "@babel/preset-react": "^7.22.3",
    "babel-loader": "^8.2.2",
    "cypress": "^7.6.0",
    "eslint": "^7.32.0",
    "eslint-config-airbnb": "^19.0.4",
    "eslint-import-resolver-webpack": "^0.13.1",
    "eslint-plugin-import": "^2.24.2",
    "sass": "^1.39.0",
    "start-server-and-test": "^1.12.6",
    "stylelint": "^13.13.1",
    "stylelint-config-standard": "^22.0.0",
    "stylelint-scss": "^3.20.1",
    "webpack": "^5.52.0",
    "webpack-cli": "^4.8.0"
  }
}
kamilzyla commented 5 months ago

Thank you so much @aswansyahputra for your proposal! I love that you included a concrete, working idea for implementation. :100: :tada:

It came just at the right time, as we are looking into making shiny.autoreload work with Rhino. It seems to have some benefits compared to restarting the whole R with nodemon:

  1. It should be somewhat faster.
  2. You won't need to manually refresh the app page.

But I do love the idea of using npm-run-all and having rhino::dev(). I will be working on it in the following days :slightly_smiling_face:

aswansyahputra commented 5 months ago

Thank you for your kind words, @kamilzyla! I'm so delighted to hear your positive feedback.

My team and I are eager to use this feature in the near future, and I'm confident that other R users would also appreciate its addition in {rhino}. :tada: