How to add CSS and JS in Magento 2® Custom Module

Till now you have got how to create Magento 2 module. Now you may want to properly add CSS and JS files to your Magento 2 module. Like Magento 1 Magento 2 provides layout xmls that are used to add your module css and js files. I will tell you two ways to add css and js files to your custom module.

Let us assume that our module namespace in Webspeaks and our module name is Test.

Method 1: Using Simple Layouts

In this method you can add the CSS/JS files in frontend using layout files only.
1. Open the layout file present at: Webspeaks/Test/view/frontend/layout/default.xml
Adding layout in default.xml will be available on almost all pages of your agento 2 site. You can also add this code to any particluar page using the following layout file:
Now change the code of layout file as follows:

<page xmlns:xsi="" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
        <css src="Webspeaks_Fancyfeedback/css/my_css.css"/>
        <link src="Webspeaks_Fancyfeedback/js/my_js.js"/>

2. Now create the css and js files at following locations:

Now clear the cache using following command:
php bin/magento cache:clear

If you refresh the page you can see the module files in your page source code.

Method 2: Using Blocks

In some cases you may want to add CSS/JS file based on certain conditions in your module. For this you can CSS/JS files by adding a block in the head block of Magento 2.
1. In your layout file add following code:

<page xmlns:xsi="" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
    <referenceBlock name="head.additional">
        <block  template="head.phtml"
                name="webspeaks_fancyfeedback_block_head" />

2. Now create the Head.php block class in your module: Webspeaks/Test/Block/Head.php

3. Add following code to this file:

namespace Webspeaks\Fancyfeedback\Block;
class Head extends \Magento\Framework\View\Element\Template
    public $assetRepository;

    public function __construct(
        \Magento\Framework\View\Element\Template\Context $context, 
        array $data = [],    
        \Magento\Framework\View\Asset\Repository $assetRepository
        // Get the asset repository to get URL of our assets
        $this->assetRepository = $assetRepository;
        return parent::__construct($context, $data);

4. You can see in step 1 we have specified the template file for our block. Now we will create the template file at: Webspeaks/Test/view/frontend/templates/head.phtml

5. In this template file add following code:

    $asset_repository = $this->assetRepository;
    $js_asset = $asset_repository->createAsset('Webspeaks_Fancyfeedback/js/ws_ff.js');
    $css_asset = $asset_repository->createAsset('Webspeaks_Fancyfeedback/css/ws_ff.css');
<link href="<?php echo $css_asset->getUrl(); ?>" rel="stylesheet" type="text/css" />
<script src="<?php echo $js_asset->getUrl(); ?>"></script>

Again clear the cache and you are done.

Adding jQuery code:

If your module file uses jQuery, you must use require.js syntax to add the code in this file otherwise your code wont be able to access the global jQuery object.
In Webspeaks/Test/view/frontend/web/js/my_js.js, add your jQuery code as follows:

], function($){
    $(document).ready(function() {
        console.log('jquery loaded from webspeaks test');

Written by Arvind Bhardwaj

Arvind is a Magento and WordPress expert with more than 6 years of industry wide experience.