Transcripts
1. Introduction: Hello. Welcome to Shopify Theme Programming: Liquid, JSON and JavaScript. This class is the sequel to my previous class, Shopify Theme Development, how to build and customize your own online store. If this is your first time learning with me, my name is Chris, and I'm a top teacher here on skillshare.com covering topics such as web development, and online freelancing. My first - class on Shopify theme development covered topics like creating a development store, using Theme Kit, and understanding theme structure. These are all important fundamentals for Shopify theme development. But in this class, we're going to go deeper into the actual theme code, and gain a better understanding of how themes are programmed. We'll take a closer look at the templating language behind Shopify themes, discuss how to create your own customizations using JSON schemas, and learn about a few APIs that help you access stored data, without having to reload the page. By the end of the class, you have a solid understanding of how to program Shopify themes, and the ability to create your own sections and snippets to access the full scope of what can be achieved with Shopify theme development. If you're ready to take your Shopify theme development skills to the next level, click on the next video, and I'll see you on the inside.
2. Required Tools & Knowledge: As this class is the SQL to Shopify theme development, how to build and customize your own online store, it is advised that you take that class first as this class assumes you understand what a development story is, how themekit works, and the folder structure of your Shopify theme. Understanding theme structure is especially important for this class as we'll be jumping straight into the files without talking too much about where they all fit into the Shopify themes structure. The focus of this course is exclusively on the programming aspects of Shopify themes. Of course, if you need more of that theoretical knowledge around themes, definitely check out the first class. Now, because this class is all about code, you're going to need a good code editor. The one I will use in this class will be the online editor in the Shopify admin but it is highly recommended that you use your own code editor and use themekit to download your theme code. Secondly, you obviously need a web browser, and third, you'll need your own Shopify store. This store doesn't need to be a real store. Of course, it can be a development store. You don't need to actually pay Shopify to work on themes. If you don't know what I'm talking about, checkout lesson 3 of the previous class. Now, I mentioned before, themekit, if you haven't already, head to shopify.github.io/themekit and grab that now, I highly recommend it. That's basically it for the tools. But in terms of knowledge, besides knowing about themes, you're going to need to have a basic understanding of HTML, CSS, and JavaScript. These are the three important languages that make up the web, and we won't be covering them specifically in this class so if you need to gain an understanding of any of these, simply check out some of my other classes first. That was quite the list. Let's quickly summarize before we move on. In terms of knowledge, you're going to need to have at least a basic understanding of the Shopify Platform, the structure of Shopify themes, I'm talking about layouts, templates, sections, etc., and finally, HTML, CSS, and JavaScript. For the tools, you'll need a code editor, a web browser, and a Shopify store to work on, and Shopify Themekit if you're working with your code locally. If you've got all of that, you're now ready to jump straight into the next lesson so I'll see you there.
3. Online Store 2.0 Updates: Hey students, I just wanted to jump in here before we start and make sure you're aware of something Shopify are calling Online Store 2.0. As you can probably tell, this video was recorded a few years after the original class was posted, but I thought it was important to jump in here and let you know about some updates. If you know what I'm talking about here with Online Store 2.0, feel free to skip this video. But for the rest of you, I just need to update you on a few changes to the online store experience since this class first went live. Just to address some of your concern students, the content in this class is still all relevant. Liquid is still in that same form. JSON is still used for section schemas and locales. The JavaScript APIs I talk about in this class all still exist at the time of recording, but we just have a new format for template files. So now templates can be of either Liquid or JSON. We'll get further into this in the class. You should probably by now know what a template is. But previously, templates were coded as only Liquid and you had to hide program in the sections. Now, in order to allow for sections everywhere, Shopify have enabled the use of JSON templates. So now instead of storing Liquid directly in your template, you store a JSON object in your template, and that JSON object has the list of sections that you can then reorder in your theme editor, and this allows you to create re-orderable sections in all of your templates, not just your homepage. If you want to learn more about JSON templates, I go deeper into it in Lesson 11 of the previous class. I just added a new video in that class for you guys so you can learn what JSON templates are and how to use them. That being said, it's going to change your development tool now if you want to use JSON templates. In the next video, I mentioned Slate. I don't recommend you use Slate unless you're picking up a legacy project. Slate is well expired now. Shopify ended support officially for Shopify Slate back in January 2020. I don't recommend you use it unless of course, you have to because you're taking on a legacy project. But even then, I would recommend migrating off of Slate. In the last video, I mentioned a tool called Theme Kit, but there's also a new tool now called Shopify CLI, and it's important to note Shopify CLI here because it's the tool that you're going to have to use if you want to use JSON templates. For whatever reason, Theme Kit hasn't been adapted to work with the new JSON templates. So if you want to use JSON templates, you're going to have to use Shopify CLI. Those are the main changes to note before we get into the class. As I said, Liquid is still the same, JSON is still the same, JavaScript API still exist. The latest change from Shopify is that template files can now be of either Liquid or JSON. Again, to learn more about Online Store 2.0, you can check out the three new videos I added to the Shopify theme development class, I mentioned the JSON Schemas one. If you want to learn about the CLI, that's in Lesson 6, I believe, so Lesson 6 of my previous class, and there's also an intro to Online Store 2.0 in that class as well. I also have a Online Store 2.0 playlist on YouTube that you can check out for more information about Online Store 2.0. But with that being said, let's return to the class and learn how we can program in Shopify theme development.
4. Theme Programming Overview: For the majority of this class on Shopify theme programming, we're going to be talking about liquid. Liquid is the templating language of Shopify themes, you can think of it as the back-end programming language of your Shopify theme, and therefore your online storefront. Of course, we can create online storefronts that link to Shopify as data in other ways. But the majority of the time when somebody is using Shopify to host an online store, they are using this online store sales channel in the way that you customize the look and feel of your online store is through a theme. You should be well familiar with this if you need to learn more about theme development, what is a theme, and where it sits in the context of your store? I have a series on YouTube and a previous class on Shopify theme development here on Skill Share. So this class is going to be primarily concerned with Shopify theme programming, as the name suggests, and so we're going to be learning more about programming patents, so we're going be working with Liquid a lot. That being said, last class, we worked directly with the Debut theme, which is an already built theme that looks like this, if you're not familiar, it's a already built theme. You don't really need to go in and build basic features, unless you need to create something that doesn't exist already. Because if you look at the code of this theme, it's already quite full, so if I look at any given section, you'll see it's quite full of code. In this class, what I'm going to do, is instead of starting from the point of an actual theme, which is more practical if you're actually doing Shopify theme development, I'm going to start with a very bare-bones theme called New Theme. This theme right here you can see is very bare-bones. The homepage has nothing on it, if I click Catalog, it takes me to the collection where I see all products, and it's currently paginating by two products at a time. Keep in mind that in order for you to test and actually program a Shopify theme, you're going to need some store data, so I've put in this dummy data already. You'll need to put in some test products as well if you want anything to display. If I click on Blog, you can see I've copied over some blog posts from the official Shopify website. Now, if you want to code along, and use this exact theme, the way I generated this theme, and the reason why it's called the New Theme is, because I used a command in Theme Kit, called, Theme New, so for those of you who aren't familiar with Theme Kit, we're not going to go into great detail, I have a 20 minute lesson in my last class here on Shopify theme development, all about how to set it up and configure it, but this is what I'm talking about when I talk about Shopify Theme Kit. It's basically a command line tool that you can use to download your theme, and then you can edit it with your own computer. I highly recommend if you're doing Shopify theme development seriously, you use the Theme Kit. But as this class is not really about development workflow and just about programming, I'm going to be using the online code editor, so I'm going to just click Edit code here, and we're going to edit it straight from here. Now I should mention one other framework and tool that you can use to create Shopify themes, it's called slate, so if I type in Shopify Slate into Google, you can learn more about it. As you can read on this GitHub page, slate is on low maintenance. Slate is a project that Shopify have created but they're not really maintaining at the moment, that could change in future, and slate is a lot more technical and hard to setup, so we're not going to be focused on slate in this class as well. I just thought it would be remiss of me not to mention, and again, if you want to learn more about slate, there is a bonus video in the previous class on Shopify theme development, go check it out. It is the second last video. Now, getting rid of that tab there and going back to our New Theme here, the reason why I wanted to start with the New Theme is it's quiet bare, so we can see here there's not a lot Liquid code, there's only 10 lines in the index file, there's only one layout, and if we go down here to sections and snippets, they are completely empty. There's only one language file and one CSS file, and one JavaScript file. This is pretty bare-bones, and it's going to allow us to learn the concepts of Liquid programming easier without having to sift through a whole bunch of HTML and CSS that would exist on a fully built theme. As I previously mentioned, you can consider Liquid the back-end programming language of Shopify themes. What I mean by that is that all this code is generated on the server side, and then it comes through the client side in HTML and CSS. Just to demonstrate that for those of you who the concept is not particularly clear, look at all these liquid tags, these aren't going to come through on the front end, is all generated on the server side, and then it comes through on the front end as just HTML and CSS, so if I click on this page, which gets me to the collection template, and I inspect what's going on here, I won't see any Liquid code whatsoever. The Liquid code is all on the server side, so the reason why that's important is, because anything I want to do that I want on the client side, still has to be done with JavaScript, and that becomes an issue of how do we access that data using JavaScript, and then work with it on the front end without having to reload the page. You should be familiar with the difference between server side and client side, if not, check out my first class on Skill Share, I have a video on the difference between front-end and back-end. But that is just something to note. Liquid covers most of Shopify the programming, but of course, if you want more interactive features, if you want to avoid reloading the page, you're going to have to use JavaScript. Back to the code, you can see a bunch of Liquid tags, and you can see that they even start with a curly bracket and a percentage sign, and end with a percentage sign curly bracket, or there are just two curly braces, and the difference between these two tags is, this is for logic, and this is for output. What I mean by that is, if I just throw collection dot title in-between these double curly braces tags, it'll just output the collection title. There's no operations or logic happening on it, unless of course, I use a filter which is down here. Obviously, there's a lot of concepts and syntax within Liquid, and for that, I have created my own documentation for that. This is my blog post which is not currently out yet, but will be out by the time you're watching this video, so I'm still working on it. But essentially, this is going to be the textbook or reference for this class, so it's a very long article, I cover all the objects, all the filters, all the tags within Liquid, so for this class, I thought of going through all the theory, but I thought it's going to be a lot better for you to actually read up on this stuff, and then we can actually practice and see it in action in our theme, so I'm going to create these patterns and break this down, but for reference, we're going to use this document. This article is going to be at christhefreelancer.com/shopify_liquid_guide, so definitely open that up, have a read, you don't have to read the whole thing. I definitely recommend you skim-read once it gets to the objects, but this is going to be your reference. Also, there are two other resources that I want to link you to, and they're actually linked in the article, the actual official documentation, so on areas where it gets in-depth from we talk about the list of attributes, the Liquid reference is still going to be a great place for you to learn all about the different objects, tags, and filters within Liquid, so it has an incredible amount of detail, for instance, if I go into, let's say the product object, you'll see all the attributes, and you can learn all about them, so this article is not intended to replace the documentation, but it's a good starting point, and I think a good overview of how it all works, and it links to the documentation numerous places. There's also the famous Cheat Sheet, so open that up in another tab, and this right here is all of the objects, tags, and filters on the same page, for instance, if I wanted to figure out how to get the title of a product, I could Control-F product, and then I find this little accordion here for the product object, gives me all the same things we were looking at before in the documentation, but in this tight little accordion, and then it gives me a little bit of information about that, then I can click Learn more and it'll take me straight back to the documentation. These are the resources I recommend having open, or having ready while you take this class, the Cheat Sheet for quick reference, got the documentation for anything detailed, and of course my article as an overview of Shopify Liquid, and if you're struggling to understand, what one of these things are, where you can find these objects, my guide is what is intended to help that. As I've written here at the start of the article, "While Shopify's Liquid Reference and the famous Cheat Sheet are great, I feel like there's a lot of details missing and that's why I've decided to write my own documentation." So as I mentioned, there's a few things that Shopify doesn't really talk about, the different types of objects, and where they're available in the scope of your Shopify theme, that is the main reason why I wrote this article, you can see here, not only can you learn more about objects, but you can also learn, do they hold multiple objects? Where can you access them? Can you loop through them? So just an extra reference there for you. If you have any questions, specific questions about Liquid, please check the blog post first, and then if you're still struggling, definitely leave a comment in the discussion box. Now, we mentioned JavaScript before as the way we're going to do anything interactive on our Shopify theme, and one way that Shopify allows us to access and manipulate data from our Shopify theme using JavaScript is, through the Ajax API, so if I search for, Shopify Ajax API, you can learn more about it here. But we're going to have a full lesson or two on the Ajax API. Don't worry. Just making you aware that we have an API for doing client-side request as well. The other code you're going to write when you're programming shopify themes is CSS or SCSS. You should be familiar with CSS. If you're not familiar with SCSS, it is a form of SASS, which is basically a programming language for CSS. It is not required to know the syntax of SASS. SASS is backwards compatible with CSS and in fact, once the code gets to the front end, it's always compiled to CSS anyway. If you want to put in CSS specifically in here, you can do so as normal but, if you know how to use SASS, you can use it as well. For those of you who do know how to use SASS, one warning is that shopify uses an older version of SASS. I believe it's 3.3 or something like that. It just means that all of the features of the latest version of SASS won't be available to you when you're developing shopify themes. If you come across anything a little bit weird, that's breaking, that is perfectly fine syntax, it might be because you're using an older version of SASS. Another warning there. Don't worry. If you don't know anything about SASS, CSS is totally fine. The final syntax that you'll have to get used to with shopify themes, of course we've got Liquid, we've got JavaScripts, and we've CSS/SCSS. But you'll also see here we've got JSON files. If I open up settings_schema.json, this is JavaScript Object Notation, aka JSON. It's just a way of easily presenting data. It mimics the structure of a JavaScript object but it has some differences. You can read more about JSON on Google, but it's quite simple to understand. Right here we have an array opening up, and then inside we have an object. If we wanted to write another object in here, we would do so like this and we can give it keys and values here. All the keys need to be with a double quote. That's one of the key differences with JSON and any strings obviously with quotes as well unless we are putting in a number which we don't need quotes for. Alright. The areas that you'll see JSON in these settings_schema.json file, the settings_ data.json file and your locale files, en.default.json. Again, we're going to go over JSON and how that all works with these various files in a later video. Don't worry about that. Just giving you a quick overview before we jump into the liquid stuff. That pretty much covers all the areas of your Shopify theme. You should know about themes structure from the last class. We've got layout, templates, sections, and snippets for structuring our shopify theme. Then we've got our assets which hold the CSS and JavaScript, config which holds data and the settings that we're able to change and locales for storing language. The final thing I need to mention in this introductory video is something that's very important to Shopify Theme Programming, and that is the idea of templates and scope. If we go and preview our theme and navigate to certain pages, you can see our template structure in the URL structure. Right now we're on the root domain. Don't be confused about this little extra attribute there. But we're on the root domain, which is the index template. If we go to here, you can see that the URL changes to collections/all. This means we're on the collection template. If I change the actual collection that we're looking at to one I have in my store called featured collection, you can see everything looks the same, It's just the title of the collection that gets displayed here and the actual products that show up on the page is different. All of this is controlled by the one collection template. If I click on any one of these products, you'll see that we get products and then the name of the product in handle form, we'll talk more about handles later, gets added to the URL. Now we know where in the product template. If I go back to my collection page and I click on this product, you'll see it shows up pretty much the exact same way as the other product because it uses the same template. How this looks in our code is, we go into our templates here, and here is the code that will show up for every single collection page. The reference to collection here really depends on what collection you're on. But it's completely dynamic so that any collection you're on gets fed into here through the collection object and you can manipulate whatever collection gets passed in the same way you would another collection. When you're on the product page, you are on the product template. It's the same code for every product that gets displayed on your website unless you use alternate templates, which we talked about in the last class, but essentially, everything that will change on the page is the dynamic content and that is brought in here with this product object. I talk about this in the article I call templates specific scope. If we scroll down, I talk about the objects that can be accessed from anywhere in your theme as global objects. If you know the actual name of your product, you can access it from anywhere in your theme by using its handle. The same can be said for pages, blogs, articles, images. Images is through the file name there. But then you get to template specific variables if you scroll down, template specific objects rather. These objects are available when you're in the respective template. If you're in the product template, you have access to the product object and that product object is whatever product you're viewing, and you can see that from the URL. We are looking at black leather bag. When we do things with the product object in the product template, we're looking at that black leather bag. The templates that we have here all have their own objects which should be labeled the same. In the collection template, we have access to the collection object. In the blog template we have access to the blog object. Templates right here, and this is something we'll get more into coding templates and layouts in the next video, but templates is basically the different groups of pages that show up in your website. Sections very powerful and snippets great for reusing code. We'll talk about them in the lesson after the next one. But I think I've talked at length already about Shopify Liquid. Again, these are all great references. I don't want to go through the entire document because it's huge. But in the next video, we're going to jump straight into coding a common pattern in shopify and learning how to use alternative layouts. I will see you in the next one.
5. Programming Layouts and Templates: In this lesson we're going to be focused on programming, layout and template files. The template that we're going to be focusing on is the collection.liquid template. The reason why I decided to use this one is because products are central to any Shopify store, or at least should be, because essentially an e-commerce store is set up to sell products. Products are the most important resource in your Shopify store, most likely. One of the ways that people can browse through different products is through a collection. We can see here a pretty simple loop here for the collection template, but there is still a bit going on here. What I want to do is simplify this and tackle this line by line. First of all, I'm going to preview this in a new tab. We can go to here and we can make sure we're in a collection template by checking that collections is in the URL. Now we have our front end, how it looks with our template that we're editing. The first thing I'm going to do is remove pagination and strip this down to just a simple loop. Pagination is handy, but I don't want to confuse you straight up, so let's just remove it for now. Let's see what happens when we do that. If I refresh the page, you'll see now every product in our store is showing on the one page. Usually you don't want to do that because you could have hundreds or thousands of products and that would take forever to load one page. Pagination is very handy, just removing it for simplicity sake. Now to make it even simpler, I'm going to remove that code and strip it down even further. We just got this loop now and let's have a look at how that looks on the front end. Refreshing the page. You can see we now just have a list of products with a link to view them. If I click on the first one, awesome sneakers, I'm now on the product template looking at this product, awesome sneakers. But we're focused on this collections loop here. Let's break down what we got going on here. In liquid, as I've mentioned before, we have two types of tags. There's actually three, and we can put in a dash here and here and that just reduces whitespace, it doesn't actually change the functionality at all. I won't worry too much about that. But essentially we just have two different types of tags, the output tag and the logic tag. When we just want to straight out output something to the page, we just use the output tag. Right now we are taking an attribute on the collection object of title. Here you can see, this is the collections title. Now it's a bit different with the old collection because it's an auto generated collection by Shopify but if we go to an actual collection that I created, featured collection, you can now see that the title of that collection is right here. If I was to go back into my back end, change that, it would change it here and anywhere else we reference collection.title. Then going into a loop now, what I'm doing is I'm taking the products attribute of the collection, which gives me access to all the products within that collection and I'm looping through them using the word product as my hook in order to access the different attributes of that particular product. This word could be any word I wanted it to be, but product makes sense. It makes it more readable. For product in collection.products, we're going to do this for every single product. Now, something that exists in for loops in Liquid, which I don't know if it exists in any other language, is you can actually have an else statement. This is if collection.products is empty, it won't loop through it and instead it'll output this. The else in this instance is for when the objects that you're looping through is empty. It's just a shorthand for if I was to put an if statement up here, checking if the length of this was bigger than zero, and then if not putting that out, we can save ourselves some code and write it this way. For every product in collection.products we're going to start a div and inside this div we're going to have a link. For the actual address of that link, we're going to put in the product.url, so the link to the actual product. Then we have got this pipe here. This pipe here is what defines a filter in Liquid. We can remove this, it's going to work pretty much just as well without that. First of all, let's look at it with that filter. If I go and inspect here and I look at the URL, you can see that the URL has featured-collection and then on the ends, products/awesome-sneakers. But if we remove that code and hit Save, that filter will not apply and the URL we'll get instead is just products/awesome-sneakers. This filter we have here within collection, it just makes the URL of the product append to the URL that we're currently on for this collection instead of cutting out the collection. That's handy for if we want to have logic on the product template and we can reference the collection that we navigated to because a product could be part of many different collections. Going back to the collection page here, the next part, very simple. We just output the product title. You can see that here, we've got a link and inside it's the product title and the a href is the link to that product. Very simple stuff. Let's add in the next line that we had here. I'm going to add in all of them, remove all of them except one, and hit Save on that. What we've got here is we're now outputting the price as well. Very basic product.price and we're using another filter called money, which formats it in a nice currency format. If I was to remove that filter again, you'll see it'll still work. Let's refresh the page. You'll get the price of all these products coming up in the pure number form. In Shopify, the pure number form of a price includes the cents. You can see here this is going to be 8,000 cents, this is 11,000 cents so on, so forth. Obviously that's not going to look that great to the end-user so what we usually do is filter it with the money filter and that's going to transform that number into a much nicer formatted currency format. Now we can see that 8,000 cents becomes $80 and we've got those decimals. We can use other money filters to filter out the decimals if we want, but money is the standard one. Let's add in the next line and remove the final line. Now we've added in an unless statement. The unless tag is basically the opposite of the if tag. It reads in a different way. Unless the product is available, we're going to do this. We can easily transform this into an if statement, we just have to change the condition here. I think in this instance it makes more sense that in terms of understanding the code to make this an if statement. I'm going to remove the unless words and what we need to do here, if product available is false, or we could also do if product available is not true. Let's just do false. We need to do for comparison double equal signs or triple equal signs, because a single equal sign is for assignment, not for comparison. Remember that guys, that's quite a common basic beginner mistake. I think this reads a lot nicer if product available is false, as in the product is not available, we want to show sold out, and this will work in the exact same way. If I go over to here, you'll see none of these actually sold out so nothing is going to show up anyway. But if I go back to the old collection, I have set up a product that is sold out. I just called it product with no image and no stock and you can see here it's sold out. If I go and put this back to how it was before and I hit Save on that, you'll see we get the exact same result. Unless is just a way to make your code more readable. In this case, I think it makes more sense to use if but they've decided to use unless here. Saves them from having to write a comparison operator. I guess that's why they did it. The final line inside this loop is this link tag. We're again creating a link with the same tag and filter as above here. This is going to link to the product URL, the actual product. We're going to include the image. The real thing to look at here is line eight, because we're constructing an image tag here with some attributes and some filters. I'll hit "Save" and we'll quickly look at how that looks. Now you'll see we've got the images included here like before. Let's break it down. Let's first remove this filter here and see what happens. Now we just loading up the product featured image source in this source tag. Image is an object as well. That's why we can chain another dot here to get the actual src of the image. You can see here we're getting a different attribute of the image here, the alt tag, but we'll get to that in just a sec. If I save and I go back to the collection page. Right now you'll see that all the links are broken. If I inspect one of them, you'll see we have a relative URL, but it's not going to work in Shopify. What we need to do pass that image through a filter. The filter we had is image URL. Here you can see a parameter of large, but we can remove that parameter and just have the image URL tag with no parameter. If we go back, refresh the page, you'll see we get images showing up, but they all show up at a 100 pixels wide. That is the default behavior. But we can actually change this to whatever you want. Maybe we want it to be 200 by 200. We can do something like this, or if we want it to be the same width and height. We don't actually need to put the value after x. We can just hit "Save" on that. Now we should see our image is being twice as big. There you go. I think that's a quite good middle ground between those really large images and the ones that come out by default, which is a 100. Now this is really handy to have this as you can put in a really big image into your Shopify dashboard, but as long as you write code that limits the size of that image, then that is how big the image will be loaded in the browser. What I mean by that is if we actually go and click on open image in new tab. Whether the original image we uploaded was a 1,000 pixels wide or 200 pixels wide. It's only going get served from Shopify servers as a 200 pixel by 200 pixel image. That's good for image optimization. So rule of thumb here, if you're including an image, always use parameter here and specify the max dimensions that you think that image needs to be. Because there's no point serving an image that is way bigger than what you need it for. This final tag is for the alt attribute of your image. Should be familiar with alt attributes. They describe the image for robots and people that can actually see the image. Here you can see alt awesome sneakers If I remove the escape filter here, you probably weren't noticed a difference. Go back, refresh the page. You'll see we still get the same result. But what the escape filter does is if there is any HTML in this attribute, it makes sure to escape it. This is something that can catch you out at any point with Shopify theme programming and Shopify theme development is HTML that is coming from an objects in Shopify, being injected into your code and breaking everything. Just a tip if you see anything really weird, you're whole pages breaking and you didn't write any code for that to happen. The code might actually be coming from a value that you're bringing through and liquid. Good practice just to be safe, escape it. Now I don't think there's going to be HTML in your alt tag typically. But just a safe little option there. You don't want any HTML coming through in this alt attribute. Now, it's not style nicely. We need to still styled with CSS. But we've got the major points coming through. We've got title, the price and the image, and both the image and the title link to the actual product for us to go check it out. Let's go back to the collection page. Now we just need to introduce back the paginate object. For that, because I don't know off the top my head how to do it because it's already written for us most of the time in Shopify. I'm going to access the docs end. This is a good opportunity to follow along as well because this is what you are going to be doing as well. If I just type in Shopify liquid, what I'm looking for is the liquid reference, say right here. What are we looking for? We're looking for the paginate tag. I will go into tags. I think it'd be closed as a theme tag, and it is. You can click here, and there you go. All you got to do is wrap these tags around a for-loop and you get pagination. Pretty simple. Pagination is a pain in the ass for a lot of other programming, but Shopify makes it really easy for us. We are on the collection template so we can just copy this example. I can go back here. I think five per page is an all right number for us. We can code mri end tag as well here and paginate. I'm going to hit save on that. Go back into here, refresh the page and you'll see that only five items show up per page. Now, what it doesn't give us is the navigation to actually paginate. Because we are missing one piece of code from the start of here. To check that we can actually go and click on here and look at older versions. Let's look at the original before we made any changes. We can see here, we've got this conditional. I'm just going copy this and go back to our current. At the end of the for-loop, I'm going to paste that code that I took from the original code. Now we can access the paginate object, which is available within the paginate tag. This is a helper object that Shopify gives us so that we can actually check how many pages there are in this pagination. You check the attribute code pages and we check to see if there's more than one page. Now we can use the paginate object again with a easy to use filter, which will transform the paginate object into a default pagination. A lot of magic is going on behind the scenes here. If you want to customize your pagination, you can access the attributes on this paginate objects and manipulate them how you want. But for our purposes, we're just going to use the default pagination. I refresh the page here after saving, and now you can see we've got this default pagination. Usually, what you would do, because you probably wouldn't be using the default pagination in a proper theme because you'd want to look nice and according to your style. You'd usually create a pagination snippet and include it here. In the next video, we'll be talking about sections and snippets. Not long to learn about snippets, but to finish off this lesson, I need to talk to you about layouts. We could have started with a layout, but I wanted to start with the 18 line file rather than this one which is 43 lines. For those of you who need a little recap on what a layout is, this is what gets served as a wrapper on all your templates. Unless you specify an alternative layout on a template, this will be the wrapper that goes around every single template in your store. Assuming we only have one layout here, and it's using the default name theme.liquid, this is going to be the wrapper that wraps around every template, and the point which it wraps around is right here. This special tag, content_for_layout is where your template gets loaded. I want to show you that in practice right now. We can see that this main tag comes in the layout file, and then within that, we're loading the template. Let's go to our collection template again, and we'll see it starts with a h1. If I look in here and inspect the code, I already have the inspect open, but you'll see we've got the h1 of the collections template, and then we have main. Everything above here is going to be the same apart from the dynamic content that gets loaded in on every single page. If I go to the blog page, you'll see the head and the start of the body is the same, and you've always got this main here, then inside the main, you have all the code of the template. Going back to the collections page. Content_for_layout, that's where the template of the page you're currently looking at is loaded. But of course, we've got all this other content around it. Right here is a navigation. Right here is a link to a cart. If customer accounts enabled and a customer is logged in, we will show a link to access their accounts. If they're not logged in, but accounts is enabled, we'll give them a login link. We're going to move that into its own section in the next video. There's a very good reason for that, but that makes up the whole body section of your layout. Then you've got the head section, which you only really need to worry about if you're going to be including extra assets. You can see all the standard stuff that you would have in an HTML head. The title, meta tags, these objects for SEO. The page title is whatever the title of the page is, it's not the same as page.title because it's not a Shopify page that the ones that you would customize here, it's whatever page you're on, the website, that's the page title. Then page_description is your SEO description, you add your SEO data here and then you have this special tag called content_for_header. As it says here, this is simply a header hook for plugins. This is a point that plugins and I believe code that you put or preferences that you put here. If I go into preferences, basically anything you want added to your head dynamically, it'll get inserted where that tag is. I believe some of this, if you add it in a Pixel or a Google Analytics, and the place where it would insert it in the head is right here, but you don't have to edit that at all. In fact, I think the editor will error, if you try and change that, that is what content_for_header is. Don't need to change it, just leave it where it is. Then right here is when we bring in our assets. We've got some filters here, and I'll just show you what these do quickly. We've got this application.scss.css and if we just output that on the layout by itself, number one it'll break any styles we created which we didn't, but you'll see here, it just literally outputs that text to the screen. If you create an output tag and just literally put a string in there, you're basically doing nothing. You could remove this from either side and it'll be the same result. But what we're doing here is we're taking that and we're filtering it, we're finding the full asset URL of that asset. Let's just do that first. Refresh the page and now you can see this becomes a full URL generated by Shopify server that will link you to the asset. Then finally, with the last filter on there, it transforms that URL into a fully constructed stylesheet tag. If I hit save, refresh the page, you'll see that the URL doesn't show up now because it's encapsulated in a HTML tag. If I look down here, there's a lot of generated tags in there. You can see that one now bringing it into our project for a link tag and not just outputting it on the screen. We can actually just copy that HTML word for word, put it in here like this. Then if we remove that, which generates the stylesheet tag and just replace the href with that value, we should get the same result. Now we should see it showing up twice, actually. Of course, because I took the stylesheet tag off this one. This one is just showing the asset URL and this one is the fully formed link to the asset. What I just did that with this line is essentially the same thing as if I used the stylesheet tag filter there. Not important for you to understand in terms of editing this because you probably don't want to touch this, but it's important to know how it works you're not confused when say, for instance, you want to include another stylesheet tag, you would just have to duplicate this, put it under, and then maybe your next file is just called styles.css. That is how you would include a new asset that you included here in your Shopify theme everywhere that this layout is included. But in terms of transforming that into a fully fledged asset URL and then creating a tag out of it, you don't really need to mess with. The same is happening here with JavaScript, where taking the filename, creating a fully fledged asset URL from Shopify and then transforming that into a script tag. I'm going to save that. This is more of a theme structuring thing. But just to demonstrate, I am going to show you how to do an alternate template. Here we can create, I'm just going to call it alternate. You can call it whatever you want. Let's just remove all of this navigation content and hit save. Now we've got this alternative layout that we can use. How we would actually make that layout apply to a certain template is we can go to the start line of any template and use the layout tag. Instead of theme.liquid, now it's going to be theme alternate and if I put that tag at the start of our template, refresh the page, you'll now see there's no navigation. All right. If I remove it and hit save, now you'll see that we have the same theme as before. Most of the time, it's not important to have a second layout, but it is there as an option. I'm just going to delete that one because we don't want to have to make changes to multiple theme layouts for this project and for this class, we only really need one layout file, but the option is there to create different layouts. Maybe you want a page with less content on it. Maybe we don't want the header or footer, for example. We can remove that from an alternative layout and then use that layout on the template. Hopefully, that has made it really clear what's going on in a basic template like here for collection and your layout file. What I want to leave you with before we go into sections and snippets, is this part of my documentation, which is template-specific objects. Talked a bit about it in the previous video. But I just want to make sure you fully understand this. We start with the layout file and then the template for the page where currently looking at gets loaded inside this container here because we've put this content_for_layout tag here. Now we have access to the particular objects that goes with that template. What I want you to understand here is when we're on the collection template, we don't have access to a product because we don't have any concept of what product we're looking for. Unless we loop through a collection and access its products, then we can affect a particular product from within a loop. Same can be said for if we're in a blog. When we're in a blog template, we're looking at a specific blog. We can use the blog object, but we can't actually access a article unless we loop through the articles in that blog. The same thing with collections and products. But then when we go into the product or the article page, we've already seen the product page or product template. Let's look at the article template. We can access the article object specifically because this is the template that gets loaded when an article is being viewed. I just wanted to make that super clear. If it still doesn't make sense, give me a comment in the discussion box below, but that is template scope and templates-specific objects. That's why templates are really important. But at the same time, you might not want to include a lot of code in your template. You might want to link directly to a section and there's a very good reason for that, which we'll go into in the next video.
6. Sections, Snippets and Locales: In this lesson, we'll be talking about sections and snippets. Snippets is quite basic and easy to understand. Basically, if we put code into a snippet, we can include it in multiple places in our theme. It allows us to reuse code, but also to organize our code better. Sections on the other hand are a little bit more intelligent and we'll see why that is in this lesson. If we go back to our theme. liquid layout, we can see a really obvious need for a section here. That is, we've got all this header content inside our layout. Now what you would usually do in a Shopify theme is have a header and footer section. What I'm going to do is I'm going to cut all of this so that's in my clipboard. I don't want to lose it, and then I'm going to replace that with a call to a section. Going to write section header. Now when I hit save, it's going to link to that section which we haven't created yet. We're going to go in, create a section with the same name, header. The editor will automatically add the extension of dot liquid for us, so we don't need to do that, and it also automatically adds in a schema, style sheet and JavaScript tags, very handy. Okay, we'll get into schemas in depth in the next lesson but for now, what I'm going to do is paste that liquid and HTML code directly into here. If I hit save, refresh any page because every page in a theme right now uses the same layout, we'll see that nothing's changed, okay? Actually something has changed, and that is that we have now got all of this encapsulated in a Shopify generated div tag. It gives it an ID of Shopify section dash, and then the name of the section. It also gives it a class of Shopify section. Let's create another section, and let's call it footer. After the main content, we usually have a footer and we can put that into its own section. If I save that, it will link to a footer that doesn't exist yet, so we need to create it. I'll create this footer.liquid file in my sections. I will go up here and let's just open up a footer tag. Close the footer tag, and maybe just put some copyright information there copyright, Christopher Dodd. There's one thing I'v forgotten to do and that's to actually name the section in the schema. We want to change this to footer, and then in our header, we want the section name to be header. This is what's going to show up in the customizer. As I said, we'll go more into schemas, but basically all of this is for the customizer. If I go back into any page because they all use the same layout, we can see that we've got a similar tag generated for the footer as well. Shopify dash, section, dash and the name of the section which is footer, and of course the class Shopify section. Now you can see down here, it's not nicely formatted, but inside you've got the footer tag with copyright Christopher Dodd. Now what I want to show you is how that looks in the customizer. This is a good visual representation of what's going on here. All I did there was I right-clicked on customize theme to go to the customizer for this theme. Now you'll see on the homepage we have header and footer. These are the sections as they appear enact theme customizer. If we go to any page, any template, because we are using the same layout file, we'll get header and footer on every page. Go back to the homepage. I'm actually going to remove footer from our theme.liquid file. Just to show you how that would show up in the customizer. If I go to the customizer, refresh the page, then we only see the header. This is something I covered in the last class so that should be just a recap for most of you. But as you can see what this really bear theme, we have created all the sections that exist in this theme. If we go to any other page, there is no section in-between header and footer for this theme yet. If we go to theme settings, we only have the default checkout list of customizations here. We can add to this as well. Here you can see the official version of this. It's the theme kit, template theme. Again, this is just the one you get by running theme new in theme kit. Alright, so to create our next section, one thing we can modify, and this is something that is quite common is to take all the code within a template and move that into a section. Now that might sound a bit weird at first, but we'll explain why that is in just a second. I'm going to call this section collection template because that's essentially what it is. Then I'm going to create that section. Now and here we've got a schema, and I'm just going to paste the exact same code we had in our collection template. I'm going to call this collection template in the actual schema. That is the name that'll show up in the customizer. If we go to our collection page, now we'll see collection template, which is the name we defined in the schema to be a section in here. As you notice, because we have no settings in our schema, it says here no content or settings. We can actually customize this. The reason why we would have an basically an empty collection template file and link straight to a section with all the code for that template there, is because we can now customize it using the customizer. If we just left that code here, it would sit outside of a section and then we wouldn't have access to a schema for which we can edit with. That's not necessarily true in the sense that there is a settings schema for the theme as a whole, but we want to section the settings for this particular template. We want to move it into its own section. Okay, right now we haven't really done anything because we haven't set any settings. Maybe I want to create a setting here and we do that in the settings object. What's something I might want to customize as the user about this page. Well, maybe I want to control the pagination. Remember when I say user, I'm talking about the shop admin who's using this customizer in this case. Maybe I want to control the pagination. What I'm going to do is open up an object, and inside this object I'm going to be writing, this is all JSON format by the way, so we're going to be opening up a double quote, and what we need to do here is insert an input. The place you can learn more about that is if we just Google Shopify input settings. I believe it's in configuring theme settings right here. If I search for input settings, here we can see the basic input settings. Text for instance, this is the input setting that we would put in. We can also put in like an image picker, we can put in a set of radio buttons, a dropdown, all things, checkbox. For pagination, I think it makes sense to use a range slider. It'll show up like this. The reason why a range slider would be good in this instance, is because we want to restrict the user's input to something reasonable. We don't want to paginate any less than say two, and we don't want to paginate any more than say 25. Otherwise, it'll take too long to load the page. What we can do is we can copy this example right here, go back into our code. Which tab was that? Okay, here we go. Rather than writing this word for word, I'm just going to copy and paste it in. Now we have got an object which represents our setting. The first thing we need is the type, and this defines that this is going to be a range input. The ID is what we can use to access it in liquid. We need to change this to something that makes more sense. I'm just going to call it pagination. Then right here, we need to insert a minimum value. Because this is a number, I'm going to get rid of the double quotes and put in let's say five. The maximum they can paginate by, I'm going to say is 25. The step is the increment that they can use. I only want them to be able to make a selection in five step increments. Units, we can put in here as products per page, but unfortunately this unit attribute has a limit of three characters. So I'm just not going to use the unit in this instance. Label is what gets shown to the user. We're going to write in here products per page, and the default value I'm going to make is five. If I hit save here, there are no errors, thankfully, and then I can refresh the page. Then once I go into that section, we can actually find our range slider in here and update it. Now of course, we have created this selection, but we haven't actually done anything with it. We're going to need to go back to our section, and reference this setting value by its ID. Instead of here where it says by five, what I'm going to do is reference that ID. The way we do that is through the section object. Because we're in a section, we can access the data within a schema of a section through this section object. I start by grabbing that section object, and now I essentially have access to this and we want to go inside here. What I'm going to do, put.settings. Now, I have access to all the settings, and inside I want to access this one, which the ID is pagination. I'm going to type pagination, and that should be all we need to get this to work. Going back, refreshing the page. If I go into collection template now, and I set it to 10, should be 10 showing up per page. This collection only has about 10 products. Let's go on the old collection. Now we're in a collection that has more than 10 products. You can see here, it's defaulted to five, 1, 2, 3, 4, 5, but I can change it to 10, hit "Save." The page will refresh, and now we will paginate by 10 instead of five. So 1, 2, 3, 4, 5, 6, 7, 8, 9, 10. That's one way we can make our collection template customizable, by using a section and giving it a input setting in its schema. In terms of this section, the collection template, I'm going to leave it there, because we're going to talk more about schemas, and add some more options in later videos. But what I want to show you is how we can create a dynamic list of sections on our homepage, using the special tag content for index. Now first of all, we're going to have to create a section that we would want to put on the homepage. A good idea, something that's pretty common in a lot of themes. Let's just go to the homepage, so we can have a look. There's currently nothing here, then maybe it'd be nice to have a row of products show up as a featured collection on the homepage. Let's actually create that section now. Going back into our editor, I'm going to create a new section, and I'm going to call it featured-collection. The dot liquid extension gets added automatically, of course. The first thing I'm going to want to do is change the section name to "Featured Collection." Now with this section, we're not going to specifically include it on any template, or layout like we've done here. But we're going to be able to include it in the homepage, through this dynamic content for index tag. You'll see what I mean in just a second. What I'm going to do is I'm going to set up a loop. Let's copy the loop from here, for our featured collection. What we need to do because we're no longer going to be placing this in the collection template, is to specify a specific collection, and that's where we now see the assign tag. Assign allows us to create our own variables. What I'm going to do here, is select what collection I want to be the collection objects for this. Again, we're not in the collection template anymore. We don't know what collection to loop through. Let's specify this and we can do that using the global collections object, and accessing its handle. I'm going to access the Featured Collection, and let's end to that tag. Going to hit "Save," and now we should have a featured collection which allows us to show the featured collection wherever we include it. Unfortunately, we can't include it in our content for index section, without whats called a preset. We need to write a preset array here. For that, I'm going to go back into the Shopify documentation. I think it might be on a different page to this one. There's two pages I end up switching between all the time when I'm programming sections. It's not this one, let's type in, "Presets." I believe it's in this one, theme sections, this should be it, if I type in presets, here we can find the details for presets. What we can see here is when a section has one or more presets, each preset becomes a dynamic section emerging can add to their theme homepage, if the content for index object has been included in index.liquid, so they say it right here, we need to set a preset at least one preset, so that we can use it in our content for index. I'm just going to copy this array that they've set here, we don't need all these details. The main purpose behind presets is that we can set some default settings for the section when it gets included on a page, but for our purposes we just want to meet the requirement so that we can actually use it on our homepage. I'm going to get rid of the settings object, we only really need category and name for this one, and we're now missing end curly bracket I believe, and we're missing end array tag as well. Here in category, I'm going to leave that as custom content, and I'm going to name this featured collection, and you'll see where this name comes up later. All right so now that we've created this section and it has a preset, we can now include it in our content for index, so we need to create that tag, I'm going to go to the index.liquid page, replace all of these with that special object, content_for_index, save that, and now, when we go to our homepage in the customizer, might need to refresh the page. We can now see this button for adding a section, interesting, let's click it and we'll see here our category and our name of our section appears in this little menu, so if we go back to the featured collection, that's what we wrote here, the category and the name shows up here, so now we can click on it, preview it, looks good, and then we can add it right in. Again we don't have any settings for this yet we're going to set up some settings in the next video, but now we have this feature collection and we can add multiple of them, right now we've had coded the collection that we want to use, but we can also reorder these, turn this off and on, and this is really user-friendly for the person who's going to be working with the theme and they don't have to actually touch the code, so that's why sections are super powerful, I'm going to hit "Save" on that so it definitely gets included on the page, that should wrap up this little introduction to sections. We're going to remove all of these for now and let's talk about snippets. A snippet as I said before, is a reusable piece of code, something that is common in Shopify theme development to reuse multiple times is a product that's shown in a list of products, so we've done that twice in our theme so far, we can go into this featured collection here, and inside this loop we can actually make this a snippet, and that way when we're looping through products, maybe not in a featured collection maybe somewhere else and we want to use the same code, we can just include this snippet without having to write this out every single time, so I'm going to cut this so it goes to my clipboard, and I'm going to write the tag to include a snippet, it's going to be product-item, I guess I can call it, and I'll hit "Save", now I will go into snippets and create product-item, we'll paste that code directly in, and now anywhere where this snippet gets included, it will include this code here. Now an important thing to note with snippets and sections, is it gets access to the product objects still, and it also will get access to the settings within the schema here, so that way nesting works in Shopify is it feeds from layouts down to templates, down to sections, down to snippets, but snippets can be included anywhere. What I mean by that is, if I set a variable here in theme.liquid, I could access that anywhere in my theme that uses that layout. If I'm in a template for page for instance, and I included a section that I intended to include on pages only, I could reference the page objects specifically in that section, and the same goes for snippets, so for this snippet, we know that we can use the product object anywhere where we have access to it, so if we include a product item right here in the loop where we've given access to a specific product, then it'll feed right into the snippet, okay, so if you include this snippet on a place that doesn't have a product object specified it will break, it will not work, but as long as we can rely on this snippet being used in a place where there is a product object, it'll work fine, just like on sections we can trust that will have access to a collection if it's on the collection template, or we can do what we did here and assign the collection specifically, so that's about it for snippets and a good introduction to sections as well hopefully. I just want to talk about a few more things to ground out Shopify theme programming, and that is, we talked about CSS and JavaScript in earlier video, but let's just demonstrate how we would add some JavaScript to our application, I can just throw in an annoying alert right here, ''You loaded the page'', hit "Save" on that, now any page I go to in my theme it'll load that JavaScript, obviously not the best example, but you get the point, this JavaScript gets loaded into every page, just that I demo that quickly, and the same thing for CSS, if you want a rule to apply everywhere within your theme, you can put it in here, so maybe we want the font size of everything, the body font size to be something ridiculous, let's say 40 pixels, it's pretty ridiculous if you ask me, refresh the page, nothing's happened, let's see what's going on here in our console, we don't actually have access to our application.css.scss, let's have a look at that, I think that's because the wrong name has been set, looks like a bug with the new theme, we're going to go into theme.liquid and change the ordering here, so it's supposed to be css.scss, save that, refresh the page, now you'll see all of our font-size gets way bigger, obviously that's a pretty silly example so I'm going to remove that style. We've talked about layouts, we talked about templates, we've talked about sections, and we've talked about snippets, and then we've talked about assets. Config we'll talk about in the next video when we dive deeper into JSON, but locales, just to mention briefly what that is, as you can see the title of this file is en.default.json, and what this file does is hold specific language for English users, we can create other locales, and then we can call the right word that we need to use in a specific instance. We can actually edit this in a user interface as well, we can go here and click "Edit languages", and we'll see the same options not in JSON form but in a user interface, see right here, if I was to actually go in and change this, maybe I say, ''Page not found'', hit "Save" on that, and I go here notice how this will change, this is the actual data of what we've set in that user interface, there we go, page not found, and it works both ways, if I was to edit it here in the data file, hit "Save" on that, go back to the user interface, refresh that, you'll see it's the value we just changed it to. Now, why this is important for us to understand is when we see these attributes or these objects being called in the actual theme code, so this one is for the 404 page, and it defines the language that will be on the 404 page, so let's go to the 404 page, and we can see here we've got these special tags that are filtered with this t filter, so if I just remove that, what do you think is going to happen? Let's have a look, usually the 404 page comes up if you type in an address that doesn't exist so I am going to just type in ha ha ha ha ha, and now instead of seeing the translated version of that you'll just see the code, so like I said, if you just put in a string in an output tag with quotes, it's the same thing is just literally putting that on the page, so we need this t tag and what that's going to do is say, ''Hey, look up this object and then get the value of it and put it on the screen'', so if we see general.404.title, we go into here, we start with general, then we dig into 404 object, and then we get the property of title, so now if I refresh the page now that we've replaced or put back in that t tag, you can see that value comes through. This is important to note when you're going through editing your theme and you come across one of these language variables, maybe you want to create your own which is totally cool, you just update this JSON file right here, but it's important to note that when you're programming Shopify themes. I think this has been quite a long lesson, a few of these are probably going to be long lessons, so I'm going to end it there. In the next video we're going to go deeper into JSON, so you're going to learn more about how this works and how to work with JSON in the next video, so I'll see you there.
7. JSON Schemas: In this lesson, we're going to learn all about JSON. JSON is a popular way of representing data and Shopify themes, the way you represent all of your data and your Shopify theme is through JSON files. We saw in the last video we've got language file here, which is stored in JSON. We can also edit that through the theme language editor, which we also saw in the last video. This is quite basic. We have access to the keys and attributes within that object, and we can just edit this directly through here, or we can edit it on the actual data file itself. What I want to discuss more in depth in this lesson is JSON Schemas. If I click out to that and I go into settings_schema, we can see the schema for our entire website. Now, I know we haven't looked at this just yet, but we have of course, looked at schemas briefly as it relates to individual sections. Right here, the schema that we see here is very similar to how it operates here in our settings_schema.JSON. If you want to learn more about JSON itself, stands for JavaScript Object Notation. It's a way of representing data that looks similar to how you would represent data in JavaScript, but it's not exactly the same. Some major differences include having double quotes around the property names. But if you want to learn more about JSON, a quick Google search, it's just J-S-O-N, and you have a world of information open up to you about JSON. It's quite simple. It's not summing to study a whole course on unless you really want to get in depth with it. But for our purposes, all we need to understand in JSON schema we've got arrays just like we would in JavaScript, and then an object is represented by these curly brackets. So as we saw with the language file, this is the object overall. Then inside this object we can target the general object. Then when we're inside the general object, we can grab the "404" object and then grab attributes or nested objects within that. We saw that coming into our output here. Going into the locales, picking out the general object, going into the nested "404" object and grabbing the title of that. All right, so that's a little bit on JSON and the syntax behind it. But let's talk more about schemas and how it all works in Shopify. We saw the schema as it relates to specific sections in previous videos. But I want to show you settings_schema.JSON. If we go back to our customizer and we go on any page, you see we've got sections in the first tab here. We can see our sections as we saw before, and any schemas within those sections will generate these inputs. But there's also this other menu called theme settings. Here we can place groups of settings that we can access throughout our theme. There are some limitations though. One of the features of a settings in sections is that we can have blocks which we'll see very soon in the overall theme settings. We can't do blocks. That's one limitation, but otherwise they work pretty much the same. Let's go in and show you an example. After this object, I'm going to create a new object and give this a name of, let's just say, general styles. This is like how you would define a section as well. Then just like we would in a sections schema, we define a settings array. Inside this settings array, we can create any types of inputs that we want. For this video, I've already loaded up the two areas of the Shopify documentation that will help you with creating these JSON Schemas. The first one is: @themes/development/sections. The title is themed sections. This one is handy for learning about how to structure your schema. You've got the different tags we saw presets in an earlier video. We will also learn about blocks here today as well. Over here in configuring theme settings, it's frustrating that they put it in a separate page. But this is the page where you'll learn about all the different input settings, so text, text area, image picker, radio, select checkbox range. Those are the basic ones and then they've got some advanced ones down here, I believe, yes. We can create inputs for color, fonts, collections, products, blogs, pages, links, lists, URLs, lots of different stuff. If you want to see if there is something that you can make a user input, chances are it's going to be in here. Going back to here, we need to create a setting. What I'm going to do just for demonstration purposes is create a setting for the color of links. Let's just say. I'm going to use the color picker. Let's just copy the example. I'll go into here and replace my empty object with the object from the documentation. The type is already set is going to be color. We just need to give that an ID. I'm going to call this link color, and the label is what gets shown to the user. I'm going to call it link color. I'm using the American spelling just to be consistent and the default value, we'll just say blue. This one here info allows us to put in an extra little bit of text. I don't think that it's necessary in this instance, but just to show you what it does for when you do need it, I'm going to write a description here. This is for the link color. If I save that, you can see we've got an error. Setting with link color default must be a CSS color. We can't use blue, it has to be a HEX value, so let me just do black. Try that. Must be a CSS color. There we go. Not the best at running hex codes. I usually just look them up. All right, but now we've got this hex code which represents black. If we go into our customizer now and refresh the page everything looks the same, but we can go in here. Now we've got this section for general styles. Click on that, and we have link color. The default value has been set to #000 and it's filled in the other zeros. We can go in, change this to that blue color and hit "save." Now just like we did with the settings in the section schema, this isn't going to do anything unless we actually reference that value. That is what, of course the ID is for. Let's go ahead and make all the links in our theme according to this link color. Now, where we should put a style that's going to be on every page of our theme is in our global CSS file. But what we want to do is reference liquid in this instance because we're going to need to access the settings object in liquid in order to access this value. One feature of Shopify themes that you may not realize is that you can use liquid on your CSS files as well. What I'm going to do is change this file name and add.liquid to the end of it. Then, I'll hit ''Done''. Now it's going to have a ridiculously long extension, but, oh, well. Now what I'm going to do is target all links using CSS, and change the color attribute based off what is set in here. As I just mentioned, the way to do that is through the global settings object. I can create an output tag, access my settings object, and then I'm going to go into the setting with the ID of link color. I'm going to put in link color here, and then I'm going to close it with a semicolon. Now, we might actually have to change the name of this inner theme.liquid, but let's go and have a look and see if that works now. I'm going to bring up the DevTools. There's no errors in the console. Let's go down to where we bring in the link. If I open the CSS file, open in a new tab, you'll see that we have our CSS, but instead of the liquid tag, which remember gets all generated on the server side, we have the actual output. Just like we calculate liquid on the back end with all of these, and it just spits out HTML and CSS, we've got the same thing happening here. We can put a.liquid at the end of this, then Shopify those to pause any liquid within here. Then by the time it gets to the front end, as we saw, it is just a css.scss file. There's no liquid extension, and it calculates all of the liquid and puts in the actual value. Very cool. So we can programmatically affect our style sheet. I'm going to go back into the customizer here and let's see if we can get our link tags changing. I'm going to refresh the page to make sure that everything's current. Go into general styles, and change this to something really obvious, like red. I'm going to hit ''Save'', and right now it isn't updating. Let's have a look inside theme, oh, wait. Here we go. Now we can see that by default, all the links are red, because we just set that right here in our general settings. If we refresh the customizer, we should get the same result here as well. Maybe it's caching a little bit. Not sure why it is not affecting in the customizer, but is definitely affecting it on the front end here. That's a great example of creating theme settings and putting it in here. This is for anything general, link colors, heading colors, fonts, anything like that that you want to affect the whole theme would go in theme settings. But most commonly, you're going to be setting settings in your section. I'm going to just go back and change this because it doesn't look too good being red. Hit ''Save'' on that, and go into here and refresh the page. There we go. Now we've got the color that we set. Cool. All right. Now let's go into one of our sections and let's look at the featured-collection section. The first thing we want to do is allow the user to actually choose the collection that gets featured rather than hard coding it in. I'm going to go in my settings here, open that up. As always, I'm going to go in and check what inputs I have available. Remember we saw one for collection. I'm going to click on that one. Here we've got an example which I can just copy word for word. I'm doing this fast, because I don't want to get caught up on the theory. But if you want to read about what we're doing here, it's all on the documentation. Go back, replace our empty object here with the attributes that we need to edit. The type is already set for us. I'm going to change the ID to collection because it just makes the most sense. Call the label collection, and we really don't need an info line here, because it's quite simple. Then up here, we can set the collection to, instead of featured-collection, we can actually reference the settings. So I'm going to grab this section object, go into its settings and find collection. Then I am going to save. Now, this will break it because we don't have a default set that then we can easily go and update it. If I go into the homepage where this featured collection section is, it says no matches because we haven't actually inserted anything. Now the content's not showing up. Let's have a look. What have we done wrong here? Everything's looking fine. Maybe we forgot to update or refresh our customizer. Let's do that right now. We should still get no matches because we haven't set a collection yet. But now we can see that collection is now an input. Now we can, as the user, have this lovely user interface to select a collection that we want to bring in here. Then as we select it, it should be used by our section. So I'm going to hit ''Save'' and we've still got an issue. Let me go and check on the front end if it's erroring as well. No matches. So let's go back again, have a look. What I think we're experiencing here is an issue I find with Shopify themes, where calling a resource object gives us its name, but not the object itself. Just to confirm this, I'm going to create an output tag and see if we just get the collection name if I put our collection. I suspect that this will definitely be the case. If I refresh the page, you can see the handle of the collection shows up. If we were actually accessing the collection object, we would get a different result. This is a frustrating thing within Shopify. You would think that if we linked a collection here and then we code it, we would get the collection object, but instead, we get the collection handle. The way we can get around this is by using the collections global. I'm going to go "collections" and then I can use this dynamic value as the handle. Maybe this looks a bit complicated, but trust me, it's not as complicated as you might think. This is essentially the same thing as doing featured-collection, which is exactly what we had before. We just replaced that handle with the handle we get from the user down here. I'm going to hit ''Save'' and see if we get a different result. Now you can see that we're actually getting the collection object and we're able to loop through the products in that collection object. Now I'm really glad we came up against that problem because this is something that's not particularly obvious in Shopify theme programming, and it's something that trips me up quite a bit as well. But from experience, I knew that sometimes you expect an object but get something else back in Shopify. Remember when we put this out before we got the collection handle. Let's now put out collection and see what we get instead. This is what we were expecting to get when we put out this object or what we thought was an object. If we go back and refresh the page, we can see words come up called CollectionDrop. Now this is special terminology in liquid, which basically says this is the collection object. So if it was an empty object, it would say empty drop. If it was a product object, it would say product drop. Unfortunately, we can't output the whole object as we would maybe in JavaScript. It just tells us that this is a collection object. So now we know because before, remember we took the collection here from our section settings and we outputted that as well. If I break those up with a break tag, you can see that the first one is the handle of the collection and the second one is the actual collection object. Okay, I probably went too much off on a tangent there, but something that really trip you up in Shopify theme programming and something I've learned the hard way is when you select resources in your customizer, sometimes you just get the handle and not the actual object. At that point, you have to actually use a global, reference the handle, and then pick it off the actual global object. So that's what we've done here, and we've got it working. So now the user can select what collection gets shown in that featured collection section. Okay. If I refresh the page here, we should get the same result. Yeah. So I could add any kind of other settings here. I could show the sale price, show wherever it's sold out on not, show vendor. Basically customize pretty much anything about this section for these section settings. So that's what we do right here. Okay. Now, the final thing to cover off with schemas is the question of where does the data actually gets stored? Remember I said all data in Shopify is stored in Shopify themes specifically is stored in JSO N format. So where do we find that? Well, all the data for your Shopify theme, gets stored in settings_data.json, regardless of where it's coming from, settings_schema, or it's coming from a specific section. So here we have schemas, and each of these. The actual value that gets stored, all of it goes in here. So you can see this current object at the top, and in our current object we have the link color stored. Okay. So if I was to go in, change that link color again. All right. I want you to notice that this value here is the same as that value there. Now, if I change it to red again, I think this is a slightly different shade of red, and we refresh this data file. I want you to look at what happens to the data file. As you can see, the value of link color has changed in the data file, and just like we did in the language file, we can actually change this value and it will change in the user interface as well. This is the back-end data that is linking to the user interface. So this will change it in the customizer and change the value wherever it's cold in the theme. So if you go in here, the link color is back to black because I changed it in this data. Now this is important because whenever you're migrating themes or copying themes or trying to merge two themes together, you need to take care of this data file. I'm not going to talk too much about staging because I do have a video on YouTube about that. Just search for Shopify theme development on YouTube and hopefully you'll find my channel. If I'm doing my SEO, right. But this is something just to be aware of with your data file. It all gets stored here, so be very careful with the data file. Try to avoid touching this. But if you do need to merge data from two themes, this is how you would do it. All right, with that side note out of the way, I want to draw your attention to a few more things in this settings_json document, and that is we have this section's object right here. Now you can see all the sections that we have. We have header, collection template, footer and this one is referenced by its ID. I'm not sure why it's referenced by its ID instead of its name, but regardless, we've got a featured collection here, and you can see in our settings, we have a key value of collection with the featured collection handle. So if I go in and change this to a different handle, that would update it in the selection I have here for my featured collection. All right, again, this is just a lovely user interface to change what's written in here. The other thing I want you to notice is the content for index array. It takes all the IDs of the sections that are in use and puts it in here. So if I just remove that ID and hit "Save". Now when we go to our "Homepage", that section that the ID referenced is now missing from our Homepage. Okay. But we can always add it back in. Add in the featured collection. Choose a collection that we want to feature. I've just called mine featured collection. Save that again, and if we refresh the data file, you'll see that that data file in the content for index array is back in there. Okay. So settings_data.json stores all the data that's generated from all your schemas in the one place. There is of course, your locales photo, but this is all just for locales. This is separate to schemas, okay? All of the settings that you set up in your settings_schema.json, and the schemas within your individual sections. All of those selections, the selection itself goes into this file right here, settings_data.json, and that is basically for JSON schemas. You've seen how to add a setting on your overall theme settings. So we saw that here, and we've seen another example of inserting a particular setting into a section right here by allowing the user to choose what collection gets to be featured. Okay? Also, just to recap, we learned about a little bit of a gotcha in Shopify Liquid. If you do select a resource like a collection, the object value will just be a handle, not the object itself. So we still need to look that up using a global object like collections, like all products, all of the global objects you can find right here in the blog post. See how, if I scroll down to "Collections". This one just shows you how you can loop through collections, but we access a particular collection via its handle. You can do the same with the old products object. You can access a product via its specific handle and then that becomes the product object. Okay. So we should be pretty clear on JSON Schemas. Remember, you're probably not going to know off by heart what settings to put in here. So make sure that you reference the documentation. This page has all the different input settings that you can put in there. On this page, theme sections, you can learn about stuff like presets and blocks. Blocks is something we're going to learn about in the next video where we actually create our own section. So I'm looking forward to that video. I will see you in the next one.
8. Programming custom sections: All right guys, in this lesson we're going to put together everything we've learned so far about Shopify Liquid and JSON Schemas to practice creating our own section. What I'm going to do is create a gallery section, which will be a section that we can include on the homepage for content, for index or on a specific page and it'll just show a gallery of images that the user in the customizer specifies. What I'm going to do, head over the sections, add a new section, and I'm going to call it gallery. As usual, Shopify gives us a Schema and we just need to change the section name to gallery. Hit "Save" on that. I'm going to just set up a div with a class of gallery and there you go. Now, how this gallery is going to work is, I'm going to allow the user to specify how many columns they want per row, and then also the height of the image, and then I am going to allow them to insert blocks which are going to be the images that we will include. Going over to the documentation and looking at the section on blocks within the document on theme sections, let's scroll back down there again for blocks. You can see here that we can put in blocks which are containers of settings and content, which can be added, removed, and reordered with intersection, and that is ideal for what we're doing here. We want them to be able to add in as many images as they want and reorder them, and we just need the same settings for each. I'm going to skip over the settings array for now and create a blocks array, and in this blocks array, I'm going to open up a block. Now, for a block, what we need is a type and a name, as it says here, a block must have a name and a type. A block's type may be any value set by the theme developer. So the type is not something that's specific in Shopify, it's just something that we set ourselves. I'm going to make the type and image, and you'll see later we can add in different types and then check the type within our section. I'm going to give it a name and call it image block. This is going to be the label that gets shown up to the user. Now, I believe we can just create a settings array just like we would do on the parent object here. I'm going to add a settings array, open that one up and inside start with the first object, which is going to be an image input. For that, we're going to swap over to this part of the documentation called configuring theme settings and I'm going to look for image. The input setting type for an image is image underscore picker and we can just copy the setting value here. It's going to be image picker, we just need a type, ID, and the label. Going back to our code here, pasting that in, we're going to change the ID to image, and we're just going to put image here, very basic. So that is the settings that we'll have for every block. If I hit "Save" on that, let's see if there's any errors, no, there isn't. What I can do now is I can create a loop through all the blocks in OWL section. I'm going to create this loop and I'm going to say, "for block in section.blocks," and then I'm going to enter the loop. We'll format this, make this look a bit nicer in a little bit, but for now let's just get this content out in the page. Now, we can reference block directly and I'm just going to create an image tag with the image that gets set, so block.settings.image. Remember how we access different attributes is just navigating this JSON object. So at the top here, we find blocks on the section object and now we're looping through an individual block and then we have access to what's in here, the settings object, and then within that, we can access the attribute using its ID. That's what's going on here. If I just output this, what I'll get is just the image address. Before we can actually look at it, however, we need to include it somewhere and what I'm going to do for that is create an alternate template for page template, and then we're going to use the ultimate template to display this section. Fortunately, there's a few steps involved with doing this. We need to first go into our templates folder and add an alternate page template. I'm just going to call this one gallery, create the template. One thing that's frustrating with Shopify is we're going to have to create this on the current theme as well. So if you're currently working on the theme that you're previewing and not actually live on your website, you have to create the same template on your current theme as well otherwise, you won't be able to select it. But for now what I'm going to do is include this section on here. So I'm going to strip out all of this and in this custom page template, just call the gallery section, and I'll hit "Save". Now as I said, in order for us to select it from the list, I'm going to have to go into the current live theme, which is debut and create the same template which I may have already done here. There is already a template with the name page.gallery. If that didn't exist, I can just delete that one, go into add page, exact same way we've done before for the other theme, and what we'll do will insert the same content as the regular page template. So you don't need to worry if you switch this within the page, it's still going to show the same page template on this theme, if that makes sense. Now, if I go into pages and I add a page, call it gallery, I can use that specific template that we just created by selecting it here. If I save the page, now we can look at what the address of it is. It's going to be @pages/gallery. So let's go back into the code. As we saw, we have already included the section on that alternate template. Now, we just need to go to the page that we just set up. Pages gallery. Right now we haven't added any content so nothing is going to show up. What we want to do is open this page in the customizer. We're going to have to first refresh because we've made changes to our theme codes since we had this open and now we should be able to see that we can edit the gallery template. Picking on that. Now we can see the section for Gallery. Just taking it a little bit slower, we're in the page for gallery and as it's using this specific alternate template, it's going to link directly to this section and then within that page now for the customizer, we can see the section showing up here. So in the gallery, you can now see that there's going to be this content section and you can add an image block. That is all from the settings we set up in our gallery section. So we don't need this anymore, we just need that one tag. We can start working directly from the gallery section right here. But remember, we called it an image block and so here in the customizer, it's add image block. If there are multiple types, we'd be able to click this and it give us different options, but we just have the one option for now. As you can see, there's our image setting that we've got here. We can now add an image. We've got men on the front and we can add another image, block, the guy with the suit and you can see here what happens when I do that. Instead of the actual image, we've got a URL section. What's happening here is that the image being selected is not actually going to give you an image tag. So in order to get the image tag, what I'm going to do is use the image tag filter right here. Now, we may need to specify a distinct path as well, let's have a look, so there you go, they are showing up and because we didn't add a parameter they are showing up quite small, this should be 100 by 100. If we have a look, so the width is a 100 and then the height is relative to the width in terms of its aspect ratio. We're going to need to make them a bit bigger. I'm going to add in a parameter for this image tag of, let's say 500x. So now they're going to be five times as bigger, five times as big, rather. I've made a mistake here and I see that the parameter, it actually represents the alt tag. If you want to put in alt value, that's where you put it. What I need to do is chain another filter in here. I'm going to filter this for image URL like before and that's where I can specify the dimension of the image. I'll save that, refresh the page, and now the image is five times as big. What we've got here is we've got, if I just refresh the page in the customizer, we've got this gallery. So we can add another image block. If the image isn't set yet, Shopify just inserts a place holder, which isn't very beautiful, but it shows us that there is at least supposed to be an image there and I can add in another image, and basically what's going to happen is they're all going to be 500 wide and they're just going to stack across the horizontal and vertical space of our page. If I refresh the page, maybe this is good enough for your gallery, but I want to make this way more responsive. What I'm going to do is I am going to give this a responsive width and create a height that the user can change. What I'm going to do is in here, instead of just outputting an image, what I'm going to do is create a image wrap and in this image wrap tag, I'm going to give it a background image of the image that we set here. The benefit of doing this if you're not familiar, is that we can control the height and width of the div and then the image will fit within that and it'll crop based on the dimensions of this div tag right here. What I'm going do is add in a style attribute and have background image URL and I don't need the image tag anymore, and I can insert this here. Now we need to give it some dimensions. Just to give it something straight away, I'm going to give it a width of 500 pixels and a height of 500 pixels, and then I'm going to give it a [inaudible] , create some space here. Here we go. Then I'm going to give it a background size of cover. Save that. See what happens when we refresh the page. You'll see now, if we have a look, these aren't image tags anymore, they are actually divs, and that's why they're stacking on top of each other because these are set to default to display block, as you can see here in the computed values. We want them to display next to each other, so inline-block. Now, we can either set it up in our main CSS file or we can do it in the actual section by refactoring this to style, not style sheet and putting in our styles here. Now, in this case, I'm going to put it in the actual section and there's a good reason for that, because when we use these style tags, we can see things live update in the customizer. We could always just throw in styles using HTML. But if we do this, if there is a user generated style within here, like something they set in the customizer and we changed that. It's not going to show up straight away. So using these liquid tags, we can actually store our styles in the section and that's going to make it easier to find. But also we're going to get the ability to see those live update if we use customize a data in here. So I'll show you what I mean by that in just a sec, but first I'm going to create a style rule in here for image rap and what I'm going to do is set all image wraps to display inline block and if we go over to our page, even the customizer or over here and refresh the page. We'll see they are now stack next to each other. If we go over here, we'll see that we've got display inline block. This is a little bit better because if we resize the window, so I'm going to move this over to the side and see how the window resizes. It's going to knock it down to the new line if there's no space. But to make it a bit more responsive, what I'm going to do is I'm going to set the width to a relative value. Going back into here, we're going to set image rap to width of 33 percent. That way we get three in a row. So I'm going to remove this value right here and actually let's move these values into the class just to make it a bit cleaner. Right here, these are going to be the same for every image rap, so we're going to put this down here in the actual style row here. Refresh the page and now you can see our images are responsive. So again, if I was to resize, you can see there's always going to be three on a row and they're going to resize in order to achieve that on any screen size. Now, for the user, they might want to choose how many images they're up for a row and they also might want to be able to change the height of the images, because, as I said, with responsive images, they automatically crop. Like we saw before, if I reduce this, they're always going to be three on every row, so now we're losing parts of the image. So maybe we want to make this less tall if we're using a lot of images per row. Anyway. So I want to give the option to the user to be able to affect this value and also the ability to affect this value. Because this is going to happen to the entire grid, this is going to be a setting up here, not in a specific block. The first setting I want to do is I think I'm going to have a select. We haven't used select before. So let's go into the different input types we have available to us and look at select. I'm going to grab the example as a starting point and replace this empty objects with the example. So we've got the type of select, I'm going to set this to, per row and it's going to show to the user products, oh sorry, images per row, and then for our options, we don't need a group, we just need a value and a label. In our options array, I'm going to have three different values and this is going to be the widths. If they choose two per row, it's going to be 50 percent. So two per row and if they choose three per row, it's going to be 33 percent, three per row. We need to duplicate that across, ends this one 44 per row, is going to be 25 percent. Let's just do five per row as well. Add in another option and we'll make this one five per row. The default, it has to be one of these. Let's make the default three per row. That's going to be 33 percent and the info we don't, really need. I'm going to hit "Save" here and I've deliberately added in a error, or I've deliberately left an error in my JSON schema. Now, unfortunately, in Shopify in their code editor and when you're using theme kit as well, they just say error invalid JSON and if you have a big schema, it could take you forever to figure out what the issue is. So I know what I've done wrong, but maybe you can't pick it right now. Luckily, because it is just a JSON object, we can actually put it through a JSONLinta and see what the issue is.So I just want to show you how to do that right now. I know that the issue right here is that we've got a comma at the end here. So remember we remove that value. The last value cannot have a comma after it, but we might not know that so one thing we can do is use a online JSONLinta, so I've just copied the whole JSON object and I'm going to go to a website called jsonlint.com I believe. I'm going to paste in our JSON object, doesn't matter that it represents Shopify data. All this does is take the format of the JSON and check whether it is correctly formatted. So right here, we have a much more detailed error message, which is we've got an error on line 24. It expected a string it got a closing curly bracket. So that's still might take a little bit deciphering to figure out what the issue is here. But at least we get a specific line number and we can say, oh, I've got this comma here. So if I go back, take away that comma, hit save, now you'll see that we have no errors. So the next thing I need to do is actually reference this value that's been set in the customizer here. So instead of 33 percent I'm going to, as we have done numerous times throughout this class, reference the section object, go into its settings and grab per row. I'm going to hit save on that and let's go back into our customizer and refresh. All right, so now I'm going to go into the gallery section and you can see that we now have a drop-down for selecting how many images per row. If I change this to two, it doesn't work with 50 unfortunately but if I change this to four, you can see this live updating. Unfortunately, there are some margins that are affecting how many can fit per row so we just need to change that. But you can see this is live updating. So going to hit save on that, you can see if we look at this in the browser, these are each going to be 50 percent. This is a little bit of an issue with inline-block, but if we reduce it by 0.5 percent, that should get around the issue of margins and now you can see we've got a two by two grid. So I'm just going to go back into our code here. Change two per row, give it a percent of wiggle room. Same thing here, and same thing here. That should hopefully get around that issue. Now if we refresh the page on both of these, let's do it in the customizer so that we can actually live update this. Change it to three per row, change it to two per row, four per row and we don't have five, but if we did have a fifth one, it will show up here. All right, pretty cool. Now, as I mentioned, if we're showing two per row, then we've got a nice aspect ratio going on here. But if we set it to four per row, we're going to lose a lot of the image because remember they crop automatically in order to stay responsive. So I also want to give the user the ability to specify the height of all these images. So let's add that in now. I'm going to add it in as another select. So, whoops, let's go copy that example again from the documentation and replace this empty object with that. This one is going to be the heights, and I'm going to call it image height. We don't need group, as I mentioned before, the default value is going to be, let's say, what do we have right now, 500 pixels. Let's say it's going to be 500 pixels. Don't need need info. So we'll make the last 1500 pixels and this 1300 pixels. Now we probably want to make more options. So let's just create one extra option, you probably want a few more as well, but it's the same process for each. So let's just put this somewhere in between 400. Now before I hit save on that, I'm going to actually insert it. So just like I've done here, instead of coding or hard-coding in a height, I'm going to reference this setting so put it in there as height. Again, we've got an error in JSON schema. I know that just from the last one we've got the same era we've got this comma here. If you didn't pick that up, you can always put it for the JSONLinta. So now if I look at this in the customizer, we've got an issue here. Let's have a look on what we might be doing wrong here. I forgot to put the semicolon on the end, refresh the page. So now we should be able to, as the user in the customizer, change the image height. There you go. So if we're doing a four images per row, we probably want the image height to get smaller as well. So we can set a smaller image height. We can set it to 400, it's 500 so a good combination, maybe on two per row we have it set to 500. But if we're doing four per row, we set it to something a little bit shorter, like 300. Now, I know this video is probably pretty long already, but I want to show you one other thing, and that is, we can add in different types of content in this gallery. Doesn't need to just be photos, we can actually add in embedded videos as well. For this, I don't want to be writing a lot of codes, I'm going to be copying across something, but it should be pretty simple to understand regardless, what I'm going to do first because we're going to use a different type, is put in a conditional. I'm going to say block type, remember, we now have access to the individual block because we're looping through, and if the block type is image, then I know I'm going to have an image setting. I'll close that, and if now because all of our block so far, the type of image, nothing should change when we refresh the page. Now, everything is normal, but we can add in a different type here. Instead of wherever we got here, I'm going to add in another block for a video embed. I'm just going to copy and paste to make this a little bit quicker, and this one instead of image is going to be a video block, and this is going to be the label that shows up to the user, and for the settings, I'm going to, I believe it's called a video URL, and so the ID of that is going to be video URL is it's just called a video URL as well, and the label is going to be video URL. I think there are a few more attributes I've got right here to look at, we can put in what it accepts as well. We can make it except YouTube and Vimeo. We're going to need to remove that comma of the end, otherwise, we'll get an error. If I hit Save on that, hopefully no errors, and now when I refresh the page and our customizer, and I go to the gallery, instead of add image block, it's just going to say add content. The reason why is when I click this, it's now going to give me the option to add in the different types. I can add in another image block like before, or I can add in a video block. In here I can paste a YouTube or Vimeo link. For that, I just need to find a YouTube video, I'm going to quickly find one from my own YouTube channel. What better video to use then, one of my videos from my series on Shopify theme development, let's use that as the example video right here, and let's hit save. Now, even though we've saved this video block, we need to actually output something to the screen. What I'm going to do is copy across some logic here, but what I'm going to do is because it's going to be different code for the video block instead of the image block is I'm going to put the conditional in straight away. This value here is what we created here, so we've got type, image, type video, this is what we are checking right now. Now, I'm going to copy and paste in some code, to save us a bit of time. To briefly explain this code, what we've got going on here is if the block type is video, we know that this is a video block, and if the URL is blank, we're going to put in a placeholder video with these different attributes. If it isn't blank, then it definitely has a value, so we just check if the type is YouTube, if so, we use the YouTube embed link, if not, we check for Vimeo, and if it is Vimeo, we use the Vimeo embed link, and then we grab the ID of video URL. This is a bit more of a complicated one because we actually get an object out of this video URL, and so we've got an ID and a type on that object. That's why I copied and pasted this code because it is a little bit more complex and it's not very common that you would use this anyway, but this is a good example here of having different types. What we're going to need to do to finish this off is also have this effect our iframe. In each of these scenarios, the iframe is going to contain the video, so I have just added the iframe onto here as well. It's going to have display inline-block width and height that we've set in the customizer. This one is not going to make any sense for the iframe, but hopefully it still works, if I go now into, let's have a look in the customizer. You'll see we've got my video showing up, unfortunately, the width isn't correct, so let's refresh the page, see what's going on. Here we've got our image wraps, image wraps, image wraps, and then we've got the iframe here, which doesn't have any styles attributed to it, so it's just doing width and height. Let me look at what I could've done wrong here, and I can see I've put a dot in front of iframe, presuming it's a class, but I'm targeting the element itself, so I don't need to use that dot. If I refresh the page, you'll now see that it conforms to our grid that we've set up. Let's customize that in the customizer, maybe let's set it to five per row. Let's do five per row, and now you can see that the video embed is the fifth item in this row and we can actually reorder the content. Now, the user can go in, add any number of image blocks and video Blocks, maybe some nice women's fashion videos and photos, and that'll go on to the new line. We might need to play around with mobile styles, change the grid to be different on mobile, so we're going to need some media queries, but that is perhaps a project for yourself to take on, I just wanted to give us some practice with schemas and liquid, and what better way to do that is through a section. If we want to be able to put this on the homepage, don't forget, we need to insert a preset on here. Let's just do that to finish the lesson, so we'll put a Presets array, and again, I'm going to go back to the reference numerous times presets right here, we just need one with a category and a name. Going back here, put in an object, I've put up that object. We've got category of what do we call the other one. I think it was custom content, so you can get it to show up in the same category, and we'll give this a name of gallery, hit Save on that. Now, this section will be able to be included on the homepage as well. If I go to the homepage, add a section, we've got a problem here. That's right. I haven't reloaded, a customizer yet, always remember to do that guys. Now when I add in a section, you'll see gallery is here, and it won't hold the same data as the place over here, because every time a section is included, it's got its own data. We can go in and create different galleries. There we go, let's put it in another image block, the woman's fashion, and let's make the last one a video, let's see if I got the add up. Haven't got the video link, but there you can see the placeholder there. We've got our custom gallery section, we can put it into our homepage now, we can use it on specific pages, and by now, you should have a pretty solid understanding of a Shopify liquid and schemas. Now of course, the more experience you gain with Shopify liquid, the better you'll get at it, but I believe this should be a good foundation for you guys. Remember the documentation, the liquid reference right here, where is it? Liquid reference there you go. This is your textbook, this is your documentation, you've also got my article, which I'll highly recommends to give you a different perspective on Shopify liquid, and then you've got the cheat sheet as well, but that's more of like a quick reference. For anything to do with learning all the different parts, maybe there's an area of liquid you don't know too much about and you want to learn more about. Either check out the blog post or check out the official documentation. Look it up, see if you can gain an understanding that way, because now we'll be moving on from liquid to talk about the Ajax API. Remember, I said that Shopify liquid is like the back-end programming language with Shopify. If we want to do something purely on the client side, we're going to need to use JavaScript, and luckily, within our theme, we've got this API called the Ajax API to allow us to do certain things. We'll learn all about that in the next lesson and maybe two lessons if it's a particularly long one, anyways, I'm excited for the next one, I'll see you there.
9. The Shopify AJAX API: Welcome back guys. In this lesson we're going to be talking all about the Shopify ajax API. I'm currently on the official Shopify documentation, I found this page just by searching for a Shopify ajax API and Google should be the first result or one of the first results and this is the page on the documentation for the Shopify ajax API. It's pretty good, covers almost everything you can do with the ajax API. There are a few hidden gems within Shopify. Basically, the Shopify ajax API is mainly for adding items to the cart, updating quantities in the cart, basically doing anything with the cart without a page refresh, as it says here, I've got an example here of a Shopify store running the impulse theme. Impulse is a premium Shopify theme that is pretty modern. I want you to have a look at what happens when I'm on this product page, I select a variance and I click "Add to cart". Here you can see that there's this side cart or side drawer that comes out with the cart, and I can actually increase the quantity here and the price updates, and I can decrease the quantity and I can set it to zero and now the cart is empty. The whole time I'm doing this, I'm not reloading the page. As you can see from up here, there is no new page being loaded, it is simply opening up this drawer which is already on the page. How is it doing this? It is doing this through the Shopify ajax API, and I can prove it by opening up my developer tools, over here in the Network tab, I can see all the network requests. Let's add an item to the cart and you'll see the first one that came up, add.js, and you can see here the endpoint that is going to is cart/add.js, and it's sending through, a bunch of information. Now you can see the response, it's a bunch of cut information for this particular product variant. You'll see here that we also have a get request to cart.js, and you can see here that we've got the full cart here in this object. We've got an array for items, and you can go in and see that item that we just added, so this is the Shopify ajax API in action. This right here, is a Shopify ajax API endpoint, and the reason I know that is because you can find it right here. Here are the different end points, and as you can see here, if I make a get request to this path within a Shopify store, I can use this to get the cart and it comes back in JSON format again. Just a heads up, this might be a little bit advanced for some viewers using APIs and what JSON is, we did learn about JSON in a previous video, but here we're actually sending requests to a server and returning back objects in JSON form if we want to actually use them in our project, we're going to have to parse these JSON objects. This can be quite a long topic and you probably need a bit of knowledge of JavaScript to get your head around this. Again, this is not a JavaScript course, this is all about Shopify, so you should have some fundamentals in HTML, CSS, and JavaScript. If not, I do have a class here on skillshed.com on JavaScript. If you want to check that out or any other place you want to learn about it. But this is what we're going to be doing, we're going to be querying these endpoints and doing what is going on here. Now unfortunately, I don't have the time to build a side cart and all of this user interface in this one lesson, what we're going to want to do is I'm going to show you the requests just in JavaScript, and then I'm going to show you an example that I've done up that I'll give you guys as well, where I have rented a cart to the page and I'm able to update it, take away items, update quantities right on the page. I'll show an example of how you could actually implement the UI and what's called the event listeners in the end of this video. But first of all, what I want to do is I'm going to close this down, I'm going to go back to my testing shop, and I'm going to go into the new theme that we're working on. Because we're going to be retrieving data purely through JavaScript, I don't actually need to open my code editor, I can actually just do it all through the console, what I'm going to do is open up a product that way we can actually add this product to the cart and then I'm going to open up my Developer Tools and go to the Console tab.Theme is going to be nicer to look at if we go down here, and let's write our first request, which is a basic one, which is going to get the cart, if you're starting on a blank project, you should have an empty cart, but you'll still get a cart object before we get started though, it's going to make it a lot easier if we have something called jQuery installed, if you don't know if jQuery is in your theme, it's in a lot of themes, you can write a basic jQuery command and see if it comes up undefined, I've got undefined for the $ sign version of jQuery and I've got jQuery is not defined. What I'm going to have to do is include jQuery in my project.I will have to make one code modification just to bring in jQuery. JQuery is a library that is just going to make it easier for us to do these Ajax requests. I'm going to type in jQuery into google and find a link to the CDN, right here, and I can just grab the minified version of the latest version. I'm going to copy that script tag, go into my layout file, and I'm just going to paste that in. Hit "Save". Now if I refresh the page, I can check if I have jQuery installed by doing the same command, and now you can see I get a function back. I can try the same thing with the jQuery keyword itself, and I get the same thing. There's no error saying what is jQuery, so we know now we've got jQuery and now we have a few nicer functions to do to get requests with. The first one is a request to cut JS to get the cart, so this is a very simple one. I'm going to use the get function in jQuery, and I'm going to put in as the first parameter, the end points, which is simply /cart.js, and then I'm going to put in my callback function. What's going to happen here is I'm going to make a request to this end point and then I'm going to access the data that comes back, so what I'm going to do is console log the data so we can see it right here in our console. I'm not sure why I get this error here, but as you can see, I've got the data back. The issue with it, however, is that it's in one giant string, so what I'm going to have to do is parse this, because this is just a JSON string, but we're easily able to what's called parse this, and we'll get back a JavaScript object that we can work with. Instead of just putting in data, I'm going to wrap that in a parse, and now you can see we get a JavaScript object back that we can actually navigate and look inside. Now it looks like I've already got an item in my cart, and to verify that that's the correct information, I'm actually just going to go to my cart page, and I see, yes, I've got three of these awesome sneakers in my cart. Let's remove that product from my cart. Cart is now empty, let's go back to that product page, any product page, and I'm going to rerun that "Command". Now, you can see in our cart, we've got item cart zero and we've got the array of items which is currently empty, just as we would expect. What's happening here is without having to go into our back-end code, I'm able to retrieve the cart from our Shopify store all in the browser. From a practical perspective, this is what allows us to do things purely on the front end and in Shopify the place where it makes the most sense to have this functionality is with the cart. Because the cart is the main point of interaction with your Shopify store. People are browsing products most of the time, they're looking at content. The main interaction happens when the person is ready to purchase. They put the item in the cart and then they turn that cart into a checkout and complete their checkout. It's no wonder that Shopify provides this API for you to actually do stuff like this with your cart. Let's run through the next one. Let's actually, add an item to our cart. I'm going to scroll up to the top and this is the one I'm looking for. Use this to add a variant to the cart. Remember, it's a variant that gets added to the cart, not the product. What we're going to need to do is grab the variant selection from this form and then submit it to the cart using this post request. We can do this in two ways. We can specify the variant ID and the quantity that we want to add to the cart. But the problem with this is we don't yet know the variant until a person puts in their selection and the variant is determined from this selection. What we can do is instead serialize the form and what that's going to do is take all the data of the form and it's going to come out as an object here for us. Let's use that example right here. I'm going to go back in here. As long as we have a form on our page with the action of cart slash add, this is going to work. I'm going to hit "Enter" on that. Now let's load the cart again, and see what happened. If we open up our cart, we can now see the item count is one. In our array we have an item, and the item is the variance of our selection here. I'm going to click this to clean this up a bit. I want to run the add to cart Ajax requests one more time and I want to have a look in a network tab at what's actually happening here. Remember, we serialized our form and we send that data off to Shopify and you can see here, what that's done is given us an object with the ID of the variant we want to add and how many of them we want to add. We don't necessarily need a product form if we're able to find the variant through other means just as a FYI there. We could actually, instead of serializing the form, if we knew the variant ID for some other means, we can just put in an object here with the variant ID, copy it from here, and then the quantity and then that will do the exact same thing. If I clear the console and I run the get cart again, you'll now see that we have three of these shoes now in our cart. Just a few more things you can do with the Ajax API. We can clear the cart. We can make a post request to /cart /clear.js, sets all quantities of all line items to zero, so clears your cart. Let's go back in here, make a post request using jQuery and the endpoints was cart clear and we don't need to send any more data with it, so we can just write it like that. Now, if we run get cart again, you'll see our cart is completely empty. The last thing you'll probably want to do with your cart using the Ajax API is to update the quantity. Here you can use the post request to the cart slash change endpoint, and you can change the quantity of an item already in the cart. What we're going to do is add a variant to the cart again. Just copying and doing the same request again. Now, I can create a post request to this endpoint and put in an object just like I had before. I can strip it off here and maybe I want to update the quantity to five. Now, I can send that post request. Let's clear the console and let's open up the cart. I just added another one. Now, we should have six is the one I'm looking for and as you can see, we have six of this item. We have just one line item because it's all the same variant, but the quantity is six. It's got all the information here about the variant. Now, in line item form, as you'll see on the cart. Alright, cool. Those are the main things you would want to do with your cart. In the example, we saw and the example, I'll show you in a sec. That's what we're using the Ajax API for. The Shopify Ajax API makes it really easy using these endpoints to retrieve data about your cart and modify your cart. The real challenge comes from sending up event listeners and handling that response to update your UI. Unfortunately, that is a very JavaScript heavy lesson and not particularly specific to Shopify. That's why I'm just going to show you an example, now and run through it, but we're not going to code it from scratch in this lesson. The reason why is, it is general JavaScript knowledge of how to do this. If you want to learn more about JavaScript, again, I have a class on skill share, or you can learn about JavaScript somewhere else. This is just concerned with Shopify, but I do want to give you an example of, what it would look like. If I close down this preview and we head back into the store, I've actually set up a theme with an example of a reactive cart. Right here, I've got this theme called Ajax API Demo, and its based off the new theme. Basically, the only thing I've changed is I've added Bootstrap, which is a CSS framework. You'll see the styles are a little bit different and we've got these buttons, styles right out the gate. If I go into a product, you can see that the cart is sitting right next to the product, and if I add an item to the cart, I don't need to go to the cart page to see my cart updating. I can even change quantities and all the different parts of my cart will update. As I said, usually you would have to go to the cart page and view it there. But even from here, you can't update quantities without having to reload the page. In order to make a cart like the one we just saw, so going back to the product template, we must use JavaScript and the Ajax API. Just to prove to you that this is using the Ajax API, I'm going to open up my Developer Tools and I'm going to have a look in the Network tab. The first thing I want to do is actually before we look in the Network tab, I just want to clear the cart completely. I'm going to clear this console as well. Now, let's add an item to the cart. As you can see, we've got a request to add.js. If I look inside there, we can see what we're sending is an ID and a quantity. This is the data from the form. What it's doing is actually serializing the form, grabbing this data and then it's sending it to the Ajax API. Actually before this, before we even add an item to the cut, if I just refresh the page. You'll see we're getting the cut from the Ajax API. The reason why you can tell that is if we look in here, we can see a get request to cart.js. If I open that up, I'm just going to have to move this across a little bit.You can see we haven't sent anything because we're just asking to get to the cart, we're not posting anything. You'll see the response we get back is the whole cart as an object. Remember we saw this before when we were just working in our console. But the difference now is the page loading is actually triggering this. Then what's happening is we're taking this data and we're representing it on the page. Let's have a look at what happens when I add another item to the cart. We make a request to add.js. You can see here what we get back is a line item. We don't get back the whole cart, but we get back a line item, and that gives us the necessary information to update our cart. Now, if I increase the quantity, you can see we're making a request to change.js, which is another end point. You can see here that change.js. What we're doing is we're sending the ID and we're sending through the quantity that we needed to change to. What that will do is it'll take the data and then it will return the whole cart again. You can see here, if we go look inside the item, we can see quantity somewhere here. There we go, it's three, and then the total item count is three there. If we added another line item, so we just need to select a different variant, add that to the cart. Now you can see we add that line item and now we have all of its data here. If I was to change the quantity on that, look at the next request. You'll see we have five items spread across two lines. The first line has a quantity of two and the second line has a quantity of three, for a total of five. Then, you can see we've got the total price and everything. I wanted to show you how the Ajax API is working as well updating the user interface on the page. Now, as I said before, there are a few parts to this. First of all, the event listeners. Certain things happen on the page called events. Then those events are set to trigger requests to the Ajax API. Now, of course, when the data comes back, we need to actually do something and then that something is updating our user interface. Let's have a look at the code right now. If I go back into this theme and I click Edit code, there is quite a bit of code here, and I'm not going to explain line by line. But what I've done here is I've used a templating library code mustache, right her. What that allows me to do is create these templates. So this is the template for the whole cart. This is the template for the line item. If you want to learn more about mustache, mustache.js is where you can learn more about it. Logic list templates, you can read the manual here. It's not the most sophisticated documentation, but essentially you can think of mustache like a JavaScript version of liquid. It actually uses the same delimiters, which is why we need to actually change the delimiters to custom ones so that they don't actually conflict. So as you can see here in this template, just like we would in liquid, we would insert a URL like this. But, of course, because we are in liquid and the liquid engine is going to interpret that as liquid, we need to use custom delimiters to differentiate these template variables from the ones in liquid. We've got the two templates right here and we've got a whole bunch of JavaScript that includes our event listeners and then now Ajax API requests, and then we handle the response. We've also got some styles in here to style the cart. As I said, I'm not gonna go through line by line of this document because there's a lot going on here. I have written extensive comments on all the different functions. I would definitely have a read of this file, and if you have any questions, let me know. You can access this file through my GitHub page, I have a repository called skillshare where you can access resources for all my classes on skillshare. Right here you can see product.liquid is one of those resources. This one's actually a little bit nicer to look at because it does syntax highlighting on these JavaScript templates. But you'll need to actually move this into your theme in order to actually interact with this code and see what it's doing. One more thing before I step through the code a little bit, is that you will need jQuery installed on your theme. So if you don't have it already, you'll need to either install it by downloading it and including it in your assets folder. Or the simple way is just to include a link via a script tag to the CDN. So you can just, how I got this link, was I went to jQuery, jQuery CDN, and I found the URL. So just like we did before when we were doing our requests in the console, we need to actually include that script in our theme.liquid. Or if it already exists, that's cool. But there is some parts in here where we're using jQuery. As I mentioned, we've got our two templates here. Before that. We've got the product page as it normally appears. So here's where our normal product template code is, which I have over here. We have a div here for the side cart. Right here we've got this div with an ID of cart goes here. The div of the cart goes here, ID is what we use to tell mustache where to put the template. When the page loads, is going to load this template right here into this div. Now, this other one line item is for when we add a new line item to the cart. So it's a section of the cart. What that's going do is it's going to append to a specific part of this template. This is basically all just mockup with the appropriate data placed in different parts of this mockup. The real magic is right here. So to go through this code in a similar fashion to what I showed you here. Remember we had, so I'll just put that back to one, refresh the page and you'll see that cart gets generated. Now, if I refresh the page again, you can see that this renders first and then this renders, that's because this is rendered by liquid. This is coming from the back-end and this is actually being rendered on the front end using mustache. So what does that is this function here, run get cart. When the page loads, that's when we run this get cart function/ if we look up here, what get cart does is it sends a request to the AJax API to get the cart, it passes that data, and then it sends it to this function which handles the data. I've done this handling of the data in a few different places, which is why I moved that into a different function. Then you can see the function up here. What this does is it updates the cart total and the items based on what comes back from the API, the API has all the prices in sense, what we need to do is divide them all by 100 in order to get the price in $, and then we render the cart with mustache. This is the mustache method in order to take our template, take our data, and combine them together to create our output. Then, as you can see here, we're taking the element that has the ID of cart goes here, and we're putting that mustache output right in there. Okay, so that is what's happening when I first load the page. It is making that Ajax request and then rendering that template using Mustache. What about when I add a product to the cart? So let's just choose this size nine variant and I click Add to cart. Oh, we already have size nine, so that's just going to increase the quantity. If I go into here and I look at the submit Event Listener for add to cart, we're doing a bunch of different things here where preventing the form from doing a standard form submit, so we can handle the form using JavaScript. We're doing like we did before. We're serializing the form so we can get its data. Then we're passing it to the Ajax API for a post request. We're going pass the response, update the cart total. Then we're going to get the response back from the server and handle that. Remember the response for adding an item to the cart in the Ajax API is the item. So it's not the whole cart like with cart.js or this one, cart/change.js. The responses for those are the whole cart, but the response for this particular request is the line item. Because of that, the cart total, we have to figure out ourselves because it's not coming back in the data. So that's what I've done here. It's pretty easy to figure out, is this going to be the previous cart total plus whatever the price of that item is. Then we actually need to go find it in the UI and update it, dividing it by 100 in order to get it i $. This right here, we'll check if the item already exists in the cut. Remember we added another item of the same variant. That means that we don't need a new line item, we just need to update the quantity of that line item. If I go in here and choose a different variant, you'll see that we get a new line item. That's what this conditional does. It checks if a variant already exists. You can see the function up here. We return an array based on whether a match has been found. If there is a match already, then instead of running mustache to render a whole new line item, we just have to update some things on the existing line item. We just grab the item from the DOM using this and then we update the quantity and the price. Here you can see if I add another one, the things that change are the quantity and the price here, and of course, the total, which we already have handled up here. But if it's a whole new item, what we're going to do is push that item into our items array. We're going to take the data, the prices and we're going to divide them by 100 again to get dollar values. Then we're going to render the line item template. Anytime we're rendering a whole new piece of HTML, I've opted with going with mustache rather than doing jQuery. If you're writing a whole lot of mark-up, it helps to have a templating language. But if you're only updating a few little things like a number here, then you don't need to really worry. The last one, which is the one I just did, is updating the quantity. If I go on any of these and I update the quantity, if I set it back to zero, as you can see here, if the new quantity is less than one, what I'm going to do is just hide that item right after the post request. Stepping back a little bit, what I'm going to do is set up event listeners here on these quantity adjustment buttons. The "Plus" one is going to adjust the quantity by positive one. The "Minus" button is going to adjust the quantity by negative one. That's going to get passed into here along with the event, and we are going to find the current quantity and variant ID of the item, apply the adjustment to the current quantity to get a new quantity, and then here we send the post request. The reason why we need to find the quantity and the variant ID is because these are what's required to send the API. Then the response we get back is the whole cart, so we can pause that and then if we are removing an item from the cart, then we're just going to hide it, and then we're going to update those variables. If not, we're going to handle a completely new cart object. It just makes it easier seeming we are getting the whole cart back from the API. All we need to do is pass that data back into this handle cart response and then it'll re-render the whole cart. If I press this, we're re-rendering the whole cart with all the data. As you can see, this amount is updating and this total is updating as well. That's a lot of code and I'm using ES6 a lot here. This is some advanced level stuff. This is definitely not beginner stuff. Definitely, don't worry if you don't fully understand this. This requires quite a bit of JavaScript knowledge and you'll need to know about ES6 syntax as well. For instance, what I've done here with the arrow function, the equivalent in traditional JavaScript is like that. I'm using ES6 just because I think it looks nicer, but maybe it's confusing to you. Again, this is a bit of an advanced levels lesson. The main thing I want you to take away from this is what we learned here with the Ajax API. I want you to understand that if we're creating carts that do not require page reloads in order to update them, then we're using the Ajax API. Remember, anything that stays on the client side and involves programming, gaining access to data from back ends, if we're not reloading the page and making a new server request that way, then we're using Ajax, and the Ajax API and Shopify is how we're able to access that data. That's the main thing I want to get across in this video. This should open you up to new possibilities with Shopify, but you may not be ready just yet in order to fully leverage this. There is a lot of depth to JavaScript and the API. But right here, I think is an example that really sums it up. If you go, again, check out the cart, spend some time looking at it, see if you can figure it out. If not, work on your JavaScript skills. If it's all too, don't worry. You've always got your standard cart page. Actually a lot of Shopify stores, even some really big ones, don't have a fully client-side cart. There was one store I saw, I was actually surprised that they didn't have this when I was doing research for this class. Luxy Hair is a really big Shopify store. If we actually go to a product, here we are. We've got this product here. If I click "Add to Bag", which is the equivalent of add to cart, we get redirected to the cart page, and if I remove an item, the whole page reloads as well. Even on a major Shopify website, they aren't using a fully client-side cart. It's not a huge deal if you're not ready to implement that yet. A lot of themes already have that. In terms of your Shopify theme programming knowledge, it depends on how far you want to go with it. But if you want to code your own client-side cart, or you want to be able to manipulate a current theme with that feature within it, then you'll need to know about this Ajax API and know JavaScript. But it's not essential to create a successful store. You can always use your cart page. You don't have to necessarily have a client-side cart or a side cart that comes out. This lesson, I think was a really big one, but it is quite a big topic. It's not a compulsory topic. I don't think you can create a course on Shopify theme programming without talking about this awesome feature and this API. If you're interested, here's the documentation on the official website. Check out my example code if you want to see my implementation. But that is where I'll leave you on the Shopify Ajax API. In the next lesson, we're going to go back into Shopify liquid and learn some more advanced patents within Shopify. I'll see you on that one.
10. Advanced Liquid Patterns: In this lesson we're going to turn our attention back to Shopify liquid,and we're going to talk about some of the limitations and quirks within the templating language. I'm going to go back to my new theme, going to the code, and I'm going to open up the index template. I'll go over here, click Index. What I'm going to do for this lesson is I'm going to copy and paste examples and then we're going to work through them. What I've done is I've gone through the language and picked out a bunch of limitation quirks and the ways around them. I've got this initial paragraph here. This is just a comment, something for us to read, and then I'm going to bring in the specific examples. What I've written here is that while you can think of liquid as a programming language, it's actually just a templating language. Certain things that should be a given like being able to cycle through a global list of articles or products are simply not possible in Shopify liquid. Very frustrating when you're looking for that consistency and convention. This is Shopify's templating language. They take a lot of liberties and defy convention in multiple areas. Also, the only data types you can create and liquid are primitives and arrays, including arrays of arrays and primitives, and what I mean by primitives are basically just strings and numbers. Strings of course are just bits of text, if you're not familiar with that term. Another thing I should just mention up front, I'm going to be using a lot of programming terminology. I'm going to basically be taking a program is approach to liquid and showing how we can do more of the advanced programming stuff in this templating language, which is a highly limited language. Here's some of the limitations. As I just mentioned, you can't create an object in liquid. You will see that in just a second, you can loop through certain array-like objects. It's very frustrating, but you can't actually loop through all the articles in your Shopify site, and you can't look through all the products in your Shopify site either. The only way you can do that is through the all Collection, which shows all products. There's no way for us to actually look through products ourselves using liquid. Very weird. But maybe they have a reason behind it. You also can't create your own functions. This is something you would do in any programming language, but you can't create functions in liquid. There is a workaround for this. Say for instance, if you wanted to use a function in order to reuse code, and you had some code that just took an input variable and did the same thing every time, you can still achieve something like a function by using a snippet, and with snippets, you can actually pass parameters in, and that's one way you could mimic certain functions that you would find in other programming languages. The final thing that I have noted here is you can create a boolean which is a true or false value. But you can't assign the result of a comparison to a variable and then cool that boolean. You'll see what I mean in just a second. Let's talk about the first example, which is string concatenation. I'm going to copy and paste in a comment here for string concatenation and a heading, so we can see it in our front end. What I've done here is I've made two variables. One is my first_ name and the other is my last_ name. Now maybe I wanted to create a new variable with my full name. In JavaScript or other programming languages, you could do this all in one line. If I open up my console, clear it, create a firstName, create a lastName,and then in order to create the fullName, I could just use what's called string concatenation. I can add strings to each other like this. I would use the variable instead of the explicit Christopher. FirstName plus a space in-between plus the lastName, and now when I call for a fullName, I've got the firstName plus a space plus the lastName. I guess I can just use plus and minuses to add together strings. In Shopify, it doesn't work like that. Let's have a look at how we would do that. The way we do that in Shopify is through the capture tag. What capture does is it will capture basically everything inside the capture tags. We can run a loop inside here. We can do all sorts of things. All I'm going to do is a very simple example. I'm going to output the first_name, then a space, then output last_name. Now we've created a variable called fullName. What I can just do is output that variable, full_Name, and just so we know where it's coming up on the front end, I'm going to put full_name in front of it as well. Now, let's open up our preview in a new tab and we'll see I've got a heading, String Concatenation, Full Name, Christopher Dodd. Unfortunately, I've got my footer here as well, which makes it look ugly. Let me just remove that from the footer briefly because this will be the last lesson we do on liquid. If I go back to here, we don't have that footer text anymore. Now you can see the results of fullName has come out. Now this is a very basic example, but you can imagine what you could do here. You could put all sorts of operations in here. You can create a full loop and we'll actually see in a later example in this video how we're putting a full loop inside a capture in order to make an array. Let's look at the next example. For the next example, I'm going to copy and paste the code directly in because there's quite a bit here and I don't want to rewrite it. Basically, this example is on sub-strings. Sub-strings, like the name suggests, a part of a string. Say for instance, we wanted to grab the actual video ID part of a YouTube video URL. In other programming languages like JavaScript, we could use a function called substring, and we could select where we want the substring to start and end, and then we could assign that to a new variable. Well, it's a bit different in Shopify liquid because there's no substring function or method within Shopify liquid. What we need to do is actually create an array from the string, and then we're going to find the part that we're looking for by taking one of the items of the array. We've got this YouTube video URL stored in this variable, and first of all, we're going to check if it contains youtube.com slash watch. This is an optional step. It's not necessarily relevant to the example, but this is what you'd want to do. You'd want to check if it actually does have this in the URL, and then if it does, what we're going to do is we're going to split the string around the v equals and then we have access to what's on either side of it. Now this is where it gets confusing because we have to do this in multiple steps, and it makes it hard to label your variables correctly. This example, we've got video_id here, and then we're reassigning it to something completely different down here. Here video_id doesn't necessarily make sense as a variable name. But what we're doing here is just creating an array in order to access our video id. If I can talk through it a little bit, what we're doing is we're creating a variable where we're taking the URL and we're going to split it by v equals. If we remember what split does, it creates an array. Now we've got this video_id array and it's got two items. It's got everything before the v equals, and after the v equals. We're going put in an extra check here. Again, it is not compulsory, but if you have a second argument in your YouTube URL, you're going to want to check for that. If that's the case, we're going to split again because we don't want the part after the end. Say for instance, I went over here and maybe I put in a time, I think the code is t in YouTube, t or s, I think let me just save that because we're filtering here and taking out the part after the end, we should be fine anyway. Now what I'm doing is taking that array up here, finding the second value in that array, which will be the part after v equals, and then I'm going to split it again by this end. I'm going to split it again, and on the same line, I'm going to take the first item in the resulting array. I've got this string which we're going to turn into an array. Then we're splitting it up with this as the first item of the array, and then this as the second item of the array. Then what we have to do is do the exact same thing on this section. This is going to be the first item of the array,and this on the other side of the end, which is this split character, is what's going to be the second item in the array. Then we just call first, to get the first item in the array, we don't care about the second. What happens is we get our final video_id and then we can insert that directly into an Embed link. Let's check if that works. We're going to go over here and refresh the page. Now we can see that we have my video link here. What we just did was we converted this YouTube URL into a YouTube embed URL, which takes the same id from here. Now I know this is a lot of lines, and as I said, the variable names are confusing because we have to take it multiple steps. You might want to name this something else. Maybe you want to call this a video URL_parts and then reference it as video_ parts here. Let's just do that for an example to make it easier. We've got video parts and then call it video_parts here. Save that it should still work, and turns out it does. That's just a tip if you want to make it more readable for yourself and it does sound confusing, you can label the variable something else, but a lot of times you're going to see it like this way. You just recycled a variable name. The next example is probably the most complicated of the examples I'm going to talk about in this advanced liquid lesson, and that's creating arrays of objects. I put objects in double quotation marks here because as we mentioned before, we can't create objects and liquid and we can't create our own arrays of objects as we saw before. The only way we can create an array is by taking a string and splitting it based on some delimiting value. Then we have an item for each of the parts of the string that are between those splitting values. So that means that we can't actually create arrays of objects. So as I wrote here, Shopify liquid does not allow for making objects and neither can you create arrays of objects. You can, however, make arrays of strings and numbers, as well as arrays of arrays using Capture and split. So how do I want to explain this, for those of you who maybe don't fully get what I'm saying here is show you an example in JavaScript first. So in JavaScript, I could create two objects. Let's create two person objects I'm going to have person1, which is going to have a first name and last name of Christopher Dodd. Then I came up with a random person name for person2, which is going to be Michael Jordan. I don't know why I chose Michael Jordan. His name just came to me not making any comparisons there at all. So then what I could do is create a person array. I could store both of those objects in this array. The way you create an array in JavaScript, open up a square bracket, put in your first object, putting your second object or value. Then now if I output person array, you can see I've got this list of objects. What this allows me to do, like we've done with looping through products in a collection, is I can loop through this array and grab the first name of every person, for instance. Now unfortunately, we can't do that ourselves in Shopify liquid. The equivalent of what I just did if it existed in Shopify liquid, would be to create an array called, let's just call it collections I don't think we're using that already. I could just can't use square brackets in liquid, but it'd be nice if you could create something like this collection, collection2 and then we end it like that. So now we've created this array of collections. So if I save that, we're going to get a liquid error up here. Liquid syntax error expected end of string but found comma in collection, collection2. So it's telling us we can't do it and indeed, if we try and reference the first item in this. So if I tried to do collections, take the first item in the array and say title, if I output that nothing's going to come up on the screen. We've just got the heading for this section. But we don't actually have the title of the first collection because we can't actually do this. So that can be frustrating at times in liquid, there are times where we might want to create our own collections, I guess. But the obvious way around it is to actually create your collection in Shopify and then you can loop through it like normal. In Shopify, you can't create objects in liquid, but you can of course, create collections in your store and that is an object with an array of products in there. There are some workarounds to this. I'm just going to copy and paste in some more code to go through if you guys now. This first example is a bit tricky, but once you get your head around it, it should make sense. What we're going to do is we're going to use that capture tag before to create a list of products. How we're going to limit each of these different attributes? Is we're going to use a pipe symbol, and then at the end of that product we're going to put in a double colon. Let's walk through what's going on here. So we are capturing the result of this into a variable. So what we're going to do is loop through a array of products in a collection and then we're going to grab the pots that we want to have access to. So we've got product title. Then we put in a character for us to split that with the next value, which is product URL, split again and split again using these values that we've pulled off the product object. Then this one puts in a delimiter to end the product as long as it's not the last one. Because we don't want to confuse our split filter here to think that there is another item after that. So if it's the last one, that's it. No more splitting required. At the end of this, what we're going to have is a string with all of this information split up by pipes, and at the end of the product, these two columns. I think it's going to make the most sense if I just outputted on the page. So if I just output products, list, save, and we'll look at the results in our preview. So if we look down, we've got the title, then we've got a pipe to separate it from the URL of that product and we've got another pipe to separate it from the description of that product. Then we've got another pipe to separate it from the image URL, and then we can see here we've got the two colons to separate it from the next product, and then we've got the same thing again. So this is not too useful because this is all just one string, but because we've got those characters in there to indicate when to split, we can now use the split filter to actually make this into an array. So now I'm going to create a product's array from that products list and splitting it by this delimiter. So now I'm going to have just this part. I'm going to have an array with items that just have this part. But again, I want to split that further once I'm inside it and I want to split by this pipe. So now I'm going to loop through all of the products and the products array and then create another array calledproduct_vals and we're going to split by this now. Now, I can reference the values inside this array by their position. So unfortunately, course we're not creating an object here. I can't actually say, give me the product title. So it's not very readable code but again, it's a workaround. So I can actually use this to find the first value and if I know the first value is always going to be product title, then this will give me the product title. This is going to give me the third value. So if I look at this one and then I go over here to number three, it's going to give me the product description. So if I save that, I think the code was running before anyway, we refresh the page. You'll see that we have the title and the description of all of these products within that array. So this isn't a very practical example, but it's showing you a way that you can actually do things that you would use an object for, but do it in Shopify liquid where you can't create objects. I'm going to do one more example and then we're going to move on. This example might actually make more sense for you. So this example I took from raisedbyturtles.org, definitely check them out and give them a shout out for me. So what we're doing here is we're creating multiple arrays. The first array is going to describe what this object is and then the second array and arrays after that will have values, attributes basically within that array. So if you can see what I'm doing here or what the author at raised by turtles.org has done. We've created this items array and we splitting by this hash symbol. So we're going to have in our items array two items, item1 and item2. Then in that colors array, we're going to have blue and green. So the way we can link these together is by their position in the array. So as long as we write the first item in our colors array to match up with the first item in our items array, then we can reference them by the same index and that's what we're doing here. So what we're doing here, and ignore these lines here. That's just to reduce white space it does the exact same thing as that. But basically what we're doing here is we're running through every item in the items array, and if it's the first item, we're going to get the color attribute by referencing the index of the loop. So let's just remove this conditional and what we'll get is we'll get an array of items outputting the color that belongs to it. So if I hit save, refresh the page, and I scroll down, we'll get blue and green. We can even come here and if we wanted to add the item name associated with that color, what we could do is because we're already inside the item and the item array, we can just output item and then I'm going to put a break tag to break these up. We should see item one blue item to green. Refresh the page and you'll see item one blue item to green. Now, I feel like I need to say something here and that's if you don't fully understand the practical application of this right now, don't worry. This is advanced liquid stuff. That's why I called it the Advanced liquid lesson. Essentially what I'm trying to do here is once you get deeper into your Shopify liquid programming journey, and start to master the language more. You're going to need to know how to do things at the fringes and so that's what this lesson is about. Using the references that I've shown you already, using your arm practice with Shopify theme programming, and then coming to a point where there's certain stuff I want to do in the programming language. What am I limitations and how do I get around that? So if you're not at that stage yet, don't worry too much, I just thought I'd mention that right now because this is an area where you might be thinking, okay, Chris, why do I need to do this stuff? Well, if you don't need to do it yet, don't worry. But this is stuff once you get real deep into Shopify liquid that you're going to want to be aware of. Okay, as program is, we'd like to think that there's a consistent, conventional way of doing things. But the frustrating thing with Shopify liquid is that it's a templating language developed by Shopify, and there's a lot of quirks and differences in there. It defies convention in a lot of ways. So this lesson is like the antidote to that. So again, this is some advanced stuff. Don't worry too much. If this is not something you can use straight away. But maybe it's something to come back to at a later date. That being said, let's move on to our final examples. The next example is about storing Boolean values. So as I mentioned up above, let me split this up. Call this creating Booleans. As I mentioned up above here. We can create a Boolean, but only by assigning it explicitly true or false. We can actually assign the result of a comparison to a variable. What I mean by that is, again, I'm going to show you an example in JavaScript.
11. Bonus: The Storefront API: All right everyone, welcome to this bonus lesson on the storefront API. Until now, we've been working just with the online store sales channel. If I look in my Shopify store, you can see a list of sales channel and online store is the one that comes pre-installed with your Shopify account. Of course, the way to customize your online store sales channel is through themes. We've been doing everything from within a theme. Well, the storefront API actually allows us to access our store data from anywhere on the web. I thought about how best to explain this and I think probably the best way is for you guys to see it straight away. What I'm going to do is show you an app that I created. I call this app the Shopify customer storefront app. I've hosted on a free app host called Heroku app. In order to use this app, I'm going to have to insert some Store details. I've got the access token that I've created already ready to go and the store domain is right here. If I hit submit, it's going to connect to my store and then suddenly you're seeing a custom storefront that I've built on a completely different address to Shopify. Right here, this app is made with a JavaScript framework called view JS, which I recently learned and it's really cool for making interactive client-side apps. What you can do with this app is you can browse collections within a particular store, in this case my store, the Chris testing shop. You can browse the different pages of content, you can click on a particular item, you can select a variant, you can add the variant to the cart, and this is all done on the client side. As you can see, there's no page refreshes at all because I've made this completely with a JavaScript framework called view JS. You could also use this API to create apps in angular or react, it's a great way for you to use your store data in a completely client-side way. Now if I click checkout here, it goes to the actual checkout of my store, and so it goes back to Shopify, but this whole shopping experience here including looking at blogs, is all on this third-party hosting platform. Each time I click on something and load data, it's coming through via the storefront API. Let's open up my network tab and we can actually see these requests coming through. I'm going to go to my Network tab and click the tab for XHR. Let's refresh my app. You can see we've made three requests here. The storefront API uses something called GraphQL, which is a whole topic in itself. If you haven't been familiar with the GraphQL way of doing APIs, but essentially we've GraphQL, there's a single endpoint rather than multiple endpoints, and you send a query to that endpoint and it gives you back the exact data that you're looking for. If you've used rest APIs before, maybe there's an API endpoint where you request all of, let's say the collections in your store, but in this case I only want the image, I want the title and I want the link to the collection. Well, in a rest API, you might not be able to select only that data, and so what you would do is you would request all of the information about collections. That means that you might have to make multiple API requests or just make requests that are bigger than they need to be. Again, this is a little bit more of an advanced topic, but I just wanted you to get the concept and perhaps maybe you can use the storefront API for your own purposes down the track. Going back to this network tab here, if I click on the first request, if I go into header, you can see the query that I send through to the API and this query right here is a GraphQL query. It basically says that I want the shop object and I want these attributes on the shop object. That's just some GraphQL syntax. Here you can see what we get back from the API. We get the shop data and we get things like currency code, the name of the store, primary domain and the reason why this request exists is because I'm using the name of the store right here. Let's look at the next one. It looks like this one is accessing the collections. As you can see here, this is the GraphQL query. I know it's quite big, if you don't understand GraphQL, don't worry, you're not going to understand this, but the point I'm making is you get something back from the storefront API. It is all the collection data, but no more than what you requested. In my case, what I've done is I've requested each collection and I want to know its handle, it's ID, and I want the first product of every collection and the first image of every product in that collection. The reason why is if the image is null, I want to be able to access the first image of the first product instead, so that's why I've accessed deep into this collection. Then you've got the third request. The third request as you can see here, is accessing the pages with in my store. Where I use this is right down here to provide some links to different pages. I'm using the name of the page and then I'm using the handle to create a unique link to that page as well. If I click on about us, you can see this pulls the data from the about us page. If we click here, we can see another request to get more information which in fact is the same information. If we do some more clicking around, if I click on blog, you can see we make another storefront API request. If I dig in here, you can see we've got a list of articles. Then of course this data is being represented on the page using view JS. So to give you a little bit of a look into the app if you're interested, I've got it right here, the services folder is where I make all my API requests. In my base service, I've got the settings for the storefront API request. Then I create this API call function, which uses a library code axis to actually query the storefront API and I expose that function to the product service and here's all my GraphQL queries. Now again, this is going deep into a lot of different concepts like view JS, which you might not be familiar with, GraphQL, which you might not be familiar with and maybe you don't even have much experience with APIs, so don't get overwhelmed right here. We're not going to spend a lot of time going through this, but what I want to do in this lesson is show you an example of how we can use this data in our theme. This class of course, is about Shopify theme programming and it is possible to use the storefront API in your theme if you so choose. So that's what we're going to focus on in this lesson, but for most people, the storefront API is going to be most useful when you need to access the data of your Shopify store. But you want to be able to do that in a completely custom way, for instance, creating a custom storefront or perhaps a phone app that uses the data of your store. The store for an API is all about accessing data that the customer sees. So none of this has to do with accessing things like adding products, adding customers, creating discounts. That is all through the admin API, which is what you use to build apps that go right here in your apps section. Again, I don't want to talk too much about all of that because that is outside the context of Shopify theme programming, but what I want to do in this lesson is show you an example of how we can actually use the storefront API in a theme on our own store. What we're going to need to do is if I go back to my app and I've sent an option here to disconnect. We can see that I need a sharp domain and I need a store for an access token. As you saw before, I already had a token and I put it inside, but let's go and recreate a token so that you guys can see how you would do this yourselves, so if I go into apps, then I go into manage private apps. You should be familiar with this process if you've configured theme kit before, because as you can see here, we had to create a private app in order to use theme kit. As you can see down here, I've got this storefront API app. I'm going to delete that and recreate it for you guys so we can see how we can create a storefront API app ourselves. Up here there's a button for Create a new private app, I'm going to click that and name this app something appropriate. I'm just going to call it storefront API app. This is basically the interface that will allow you to connect to the storefront API. We're going to put in the emergency developer e-mail. As you can see here, we can set some admin API permissions. We don't need that. What we need is some storefront API permissions. Right here, all we need to do is check this check box and then we can customize what permissions we're going to enable this API. The ones that it's checked already should be good enough but let's just check everything just in case. If we hit "Save", it's going to warn us that anyone who has these credentials can make requests to the API so be careful about who you share this API with. I'm going to click "I understand, create the app". Now you can see that the app is created and if I scroll down, it gives me the storefront access token. I'm going to leave this page open so we can access that token later, and I'm going to open up my online store sales channel in a new tab. What I'm going to do is head back into our new theme and let's edit the index template. We've got all of this code here from our advanced liquid lesson, going to remove that. What I'm going to do instead is put one div that's going to hold our content. Actually I'm going to give it an ID because there's only going to be one and I'm going to open up some script tags. Because we are using an API that can access data from wherever on the Internet, we could do this in any template. It doesn't have to be in the index.liquid template, could be literally anywhere. For this video, for demonstration purposes, it just makes sense to do it in the index.liquid template. What I'm going to do is grab some data using the storefront API and then represent it on the page via jQuery inserting that content into this div. I'm going to copy and paste the API code because it does take some configuration. This is a function that I created earlier, obviously. What it does is it takes a query and then sends that query to the Ajax API. Then with that response, we can actually access the data that comes back. Let's step through this really quickly. We're using the inbuilt fetch function within JavaScript to make a request to the storefront API endpoint, which is just your storefront name/api/graphql.json. If we were making this request off of Shopify, we would of course have to include the store name. If I switch over to my app and I go to the settings in my apiCall here, you see that we've had to set the store name here. But because we're already on the store itself right here, we can just use the relative URL and send a request to /api/graphql.json. Then we open up this object here. We make sure that the method is post and we have to send these headers. We have to make sure the content type is GraphQL, we have to allow control origin and of course, we need our access token. This is what we generated before. If I go back to my private app, remember I wanted to keep this open, I'm going to have to go down here, copy that access token, and replace the access token here with my own. Next we're setting the body of the request to the query which is going to be passed in to here. Then with the response, we are going to encode it with json. We need to do this in order for us to actually read the data. The two things that we're going to need is we're going to need an actual query. Just going to set up a blank query up here. Then we have to actually call the API. I'm going to set them up now, going to API query, and then I'm going to use that promise. I'm going to say response, console, log response. All this is going to do, once we send the query is console log what we get back from the server. In order to create this query, a handy tool is on the storefront API documentation. I believe it's on getting started or the first page of API reference. Just to note, there is a lot of information here if you want to do your own research into the storefront API. This is more of a practical little show and tell of how you can actually use the API. But if you go to this page, the API reference page for the storefront API, you can scroll down and you get this interactive GraphQL Explorer. This helps you to create GraphQL queries. As you can see here, we've got a very basic one which grabs the sharp object and then gets the name from it. If I run that, you can see what we'll get back is something like this. Let's just use this to test whether our API call is set up correctly. In this query, I'm going to send through this GraphQL query. If I hit "Save" on that, and then I preview the theme, we should see nothing come up on the page apart from the header. But if I open up my console, we will see we've got an error, we've got a missing bracket after an argument list. Let's just go back. Maybe there was a mistake somewhere here. Yes, I have forgotten to put an extra bracket there. Let's refresh this page. Now that we've got this console open, we can see that we've got an object that comes back from the storefront API. We can verify this is from the storefront API by going over to our network tab, and you can see here is a response from the API. We can see the query that we sent through and we can see the response. Since we console logged that object, we now have it available in our console as well. We've got our store name, which is something we could easily do within a theme anyway. Let's do something a little bit more involved. What I'm going to do, head back over to here, and I'm going to copy across a GraphQL query that I had in my custom storefront app. If I go over to my project code, I'm just going to grab the API code here for grabbing the first 20 products of the store and I'm going to update our query here. Let's save that and let's see if that works. Going into here, we have got an object coming back with all these products. So if we open all of this up, we can see we have got all the data that we asked for. If we go into the Network tab, everything's still good. We've got what we sent through in our GraphQL query, and we've got the result back. Again, I'm not going to spend a whole lot of time teaching you GraphQL because that is a whole topic in itself. But I just want to show you what we're able to do here. We've got all this data, which is lovely. But we want to actually use this data. What we can do is use jQuery to update our page. Most themes have jQuery already installed. If you're working on an existing theme, definitely check if you already have jQuery because this is the new theme and it's very basic. I'm going to have to actually import jQuery from the CDN. If I just look up jQuery on Google, there should be a link here to the jQuery CDN, and this gives us a link to a minified version of jQuery. I can grab that, and using my knowledge of liquid tags, can put in that as a string and then use the script tag filter to actually create a script tag out of that. What I'm going to do in order to test whether jQuery is working, is use a jQuery function which shouldn't work if jQuery isn't installed, but should work if jQuery is installed. What I'm going to do, this just console log ready when the document is ready. If I hit "Save" on that, I refresh the page, open up the console first rather, and then refresh the page, you'll see we've got ready and then data. We know that we've definitely got jQuery installed now. I'm going to get rid of that ready function. Now what we need to do is handle our response differently. What I'm going to do is put in some curly brackets here, and I'm going to keep the console log response because I'm going to reference it. But what we're going to do is actually loop through the products here and have something come out on the screen. I'm using what's in the console log to figure out how to navigate these objects. We've got a data object, then we've got products, then we've got edges inside of that. Edges is an array. Then we're going to loop through that array, find the node of each of these array items, and then that is the data for each of our products. I'll go back into here, and I'm going to take the response, then I'm going to navigate into data, then I'm going to navigate into products, then edges. I know there's a lot of dots here. Then this is where we start our loop. So I can say for each and I can grab the product, and then what we're going to do for each product is I just want to make sure that we're looking at the right thing. I'm going to actually just console log product.node. Let's have a look if that works. I'll hit "Save', refresh the page over here with the console open. As you can see, we've got the initial console log, which has the entire response that we got back. Then you can see an individual console log for each of the products with their attributes that we got back in that data object. Now we're inside this loop, we can actually translate this data into content on the actual page. What I'm going to do is create a template. I'm going to call this const template, and in this template, I'm going to construct some HTML. Let's say div class, product. Let's break this up into another line so that we have some nice spacing, makes it a bit more readable, and then I'm going to do a heading for each. Using string interpolation, I'm going to navigate into that product node, so product.node, and the attribute I'm looking for is title. I'm going to grab the title of the product, then underneath, what should we show? Maybe the product description, product.node.description, one more thing, maybe the image. There's going to be multiple images for a particular product. Well, the possibility at least for a multiple images for a particular product, so this one is going to be a little bit more complicated, but we'll get there. What I'm going to do is open up an HTML image tag, and in order to get the src, the actual address to the image. What I'm going to have to do is navigate into our product node, and then from within our node, I need to access this images, object, and then inside the edges. I am going to do this little bit step-by-step, so images, edges, and I want the first image of the list of images available in this product. I'm going to select that using it's zero index. Now, we're going to be inside this one, and we want to get the node, and then within node, the transformedSrc, node.transformedSrc. If you're wondering what transformedSrc is, we can actually in our graph QL request, specify what we want the maxWidth and maxHeight of the image to be, like what we did with image URL tags or filters in Liquid. Hopefully, we have navigated our objects correctly, I've missed out one final step here, and that is, I have to actually append the template to this div up here. I'm going to open up a jQuery selector, target that div, and then I'm going to append the template. This is going to be added for every product in the loop to this content div up here, so I'm going to hit ''Save'' on that, refresh the page. Now you'll see we have the data that we got from here in our Storefront API represented on our page. We've got the title, we've got the image, we've got the description, and you can see it, all the first 20 products in our store are coming out. Now, this is all through JavaScript, we're not using any Liquid here, this is all client side. You can maybe see this on a slower connection or maybe if I just refresh the page, you'll see there's a slight delay before everything loads, and then the products, and their names, and images loads. Basically what's happening is, the server side code gets generated first, you get the page back, the page finishes loading, and then shortly after, we get the asynchronous load in JavaScript. Again, it's not entirely clear perhaps why we would use the Storefront API to access this data when we can already access it in Liquid. But this is an example of how you could actually use the Storefront API in your themes. Again, the best use of the Storefront API is if you want to create a fully client-side application. If I just throw in my store for an access token into this app again, this right here is a perfect example of a purely client-side app, and it makes sense that we would use the data using a JSON API, which doesn't make us reload the page every time. You can see here that this is all done in the client side, meaning that we don't ever have to reload the page. I guess that would be a major benefit of using the Storefront API. Again, this is why this is a bonus lesson, and it's a bonus lesson because you're probably not going to use the Storefront API, but I wanted to leave you with a short lesson on this API to show you what's possible. Maybe you actually want to create a custom Storefront, or maybe you actually need to access some data that's available in the API that is not available in Liquid. I actually know of a few examples where the Storefront API gives you data that Liquid does not, so maybe you want to use it for those fringe cases. If you want to learn all about the different objects in the Storefront API, here's where you can do so. Just like we saw in the Shopify Liquid documentation, we can look at the objects available in the Storefront API through this menu here. It did take me a while to figure out how to actually read this correctly, but if we have a look at what we did for today's lesson with products, you can see here that this shows you all of the, what's called connections. This is other resources that you can access from a product as an entry point, and then down here, is all the attributes. For instance, if I wanted to access the product handle, this is how you would do it. The description in HTML, the createdAt date right here, and metafield stored on that product. Finally, right here is what's called a QueryRoute, which is the entry point for queries, this is what we used to access all the products. As you can see from the QueryRoute, we can access articles, blogs, collections, pages, and products as we did. Then once you're inside the product, you can click here to learn about the product connection and you navigate this API documentation as if you were navigating a graph QL response. This mimics what we saw here in the sense that right here we're at the QueryRoute. So we go back to QueryRoute, and in our QueryRoute, we're going into products, so down here, products. If I click on products connection, you'll now see we can do edges or page infur, here we go. Edges. If I go into edges, each edge is going to have a node and cursor if we ask for it. As you can see, each has a node, and then if we click on ''Node'', it gives us a product, and then you can see the connections on that object and the fields available. As you can see, we accessed some of those fields, we accessed description, handle ID, and we accessed connections to the images and tags as well. This is definitely a more advanced a lesson, and it took me a while to figure out how to use the Storefront API myself. It's definitely not something you can learn in a 20 minute lesson, but this is why it's a bonus lesson. It's a bit of an eye-opener to show you another way that you can represent your store data in a custom Storefront, or perhaps in a unique way on your online theme. There is, of course, one more API which I mentioned before, which is the Admin API, and if you want to go into Shopify App Development, this is the API that you're going to need to learn. I have actually created a Shopify App myself using this API, it was a pretty cool experience, but definitely not something I could cover in a 20 minute video ever. That's perhaps a topic for another class. But that's pretty much it guys, that should cover a pretty good overview of everything to do with Shopify Theme Programming. If you've made it this far, I want to thank you and congratulate you on sticking with it. There is a lot to Shopify Theme Programming, and if you want to learn more about it, the blog post is out on my website, christhefreelancer.com/Shopify-Liquid-guide/. It's over 10,000 words on Shopify, so if you're feeling bored or adventurous and want to have a long read about everything, Shopify Liquid, obviously we can't cover 10,000 words of content in a single skill share class, but this is where I would go to learn more about the different pots. If you have any questions, as always, leave them in discussion box below. Thanks a lot guys, and I'll see you in the next one.
12. Conclusion: So that pretty much concludes this class on Shopify Theme programming. For your class project, I want you to create your own template section, snippet, or whole theme if you're feeling adventurous. As we've seen in this class, combining liquid code and JSON Schema allows us to create our own customizable templates and sections. Now it's your chance to create something you wish existed and share it with the class if you so choose. If you would like to learn more about Shopify theme development and theme programming, follow me online and check out my YouTube channel for additional tutorials. Finally, if you need any tips or guidance on what we've covered in today's class, be sure to leave a comment in the discussion box below and I'll do my best to point you in the right direction. Thanks as always for watching and I hope to see you again on some of my other classes.