Wednesday, 28 June 2017

Loading and Using JavaScript in Drupal 8

Managing JavaScript in Drupal 8 with Libraries
Drupal 8’s JavaScript handling is a conceptual extension of D7’s hook_library()and the D7 Libraries API Module.
Libraries are defined in YAML format, of course. You can define one or more libraries in each file.
Define a Library
Create or edit the <some-file-name>.libraries.yml file that goes in the root of your theme or module:
this-lib-name:
 js:
 js-path/my-theme.js: {}
some-file-name can be any name really, but should be the name of your theme or module.
Drupal will aggregate JS files by default, so to avoid that if necessary:
js-path/my-theme.js: { preprocess: false }
Of course, adjust js-path as needed. See PSR-4 namespaces and autoloading in Drupal 8 for more info on pathing.

Library Options

You can optionally provide a version number per library, but Drupal doesn’t use it for anything:
this-lib-name:
  version: "1.0.1"
You can also define dependencies per library, which are followed:
this-lib-name:
  dependencies:
    - core/jquery
D8 by default loads JS into the footer; to load to the header:
this-lib-name:
  header: true

Attaching Libraries in a Theme

Reference them in your my-theme-name.info.yml file. They load globally as in on every page.
libraries:
  - core/jquery
  - my-theme-name/this-lib-name
Here we’re loading our libraries this-lib-name and core/jquery (which is no longer loaded by default).

Attaching Libraries in Twig

You can attach a JS library from a twig template. It will only load if the template loads which means you can conditionally load it based on the naming structure of the Twig template file.
{{ attach_library('my-theme-name/some-other-lib') }}

Attaching Libraries in your Module’s PHP

PHP allows you to control what libraries are loaded and when.
function mymodule_page_attachments(array &$attachments) {
  $attachments['#attached']['library'][] =
    'mymodule/some-other-lib';
}
Of course you can load any number of libraries using this, and related, hooks.

Attaching Libraries in your Theme’s PHP

If not loading everywhere by using the .yml file.
function mytheme_preprocess_page(&$variables) {
  $variables['#attached']['library'][] =
    'mytheme/some-other-lib';
}
See also related THEME_preprocess_HOOK()’s. Although some discourage using these hooks as they’re intended for preprocessing variables.

Conditional Libraries in PHP

To support D8’s caching, if you want to *conditionally* attach libraries, you need to provide cacheability metadata*.
function mytheme_or_module_preprocess_page(&$variables) {
  $variables['page']['#cache']['contexts'][] = 'url.path';
  // above line sets the cacheability metadata
 
  if (\Drupal::service('path.matcher')->isFrontPage()) {
    $variables['#attached']['library'][] =
      'mytheme_or_module/some-other-lib';
    }
}
*Metadata is comprised of a combination of up to 3 things: tags, contexts, and max-age. See the Cache API https://www.drupal.org/developing/api/8/cache for more info.

Loading External JavaScript

External “libraries” still have to be defined inside Drupal libraries*.
this-lib-name:
  js:
    https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.8/
      angular.js: { type: external }
Since Drupal will minify, if it already is, let D know:
{ type: external, minified: true }
If attributes are needed in the resulting <script> line:
{ type: external , attributes: { defer: true, async: true } }
*I “broke” the code lines for readability, but it’s not legal.

JavaScript Settings

To add “computed” settings or configuration, first you have to define a dependency on core/drupalSettings.
this-lib:
  dependencies:
    - core/jquery
    - core/drupalSettings
Then…
function mytheme_preprocess_page(&$vars) {
  $vars['#attached']['library'][] = 'mytheme/this-lib';
  $vars['#attached']['drupalSettings']['mytheme']
    ['this-lib']['some-prop'] = $some_var;
}
Then access the some-prop setting in JS with:
console.log(drupalSettings.mytheme.this-lib.some-prop);

Manipulating Libraries

The theme is able to use two new directives, libraries-extend and libraries-override to extend, remove or replace whole libraries or individual library files.
Both of these are placed in the theme’s my-theme.info.yml file.

Libraries-Extend

By “extending” a library it means the new library is always loaded with the target library, regardless of conditions.
libraries-extend:
  other_theme_or_module/some-lib:
    - mytheme/some-other-lib
Here, the some-other-lib of the theme is used to extend some-lib of some mytheme_or_module.

Libraries-Override

This directive is more powerful, but when dealing with JS (unlike CSS which may just result in poor layout/design), you can break JavaScript on your site by not paying close attention to JS code dependencies.
You can remove a whole library:
libraries-override:
  other_theme_or_module/some-lib: false
Or remove a library file:
libraries-override:
  other_theme_or_module/some-lib:
    js:
      full-path-to-library/some-file.js: false
Or replace a whole libs:
libraries-override:
  other_theme_or_module/some-lib: mytheme/some-other-lib
Or replace a library file:
libraries-override:
  other_theme_or_module/some-lib:
    js:
      full-path-to-library/some-file.js: path-to-theme-lib/some-other-file.js

Inline JavaScript

Almost always JavaScript should be included in a library.
But if you must, put the complete script tag in the html.html.twig file (yes, “html” is repeated twice.)

Dynamically Altering Libraries

Use this when you want to dynamically specify JS (or CSS) Libraries used across multiple requests.
hook_library_info_alter(&$libraries, $extension)
Allows modules and themes to change libraries' definitions.
An example of this is the Color module which uses this hook to replace CSS Libraries with the “colored” CSS libraries.

Dynamically Adding Libraries

This is most like D7’s Libraries. Use it to programmatically add an entire library definition. And they are still cached.
Modules may implement hook_library_info_build() to add dynamic library definitions
function my_module_library_info_build() {
  $libs = array();
  $libs['my-lib'] = [
    'js' => [
      'my-lib-code.js' => [],
    ],
  ]
}

Sneaky JavaScript

While you’re suppose to use libraries you could attach into HTML head and create a <script> tag directly. These are (re)built on every single request and therefore aren’t cached and can slow down Drupal, so beware.
If possible, it’s best to leave your JS file(s) static and just use JS Settings configurations.
$page['#attached']['html_head'][] = [
  [
    '#type' => 'html_tag',
    '#tag' => 'script',
      '#attributes' => [
        'src' => 'some-path/my-file.js',
      ],
  ], 'my-mode-js', // an identifier for Drupal
];

In Closing

Hopefully this shed some light on D8’s JavaScript handling. Happy coding.
   Posted on  Wednesday, June 28, 2017  / 

Managing JavaScript in Drupal 8 with Libraries
Drupal 8’s JavaScript handling is a conceptual extension of D7’s hook_library()and the D7 Libraries API Module.
Libraries are defined in YAML format, of course. You can define one or more libraries in each file.
Define a Library
Create or edit the <some-file-name>.libraries.yml file that goes in the root of your theme or module:
this-lib-name:
 js:
 js-path/my-theme.js: {}
some-file-name can be any name really, but should be the name of your theme or module.
Drupal will aggregate JS files by default, so to avoid that if necessary:
js-path/my-theme.js: { preprocess: false }
Of course, adjust js-path as needed. See PSR-4 namespaces and autoloading in Drupal 8 for more info on pathing.

Library Options

You can optionally provide a version number per library, but Drupal doesn’t use it for anything:
this-lib-name:
  version: "1.0.1"
You can also define dependencies per library, which are followed:
this-lib-name:
  dependencies:
    - core/jquery
D8 by default loads JS into the footer; to load to the header:
this-lib-name:
  header: true

Attaching Libraries in a Theme

Reference them in your my-theme-name.info.yml file. They load globally as in on every page.
libraries:
  - core/jquery
  - my-theme-name/this-lib-name
Here we’re loading our libraries this-lib-name and core/jquery (which is no longer loaded by default).

Attaching Libraries in Twig

You can attach a JS library from a twig template. It will only load if the template loads which means you can conditionally load it based on the naming structure of the Twig template file.
{{ attach_library('my-theme-name/some-other-lib') }}

Attaching Libraries in your Module’s PHP

PHP allows you to control what libraries are loaded and when.
function mymodule_page_attachments(array &$attachments) {
  $attachments['#attached']['library'][] =
    'mymodule/some-other-lib';
}
Of course you can load any number of libraries using this, and related, hooks.

Attaching Libraries in your Theme’s PHP

If not loading everywhere by using the .yml file.
function mytheme_preprocess_page(&$variables) {
  $variables['#attached']['library'][] =
    'mytheme/some-other-lib';
}
See also related THEME_preprocess_HOOK()’s. Although some discourage using these hooks as they’re intended for preprocessing variables.

Conditional Libraries in PHP

To support D8’s caching, if you want to *conditionally* attach libraries, you need to provide cacheability metadata*.
function mytheme_or_module_preprocess_page(&$variables) {
  $variables['page']['#cache']['contexts'][] = 'url.path';
  // above line sets the cacheability metadata
 
  if (\Drupal::service('path.matcher')->isFrontPage()) {
    $variables['#attached']['library'][] =
      'mytheme_or_module/some-other-lib';
    }
}
*Metadata is comprised of a combination of up to 3 things: tags, contexts, and max-age. See the Cache API https://www.drupal.org/developing/api/8/cache for more info.

Loading External JavaScript

External “libraries” still have to be defined inside Drupal libraries*.
this-lib-name:
  js:
    https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.8/
      angular.js: { type: external }
Since Drupal will minify, if it already is, let D know:
{ type: external, minified: true }
If attributes are needed in the resulting <script> line:
{ type: external , attributes: { defer: true, async: true } }
*I “broke” the code lines for readability, but it’s not legal.

JavaScript Settings

To add “computed” settings or configuration, first you have to define a dependency on core/drupalSettings.
this-lib:
  dependencies:
    - core/jquery
    - core/drupalSettings
Then…
function mytheme_preprocess_page(&$vars) {
  $vars['#attached']['library'][] = 'mytheme/this-lib';
  $vars['#attached']['drupalSettings']['mytheme']
    ['this-lib']['some-prop'] = $some_var;
}
Then access the some-prop setting in JS with:
console.log(drupalSettings.mytheme.this-lib.some-prop);

Manipulating Libraries

The theme is able to use two new directives, libraries-extend and libraries-override to extend, remove or replace whole libraries or individual library files.
Both of these are placed in the theme’s my-theme.info.yml file.

Libraries-Extend

By “extending” a library it means the new library is always loaded with the target library, regardless of conditions.
libraries-extend:
  other_theme_or_module/some-lib:
    - mytheme/some-other-lib
Here, the some-other-lib of the theme is used to extend some-lib of some mytheme_or_module.

Libraries-Override

This directive is more powerful, but when dealing with JS (unlike CSS which may just result in poor layout/design), you can break JavaScript on your site by not paying close attention to JS code dependencies.
You can remove a whole library:
libraries-override:
  other_theme_or_module/some-lib: false
Or remove a library file:
libraries-override:
  other_theme_or_module/some-lib:
    js:
      full-path-to-library/some-file.js: false
Or replace a whole libs:
libraries-override:
  other_theme_or_module/some-lib: mytheme/some-other-lib
Or replace a library file:
libraries-override:
  other_theme_or_module/some-lib:
    js:
      full-path-to-library/some-file.js: path-to-theme-lib/some-other-file.js

Inline JavaScript

Almost always JavaScript should be included in a library.
But if you must, put the complete script tag in the html.html.twig file (yes, “html” is repeated twice.)

Dynamically Altering Libraries

Use this when you want to dynamically specify JS (or CSS) Libraries used across multiple requests.
hook_library_info_alter(&$libraries, $extension)
Allows modules and themes to change libraries' definitions.
An example of this is the Color module which uses this hook to replace CSS Libraries with the “colored” CSS libraries.

Dynamically Adding Libraries

This is most like D7’s Libraries. Use it to programmatically add an entire library definition. And they are still cached.
Modules may implement hook_library_info_build() to add dynamic library definitions
function my_module_library_info_build() {
  $libs = array();
  $libs['my-lib'] = [
    'js' => [
      'my-lib-code.js' => [],
    ],
  ]
}

Sneaky JavaScript

While you’re suppose to use libraries you could attach into HTML head and create a <script> tag directly. These are (re)built on every single request and therefore aren’t cached and can slow down Drupal, so beware.
If possible, it’s best to leave your JS file(s) static and just use JS Settings configurations.
$page['#attached']['html_head'][] = [
  [
    '#type' => 'html_tag',
    '#tag' => 'script',
      '#attributes' => [
        'src' => 'some-path/my-file.js',
      ],
  ], 'my-mode-js', // an identifier for Drupal
];

In Closing

Hopefully this shed some light on D8’s JavaScript handling. Happy coding.

Posted in: , , Read Complete Article»

Thursday, 10 July 2014

Setup LAMP and Install Drupal

Setting up LAMP (Linux, Apache, MySQL & PHP)
  • If you have Debian or Ubuntu OS installed in your system, type su for Debian or sudo su for Ubuntu and press enter it will prompt for password, enter your root password
  • Update package sources
apt-get update
(This is safer than apt-get upgrade or apt-get dist-upgrade, because it safely upgrades your server and resolves dependencies)
  • Install Apache2 and PHP5
apt-get install apache2 php5 libapache2-mod-php5 php5-gd
chmod -R 777 /var/www
Check if apache is working
/etc/init.d/apache2 restart
nano /var/www/info.php
Copy & paste the folowing php code in the nano editor
<?php
phpinfo();
?>
Go and check http://localhost/info.php in your browser to see configuration of installed php version.
  • Install Mysql and PHPmyadmin
apt-get install mysql-server mysql-client php5-mysql
apt-get install phpmyadmin
When prompted for a password enter MySql Password.
  • Creating a MySQL DB & user for your Drupal installation
mysqladmin -u root -p create d7
Enter MySql Password when you are prompted for password. If you get a “Database exists” error, please issue “mysqladmin -u root -p drop d7” to delete the existing database and then issue the create command.
  • Configuring Apache for Clean URLs
a2enmod rewrite
/etc/init.d/apache2 restart
chmod -R 777 /var/www
Install Drupal
  • Download the latest stable version of drupal from http://drupal.org/project/drupal
  • Prepare server for drupal setup
    • Copy the drupal-7.2x.tar.gz file to /var/www and uncompress the files so that you get /var/www/drupal-7.2x finally
    • Rename the drupal folder to d7
    • Goto d7/sites/default, create a folder called files so that you have d7/sites/default/files
    • Copy default.settings.php as settings.php so that you have d7/sites/default/settings.php
    • Give 777 permissions to file(apply permissions to enclosed files) & settings.php
  • Install drupal
    • Choose Standard installation profile and save and continue
    • Leave English as is and save and continue
    • Give Database Name as d7Database username as root & Database password as hello for LAMP or leave blank for XAMPP and Save and continue
    • configure Site information
      • Site Name your full name
      • Site e-mail address your email id
    • configure Site maintenance account
      • username as admin
      • password & Confirm password as hello
    • configure Server settings
      • Choose India under Default country
      • Choose Asia/Kolkata: Tuesday, June 21, 2011 - 14:51 +0530 under Default time zone and Save and continue
    • Now click on Visit your new site
Menus
Adding content
  • Click on add content in top black menu
  • Then click on Basic page
  • Give Title as Workshop
  • Write a summary about workshop in the body
  • Check the box Provide a menu link under Menu Settings below Text format group
  • Give Workshop in Menu link title
  • Ensure <Main menu> under Parent item
  • Choose 1 as Weight and click save

   Posted on  Thursday, July 10, 2014  / 

Setting up LAMP (Linux, Apache, MySQL & PHP)
  • If you have Debian or Ubuntu OS installed in your system, type su for Debian or sudo su for Ubuntu and press enter it will prompt for password, enter your root password
  • Update package sources
apt-get update
(This is safer than apt-get upgrade or apt-get dist-upgrade, because it safely upgrades your server and resolves dependencies)
  • Install Apache2 and PHP5
apt-get install apache2 php5 libapache2-mod-php5 php5-gd
chmod -R 777 /var/www
Check if apache is working
/etc/init.d/apache2 restart
nano /var/www/info.php
Copy & paste the folowing php code in the nano editor
<?php
phpinfo();
?>
Go and check http://localhost/info.php in your browser to see configuration of installed php version.
  • Install Mysql and PHPmyadmin
apt-get install mysql-server mysql-client php5-mysql
apt-get install phpmyadmin
When prompted for a password enter MySql Password.
  • Creating a MySQL DB & user for your Drupal installation
mysqladmin -u root -p create d7
Enter MySql Password when you are prompted for password. If you get a “Database exists” error, please issue “mysqladmin -u root -p drop d7” to delete the existing database and then issue the create command.
  • Configuring Apache for Clean URLs
a2enmod rewrite
/etc/init.d/apache2 restart
chmod -R 777 /var/www
Install Drupal
  • Download the latest stable version of drupal from http://drupal.org/project/drupal
  • Prepare server for drupal setup
    • Copy the drupal-7.2x.tar.gz file to /var/www and uncompress the files so that you get /var/www/drupal-7.2x finally
    • Rename the drupal folder to d7
    • Goto d7/sites/default, create a folder called files so that you have d7/sites/default/files
    • Copy default.settings.php as settings.php so that you have d7/sites/default/settings.php
    • Give 777 permissions to file(apply permissions to enclosed files) & settings.php
  • Install drupal
    • Choose Standard installation profile and save and continue
    • Leave English as is and save and continue
    • Give Database Name as d7Database username as root & Database password as hello for LAMP or leave blank for XAMPP and Save and continue
    • configure Site information
      • Site Name your full name
      • Site e-mail address your email id
    • configure Site maintenance account
      • username as admin
      • password & Confirm password as hello
    • configure Server settings
      • Choose India under Default country
      • Choose Asia/Kolkata: Tuesday, June 21, 2011 - 14:51 +0530 under Default time zone and Save and continue
    • Now click on Visit your new site
Menus
Adding content
  • Click on add content in top black menu
  • Then click on Basic page
  • Give Title as Workshop
  • Write a summary about workshop in the body
  • Check the box Provide a menu link under Menu Settings below Text format group
  • Give Workshop in Menu link title
  • Ensure <Main menu> under Parent item
  • Choose 1 as Weight and click save

Creative Commons License
This work is licensed under a Creative Commons Attribution-ShareAlike 4.0 International License .