Auto generate a build number in SPA



  • Hi. I was wondering if it is possible to auto-generate a build number each time I build my quasar SPA app? I would like to have that available to be displayed in the app’s “About” info. I know I could do it manually but I wondered whether there is a built-in way to do that.
    Searching the docs did not yield an answer that I could find.
    Thanks. I am very new to Quasar and Vue and am loving it.
    Murray



  • @murrah you can use quasar.conf.js in build time like this:

    module.exports = function (ctx) {
      ...
      ctx.dev['BUILD_NUMBER']=<my_generated_build_number>
    

    … and in app, at runtime, you can access that like this:

      console.log(process.env.BUILD_NUMBER)
    

    more here:
    https://quasar.dev/quasar-cli/handling-process-env

    you can also use htmlVariables - more here:
    https://quasar.dev/quasar-cli/quasar-conf-js#Property%3A-htmlVariables



  • @murrah I’ve done it based on the git hash like this (in quasar.conf.js)

    const GitRevisionPlugin = require('git-revision-webpack-plugin')
    const version = JSON.stringify(new GitRevisionPlugin().version())
    
    module.exports = function (ctx) {
      return {
        // ...
    
        build: {
          env: {
            VERSION: version
          },
          // ...
        }
      }
    }
    

    And use process.env.VERSION somewhere in your about screen.



  • @beets

    Nice idea! But what guaranties that you haven’t changed your code ( after the (latest) git commit when you build you app to deploy?

    Like a check if git’s staging area is empty.



  • @dobbel said in Auto generate a build number in SPA:

    But what guaranties that you haven’t changed your code ( after the (latest) git commit when you build you app to deploy?

    Your conscious? 🙂 Basically it’s for you to decide.

    In my case it is just a date and time of build, for @beets it may be last commit hash / branch, for you it may be something incremental, for somebody using CI/CD or else it may be something compound like <build-machine>-<hash>-<date>-<time>.



  • @qyloxe

    I understand, just wondering if @beets has a solution for his specific git hash way of creating a version number.



  • @dobbel I don’t check if there’s uncommitted files. I suppose you could (if there’s not already a solution) use node to call git and throw an error in quasar.conf, but it should just be habbit to make sure all files are pushed to the repo before you make a build that you will deploy. If you build on the target machine at least, there shouldn’t be any uncommitted files. Plus it probably also works well with automatically deployment schemes, CI, etc.



  • @qyloxe Thanks. I was looking for something that generated the build number itself.



  • @beets Aha… I didn’t know about that git-revision-webpack-plugin. Thanks, I will look at that. Much appreciated.



  • So, just to complete this…
    I ended up going with semver and using the patch as the build number because all I really wanted was to auto generate a new version number to display to users in the app. Since I am pretty new to all this I didn’t realise npm version could be leveraged to auto-update the version in package.json.

    So when I am ready to release a new version I run my simple batch file:

    npm version patch
    quasar build
    

    In my app, on the .vue file that displays the version number (simplified and adjust your relative path):

    import { version } from '../../package.json'
    export default {
      data () {
        return {
          appVersion: version
        }
      }
    }
    

    In the template (eg):

    <div>v{{ appVersion }}</div>
    

    Thanks,
    Murray



  • @murrah dark and twisted solution 🙂 me likey



  • I also do something similar. I built out our build system at work, and pipe info to files that is used later.

    BRANCH=`git rev-parse --abbrev-ref HEAD`
    echo $BRANCH > ../../database/revision/branch.var
    
    COMMITS=`git rev-list --count HEAD`
    echo $COMMITS > ../../database/revision/commits.var
    

    You can pipe to a JSON file if you wish and import it directly into your app.



  • Here’s the consuming code for our installer:

    // ------------------------------------------------------------------
    // Get version
    // ex: 5.0.0
    let versionNumber = fs.readFileSync('../../database/revision/version.var').toString()
    // allow only numbers and period
    versionNumber = versionNumber.replace(/[^0-9.]/g, '')
    console.log('Version:', versionNumber)
    // ------------------------------------------------------------------
    
    // ------------------------------------------------------------------
    // Get build
    // ex: 48
    let buildNumber = fs.readFileSync('../../database/revision/build.var').toString()
    // allow only numbers
    buildNumber = buildNumber.replace(/[^0-9]/g, '')
    console.log('Build number:', buildNumber)
    // ------------------------------------------------------------------
    
    // ------------------------------------------------------------------
    // Get commit
    // ex: 1198
    let commitNumber = fs.readFileSync('../../database/revision/commits.var').toString()
    // allow only numbers
    commitNumber = commitNumber.replace(/[^0-9]/g, '')
    console.log('Commit number:', commitNumber)
    // ------------------------------------------------------------------
    
    // ------------------------------------------------------------------
    // Get branch
    // ex: 'origin/develop' or 'develop'
    let branchString = fs.readFileSync('../../database/revision/branch.var').toString()
    branchString = branchString.replace(/[\n\r]/g, '');
    if (branchString.indexOf('/') > -1) {
      branchString = branchString.split('/')
      branchString = `${branchString[0]}.${branchString[1]}`
    }
    console.log('Branch:', branchString)
    // ------------------------------------------------------------------
    
    // ------------------------------------------------------------------
    // Get release
    // ex: 'Alpha|Beta|RC|Release'
    let releaseString = fs.readFileSync('../../database/revision/release.var').toString()
    releaseString = releaseString.replace(/[\n\r]/g, '');
    console.log('Release:', releaseString)
    // ------------------------------------------------------------------
    
    // ------------------------------------------------------------------
    // Get buildhost
    // ex: host name
    let buildHostString = fs.readFileSync('../../database/revision/hostname.var').toString()
    buildHostString = buildHostString.replace(/[\n\r]/g, '');
    console.log('Build Host:', buildHostString)
    // ------------------------------------------------------------------
    


  • @Hawkeye64 Cool, thanks! That certainly takes it to another level. 🙂



  • @murrah Just as a note, I never used this method because at least previous versions of webpack would bundle the entire package.json in your frontend code, which could be a security concern (exposes packages / package versions, build / test commands, etc.) I think webpack 4 can now tree shake json imports, but probably worth it to grep your build directory for one of your dependencies just to be sure.

    Instead if I wanted to use data from package.json, I would just do the same in quasar.conf:

    const { version } = require('./package.json')
    
    module.exports = function (ctx) {
      return {
        // ...
    
        build: {
          env: {
            VERSION: version
          },
          // ...
        }
      }
    }
    

    Again, I think it’s not a problem these days, but thought I’d mention it since it was in the past a security issue that’s not necessarily obvious.


Log in to reply