Skip Navigation
Show nav
Heroku Dev Center
  • Get Started
  • Documentation
  • Changelog
  • Search
  • Get Started
    • Node.js
    • Ruby on Rails
    • Ruby
    • Python
    • Java
    • PHP
    • Go
    • Scala
    • Clojure
  • Documentation
  • Changelog
  • More
    Additional Resources
    • Home
    • Elements
    • Products
    • Pricing
    • Careers
    • Help
    • Status
    • Events
    • Podcasts
    • Compliance Center
    Heroku Blog

    Heroku Blog

    Find out what's new with Heroku on our blog.

    Visit Blog
  • Log inorSign up
View categories

Categories

  • Heroku Architecture
    • Dynos (app containers)
    • Stacks (operating system images)
    • Networking & DNS
    • Platform Policies
    • Platform Principles
  • Command Line
  • Deployment
    • Deploying with Git
    • Deploying with Docker
    • Deployment Integrations
  • Continuous Delivery
    • Continuous Integration
  • Language Support
    • Node.js
    • Ruby
      • Working with Bundler
      • Rails Support
    • Python
      • Working with Django
      • Background Jobs in Python
    • Java
      • Working with Maven
      • Java Database Operations
      • Working with the Play Framework
      • Java Advanced Topics
      • Working with Spring Boot
    • PHP
    • Go
      • Go Dependency Management
    • Scala
    • Clojure
  • Databases & Data Management
    • Heroku Postgres
      • Postgres Basics
      • Postgres Getting Started
      • Postgres Performance
      • Postgres Data Transfer & Preservation
      • Postgres Availability
      • Postgres Special Topics
    • Heroku Redis
    • Apache Kafka on Heroku
    • Other Data Stores
  • Monitoring & Metrics
    • Logging
  • App Performance
  • Add-ons
    • All Add-ons
  • Collaboration
  • Security
    • App Security
    • Identities & Authentication
    • Compliance
  • Heroku Enterprise
    • Private Spaces
      • Infrastructure Networking
    • Enterprise Accounts
    • Enterprise Teams
    • Heroku Connect (Salesforce sync)
      • Heroku Connect Administration
      • Heroku Connect Reference
      • Heroku Connect Troubleshooting
    • Single Sign-on (SSO)
  • Patterns & Best Practices
  • Extending Heroku
    • Platform API
    • App Webhooks
    • Heroku Labs
    • Building Add-ons
      • Add-on Development Tasks
      • Add-on APIs
      • Add-on Guidelines & Requirements
    • Building CLI Plugins
    • Developing Buildpacks
    • Dev Center
  • Accounts & Billing
  • Troubleshooting & Support
  • Integrating with Salesforce
  • Language Support
  • Java
  • Working with Maven
  • Using Grunt with Java and Maven to Automate JavaScript Tasks

Using Grunt with Java and Maven to Automate JavaScript Tasks

English — 日本語に切り替える

Last updated December 16, 2019

Table of Contents

  • Using multiple buildpacks
  • Calling Grunt from Maven

Grunt is a task runner utility. It’s used to automate various Javascript tasks including minification, obfuscation, and testing. It’s also used to help with other types of static content such as Sass, CSS and even HTML.

In this article, you’ll learn how to use Grunt in a Maven project to minify your Javascript files. With this foundation, you’ll be able to add more Grunt plugins that validate Javascript files, compile Sass to CSS, run Jasmine tests with PhantomJS, and more.

This tutorial assumes you already have a Java project running on Heroku. If you do not, download the Java Grunt example project and deploy it to Heroku by following the Getting Started with Java guide.

Using multiple buildpacks

In order to manage Grunt as a dependency, you’ll need to configure your project to use both the Node.js and Java buildpacks. This is done with the heroku buildpacks command.

First, add the Node.js and Java buildpacks to your application by running this:

$ heroku buildpacks:add heroku/nodejs
$ heroku buildpacks:add heroku/java

Then confirm the execution order by running this command:

$ heroku buildpacks
=== nameless-brushlands-4859 Buildpack
1. heroku/nodejs
2. heroku/java

In order for the Node.js buildpack to work, it must find a package.json file in your app. We can also use this file to define the Grunt dependency. Create a package.json file in the root of your project, and put the following code in it:

{
  "name": "java-grunt",
  "dependencies": {
    "grunt-cli": "0.1.13",
    "grunt": "~0.4.5",
    "grunt-contrib-uglify": "~0.5.0"
  }
}

This defines the grunt-cli as a primary dependency. It also defines grunt itself and the grunt-contrib-uglify module as dependencies. You’ll use these from Maven in a moment.

Now add this file to your Git repository like so:

$ git add package.json
$ git commit -m "added package.json"

On your next deploy, the buildpack will install npm, which will then install Grunt. But before deploying, you’ll need to configure the Java side of your project.

Calling Grunt from Maven

You can use Grunt from Maven by adding the grunt-maven-plugin to your configuration. This plugin allows you to integrate Grunt tasks into the Maven build process. To add it, open your pom.xml file and add the follow code to the <project> element:

<build>
  ...
  <plugins>
    ...
    <plugin>
      <groupId>pl.allegro</groupId>
      <artifactId>grunt-maven-plugin</artifactId>
      <version>1.4.1</version>
      <executions>
        <execution>
          <goals>
            <goal>npm</goal>
            <goal>grunt</goal>
          </goals>
        </execution>
      </executions>
    </plugin>
  </plugins>
</build>

This tells Maven to run the npm, which will prepare the environment, and grunt, which will run the automated tasks defined in your Gruntfile.js. Of course, you’ll need a Gruntfile.js file in order for this to work. Create the file in the root directory of your project, and add the following code to it:

module.exports = function(grunt) {
  grunt.initConfig({
    uglify: {
      core: {
        files: [{
          expand: true,
          cwd: 'src/main/resources',
          src: 'public/js/**/*.js',
          dest: "target/classes",
          ext: '.min.js'
        }]
      }
    }
  });

  grunt.loadNpmTasks('grunt-contrib-uglify');
  grunt.registerTask('default', ['uglify']);
};

This simple configuration loads the grunt-contrib-uglify module and uses it to convert all of your Javascript files under the src/main/resources/public directory into Minified Javascript files (i.e. compressed versions of Javascript code) in your target/classes/public/js directory. The new files will have the extension .min.js but will have the same basename.

You can reference these files in your applications HTML files like this:

<script src="js/index.min.js"></script>

In the Heroku Java Grunt example, the index.js file contains this code:

$(function () {
  $('body p').append(" and Javascript!");
});

And the index.html file contains this code:

<html>
<head>
  <title>Java Grunt Example</title>
  <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
  <script src="js/index.min.js"></script>
  </style>
</head>
<body>
  <p>Hello from Java Grunt!</p>
</body>
</html>

Now run maven to build the project (you must have npm installed and grunt installed for this to work):

$ mvn clean package
[INFO] Scanning for projects...
...
[INFO] --- grunt-maven-plugin:1.4.1:npm (default) @ java-grunt ---
[INFO] OS Name: Mac OS X
npm WARN package.json java-grunt@ No description
npm WARN package.json java-grunt@ No repository field.
grunt-cli@0.1.13 ../node_modules/grunt-cli
├── nopt@1.0.10 (abbrev@1.0.5)
├── resolve@0.3.1
└── findup-sync@0.1.3 (glob@3.2.11, lodash@2.4.1)

grunt@0.4.5 ../node_modules/grunt
├── which@1.0.8
├── dateformat@1.0.2-1.2.3
├── eventemitter2@0.4.14
├── getobject@0.1.0
├── rimraf@2.2.8
├── colors@0.6.2
├── async@0.1.22
├── hooker@0.2.3
├── grunt-legacy-util@0.2.0
├── nopt@1.0.10 (abbrev@1.0.5)
├── exit@0.1.2
├── minimatch@0.2.14 (sigmund@1.0.0, lru-cache@2.5.0)
├── lodash@0.9.2
├── glob@3.1.21 (inherits@1.0.0, graceful-fs@1.2.3)
├── coffee-script@1.3.3
├── underscore.string@2.2.1
├── iconv-lite@0.2.11
├── findup-sync@0.1.3 (glob@3.2.11, lodash@2.4.1)
├── grunt-legacy-log@0.1.1 (underscore.string@2.3.3, lodash@2.4.1)
└── js-yaml@2.0.5 (argparse@0.1.16, esprima@1.0.4)

grunt-contrib-uglify@0.5.1 ../node_modules/grunt-contrib-uglify
├── chalk@0.5.1 (escape-string-regexp@1.0.2, ansi-styles@1.1.0, supports-color@0.2.0, strip-ansi@0.3.0, has-ansi@0.1.0)
├── lodash@2.4.1
├── uglify-js@2.4.16 (uglify-to-browserify@1.0.2, async@0.2.10, optimist@0.3.7, source-map@0.1.34)
└── maxmin@0.2.2 (figures@1.3.5, pretty-bytes@0.1.2, gzip-size@0.2.0)
[INFO]
[INFO] --- grunt-maven-plugin:1.4.1:grunt (default) @ java-grunt ---
[INFO] OS Name: Mac OS X
Running "uglify:core" (uglify) task

Done, without errors.
...
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 6.156 s
[INFO] Finished at: 2014-12-11T09:54:44-06:00
[INFO] Final Memory: 23M/227M
[INFO] ------------------------------------------------------------------------

When the process has finished, check the contents of target/classes/public/js/index.min.js. You find that the Javascript code has been reduced to a single line (it has been “minified”).

Now run the application by executing heroku local, and open a browser to the index page. You will see the following text:

Hello from Java Grunt! and Javascript!

Finally, add your changes to the Git repo and push your code to Heroku:

$ git add Gruntfile.js pom.xml
$ git commit -m "added grunt task"
$ git push heroku master
...
remote: -----> Fetching custom git buildpack... done
remote: -----> Multipack app detected
remote: -----> Node.js app detected
remote:        Installing node modules
...
remote: -----> Fetching custom git buildpack... done
remote: -----> Java app detected
remote: -----> Installing OpenJDK 1.7... done
remote: -----> Installing Maven 3.2.3... done
...
remote:        [INFO] --- grunt-maven-plugin:1.4.1:npm (default) @ java-grunt ---
remote:        [INFO] OS Name: Linux
...
remote:        Running "uglify:core" (uglify) task
remote:
remote:        Done, without errors.
...
remote: Verifying deploy... done.

You can view the application by running heroku open. Your Grunt build has run, and your application is using the minified Javascript files.

Now you can add more modules to your package.json file, such as grunt-contrib-watch or grunt-contrib-cssmin, and those libraries can be used in your Gruntfile.js configuration. For more information on using Grunt see the Grunt documentation. For more information on using Grunt with Maven see the grunt-maven-plugin documentation.

Keep reading

  • Working with Maven

Feedback

Log in to submit feedback.

Information & Support

  • Getting Started
  • Documentation
  • Changelog
  • Compliance Center
  • Training & Education
  • Blog
  • Podcasts
  • Support Channels
  • Status

Language Reference

  • Node.js
  • Ruby
  • Java
  • PHP
  • Python
  • Go
  • Scala
  • Clojure

Other Resources

  • Careers
  • Elements
  • Products
  • Pricing

Subscribe to our monthly newsletter

Your email address:

  • RSS
    • Dev Center Articles
    • Dev Center Changelog
    • Heroku Blog
    • Heroku News Blog
    • Heroku Engineering Blog
  • Heroku Podcasts
  • Twitter
    • Dev Center Articles
    • Dev Center Changelog
    • Heroku
    • Heroku Status
  • Facebook
  • Instagram
  • Github
  • LinkedIn
  • YouTube
Heroku is acompany

 © Salesforce.com

  • heroku.com
  • Terms of Service
  • Privacy
  • Cookies
  • Cookie Preferences