{"componentChunkName":"component---src-templates-blog-list-template-js","path":"/158","result":{"data":{"allMarkdownRemark":{"edges":[{"node":{"excerpt":"Let's face it, at some point you look at a radio or a checkbox button and you're like... this looks like something that starts with an \"s…","fields":{"slug":"/engineering/styling-radio-and-check-buttons-with-css/"},"html":"<p>Let's face it, at some point you look at a radio or a checkbox button and you're like... this looks like something that starts with an \"s\" and ends with a \"hit\". I'm here to stop you from saying that word and go on with your life without worrying about those ugly things.</p>\n<p>We're just going to use code here. No images, just pure scalable user interface using code. Cool, eh? Let's get started.</p>\n<p>Let's create our code structure first.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"0\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!-- </span><span class=\"mtk12\">Radio</span><span class=\"mtk1\"> --&gt; </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;</span><span class=\"mtk4\">label</span><span class=\"mtk17\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;</span><span class=\"mtk4\">input</span><span class=\"mtk1\"> </span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;radio&quot;</span><span class=\"mtk17\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;</span><span class=\"mtk4\">span</span><span class=\"mtk17\">&gt;</span><span class=\"mtk1\">I&#39;m a radio button</span><span class=\"mtk17\">&lt;/</span><span class=\"mtk4\">span</span><span class=\"mtk17\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;/</span><span class=\"mtk4\">label</span><span class=\"mtk17\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!-- Checkbox --&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;</span><span class=\"mtk4\">label</span><span class=\"mtk17\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;</span><span class=\"mtk4\">input</span><span class=\"mtk1\"> </span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk17\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;</span><span class=\"mtk4\">span</span><span class=\"mtk17\">&gt;</span><span class=\"mtk1\">I&#39;m a checkbox</span><span class=\"mtk17\">&lt;/</span><span class=\"mtk4\">span</span><span class=\"mtk17\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk17\">&lt;/</span><span class=\"mtk4\">label</span><span class=\"mtk17\">&gt;</span></span></code></pre>\n<p>If it looks ugly, don't be alarmed. That's normal for an untamed code from the wild. All you gotta do now is to tame it with our very best tool, CSS.</p>\n<p>First thing you have to do is to hide the element that generates the hideous button, which is... DUN DUN DUN... the input tag. Don't worry, we can still trigger it even though it's hidden. How? by nesting it inside the label tag.</p>\n<p>Now that the default toggles are gone, we need to create our fake —but amazing— toggles.</p>\n<p><strong>Radio Button</strong></p>\n<p>We can't really customize this toggle that much because it needs other toggles to work properly. Let's just prettify it a bit.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"1\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;radio&quot;</span><span class=\"mtk1\">] {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">none</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;radio&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">position</span><span class=\"mtk1\">: </span><span class=\"mtk8\">relative</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">inline-block</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">padding</span><span class=\"mtk1\">: </span><span class=\"mtk7\">3px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">0</span><span class=\"mtk1\"> </span><span class=\"mtk7\">3px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">25px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;radio&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span:before</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">content</span><span class=\"mtk1\">: </span><span class=\"mtk8\">&quot;&quot;</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">position</span><span class=\"mtk1\">: </span><span class=\"mtk8\">absolute</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">block</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">width</span><span class=\"mtk1\">: </span><span class=\"mtk7\">18px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">height</span><span class=\"mtk1\">: </span><span class=\"mtk7\">18px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">background</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#fff</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">margin-right</span><span class=\"mtk1\">: </span><span class=\"mtk7\">5px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border</span><span class=\"mtk1\">: </span><span class=\"mtk7\">1px</span><span class=\"mtk1\"> </span><span class=\"mtk8\">solid</span><span class=\"mtk1\"> </span><span class=\"mtk8\">#ccc</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border-radius</span><span class=\"mtk1\">: </span><span class=\"mtk7\">50%</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">left</span><span class=\"mtk1\">: </span><span class=\"mtk7\">0</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">top</span><span class=\"mtk1\">: </span><span class=\"mtk7\">0</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">box-sizing</span><span class=\"mtk1\">: </span><span class=\"mtk8\">border-box</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">transition</span><span class=\"mtk1\">: </span><span class=\"mtk8\">all</span><span class=\"mtk1\"> </span><span class=\"mtk7\">300ms</span><span class=\"mtk1\"> </span><span class=\"mtk8\">ease-in-out</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;radio&quot;</span><span class=\"mtk1\">]</span><span class=\"mtk6\">:checked</span><span class=\"mtk1\"> ~ </span><span class=\"mtk6\">span:before</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border</span><span class=\"mtk1\">: </span><span class=\"mtk7\">5px</span><span class=\"mtk1\"> </span><span class=\"mtk8\">solid</span><span class=\"mtk1\"> </span><span class=\"mtk8\">#29d</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span></code></pre>\n<p><span\n      class=\"gatsby-resp-image-wrapper\"\n      style=\"position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 182px; \"\n    >\n      <span\n    class=\"gatsby-resp-image-background-image\"\n    style=\"padding-bottom: 23.626373626373624%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAFCAIAAADKYVtkAAAACXBIWXMAAAsTAAALEwEAmpwYAAAAzklEQVQY05WQyw7BQBSG+5b2XsQjsOiuCxHRtDZFhLgkwkIi4hJF4hLBRDFuIQ06c2ZG3Srs/Jtzyfny/znS6EgPDhNCcPG3JF9hE2jamyXq9HtojuyTvd8dVqultbD6ZncwnmCMR4Pher0w2+YMWQjN+dtH8pe2we4ZW9N8PlfOZmrVRjZdrJQKckjW1Xg4ptVb7YiiJJO6pmpRLZEyDGDwgvGFXYF7sQGAUOpOhBJCAShljLmFEAKMUeJ8xb5j/E7yh55brxH85xufG1c3pK8UXOSsdQoAAAAASUVORK5CYII='); background-size: cover; display: block;\"\n  ></span>\n  <img\n        class=\"gatsby-resp-image-image\"\n        alt=\"checked-radio\"\n        title=\"checked-radio\"\n        src=\"/static/dd7aede644fb32d40c0126a61fa8e2b3/a51ee/checked-radio.png\"\n        srcset=\"/static/dd7aede644fb32d40c0126a61fa8e2b3/a51ee/checked-radio.png 182w\"\n        sizes=\"(max-width: 182px) 100vw, 182px\"\n        style=\"width:100%;height:100%;margin:0;vertical-align:middle;position:absolute;top:0;left:0;\"\n        loading=\"lazy\"\n      />\n    </span></p>\n<p><span\n      class=\"gatsby-resp-image-wrapper\"\n      style=\"position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 167px; \"\n    >\n      <span\n    class=\"gatsby-resp-image-background-image\"\n    style=\"padding-bottom: 23.952095808383234%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAFCAIAAADKYVtkAAAACXBIWXMAAAsTAAALEwEAmpwYAAAAuUlEQVQY06WOzQqCQBCAffa6dEwvejEPhiFETxGU/ZAYpd3EINIt0kZ33XXVVnuD+g4DA/MNn8R72p+QKKWMsbIkweV8jaI3QJameYHjBD2TOAj8O3pB+gjDG+T50fMQQkkSY1z2MmM151mWrp2lrmmblbOw7d32MDGt0WCoyLJhz113r6q6YeiKPLZMYzqzvZPfyd/spmnquuYVF48wxlXFRRHkQAjBRKyVmADAKC2KQpSKu05u/+ADkdIVMshhEA4AAAAASUVORK5CYII='); background-size: cover; display: block;\"\n  ></span>\n  <img\n        class=\"gatsby-resp-image-image\"\n        alt=\"unchecked-radio\"\n        title=\"unchecked-radio\"\n        src=\"/static/370b28a6fd25d3bb185d471d75d8cca9/21521/unchecked-radio.png\"\n        srcset=\"/static/370b28a6fd25d3bb185d471d75d8cca9/21521/unchecked-radio.png 167w\"\n        sizes=\"(max-width: 167px) 100vw, 167px\"\n        style=\"width:100%;height:100%;margin:0;vertical-align:middle;position:absolute;top:0;left:0;\"\n        loading=\"lazy\"\n      />\n    </span></p>\n<p>By now it should like this.  </p>\n<p>Cleaner toggles!</p>\n<p><strong>Checkbox</strong></p>\n<p>This one is fun to customize because it has an on and off feature or a switch. Let's start with a simple toggle. We're going to transform this hideous toggle (screenshot) to this beautiful creature (screenshot).</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"2\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label.spin</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">none</span><span class=\"mtk1\">; </span><span class=\"mtk3\">/*hides ugly toggle*/</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk6\">label.spin</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">position</span><span class=\"mtk1\">: </span><span class=\"mtk8\">relative</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">inline-block</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">padding</span><span class=\"mtk1\">: </span><span class=\"mtk7\">3px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">0</span><span class=\"mtk1\"> </span><span class=\"mtk7\">3px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">25px</span><span class=\"mtk1\">; </span><span class=\"mtk3\">/*adds spacing on the left*/</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk3\">/*create our new toggle*/</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk6\">label.spin</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span:before</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">content</span><span class=\"mtk1\">: </span><span class=\"mtk8\">&quot;</span><span class=\"mtk6\">\\2713</span><span class=\"mtk8\">&quot;</span><span class=\"mtk1\">; </span><span class=\"mtk3\">/*add a new check mark*/</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">text-align</span><span class=\"mtk1\">: </span><span class=\"mtk8\">center</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">font-size</span><span class=\"mtk1\">: </span><span class=\"mtk7\">13px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">position</span><span class=\"mtk1\">: </span><span class=\"mtk8\">absolute</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">block</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">width</span><span class=\"mtk1\">: </span><span class=\"mtk7\">18px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">height</span><span class=\"mtk1\">: </span><span class=\"mtk7\">18px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">background</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#fff</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">color</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#fff</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">margin-right</span><span class=\"mtk1\">: </span><span class=\"mtk7\">5px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border</span><span class=\"mtk1\">: </span><span class=\"mtk7\">1px</span><span class=\"mtk1\"> </span><span class=\"mtk8\">solid</span><span class=\"mtk1\"> </span><span class=\"mtk8\">#ccc</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border-radius</span><span class=\"mtk1\">: </span><span class=\"mtk7\">50%</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">left</span><span class=\"mtk1\">: </span><span class=\"mtk7\">0</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">top</span><span class=\"mtk1\">: </span><span class=\"mtk7\">0</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">box-sizing</span><span class=\"mtk1\">: </span><span class=\"mtk8\">border-box</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">transition</span><span class=\"mtk1\">: </span><span class=\"mtk8\">all</span><span class=\"mtk1\"> </span><span class=\"mtk7\">500ms</span><span class=\"mtk1\"> </span><span class=\"mtk8\">ease-in-out</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk3\">/*if checked do this*/</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk6\">label.spin</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">]</span><span class=\"mtk6\">:checked</span><span class=\"mtk1\"> ~ </span><span class=\"mtk6\">span:before</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">transform</span><span class=\"mtk1\">: </span><span class=\"mtk11\">rotatez</span><span class=\"mtk1\">(</span><span class=\"mtk7\">360deg</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">background</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#29d</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border-color</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#29d</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span></code></pre>\n<p>Oh yes! Beautiful toggle.</p>\n<p><span\n      class=\"gatsby-resp-image-wrapper\"\n      style=\"position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 157px; \"\n    >\n      <span\n    class=\"gatsby-resp-image-background-image\"\n    style=\"padding-bottom: 25.477707006369428%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAFCAIAAADKYVtkAAAACXBIWXMAAAsTAAALEwEAmpwYAAAA2klEQVQY023Py2rCUBAGYB+k79KN7+XabV14j6bWlnqBvoGrrgoiDboSOedokhaMyeSIPdeJMZui+MEMzGLmZ0rZBSopT0Kitdk/zK5cjVhMpbwqM/L47EXA0Ro4RIztOOfGaCmltRj44ZFzrWQKyc8+AkikUtoYRMyXsTwlD92N+DtprTYr7+NtMhiMveX38GX0NV+8991Oq1GrN1ynW31qOm7vddh32h1limQQ+pMl622Q31ZCpDHEcQoQE7rdF8LfkBAS+j7bBZRSRknejb0k30LEm18xu+8MtHsRCtP66PcAAAAASUVORK5CYII='); background-size: cover; display: block;\"\n  ></span>\n  <img\n        class=\"gatsby-resp-image-image\"\n        alt=\"checked-check\"\n        title=\"checked-check\"\n        src=\"/static/3e1e005085688e17655e8f0b5963e4a7/fdd16/checked-check.png\"\n        srcset=\"/static/3e1e005085688e17655e8f0b5963e4a7/fdd16/checked-check.png 157w\"\n        sizes=\"(max-width: 157px) 100vw, 157px\"\n        style=\"width:100%;height:100%;margin:0;vertical-align:middle;position:absolute;top:0;left:0;\"\n        loading=\"lazy\"\n      />\n    </span></p>\n<p><span\n      class=\"gatsby-resp-image-wrapper\"\n      style=\"position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 159px; \"\n    >\n      <span\n    class=\"gatsby-resp-image-background-image\"\n    style=\"padding-bottom: 24.528301886792455%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAFCAIAAADKYVtkAAAACXBIWXMAAAsTAAALEwEAmpwYAAAA4UlEQVQY02WPQWvCQBCFc9L/418sFLxbgo1GbAm24EFavHlVFL15ENpA080mwaQxRpfN7rqZdRUEq98wMLxhePMMpZQsS04plxLUNXCuy/wfOAuGPBy4UuT7a12r0Y9BSkjgY0qp1oUQukMcsKLgjOXbbZQkhOwZF9oPAAy9KKRkUcQqVfH4sHTdN6sz+BwtZuN+fzieTN/btmk+mc1n22rVG81Xp/vSsXpO7+SsP0iybL1asfkcSllQmqdZviPpX+zjMI7jTbbxA4y83ygMPYQRQp73gzGG0/EdcBv9LvGFIxuREBwjsGf8AAAAAElFTkSuQmCC'); background-size: cover; display: block;\"\n  ></span>\n  <img\n        class=\"gatsby-resp-image-image\"\n        alt=\"unchecked-checkbox\"\n        title=\"unchecked-checkbox\"\n        src=\"/static/0d23223ae9ca968f75a80edb9d1cbaa7/f69fa/unchecked-checkbox.png\"\n        srcset=\"/static/0d23223ae9ca968f75a80edb9d1cbaa7/f69fa/unchecked-checkbox.png 159w\"\n        sizes=\"(max-width: 159px) 100vw, 159px\"\n        style=\"width:100%;height:100%;margin:0;vertical-align:middle;position:absolute;top:0;left:0;\"\n        loading=\"lazy\"\n      />\n    </span></p>\n<p><strong>Bonus!</strong></p>\n<p>Have you ever seen those toggles where it slides to the left and right when you click it? Did you know you can do that too using CSS? Let's try it.</p>\n<p>First, we're going to design the default look of an unchecked checkbox. By now you know that we need to hide the default toggle.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"3\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] { </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">none</span><span class=\"mtk1\">; }</span></span></code></pre>\n<p>And then add a space on the left of the span using padding. While you're there, add a position relative to because we need to contain the rest of the elements inside the span.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"4\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span</span><span class=\"mtk1\"> { </span><span class=\"mtk12\">position</span><span class=\"mtk1\">: </span><span class=\"mtk8\">relative</span><span class=\"mtk1\">; </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">inline-block</span><span class=\"mtk1\">; </span><span class=\"mtk12\">padding</span><span class=\"mtk1\">: </span><span class=\"mtk7\">3px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">0</span><span class=\"mtk1\"> </span><span class=\"mtk7\">3px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">35px</span><span class=\"mtk1\">; }</span></span></code></pre>\n<p>Now, let's create our toggles using CSS pseudo element :before and :after. Why? Because generated CSS is easier to handle.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"5\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span:before</span><span class=\"mtk1\">, </span><span class=\"mtk6\">label.slide</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span:after</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">content</span><span class=\"mtk1\">: </span><span class=\"mtk8\">&quot;&quot;</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">position</span><span class=\"mtk1\">: </span><span class=\"mtk8\">absolute</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">display</span><span class=\"mtk1\">: </span><span class=\"mtk8\">block</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">width</span><span class=\"mtk1\">: </span><span class=\"mtk7\">18px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">height</span><span class=\"mtk1\">: </span><span class=\"mtk7\">18px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">background</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#fff</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">margin-right</span><span class=\"mtk1\">: </span><span class=\"mtk7\">5px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border</span><span class=\"mtk1\">: </span><span class=\"mtk7\">1px</span><span class=\"mtk1\"> </span><span class=\"mtk8\">solid</span><span class=\"mtk1\"> </span><span class=\"mtk8\">#ccc</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">left</span><span class=\"mtk1\">: </span><span class=\"mtk7\">0</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">top</span><span class=\"mtk1\">: </span><span class=\"mtk7\">0</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">box-sizing</span><span class=\"mtk1\">: </span><span class=\"mtk8\">border-box</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">transition</span><span class=\"mtk1\">: </span><span class=\"mtk8\">all</span><span class=\"mtk1\"> </span><span class=\"mtk7\">300ms</span><span class=\"mtk1\"> </span><span class=\"mtk8\">ease-in-out</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span></code></pre>\n<p>This will generate a box looking element. Since it's targeting both pseudo elements, they will look identical and on top of each other.</p>\n<p>It's time to start prettifying those pseudo elements.</p>\n<p>For :after, since this is the background where the :before toggle slides through. We need to modify the width to look bigger. Add an inset shadow to make it look like it's pushed through and a red background for an \"off\" effect.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"6\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span:before</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">width</span><span class=\"mtk1\">: </span><span class=\"mtk7\">30px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border-radius</span><span class=\"mtk1\">: </span><span class=\"mtk7\">20px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">box-shadow</span><span class=\"mtk1\">: </span><span class=\"mtk8\">inset</span><span class=\"mtk1\"> </span><span class=\"mtk7\">0</span><span class=\"mtk1\"> </span><span class=\"mtk7\">2px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">5px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">-1px</span><span class=\"mtk1\"> </span><span class=\"mtk11\">rgba</span><span class=\"mtk1\">(</span><span class=\"mtk7\">0</span><span class=\"mtk1\">, </span><span class=\"mtk7\">0</span><span class=\"mtk1\">, </span><span class=\"mtk7\">0</span><span class=\"mtk1\">, </span><span class=\"mtk7\">0.4</span><span class=\"mtk1\">), </span><span class=\"mtk8\">inset</span><span class=\"mtk1\"> </span><span class=\"mtk7\">0</span><span class=\"mtk1\"> </span><span class=\"mtk7\">-2px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">0</span><span class=\"mtk1\"> </span><span class=\"mtk7\">-1px</span><span class=\"mtk1\"> </span><span class=\"mtk11\">rgba</span><span class=\"mtk1\">(</span><span class=\"mtk7\">255</span><span class=\"mtk1\">, </span><span class=\"mtk7\">255</span><span class=\"mtk1\">, </span><span class=\"mtk7\">255</span><span class=\"mtk1\">, </span><span class=\"mtk7\">0.2</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">background</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#F22613</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span></code></pre>\n<p>For :before, we just need to make it look like a circle and lift it off a bit using box-shadow.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"7\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label.slide</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">] ~ </span><span class=\"mtk6\">span:after</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">box-shadow</span><span class=\"mtk1\">: </span><span class=\"mtk7\">0</span><span class=\"mtk1\"> </span><span class=\"mtk7\">3px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">4px</span><span class=\"mtk1\"> </span><span class=\"mtk7\">-2px</span><span class=\"mtk1\"> </span><span class=\"mtk11\">rgba</span><span class=\"mtk1\">(</span><span class=\"mtk7\">0</span><span class=\"mtk1\">, </span><span class=\"mtk7\">0</span><span class=\"mtk1\">, </span><span class=\"mtk7\">0</span><span class=\"mtk1\">, </span><span class=\"mtk7\">0.5</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">border-radius</span><span class=\"mtk1\">: </span><span class=\"mtk7\">50%</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span></code></pre>\n<p>The \"on\" part just needs a little bit of pushing to the side and changing the background to blue or green.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"css\" data-index=\"8\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk6\">label.slide</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">]</span><span class=\"mtk6\">:checked</span><span class=\"mtk1\"> ~ </span><span class=\"mtk6\">span:before</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">background</span><span class=\"mtk1\">: </span><span class=\"mtk8\">#29d</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk6\">label.slide</span><span class=\"mtk1\"> </span><span class=\"mtk6\">input</span><span class=\"mtk1\">[</span><span class=\"mtk12\">type</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;checkbox&quot;</span><span class=\"mtk1\">]</span><span class=\"mtk6\">:checked</span><span class=\"mtk1\"> ~ </span><span class=\"mtk6\">span:after</span><span class=\"mtk1\"> {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">left</span><span class=\"mtk1\">: </span><span class=\"mtk7\">13px</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span></code></pre>\n<p>The CSS is a bit longer here because there's a lot of elements that need to change, but take a chill pill because CSS won't slow your page down.</p>\n<p>And that's it. Your pretty checkbox or radio button toggles.</p>\n<style class=\"grvsc-styles\">\n  .grvsc-container {\n    overflow: auto;\n    -webkit-overflow-scrolling: touch;\n    padding-top: 1rem;\n    padding-top: var(--grvsc-padding-top, var(--grvsc-padding-v, 1rem));\n    padding-bottom: 1rem;\n    padding-bottom: var(--grvsc-padding-bottom, var(--grvsc-padding-v, 1rem));\n    border-radius: 8px;\n    border-radius: var(--grvsc-border-radius, 8px);\n    font-feature-settings: normal;\n  }\n  \n  .grvsc-code {\n    display: inline-block;\n    min-width: 100%;\n  }\n  \n  .grvsc-line {\n    display: inline-block;\n    box-sizing: border-box;\n    width: 100%;\n    padding-left: 1.5rem;\n    padding-left: var(--grvsc-padding-left, var(--grvsc-padding-h, 1.5rem));\n    padding-right: 1.5rem;\n    padding-right: var(--grvsc-padding-right, var(--grvsc-padding-h, 1.5rem));\n  }\n  \n  .grvsc-line-highlighted {\n    background-color: var(--grvsc-line-highlighted-background-color, transparent);\n    box-shadow: inset var(--grvsc-line-highlighted-border-width, 4px) 0 0 0 var(--grvsc-line-highlighted-border-color, transparent);\n  }\n  \n  .dark-default-dark {\n    background-color: #1E1E1E;\n    color: #D4D4D4;\n  }\n  .dark-default-dark .mtk1 { color: #D4D4D4; }\n  .dark-default-dark .mtk12 { color: #9CDCFE; }\n  .dark-default-dark .mtk17 { color: #808080; }\n  .dark-default-dark .mtk4 { color: #569CD6; }\n  .dark-default-dark .mtk8 { color: #CE9178; }\n  .dark-default-dark .mtk6 { color: #D7BA7D; }\n  .dark-default-dark .mtk7 { color: #B5CEA8; }\n  .dark-default-dark .mtk3 { color: #6A9955; }\n  .dark-default-dark .mtk11 { color: #DCDCAA; }\n</style>","frontmatter":{"date":"June 16, 2015","updated_date":null,"description":null,"title":"Styling Radio and Check buttons with CSS","tags":["CSS"],"pinned":null,"coverImage":{"childImageSharp":{"fluid":{"aspectRatio":1,"src":"/static/56b8ac1b7f3b7dfdc03ce43aa1e62eaa/7d145/radio-check-buttons-css-1.png","srcSet":"/static/56b8ac1b7f3b7dfdc03ce43aa1e62eaa/69585/radio-check-buttons-css-1.png 200w,\n/static/56b8ac1b7f3b7dfdc03ce43aa1e62eaa/497c6/radio-check-buttons-css-1.png 400w,\n/static/56b8ac1b7f3b7dfdc03ce43aa1e62eaa/7d145/radio-check-buttons-css-1.png 610w","sizes":"(max-width: 610px) 100vw, 610px"}}},"author":{"id":"Team LoginRadius","github":"LoginRadius","avatar":null}}}},{"node":{"excerpt":"Social sharing button offers an easy way to distribute your content to a wider audience. The major social providers allow options to…","fields":{"slug":"/engineering/configuring-social-sharing-buttons/"},"html":"<p>Social sharing button offers an easy way to distribute your content to a wider audience. The major social providers allow options to configure the content that will be shared programmatically. In this guide we explore the options that you can use in order to configure the shared content of your social shares including: Message, URL, Image, and Image Caption/Description.</p>\n<p><strong>Facebook</strong></p>\n<p>Facebook utilizes Open Graph Tags which are meta tags that can be included on your page and are scrapped by Facebook when determining the content that should be shared with a specific button. These tags can be included in the head section of your page. All meta tags should be formatted with a property value of \"og:<tag-name>\", some useful tag names are:</p>\n<ul>\n<li>title- The title of your article.</li>\n<li>type- The media content that is included in the shared article. This is defaulted to \"website\".</li>\n<li>image- The image that will be included in the share.</li>\n<li>url- The canonical URL that will be used to identify the share and aggregate the community shares/likes.</li>\n<li>description- A  brief description that is displayed below the image in the share.</li>\n</ul>\n<p>Example of og meta tags that can be included in your html head tag:</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"0\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!--</span></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">--&gt;</span></span></code></pre>\n<p>If you are modifying these tags it can take some time for the changes to translate over to Facebook. You can refer to <a href=\"/social-provider-social-sharing-troubleshooting-resources/\">this blog</a> on troubleshooting, testing, and force updating your configured sharing systems.</p>\n<p><strong>Google</strong></p>\n<p>Google offers multiple ways that you can set the shared content which it intelligently determines the most relevant details to be displayed in the share. This works to varying degrees with the following options available and taking precedence respectively:</p>\n<ul>\n<li>Structured Data Markup- HTML markup detailed on <a href=\"http://schema.org/\">Schema</a>.</li>\n<li>Open Graph Tags- Turn your page into a rich data object, commonly used to customize Facebook sharing details. Information on the markup is available on <a href=\"http://ogp.me/\">OGP</a></li>\n<li>Title or Meta Description- HTML attributes that provide details on the site.</li>\n<li>Google’s best guess- If none of the above are included, Google will crawl your page and try to interpret the most suitable details to include in the share.</li>\n</ul>\n<p>Below is an example of basic structured data markup:</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"1\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!--</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Your</span><span class=\"mtk1\"> </span><span class=\"mtk12\">Site</span><span class=\"mtk1\"> </span><span class=\"mtk12\">Title</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk12\">A</span><span class=\"mtk1\"> </span><span class=\"mtk12\">description</span><span class=\"mtk1\"> </span><span class=\"mtk4\">of</span><span class=\"mtk1\"> </span><span class=\"mtk12\">your</span><span class=\"mtk1\"> </span><span class=\"mtk12\">site</span><span class=\"mtk1\">.</span></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">--&gt;</span></span></code></pre>\n<p>Below is an example of using basic meta tags to define the shared content:</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"2\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!--</span></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">--&gt;</span></span></code></pre>\n<p><strong>Twitter</strong></p>\n<p>The best way to customize your Twitter shares is to modify the URL query string parameters that gets triggered when the share icon is clicked. Another way is to customize the <code>&#x3C;a></code> tag by including data-attribute tags as detailed on Twitters <a href=\"https://developer.twitter.com/en/docs/twitter-for-websites/tweet-button/overview\">Tweet button creation instructions</a> . If you do not have control over the links or triggers that are being used to activate the Tweet popup you can also set Twitter Card meta tags which handle the Twitter customizations.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"3\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!--</span></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">--&gt;</span></span></code></pre>\n<p>Various providers will utilize some of the above methods with open graph tags being one of the most common methods for controlling the shared content. Other systems will customize this content based off of parameters that are passed into the script or URL that is used to trigger the share interface. Getting these to be correctly configured can be a bit of a trial and error process, you can use the resources detailed in <a href=\"/social-provider-social-sharing-troubleshooting-resources/\">this blog post</a> to help test and verify that you have correctly configured your social sharing content.</p>\n<style class=\"grvsc-styles\">\n  .grvsc-container {\n    overflow: auto;\n    -webkit-overflow-scrolling: touch;\n    padding-top: 1rem;\n    padding-top: var(--grvsc-padding-top, var(--grvsc-padding-v, 1rem));\n    padding-bottom: 1rem;\n    padding-bottom: var(--grvsc-padding-bottom, var(--grvsc-padding-v, 1rem));\n    border-radius: 8px;\n    border-radius: var(--grvsc-border-radius, 8px);\n    font-feature-settings: normal;\n  }\n  \n  .grvsc-code {\n    display: inline-block;\n    min-width: 100%;\n  }\n  \n  .grvsc-line {\n    display: inline-block;\n    box-sizing: border-box;\n    width: 100%;\n    padding-left: 1.5rem;\n    padding-left: var(--grvsc-padding-left, var(--grvsc-padding-h, 1.5rem));\n    padding-right: 1.5rem;\n    padding-right: var(--grvsc-padding-right, var(--grvsc-padding-h, 1.5rem));\n  }\n  \n  .grvsc-line-highlighted {\n    background-color: var(--grvsc-line-highlighted-background-color, transparent);\n    box-shadow: inset var(--grvsc-line-highlighted-border-width, 4px) 0 0 0 var(--grvsc-line-highlighted-border-color, transparent);\n  }\n  \n  .dark-default-dark {\n    background-color: #1E1E1E;\n    color: #D4D4D4;\n  }\n  .dark-default-dark .mtk1 { color: #D4D4D4; }\n  .dark-default-dark .mtk12 { color: #9CDCFE; }\n  .dark-default-dark .mtk4 { color: #569CD6; }\n</style>","frontmatter":{"date":"June 09, 2015","updated_date":null,"description":null,"title":"Configuring Your Social Sharing Buttons","tags":["SocialSharing"],"pinned":null,"coverImage":{"childImageSharp":{"fluid":{"aspectRatio":1,"src":"/static/238b1852ad4d0bf59dc00d0079239993/630fb/configuring-social-share-buttons-300x300.png","srcSet":"/static/238b1852ad4d0bf59dc00d0079239993/69585/configuring-social-share-buttons-300x300.png 200w,\n/static/238b1852ad4d0bf59dc00d0079239993/630fb/configuring-social-share-buttons-300x300.png 300w","sizes":"(max-width: 300px) 100vw, 300px"}}},"author":{"id":"Karl Wittig","github":null,"avatar":null}}}},{"node":{"excerpt":"Recently, I was working on an implementation to build an embedded app on Shopify with PHP. I realized that the 3rd party PHP SDK recommended…","fields":{"slug":"/engineering/shopify-embedded-app/"},"html":"<p>Recently, I was working on an implementation to build an embedded app on Shopify with PHP. I realized that the 3rd party PHP SDK recommended by Shopify called \"phpish\" does not support the feature to \"PUT\" assets into your shopify shop's theme. The link to \"phpish\" git repository can be found  <a href=\"https://github.com/phpish/shopify\">here</a>, I'd like to thank these guys for their great work, it saved me lots of time to get the implementation on the right track.</p>\n<p>So if you want to do a PUT API call to Shopify web service, you can do it in raw PHP by customizing a CURL request, this is not very hard. But prior to make the Asset API call, first you need to retrieve the currently activated theme ID by calling the Shopify Theme API call, this part can be done easily with the help of phpish.</p>\n<p>Then it is the time to customize your CURL request to do the PUT API call, remember phpish stores our information such as Oauth Token and Shop into the $_SESSION, we can leverage on that or manually fill in the correct information</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"php\" data-index=\"0\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!-- </span><span class=\"mtk11\">array</span><span class=\"mtk1\">(</span><span class=\"mtk8\">&quot;key&quot;</span><span class=\"mtk1\"> =&gt; </span><span class=\"mtk8\">&quot;snippets/put-asset.liquid&quot;</span><span class=\"mtk1\">, </span><span class=\"mtk8\">&quot;value&quot;</span><span class=\"mtk1\"> =&gt; </span><span class=\"mtk8\">&quot;this is a test to put assets&quot;</span><span class=\"mtk1\">));</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$ch</span><span class=\"mtk1\"> = </span><span class=\"mtk11\">curl_init</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$_SESSION</span><span class=\"mtk1\">[</span><span class=\"mtk8\">&#39;shop&#39;</span><span class=\"mtk1\">].</span><span class=\"mtk8\">&quot;/admin/themes/</span><span class=\"mtk12\">$theme_id</span><span class=\"mtk8\">/assets.json&quot;</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">curl_setopt</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">, CURLOPT_RETURNTRANSFER, </span><span class=\"mtk4\">true</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">curl_setopt</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">, CURLOPT_CUSTOMREQUEST, </span><span class=\"mtk8\">&quot;PUT&quot;</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$headers</span><span class=\"mtk1\"> = </span><span class=\"mtk11\">array</span><span class=\"mtk1\">();</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$headers</span><span class=\"mtk1\">[] = </span><span class=\"mtk8\">&quot;X-Shopify-Access-Token: &quot;</span><span class=\"mtk1\">.</span><span class=\"mtk11\">echo</span><span class=\"mtk1\"> </span><span class=\"mtk12\">$_SESSION</span><span class=\"mtk1\">[</span><span class=\"mtk8\">&#39;oauth_token&#39;</span><span class=\"mtk1\">];</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$headers</span><span class=\"mtk1\">[] = </span><span class=\"mtk8\">&quot;Content-Type: application/json&quot;</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">curl_setopt</span><span class=\"mtk1\">( </span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">, CURLOPT_HTTPHEADER, </span><span class=\"mtk12\">$headers</span><span class=\"mtk1\"> );</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">curl_setopt</span><span class=\"mtk1\">( </span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">, CURLOPT_POSTFIELDS, </span><span class=\"mtk11\">json_encode</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$data</span><span class=\"mtk1\">));</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$response</span><span class=\"mtk1\"> = </span><span class=\"mtk11\">curl_exec</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">echo</span><span class=\"mtk1\"> </span><span class=\"mtk8\">&quot;&quot;</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">echo</span><span class=\"mtk1\"> </span><span class=\"mtk11\">curl_error</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">).</span><span class=\"mtk8\">&quot;&quot;</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">var_dump</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$response</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">curl_close</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">?&gt;--&gt;</span></span></code></pre>\n<p>Let me briefly explain this snippet, so first you define an array with key and value, key maps to the file name that you want to create, and value is the actual code or asset you want to pass in. Then you create a curl request with method \"PUT\" like all the other requests</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"php\" data-index=\"1\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk12\">$ch</span><span class=\"mtk1\"> = </span><span class=\"mtk11\">curl_init</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$_SESSION</span><span class=\"mtk1\">[</span><span class=\"mtk8\">&#39;shop&#39;</span><span class=\"mtk1\">].</span><span class=\"mtk8\">&quot;/admin/themes/</span><span class=\"mtk12\">$theme_id</span><span class=\"mtk8\">/assets.json&quot;</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">curl_setopt</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">, CURLOPT_RETURNTRANSFER, </span><span class=\"mtk4\">true</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">curl_setopt</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">, CURLOPT_CUSTOMREQUEST, </span><span class=\"mtk8\">&quot;PUT&quot;</span><span class=\"mtk1\">);</span></span></code></pre>\n<p>Next is something special for Shopify, to make an API call to Shopify you have to specify Oauth_Token in your request to tell Shopify who you are, and so does Content-Type.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"php\" data-index=\"2\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk12\">$headers</span><span class=\"mtk1\"> = </span><span class=\"mtk11\">array</span><span class=\"mtk1\">();</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$headers</span><span class=\"mtk1\">[] = </span><span class=\"mtk8\">&quot;X-Shopify-Access-Token: &quot;</span><span class=\"mtk1\">.</span><span class=\"mtk11\">echo</span><span class=\"mtk1\"> </span><span class=\"mtk12\">$_SESSION</span><span class=\"mtk1\">[</span><span class=\"mtk8\">&#39;oauth_token&#39;</span><span class=\"mtk1\">];</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$headers</span><span class=\"mtk1\">[] = </span><span class=\"mtk8\">&quot;Content-Type: application/json&quot;</span><span class=\"mtk1\">;</span></span></code></pre>\n<p>Last but not least, json encode your data array into JSON format and send the request.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"php\" data-index=\"3\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk11\">curl_setopt</span><span class=\"mtk1\">( </span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">, CURLOPT_POSTFIELDS, </span><span class=\"mtk11\">json_encode</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$data</span><span class=\"mtk1\">));</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk12\">$response</span><span class=\"mtk1\"> = </span><span class=\"mtk11\">curl_exec</span><span class=\"mtk1\">(</span><span class=\"mtk12\">$ch</span><span class=\"mtk1\">);</span></span></code></pre>\n<p>The last part is just to catch the returned response or show the error message from your CURL request if something is going wrong.</p>\n<p>Hope this can help someone, happy coding.</p>\n<style class=\"grvsc-styles\">\n  .grvsc-container {\n    overflow: auto;\n    -webkit-overflow-scrolling: touch;\n    padding-top: 1rem;\n    padding-top: var(--grvsc-padding-top, var(--grvsc-padding-v, 1rem));\n    padding-bottom: 1rem;\n    padding-bottom: var(--grvsc-padding-bottom, var(--grvsc-padding-v, 1rem));\n    border-radius: 8px;\n    border-radius: var(--grvsc-border-radius, 8px);\n    font-feature-settings: normal;\n  }\n  \n  .grvsc-code {\n    display: inline-block;\n    min-width: 100%;\n  }\n  \n  .grvsc-line {\n    display: inline-block;\n    box-sizing: border-box;\n    width: 100%;\n    padding-left: 1.5rem;\n    padding-left: var(--grvsc-padding-left, var(--grvsc-padding-h, 1.5rem));\n    padding-right: 1.5rem;\n    padding-right: var(--grvsc-padding-right, var(--grvsc-padding-h, 1.5rem));\n  }\n  \n  .grvsc-line-highlighted {\n    background-color: var(--grvsc-line-highlighted-background-color, transparent);\n    box-shadow: inset var(--grvsc-line-highlighted-border-width, 4px) 0 0 0 var(--grvsc-line-highlighted-border-color, transparent);\n  }\n  \n  .dark-default-dark {\n    background-color: #1E1E1E;\n    color: #D4D4D4;\n  }\n  .dark-default-dark .mtk1 { color: #D4D4D4; }\n  .dark-default-dark .mtk11 { color: #DCDCAA; }\n  .dark-default-dark .mtk8 { color: #CE9178; }\n  .dark-default-dark .mtk12 { color: #9CDCFE; }\n  .dark-default-dark .mtk4 { color: #569CD6; }\n</style>","frontmatter":{"date":"June 02, 2015","updated_date":null,"description":null,"title":"Shopify Embedded App","tags":["Shopify","PHP"],"pinned":null,"coverImage":{"childImageSharp":{"fluid":{"aspectRatio":1.8867924528301887,"src":"/static/4872b27152104126f3a84ce3bb3dc334/2b011/shopify.png","srcSet":"/static/4872b27152104126f3a84ce3bb3dc334/69585/shopify.png 200w,\n/static/4872b27152104126f3a84ce3bb3dc334/2b011/shopify.png 308w","sizes":"(max-width: 308px) 100vw, 308px"}}},"author":{"id":"Lucius Yu","github":null,"avatar":null}}}},{"node":{"excerpt":"Are you having trouble with accessing API endpoint?   Unsure why your API is not returning data? Most modern browsers have tools or plugins…","fields":{"slug":"/engineering/api-debugging-tools/"},"html":"<p><strong>Are you having trouble with accessing API endpoint?</strong>   <strong>Unsure why your API is not returning data?</strong> Most modern browsers have tools or plugins that allows you to quickly and easily test your API calls and see the sample returned data. In this post we go through some tools available for common browsers and web tools that will cut down the total troubleshooting time.</p>\n<h2 id=\"google-chrome\" style=\"position:relative;\"><a href=\"#google-chrome\" aria-label=\"google chrome permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Google Chrome</h2>\n<p>Chrome offers a wide variety of apps that are quick and easy to install through the <a href=\"https://chrome.google.com/webstore/\">Chrome app webstore</a>. <a href=\"http://www.getpostman.com/\">Postman</a> is one of those app and it offers a very robust REST API testing solution. It allows you to quickly create and format a wide range of API calls, and keeps a record of previously accessed APIs for easy reference and reuse. Postman have an easy to understand interface that allows you to quickly reformat the included parameters, headers, and form data. Returned data can be viewed in multiple different formats depending on your preferences.</p>\n<p>Another added benefit of Postman is its built-in support for common authentication procedures like: Basic Auth, Digest Auth, and OAuth 1.0/2.0. These \"helpers\" allow you to bypass some of the common tasks that can be troublesome in the mentioned protocols such as signing your request(OAuth 1.0) or requesting an Access token(OAuth 2.0).</p>\n<h2 id=\"mozilla-firefox\" style=\"position:relative;\"><a href=\"#mozilla-firefox\" aria-label=\"mozilla firefox permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Mozilla Firefox</h2>\n<p>Poster or RestClient are both useful tools that allow you to test out your API calls within Mozilla Firefox. They offer many similar systems as Postman, allowing you to set various parts of your API quickly and easily. With built in features to set such as Base URL, Auth method, Timeout, Action, Content, headers, and query parameters; It returns a complete response object allowing you to troubleshoot APIs before integrating them into your systems. Both RestClient and Poster allow you to save your requests for future use.</p>\n<h2 id=\"other-systems\" style=\"position:relative;\"><a href=\"#other-systems\" aria-label=\"other systems permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Other Systems</h2>\n<p><strong>Runscope:</strong> This is a powerful tool that allows you to set up test cases for your APIs. Which makes it easy for you to not only handle many of the features as described in the above two systems, but to also schedule these requests to perform periodically. This allows you to monitor your APIs and have email notifications sent out when specific conditions are met. You can also mask the API requests to run them from different locations worldwide allowing you to test user cases from a global audience.</p>\n<p><strong>SoapUI:</strong> This is an extremely robust solution that can handle your entire testing environment. It also have built in features to test out RESTful API calls, as well as SOAP calls. This solution is very extensive and has many options that cover the full suite of features detailed in the above technologies. On top of that, they have a well formatted instructions available on their site, detailing how to setup and configure the program.</p>\n<style class=\"grvsc-styles\">\n  .grvsc-container {\n    overflow: auto;\n    -webkit-overflow-scrolling: touch;\n    padding-top: 1rem;\n    padding-top: var(--grvsc-padding-top, var(--grvsc-padding-v, 1rem));\n    padding-bottom: 1rem;\n    padding-bottom: var(--grvsc-padding-bottom, var(--grvsc-padding-v, 1rem));\n    border-radius: 8px;\n    border-radius: var(--grvsc-border-radius, 8px);\n    font-feature-settings: normal;\n  }\n  \n  .grvsc-code {\n    display: inline-block;\n    min-width: 100%;\n  }\n  \n  .grvsc-line {\n    display: inline-block;\n    box-sizing: border-box;\n    width: 100%;\n    padding-left: 1.5rem;\n    padding-left: var(--grvsc-padding-left, var(--grvsc-padding-h, 1.5rem));\n    padding-right: 1.5rem;\n    padding-right: var(--grvsc-padding-right, var(--grvsc-padding-h, 1.5rem));\n  }\n  \n  .grvsc-line-highlighted {\n    background-color: var(--grvsc-line-highlighted-background-color, transparent);\n    box-shadow: inset var(--grvsc-line-highlighted-border-width, 4px) 0 0 0 var(--grvsc-line-highlighted-border-color, transparent);\n  }\n  \n</style>","frontmatter":{"date":"May 26, 2015","updated_date":null,"description":null,"title":"API Debugging Tools","tags":["Engineering","GoogleChorme","MozilaFirefox","SoupUI","RunScope"],"pinned":null,"coverImage":{"childImageSharp":{"fluid":{"aspectRatio":1,"src":"/static/949b6e4da71216d7a55b82e01a8bcaa1/630fb/api_debugging-tools-300x300.png","srcSet":"/static/949b6e4da71216d7a55b82e01a8bcaa1/69585/api_debugging-tools-300x300.png 200w,\n/static/949b6e4da71216d7a55b82e01a8bcaa1/630fb/api_debugging-tools-300x300.png 300w","sizes":"(max-width: 300px) 100vw, 300px"}}},"author":{"id":"Karl Wittig","github":null,"avatar":null}}}},{"node":{"excerpt":"Overview Filter Portfolio can be very useful for websites, especially when there is a lot of images you want to show to users. It is always…","fields":{"slug":"/engineering/use-php-to-generate-filter-portfolio/"},"html":"<p><strong>Overview</strong></p>\n<p>Filter Portfolio can be very useful for websites, especially when there is a lot of images you want to show to users. It is always nice to keep it into different categories and allow your user to play with them.</p>\n<p>But adding a tag and a div on hundreds of images is definitely not fun. Our goal today is to use PHP to generate the Filter Portfolio instead of manually adding them one by one.</p>\n<p>The logic is like this, first we have a folder to contain all the portfolio images. It could be like this:</p>\n<p>\"assets->img->logos->businesses\"</p>\n<p><span\n      class=\"gatsby-resp-image-wrapper\"\n      style=\"position: relative; display: block; margin-left: auto; margin-right: auto; max-width: 670px; \"\n    >\n      <span\n    class=\"gatsby-resp-image-background-image\"\n    style=\"padding-bottom: 58.00000000000001%; position: relative; bottom: 0; left: 0; background-image: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAMCAIAAADtbgqsAAAACXBIWXMAAAsTAAALEwEAmpwYAAABVUlEQVQoz8WRz04CMRDG9+V9AA++hheNBwXUSDSCEdEAahRkYbfl32a72+522g5jV4zRxAPx4nea9ptf5ps20HKKTlmHWnFTLpxD0AJKbi0YA1pF1siN62BVuWUKKkaEoiiCbHGx5CERlaItlk+4JqeHfFQzxhBBwuoi5d6F/CYOO4iEMEzYtS4KAAj4y+H1aZOslfPGbNK3jlze7TT2UmGJbOto57bd9LCcn7Qu6xbJqd6oV5vFmXUmYOF9FDEAK1bDcPwqFZDL2GSQy5II2fhuGkYeTvhjFA6zvECT8ukgz1U1WYp5JhLEtYVcF6lzzrci4qbw2hQOCcBY6+P4lNb3a62D1G+VvFbBVleLuOupD2RNn/oqvqu6rOD++W7v4dgfps/7Z7WDsoTKXP/K/FAFs7cWY7FPVYgXHo00GNpOFezfXEn18TEkc7nZaluY/qp/hd8Bhl60n/dN47sAAAAASUVORK5CYII='); background-size: cover; display: block;\"\n  ></span>\n  <img\n        class=\"gatsby-resp-image-image\"\n        alt=\"folder-structure\"\n        title=\"folder-structure\"\n        src=\"/static/d4a3eedb9dab04f462db04bf921452f6/d67fd/folder-structure.png\"\n        srcset=\"/static/d4a3eedb9dab04f462db04bf921452f6/a6d36/folder-structure.png 650w,\n/static/d4a3eedb9dab04f462db04bf921452f6/d67fd/folder-structure.png 670w\"\n        sizes=\"(max-width: 670px) 100vw, 670px\"\n        style=\"width:100%;height:100%;margin:0;vertical-align:middle;position:absolute;top:0;left:0;\"\n        loading=\"lazy\"\n      />\n    </span></p>\n<p>And in the \"businesses\" folder, we have some sub-folders to put all the images in different categories, like this:  </p>\n<p>Each sub-folder contains different images in that category, and our goal is to use those sub-folders name as the filters, and the images under each category will be added automatically. Let's do it.</p>\n<ul>\n<li>First we need to implement a filter portfolio.</li>\n</ul>\n<p>I know people hate this, but we are going to use a little pre-built javascript file called MixitUp, I promise it is a very easy but powerful tool to use, see a <a href=\"http://www.jqueryrain.com/?URGti1_4\">demo here</a>.</p>\n<p>There is already very comprehensive tutorial on how to install that plugin  in their <a href=\"https://github.com/patrickkunka/mixitup\">github</a> repository, you can follow either of these.</p>\n<ol>\n<li><strong>Download the javascript file from github</strong></li>\n</ol>\n<p>Click this link <a href=\"https://github.com/patrickkunka/mixitup/tree/v3/src\">git -> src</a> to open the repository for the javascript file, download and save it in your asset folder.</p>\n<ol>\n<li><strong>Import js and css</strong></li>\n</ol>\n<p>You can do this right before the closing body tag. You probably have Jquery installed already, but just in case you don't.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"0\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!--</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">--&gt;</span></span></code></pre>\n<p>It is recommended to link your Mixitup function while your document is ready, so add this after the importing lines.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"1\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!--</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">$</span><span class=\"mtk1\">(</span><span class=\"mtk12\">document</span><span class=\"mtk1\">).</span><span class=\"mtk11\">ready</span><span class=\"mtk1\">(</span><span class=\"mtk4\">function</span><span class=\"mtk1\">(){</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk11\">jQuery</span><span class=\"mtk1\">(</span><span class=\"mtk4\">function</span><span class=\"mtk1\">(){</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        </span><span class=\"mtk11\">$</span><span class=\"mtk1\">(</span><span class=\"mtk4\">function</span><span class=\"mtk1\">() {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">            </span><span class=\"mtk11\">$</span><span class=\"mtk1\">(</span><span class=\"mtk8\">&#39;#Container&#39;</span><span class=\"mtk1\">).</span><span class=\"mtk11\">mixItUp</span><span class=\"mtk1\">();</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        });</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    });</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">});</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">--&gt;</span></span></code></pre>\n<ol>\n<li><strong>Add the code</strong></li>\n</ol>\n<p>Here is where the fun begins! I am not going to do any stylings in this tutorial, since you can always customize it yourself. Okay, first of first, add a div as a container of your filter portfolio section, so:</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"2\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!----&gt;</span></span></code></pre>\n<p>Next, we need to add those clickable filter buttons to the div we just created. We can add them programmatically, but to be honest, it is not that bad to do it manually.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"js\" data-index=\"3\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!-- </span><span class=\"mtk12\">All</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Eateries</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Cafes</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Bars</span><span class=\"mtk1\">, </span><span class=\"mtk12\">Clubs</span><span class=\"mtk1\"> & </span><span class=\"mtk12\">Lounges</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Lifestyle</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Health</span><span class=\"mtk1\"> & </span><span class=\"mtk12\">Fitness</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Fashion</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Beauty</span><span class=\"mtk1\"> & </span><span class=\"mtk12\">Spas</span><span class=\"mtk1\"> </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\"> </span><span class=\"mtk12\">Entertainment</span><span class=\"mtk1\"> --&gt;</span></span></code></pre>\n<p>Please note, for these <code>&#x3C;a></code> tags, you need to follow the patterns of MixitUp. Basically in class attribute you need to specify \"filter\" for it, and in data-filter, you need to tell which category it is. Next we are going to write some PHP code, to iterate through the destination folder, and process the files within it.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"php\" data-index=\"4\"><code class=\"grvsc-code\"><span class=\"grvsc-line\"><span class=\"mtk1\">&lt;!--</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">valid</span><span class=\"mtk1\">()) {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span><span class=\"mtk15\">if</span><span class=\"mtk1\"> (!</span><span class=\"mtk12\">$it</span><span class=\"mtk1\">-&gt;</span><span class=\"mtk11\">isDot</span><span class=\"mtk1\">()) {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        </span><span class=\"mtk12\">$subject</span><span class=\"mtk1\"> = </span><span class=\"mtk12\">$it</span><span class=\"mtk1\">-&gt;</span><span class=\"mtk11\">getSubPathName</span><span class=\"mtk1\">();</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        </span><span class=\"mtk3\">// Mac OS automatically creates .DS_store file to store metadata</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        </span><span class=\"mtk3\">// The following regex is used to ignore those files</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        </span><span class=\"mtk12\">$pattern</span><span class=\"mtk1\"> = </span><span class=\"mtk5\">&#39;/</span><span class=\"mtk6\">\\\\.</span><span class=\"mtk5\">DS/&#39;</span><span class=\"mtk1\">;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        </span><span class=\"mtk11\">preg_match</span><span class=\"mtk1\">( </span><span class=\"mtk12\">$pattern</span><span class=\"mtk1\">, </span><span class=\"mtk12\">$subject</span><span class=\"mtk1\">, </span><span class=\"mtk12\">$match</span><span class=\"mtk1\"> );</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        </span><span class=\"mtk15\">if</span><span class=\"mtk1\">( !</span><span class=\"mtk12\">$match</span><span class=\"mtk1\"> ) {</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">            </span><span class=\"mtk12\">$file_path_name</span><span class=\"mtk1\"> = </span><span class=\"mtk11\">str_replace</span><span class=\"mtk1\">(</span><span class=\"mtk8\">&quot;</span><span class=\"mtk6\">\\\\</span><span class=\"mtk8\">&quot;</span><span class=\"mtk1\">, </span><span class=\"mtk8\">&quot;/&quot;</span><span class=\"mtk1\">, </span><span class=\"mtk12\">$subject</span><span class=\"mtk1\">);</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">?&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    &lt;div </span><span class=\"mtk4\">class</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;mix getSubPath(); ?&gt; col-md-3 &quot;</span><span class=\"mtk1\">&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">        &lt;img src=</span><span class=\"mtk8\">&quot;&quot;</span><span class=\"mtk1\"> alt=</span><span class=\"mtk8\">&quot;&quot;</span><span class=\"mtk1\"> </span><span class=\"mtk4\">class</span><span class=\"mtk1\">=</span><span class=\"mtk8\">&quot;business-logo-img&quot;</span><span class=\"mtk1\">/&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">    </span></span>\n<span class=\"grvsc-line\"><span class=\"mtk11\">next</span><span class=\"mtk1\">();</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">}</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">?&gt;</span></span>\n<span class=\"grvsc-line\"><span class=\"mtk1\">--&gt;</span></span></code></pre>\n<p>The code is pretty straightforward, just want to label out a couple of things.</p>\n<p>First, we specified which folders we are working with and then we used a built-in recursive iterators to cycle through the folder.</p>\n<p>For each item we found in every sub-folder, $it->getSubPath will return the sub-folder name and $it->getSubPathName will return the name of the file. Create a div for each image, and play with those returned parameters to fit them into the pattern of MixitUp.</p>\n<p>The $it->isDot() function and regular expressions are used to filter out some system hidden files such as \".DS_Store\" and others, since we do not want to them to be shown as images.</p>\n<p>Easy, right? If you like this post, click share and help people who's having this kind of issue.</p>\n<style class=\"grvsc-styles\">\n  .grvsc-container {\n    overflow: auto;\n    -webkit-overflow-scrolling: touch;\n    padding-top: 1rem;\n    padding-top: var(--grvsc-padding-top, var(--grvsc-padding-v, 1rem));\n    padding-bottom: 1rem;\n    padding-bottom: var(--grvsc-padding-bottom, var(--grvsc-padding-v, 1rem));\n    border-radius: 8px;\n    border-radius: var(--grvsc-border-radius, 8px);\n    font-feature-settings: normal;\n  }\n  \n  .grvsc-code {\n    display: inline-block;\n    min-width: 100%;\n  }\n  \n  .grvsc-line {\n    display: inline-block;\n    box-sizing: border-box;\n    width: 100%;\n    padding-left: 1.5rem;\n    padding-left: var(--grvsc-padding-left, var(--grvsc-padding-h, 1.5rem));\n    padding-right: 1.5rem;\n    padding-right: var(--grvsc-padding-right, var(--grvsc-padding-h, 1.5rem));\n  }\n  \n  .grvsc-line-highlighted {\n    background-color: var(--grvsc-line-highlighted-background-color, transparent);\n    box-shadow: inset var(--grvsc-line-highlighted-border-width, 4px) 0 0 0 var(--grvsc-line-highlighted-border-color, transparent);\n  }\n  \n  .dark-default-dark {\n    background-color: #1E1E1E;\n    color: #D4D4D4;\n  }\n  .dark-default-dark .mtk1 { color: #D4D4D4; }\n  .dark-default-dark .mtk11 { color: #DCDCAA; }\n  .dark-default-dark .mtk12 { color: #9CDCFE; }\n  .dark-default-dark .mtk4 { color: #569CD6; }\n  .dark-default-dark .mtk8 { color: #CE9178; }\n  .dark-default-dark .mtk15 { color: #C586C0; }\n  .dark-default-dark .mtk3 { color: #6A9955; }\n  .dark-default-dark .mtk5 { color: #D16969; }\n  .dark-default-dark .mtk6 { color: #D7BA7D; }\n</style>","frontmatter":{"date":"May 19, 2015","updated_date":null,"description":null,"title":"Use PHP to generate filter portfolio","tags":["PHP"],"pinned":null,"coverImage":{"childImageSharp":{"fluid":{"aspectRatio":1,"src":"/static/1ea6f04417f886989e6dc30837c305f5/7d145/php-filter-portfolio.png","srcSet":"/static/1ea6f04417f886989e6dc30837c305f5/69585/php-filter-portfolio.png 200w,\n/static/1ea6f04417f886989e6dc30837c305f5/497c6/php-filter-portfolio.png 400w,\n/static/1ea6f04417f886989e6dc30837c305f5/7d145/php-filter-portfolio.png 610w","sizes":"(max-width: 610px) 100vw, 610px"}}},"author":{"id":"Lucius Yu","github":null,"avatar":null}}}},{"node":{"excerpt":"When we start thinking about authentication in any kind of software (it can be web, mobile, desktop, or even console), the first thing that…","fields":{"slug":"/engineering/password-secure/"},"html":"<p>When we start thinking about authentication in any kind of software (it can be web, mobile, desktop, or even console), the first thing that comes to mind is username/password, this is an older but still effective technique to protect and identify users. Securing these passwords is not an easy task we require better techniques to secure these passwords from attackers. Generally, passwords stored in databases, so we can secure passwords by traditional techniques to prevent access to databases like firewalls, role definitions, etc. but just to prevent database intrusions is not a fully secured way, we require further password protections by converting them into non-readable (encrypted) formats. To understand encrypting passwords we have to understand plain text passwords and how these kinds of passwords are insecure.</p>\n<p><strong>Let's start our journey</strong></p>\n<h1 id=\"plain-text-passwords-never-store-plain-text-passwords\" style=\"position:relative;\"><a href=\"#plain-text-passwords-never-store-plain-text-passwords\" aria-label=\"plain text passwords never store plain text passwords permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Plain text passwords [Never Store Plain text Passwords]</h1>\n<p>Plain text passwords are stored directly in a database without any encryption. These passwords are very insecure because:\n- If someone hacks your database he can access any account and do anything possible after login.\n- Developers or employees who are working on a project commonly misuse the password and spread these passwords to other people for misuse.</p>\n<p>  As a hard and fast rule plain text passwords should NOT be accepted in any case or used for any project or product.</p>\n<h1 id=\"encrypted-passwords-not-recommended\" style=\"position:relative;\"><a href=\"#encrypted-passwords-not-recommended\" aria-label=\"encrypted passwords not recommended permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Encrypted passwords [Not recommended]:</h1>\n<p>Encryption helps us by protecting data from hackers. In network communication, the same techniques can be used in saving passwords. Any encryption algorithm can be used to protect passwords. So on registration plain text passwords are encrypted and saved to your database.</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"0\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">```</span>\n<span class=\"grvsc-line\">EncryptedPassword = Encrypt ( Password, Key);</span>\n<span class=\"grvsc-line\">```</span></code></pre>\n<p>Get this encrypted password from database then de-crypt and match\n<code>Password = Decrypt ( EncryptedPasword, Key);</code></p>\n<p>Match with user entered password.</p>\n<p>But passwords will still not be fully secured because encrypted data can be always be de-crypted with the encryption key if someone get the key then they can de-crypt your password.</p>\n<h1 id=\"hashed-passwords-recommended\" style=\"position:relative;\"><a href=\"#hashed-passwords-recommended\" aria-label=\"hashed passwords recommended permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Hashed passwords [Recommended]</h1>\n<p>Hashing is a method of encryption to get original data from hash. Hashing algorithms are used in network data communications. The encryption encrypts the data but hashing protects tampering with the encrypted data. Hashing algorithms are widely used in securing passwords.</p>\n<p>In case of hashing validation of password performed refer to the following pseudo-code:</p>\n<p>On registration</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"1\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">PasswordHash = HASH(Password);</span></code></pre>\n<p>Some of the hashing algorithms support salts(a set of characters that is appended to your hash) like HMAC</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"2\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">PasswordHash = HASH(Password, salt);</span></code></pre>\n<p>On login the same process happens, get hash from users entered password</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"3\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">  inputPasswordHash = HASH(inputPassword);</span></code></pre>\n<p>And compare with the saved password</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"4\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">  If(SavedPassworHash == inputPasswordHash){</span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\">  //user get login</span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\">  }</span></code></pre>\n<p>For making a strong hash from non-salted hash algorithms, salt is appended or prepended to your password string. Appending and prepending also has two kinds of implementations one is a universal salt and the second is per password random salt, let us understand one by one.</p>\n<p><strong>Universal salt :</strong> in this implementation every password has one salt.</p>\n<ul>\n<li>\n<p>Universal salt prepend</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"5\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">PasswordHash = Hash(Salt+Password);</span></code></pre>\n</li>\n<li>\n<p>Universal salt append</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"6\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">PasswordHash = Hash(Password+Salt);</span></code></pre>\n<p><strong>Per password salt :</strong></p>\n</li>\n</ul>\n<p>In this implementation every password has it's own random salt, but the question is how we preserve salt for a password? Answer is the salt is appended with password by a separator. And on login split that saved string by separator and get hashed password and salt.</p>\n<p>On registration when we save password</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"7\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">  Salt = RandomString();</span>\n<span class=\"grvsc-line\">  PasswordHashWithSalt = Hash(Password+Salt) + &quot;:&quot; + Salt;</span></code></pre>\n<p>On login when compare password : first split salt and password hash</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"8\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">  StringArray = Split(PasswordHashWithSalt , &quot;:&quot; );</span>\n<span class=\"grvsc-line\">  Salt = StringArray\\[1\\];</span>\n<span class=\"grvsc-line\">  PasswordHash = StringArray\\[0\\];</span></code></pre>\n<p>Than get hash of user entered password by salt</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"9\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">inputPasswordHash = Hash(inputPassword + Salt);</span></code></pre>\n<p>Then compare both password hash</p>\n<pre class=\"grvsc-container dark-default-dark\" data-language=\"\" data-index=\"10\"><code class=\"grvsc-code\"><span class=\"grvsc-line\">If(PasswordHash == inputPasswordHash){</span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\">//user get login</span>\n<span class=\"grvsc-line\"></span>\n<span class=\"grvsc-line\">}</span></code></pre>\n<p><strong>Some popular encryption methods :</strong> Most of people use following algorithms for hashing passwords, explaining all algorithms is out of scope of this blog. I am adding reference URLs for more reading. I am adding only strong hashing algorithms </p>\n<ol>\n<li><a href=\"http://en.wikipedia.org/wiki/PBKDF2\">PBKDF2</a></li>\n<li><a href=\"http://en.wikipedia.org/wiki/Bcrypt\">bcrypt</a></li>\n<li><a href=\"http://www.tarsnap.com/scrypt.html\">scrypt</a></li>\n<li><a href=\"https://en.wikipedia.org/wiki/Argon2\">Argon2</a></li>\n</ol>\n<h2 id=\"hash-cracking-techniques\" style=\"position:relative;\"><a href=\"#hash-cracking-techniques\" aria-label=\"hash cracking techniques permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Hash cracking techniques</h2>\n<p><strong>Brute force:</strong> It is the most popular password cracking technique, in this loop every combination of numbers and alphabets are tried. Suppose one system have password minimum length is 6 digits then</p>\n<p>000000, 000001,000002……………….111111,111112……..AAAAAA etc.</p>\n<p>In any case user have set simple password like 123123, it will be cracked simply. How to prevent this kind of scenarios</p>\n<ol>\n<li>Enforce to user to use at-least one number, one symbols, one capital letter and one small letter in password.</li>\n<li>On login form if someone entered more than three time wrong password for one username then ask for human verification by captcha, it will be prevented by automatic brute force password generator.</li>\n</ol>\n<p><strong>Dictionary attacks:</strong></p>\n<p>In crypt-analysis and computer security, a dictionary attack is a technique for defeating a cipher or authentication mechanism by trying to determine its decryption key or pass-phrase by trying hundreds or sometimes millions of likely possibilities, such as words in a dictionary. (<a href=\"http://en.wikipedia.org/wiki/Dictionary_attack\">Wikipedia</a>)</p>\n<p>it is just extended version of brute force attack, in this attacker attack by dictionary words, most of time people set their password as meaningful name to keep easily in mind. And in this attack.</p>\n<p><strong>Rainbow tables</strong></p>\n<p>A rainbow table is a precomputed table for reversing cryptographic hash functions, usually for cracking password hashes. Tables are usually used in recovering a plain text password up to a certain length consisting of a limited set of characters. It is a practical example of a space/time trade-off, using less computer processing time and more storage than a brute-force attack which calculates a hash on every attempt, but more processing time and less storage than a simple look-up table with one entry per hash. Use of a key derivation function that employs a salt makes this attack unfeasible. (<a href=\"http://en.wikipedia.org/wiki/Rainbow_table\">Wikipedia</a>)</p>\n<h2 id=\"migrating-hashing-algorithm\" style=\"position:relative;\"><a href=\"#migrating-hashing-algorithm\" aria-label=\"migrating hashing algorithm permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Migrating Hashing algorithm</h2>\n<p>Sometimes people realize that their Hashing algorithm is weak so they think to migrate system to one algorithm to another but hashing algorithms are one way so getting original password is not possible so the question becomes how to make this possible. There are two ways to do this.</p>\n<p><strong>Reset all passwords:</strong> In this approach just migrate your algorithm from one to another but keep password hash same, but password will not be matched because hash of one algorithm doesn't match with hash of another algorithm, so email to user about it that our system has improved security system and send link with this email for resetting password, so user will reset password.</p>\n<p><strong>Migrate on login:</strong> this approach is tricky in this case maintain one parameter for checking is password upgraded to new algorithm, set false for all user by default and when use come for login check this check if it is false then compare password with old algorithm and if password get matched then start user's session and get newer hash from plain text password and saved to database and update is password upgraded check to true. Now from next time user's password will be checked by newer algorithm.</p>\n<style class=\"grvsc-styles\">\n  .grvsc-container {\n    overflow: auto;\n    -webkit-overflow-scrolling: touch;\n    padding-top: 1rem;\n    padding-top: var(--grvsc-padding-top, var(--grvsc-padding-v, 1rem));\n    padding-bottom: 1rem;\n    padding-bottom: var(--grvsc-padding-bottom, var(--grvsc-padding-v, 1rem));\n    border-radius: 8px;\n    border-radius: var(--grvsc-border-radius, 8px);\n    font-feature-settings: normal;\n  }\n  \n  .grvsc-code {\n    display: inline-block;\n    min-width: 100%;\n  }\n  \n  .grvsc-line {\n    display: inline-block;\n    box-sizing: border-box;\n    width: 100%;\n    padding-left: 1.5rem;\n    padding-left: var(--grvsc-padding-left, var(--grvsc-padding-h, 1.5rem));\n    padding-right: 1.5rem;\n    padding-right: var(--grvsc-padding-right, var(--grvsc-padding-h, 1.5rem));\n  }\n  \n  .grvsc-line-highlighted {\n    background-color: var(--grvsc-line-highlighted-background-color, transparent);\n    box-shadow: inset var(--grvsc-line-highlighted-border-width, 4px) 0 0 0 var(--grvsc-line-highlighted-border-color, transparent);\n  }\n  \n  .dark-default-dark {\n    background-color: #1E1E1E;\n    color: #D4D4D4;\n  }\n</style>","frontmatter":{"date":"May 14, 2015","updated_date":null,"description":null,"title":"Password Security","tags":["Security","Password"],"pinned":null,"coverImage":{"childImageSharp":{"fluid":{"aspectRatio":1,"src":"/static/e7bb89604f85c7699b36ea7c43eab30e/7d145/password-security.png","srcSet":"/static/e7bb89604f85c7699b36ea7c43eab30e/69585/password-security.png 200w,\n/static/e7bb89604f85c7699b36ea7c43eab30e/497c6/password-security.png 400w,\n/static/e7bb89604f85c7699b36ea7c43eab30e/7d145/password-security.png 610w","sizes":"(max-width: 610px) 100vw, 610px"}}},"author":{"id":"Kundan Singh","github":null,"avatar":null}}}}]},"markdownRemark":{"excerpt":"Identity is evolving, and developers are at the forefront of this transformation. Every day brings a new learning—adapting to new standards…","fields":{"slug":"/identity/developer-first-identity-provider-loginradius/"},"html":"<p>Identity is evolving, and developers are at the forefront of this transformation. Every day brings a new learning—adapting to new standards and refining approaches to building secure, seamless experiences.</p>\n<p>We’re here to support developers on that journey. We know how important simplicity, efficiency, and well-structured documentation are when working with identity and access management solutions. That’s why we’ve redesigned the <a href=\"https://www.loginradius.com/\">LoginRadius website</a>—to be faster, more intuitive, and developer-first in every way.</p>\n<p>The goal? Having them spend less time searching and more time building.</p>\n<h2 id=\"whats-new-and-improved-on-the-loginradius-website\" style=\"position:relative;\"><a href=\"#whats-new-and-improved-on-the-loginradius-website\" aria-label=\"whats new and improved on the loginradius website permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>What’s New and Improved on the LoginRadius Website?</h2>\n<p>LoginRadius’ vision is to give developers a product that simplifies identity management so they can focus on building, deploying, and scaling their applications. To enhance this experience, we’ve spent the last few months redesigning our interface— making navigation more intuitive and reassuring that essential resources are easily accessible.</p>\n<p>Here’s a closer look at what’s new and why it’s important:</p>\n<h3 id=\"a-developer-friendly-dark-theme\" style=\"position:relative;\"><a href=\"#a-developer-friendly-dark-theme\" aria-label=\"a developer friendly dark theme permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>A Developer-Friendly Dark Theme</h3>\n<p><img src=\"/f46881583c7518a93bb24e94c32320de/a-developer-friendly-dark-theme.webp\" alt=\"This image shows how LoginRadius offers several authentication methods like traditional login, social login, passwordless login, passkeys and more in a dark mode.\">    </p>\n<p>Developers spend long hours working in dark-themed IDEs and terminals, so we’ve designed the LoginRadius experience to be developer-friendly and align with that preference.</p>\n<p>The new dark mode reduces eye strain, enhances readability, and provides a seamless transition between a coding environment and our platform. Our new design features a clean, modern aesthetic with a consistent color scheme and Barlow typography, ensuring better readability. High-quality graphics and icons are thoughtfully placed to enhance the content without adding visual clutter.</p>\n<p>So, whether you’re navigating our API docs or configuring authentication into your system, our improved interface will make those extended development hours more comfortable and efficient.</p>\n<h3 id=\"clear-categorization-for-loginradius-capabilities\" style=\"position:relative;\"><a href=\"#clear-categorization-for-loginradius-capabilities\" aria-label=\"clear categorization for loginradius capabilities permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Clear Categorization for LoginRadius Capabilities</h3>\n<p><img src=\"/e5358b82be414940f3fb146013845933/capabilities.webp\" alt=\"This image shows a breakdown of all the LoginRadius CIAM capabilities, including authentication, security, UX, scalability and multi-brand management.\"></p>\n<p>We’ve restructured our website to provide a straightforward breakdown of our customer identity and access management platform capabilities, helping you quickly find what you need:</p>\n<ul>\n<li>Authentication: Easily understand <a href=\"https://www.loginradius.com/blog/identity/authentication-option-for-your-product/\">how to choose the right login method</a>, from traditional passwords and OTPs to social login, federated SSO, and passkeys with few lines of code.</li>\n<li>Security: Implement no-code security features like bot detection, IP throttling, breached password alerts, DDoS protection, and adaptive MFA to safeguard user accounts.</li>\n<li>User Experience: Leverage AI builder, hosted pages, and drag-and-drop workflows to create smooth, branded sign-up and login experiences.</li>\n<li>High Performance &#x26; Scalability: Confidently scale with sub-100ms API response times, 100% uptime, 240K+ RPS, and 28+ global data center regions.</li>\n<li>Multi-Brand Management: Efficiently manage multiple identity apps, choosing isolated or shared data stores based on your brand’s unique needs.</li>\n</ul>\n<p>This structured layout ensures you can quickly understand each capability and how it integrates into your identity ecosystem.</p>\n<h3 id=\"developer-first-navigation\" style=\"position:relative;\"><a href=\"#developer-first-navigation\" aria-label=\"developer first navigation permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Developer-First Navigation</h3>\n<p><img src=\"/a8c155c2b6faf3d5f4b4de4e2b14d763/developers-menu.webp\" alt=\"This image shows the LoginRadius menu bar, highlighting the developer dropdown.\">   </p>\n<p>We’ve been analyzing developer workflows to identify how you access key resources. That’s why we redesigned our navigation with one goal in mind: to reduce clicks and make essential resources readily available.</p>\n<p>The new LoginRadius structure puts APIs, SDKs, and integration guides right at the menu bar under the Developers dropdown so you can get started faster. Our Products, Solutions, and Customer Services are also clearly categorized, helping development teams quickly find the right tools and make informed decisions.</p>\n<h3 id=\"quick-understanding-of-integration-benefits\" style=\"position:relative;\"><a href=\"#quick-understanding-of-integration-benefits\" aria-label=\"quick understanding of integration benefits permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Quick Understanding of Integration Benefits</h3>\n<p><img src=\"/b2f9a964a2da0ea83e2f8596b833bba7/we-support-your-tech-stack.webp\" alt=\"This image shows a list of popular programming languages and frameworks offered by LoginRadius.\"></p>\n<p>Developers now have a clear view of the tech stack available with LoginRadius, designed to support diverse business needs.</p>\n<p>Our platform offers pre-built SDKs for Node.js, Python, Java, and more, making CIAM integration seamless across popular programming languages and frameworks.</p>\n<h2 id=\"over-to-you-now\" style=\"position:relative;\"><a href=\"#over-to-you-now\" aria-label=\"over to you now permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Over to You Now!</h2>\n<p>Check out our <a href=\"https://www.loginradius.com/\">revamped LoginRadius website</a> and see how the improved experience makes it easier to build, scale, and secure your applications.</p>\n<p>Do not forget to explore the improved navigation and API documentation, and get started with our free trial today. We’re excited to see what you’ll build with LoginRadius!</p>\n<style class=\"grvsc-styles\">\n  .grvsc-container {\n    overflow: auto;\n    -webkit-overflow-scrolling: touch;\n    padding-top: 1rem;\n    padding-top: var(--grvsc-padding-top, var(--grvsc-padding-v, 1rem));\n    padding-bottom: 1rem;\n    padding-bottom: var(--grvsc-padding-bottom, var(--grvsc-padding-v, 1rem));\n    border-radius: 8px;\n    border-radius: var(--grvsc-border-radius, 8px);\n    font-feature-settings: normal;\n  }\n  \n  .grvsc-code {\n    display: inline-block;\n    min-width: 100%;\n  }\n  \n  .grvsc-line {\n    display: inline-block;\n    box-sizing: border-box;\n    width: 100%;\n    padding-left: 1.5rem;\n    padding-left: var(--grvsc-padding-left, var(--grvsc-padding-h, 1.5rem));\n    padding-right: 1.5rem;\n    padding-right: var(--grvsc-padding-right, var(--grvsc-padding-h, 1.5rem));\n  }\n  \n  .grvsc-line-highlighted {\n    background-color: var(--grvsc-line-highlighted-background-color, transparent);\n    box-shadow: inset var(--grvsc-line-highlighted-border-width, 4px) 0 0 0 var(--grvsc-line-highlighted-border-color, transparent);\n  }\n  \n</style>","frontmatter":{"date":"February 21, 2025","updated_date":null,"description":"LoginRadius’ vision is to give developers a product that simplifies identity management so they can focus on building, deploying, and scaling their applications. To enhance this experience, we’ve redesigned our website interface, making navigation more intuitive and reassuring that essential resources are easily accessible.","title":"Revamped & Ready: Introducing the New Developer-First LoginRadius Website","tags":["Developer tools","API","Identity Management","User Authentication"],"pinned":true,"coverImage":{"childImageSharp":{"fluid":{"aspectRatio":1.7857142857142858,"src":"/static/80b4e4fbe176a10a327d273504607f32/58556/hero-section.webp","srcSet":"/static/80b4e4fbe176a10a327d273504607f32/61e93/hero-section.webp 200w,\n/static/80b4e4fbe176a10a327d273504607f32/1f5c5/hero-section.webp 400w,\n/static/80b4e4fbe176a10a327d273504607f32/58556/hero-section.webp 800w,\n/static/80b4e4fbe176a10a327d273504607f32/99238/hero-section.webp 1200w,\n/static/80b4e4fbe176a10a327d273504607f32/7c22d/hero-section.webp 1600w,\n/static/80b4e4fbe176a10a327d273504607f32/1258b/hero-section.webp 2732w","sizes":"(max-width: 800px) 100vw, 800px"}}},"author":{"id":"Rakesh Soni","github":"oyesoni","avatar":"rakesh-soni.jpg"}}}},"pageContext":{"limit":6,"skip":942,"currentPage":158,"type":"///","numPages":161,"pinned":"ee8a4479-3471-53b1-bf62-d0d8dc3faaeb"}},"staticQueryHashes":["1171199041","1384082988","2100481360","23180105","528864852"]}