{"id":6175,"date":"2021-09-02T11:55:02","date_gmt":"2021-09-02T09:55:02","guid":{"rendered":"https:\/\/florianbrinkmann.com\/en\/?p=6175"},"modified":"2021-09-02T11:55:27","modified_gmt":"2021-09-02T09:55:27","slug":"visual-regression-tests-jlineup","status":"publish","type":"post","link":"https:\/\/florianbrinkmann.com\/en\/visual-regression-tests-jlineup-6175\/","title":{"rendered":"Visual regression tests with JLineup"},"content":{"rendered":"<p>With visual regression tests, one can check two versions of a website for visual differences. Those tests are, for example, useful to check a website on a test server before and after deploying changes, to only move the changes to the live server when no differences are found.<\/p>\n\n\n\n<p>There are various solutions to run such tests, here I will show you <a href=\"https:\/\/github.com\/otto-de\/jlineup\">JLineup<\/a>. JLineup can be used as a command-line tool or as a web service. I only tried the CLI version and am not going to describe the web service possibility.<\/p>\n\n\n\n<!--more-->\n\n\n\n<h2 class=\"wp-block-heading\">Installation of JLineup CLI<\/h2>\n\n\n\n<p>The GitHub repo contains a file with <a href=\"https:\/\/github.com\/otto-de\/jlineup\/blob\/master\/docs\/CLI.md\">installation and usage instructions for the CLI version of JLineup<\/a>. Because it is a Java archive, the server needs to have at least Java 8 installed. On Ubuntu 20.04 we could install Java in form of OpenJDK with the following command:<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-1\" data-shcb-language-name=\"Bash\" data-shcb-language-slug=\"bash\"><span><code class=\"hljs language-bash\">sudo apt-get install openjdk-14-jre <\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-1\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">Bash<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">bash<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<p>Installing the CLI itself happens with just downloading the <code>.jar<\/code> file:<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-2\" data-shcb-language-name=\"Bash\" data-shcb-language-slug=\"bash\"><span><code class=\"hljs language-bash\">wget https:\/\/repo1.maven.org\/maven2\/de\/otto\/jlineup-cli\/4.3.4\/jlineup-cli-4.3.4.jar -O jlineup.jar<\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-2\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">Bash<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">bash<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<p>To be able to run visual regression tests, we need a browser, too. I decided to use Firefox, JLineup also supports Chrome and Chromium. To install Firefox on Ubuntu, we run the following command:<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-3\" data-shcb-language-name=\"JavaScript\" data-shcb-language-slug=\"javascript\"><span><code class=\"hljs language-javascript\">sudo apt-<span class=\"hljs-keyword\">get<\/span> install --no-install-recommends firefox<\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-3\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">JavaScript<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">javascript<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<p>The <code>--no-install-recommends<\/code> param prevents the installation of GNOME dependencies.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Configuration<\/h2>\n\n\n\n<p>Configuration of JLineup is done in a JSON file, the tool by default looks for a <code>lineup.json<\/code> in the current directory when no other file is specified via the <code>--config<\/code> parameter.<\/p>\n\n\n\n<p>The tool comes with many <a href=\"https:\/\/github.com\/otto-de\/jlineup\/blob\/master\/docs\/CONFIGURATION.md\">configuration options<\/a> that are described in the repo in detail. For example, you can define multiple URLs to check, test in different viewport dimensions, and set a time in seconds that should be waited before taking the screenshot after loading the page.<\/p>\n\n\n\n<p>An easy example for testing a site looks like the following:<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-4\" data-shcb-language-name=\"JSON \/ JSON with Comments\" data-shcb-language-slug=\"json\"><span><code class=\"hljs language-json\">{\n  <span class=\"hljs-attr\">\"urls\"<\/span>: {\n    <span class=\"hljs-attr\">\"https:\/\/time.gov\/\"<\/span>: {\n      <span class=\"hljs-attr\">\"paths\"<\/span>: &#91;\n        <span class=\"hljs-string\">\"\"<\/span>\n      ],\n      <span class=\"hljs-attr\">\"max-diff\"<\/span>: <span class=\"hljs-number\">0.0<\/span>,\n      <span class=\"hljs-attr\">\"devices\"<\/span> : &#91;{\n        <span class=\"hljs-attr\">\"width\"<\/span> : <span class=\"hljs-number\">800<\/span>,\n        <span class=\"hljs-attr\">\"height\"<\/span> : <span class=\"hljs-number\">600<\/span>\n      }],\n      <span class=\"hljs-attr\">\"max-scroll-height\"<\/span>: <span class=\"hljs-number\">100000<\/span>,\n      <span class=\"hljs-attr\">\"wait-after-page-load\"<\/span>: <span class=\"hljs-number\">5<\/span>,\n      <span class=\"hljs-attr\">\"wait-after-scroll\"<\/span>: <span class=\"hljs-number\">0<\/span>\n    }\n  },\n  <span class=\"hljs-attr\">\"browser\"<\/span>: <span class=\"hljs-string\">\"firefox-headless\"<\/span>\n}<\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-4\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">JSON \/ JSON with Comments<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">json<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<p>Using this configuration, JLineup checks the time.gov site with Firefox in headless mode and a window width of 800x600 pixels. The max height that is scrolled for taking screenshots is 100.000 pixels and after loading the page, the tool waits 5 seconds before taking a screenshot, after scrolling there is no pause.<\/p>\n\n\n\n<p>The defined window size also specifies the screenshot size, because JLineup does not take one screenshot of the whole site but multiple in the specified size. It visits the page, makes a screenshot, scrolls down, makes a screenshot, scrolls down, and so on.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Run tests<\/h2>\n\n\n\n<p>To run a test with the configuration from above, we need the following command to run the \u00bbbefore\u00ab step:<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-5\" data-shcb-language-name=\"CSS\" data-shcb-language-slug=\"css\"><span><code class=\"hljs language-css\"><span class=\"hljs-selector-tag\">java<\/span> <span class=\"hljs-selector-tag\">-jar<\/span> <span class=\"hljs-selector-tag\">jlineup<\/span><span class=\"hljs-selector-class\">.jar<\/span> <span class=\"hljs-selector-tag\">--step<\/span> <span class=\"hljs-selector-tag\">before<\/span><\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-5\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">CSS<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">css<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<p>The command line shows a log of what JLineup does, for example, \u00bbBrowsing to https:\/\/time.gov\/ with window size 800x600\u00ab.<\/p>\n\n\n\n<p>Let\u2019s imagine our changes were deployt now, and we run the \u00bbafter\u00ab step and comparison:<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-6\" data-shcb-language-name=\"CSS\" data-shcb-language-slug=\"css\"><span><code class=\"hljs language-css\"><span class=\"hljs-selector-tag\">java<\/span> <span class=\"hljs-selector-tag\">-jar<\/span> <span class=\"hljs-selector-tag\">jlineup<\/span><span class=\"hljs-selector-class\">.jar<\/span> <span class=\"hljs-selector-tag\">--step<\/span> <span class=\"hljs-selector-tag\">after<\/span><\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-6\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">CSS<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">css<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<p>time.gov changes every second, so the command should finish with \u00bbJLineup finished. There was a difference between before and after. Return code is 1.\u00ab. In background, JLineup created a <code>report<\/code> directory that contains, among other files, the screenshot files and a report in JSON and one in HTML format.<\/p>\n\n\n\n<p>The result in HTML format looks like the following example when an error is found:<\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><noscript><img decoding=\"async\" width=\"806\" height=\"268\" src=\"https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-806x268.png\" alt class=\"wp-image-6176\" srcset=\"https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-806x268.png 806w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-300x100.png 300w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-601x200.png 601w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-768x256.png 768w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report.png 1241w\" sizes=\"(max-width: 806px) 100vw, 806px\"><\/noscript><img decoding=\"async\" width=\"806\" height=\"268\" src=\"data:image\/svg+xml,%3Csvg%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%20viewBox%3D%220%200%20806%20268%22%3E%3C%2Fsvg%3E\" alt class=\"wp-image-6176 lazyload\" srcset=\"data:image\/svg+xml,%3Csvg%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%20viewBox%3D%220%200%20806%20268%22%3E%3C%2Fsvg%3E 806w\" sizes=\"(max-width: 806px) 100vw, 806px\" data-srcset=\"https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-806x268.png 806w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-300x100.png 300w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-601x200.png 601w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-768x256.png 768w, https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report.png 1241w\" data-src=\"https:\/\/florianbrinkmann.com\/en\/wp-content\/uploads\/sites\/11\/2021\/09\/jlineup-report-806x268.png\"><\/figure>\n\n\n\n<p>The report shows information about window size, scroll position, and the difference between before and after in percent, and the before and after screenshots. If there is a difference between them, you also get an image with the difference.<\/p>\n\n\n\n<p>And that\u2019s it. As described here, one could use JLineup with GitHub actions, for example, to make sure, a change does not have unwanted side effects.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>With visual regression tests, one can check two versions of a website for visual differences. Those tests are, for example, useful to check a website on a test server before and after deploying changes, to only move the changes to the live server when no differences are found. There are various solutions to run such [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"wpf_show_in_dewp_planet_feed":false,"flobn_post_versions":"","webmentions_disabled_pings":false,"webmentions_disabled":false,"lazy_load_responsive_images_disabled":false,"footnotes":""},"categories":[6],"tags":[],"class_list":["post-6175","post","type-post","status-publish","format-standard","hentry","category-web-development"],"wp-worthy-pixel":{"ignored":false,"public":"a7a958ed8d0c46c6895d5e5deb9440be","server":"vg07.met.vgwort.de","url":"https:\/\/vg07.met.vgwort.de\/na\/a7a958ed8d0c46c6895d5e5deb9440be"},"wp-worthy-type":"normal","_links":{"self":[{"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/posts\/6175","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/comments?post=6175"}],"version-history":[{"count":4,"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/posts\/6175\/revisions"}],"predecessor-version":[{"id":6180,"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/posts\/6175\/revisions\/6180"}],"wp:attachment":[{"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/media?parent=6175"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/categories?post=6175"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/florianbrinkmann.com\/en\/wp-json\/wp\/v2\/tags?post=6175"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}