Logo
  1. Docs
  2. Resources

Weaverse Tutorial - Build Your First Hydrogen Store

Published on Aug 15, 2025, updated 4 days ago

Build Your First Weaverse Hydrogen Store

Welcome to the complete Weaverse tutorial! In 45 minutes, you'll build a modern Shopify Hydrogen storefront with visual customization capabilities. By the end, you'll have a live store that you and your team can edit visually through Weaverse Studio.

What You'll Build

  • Modern Shopify storefront with React Router v7 and React 19
  • Visual editing capabilities through Weaverse Studio
  • Custom components with schema-driven configurations
  • Production-ready deployment on Shopify Oxygen

Prerequisites

Before starting, ensure you have:

  • Node.js 20+ (check with node --version)
  • Shopify store (any plan, development store works fine)
  • Basic knowledge of React, TypeScript, and Shopify concepts
  • 30-45 minutes of focused time

New to these technologies? Review these resources first:


Part 1: Quick Start (5 minutes)

Install Weaverse Studio

  1. Go to Shopify App Store: Visit Weaverse on Shopify App Store
  2. Install the app on your Shopify store
  3. Open Weaverse from your Shopify admin dashboard

Create Your First Project

  1. Click "Create Project" in Weaverse Studio
  2. Choose the Pilot theme (recommended starter theme)
  3. Name your project (e.g., "My Store")
  4. Click "Create"

Weaverse Studio Project Creation

🎉 Success! You now have a Weaverse project with the Pilot theme. You can see the visual editor with pre-built sections ready to customize.


Part 2: Local Development Setup (10 minutes)

Set Up Your Development Environment

  1. Clone the Pilot theme:

    git clone https://github.com/weaverse/pilot.git my-weaverse-storecd my-weaverse-store
  2. Install dependencies:

    npm install
  3. Set up environment variables:

    Create a .env file in your project root:

    # Copy from the examplecp .env.example .env

    Update .env with your store details:

    # Required - Get from Weaverse StudioWEAVERSE_PROJECT_ID="your-project-id-from-studio"
    # Required - Your Shopify storePUBLIC_STORE_DOMAIN="your-store.myshopify.com"PUBLIC_STOREFRONT_API_TOKEN="your-storefront-access-token"
    # Required - Generate a random stringSESSION_SECRET="your-random-session-secret"
    # Optional - For customer accountsPUBLIC_CUSTOMER_ACCOUNT_API_CLIENT_ID="your-client-id"PUBLIC_CUSTOMER_ACCOUNT_API_URL="https://your-store.myshopify.com/api/2023-04/graphql"

    Where to find these values:

    • WEAVERSE_PROJECT_ID: Copy from Weaverse Studio project settings
    • PUBLIC_STOREFRONT_API_TOKEN: Create in Shopify Admin → Apps → App and sales channel settings → Develop apps
    • SESSION_SECRET: Generate with openssl rand -base64 32
  4. Start the development server:

    npm run dev

    Your store will be available at: http://localhost:3456

Connect to Weaverse Studio

  1. Open Weaverse Studio in another browser tab
  2. Go to Project Settings → Preview URL
  3. Set Preview URL to http://localhost:3456
  4. Save changes

Weaverse Preview URL Setup

Checkpoint: You should now see your local development server in Weaverse Studio's preview panel. Changes in Studio should appear immediately in your local site.


Part 3: Understanding Weaverse Architecture (5 minutes)

How Weaverse Works

┌─────────────────┐    ┌─────────────────┐    ┌─────────────────┐Weaverse      │───▶│   Your Local    │───▶│   ProductionStudio        │    │   Development   (Oxygen)   (Visual CMS)  │    │   Server        │    │                 │└─────────────────┘    └─────────────────┘    └─────────────────┘

Weaverse Studio: Visual editor where you and your team create content Your Code: React components with schemas that define what's editable Production: Shopify Oxygen hosting your fast, static-generated site

Key Concepts

Components: React components that render sections of your store Schemas: Define what users can edit in Studio (text, images, colors, etc.) Loaders: Fetch data from Shopify (products, collections, etc.) Studio: No-code visual editor for content creators


Part 4: Build Your First Component (15 minutes)

Let's create a customizable Hero Banner that showcases your products.

Create the Component

  1. Create the component file:

    mkdir -p app/sections/hero-bannertouch app/sections/hero-banner/index.tsx
  2. Add the Hero Banner component:

    // app/sections/hero-banner/index.tsximport { Image } from '@shopify/hydrogen';import { createSchema } from '@weaverse/hydrogen';import type { HydrogenComponentProps } from '@weaverse/hydrogen';
    interface HeroBannerProps extends HydrogenComponentProps {  heading: string;  description: string;  buttonText: string;  buttonLink: string;  backgroundImage: {    url: string;    altText: string;    width: number;    height: number;  };}
    function HeroBanner(props: HeroBannerProps) {  const {     heading,     description,     buttonText,     buttonLink,     backgroundImage,    ...rest   } = props;
      return (    <section {...rest} className="relative min-h-[500px] flex items-center justify-center overflow-hidden">      {/* Background Image */}      {backgroundImage && (        <div className="absolute inset-0 z-0">          <Image            data={backgroundImage}            className="w-full h-full object-cover"            sizes="100vw"          />          <div className="absolute inset-0 bg-black/40" />        </div>      )}            {/* Content */}      <div className="relative z-10 text-center text-white max-w-4xl mx-auto px-6">        <h1 className="text-4xl md:text-6xl font-bold mb-6">          {heading}        </h1>        <p className="text-lg md:text-xl mb-8 opacity-90">          {description}        </p>        {buttonText && buttonLink && (          <a            href={buttonLink}            className="inline-block bg-white text-black px-8 py-3 rounded-lg font-semibold hover:bg-gray-100 transition-colors"          >            {buttonText}          </a>        )}      </div>    </section>  );}
    export default HeroBanner;
    export let schema = createSchema({  type: 'hero-banner',  title: 'Hero Banner',  settings: [    {      group: 'Content',      inputs: [        {          type: 'text',          name: 'heading',          label: 'Heading',          defaultValue: 'Welcome to Our Store',        },        {          type: 'textarea',          name: 'description',          label: 'Description',          defaultValue: 'Discover amazing products that will transform your life.',        },        {          type: 'text',          name: 'buttonText',          label: 'Button Text',          defaultValue: 'Shop Now',        },        {          type: 'text',          name: 'buttonLink',          label: 'Button Link',          defaultValue: '/collections/all',        },      ],    },    {      group: 'Design',      inputs: [        {          type: 'image_picker',          name: 'backgroundImage',          label: 'Background Image',        },      ],    },  ],});

Register the Component

  1. Add to components registry:
    // app/weaverse/components.tsimport * as HeroBanner from '~/sections/hero-banner';
    export let components: HydrogenComponent[] = [  // ... existing components  HeroBanner,];

Test Your Component

  1. Go to Weaverse Studio
  2. Click "Add Section"
  3. Select "Hero Banner"
  4. Customize the content using the settings panel
  5. Upload a background image
  6. See changes appear instantly in your local preview

Hero Banner in Weaverse Studio

🎯 Achievement Unlocked: You've created your first Weaverse component with full visual editing capabilities!


Part 5: Advanced Features (10 minutes)

Add Dynamic Product Data

Let's enhance our Hero Banner to feature a specific product.

  1. Create a product loader:

    // Add to app/sections/hero-banner/index.tsx
    import type { ComponentLoaderArgs } from '@weaverse/hydrogen';
    export async function loader(args: ComponentLoaderArgs<HeroBannerProps>) {  const { weaverse } = args;  const { storefront } = weaverse;
      if (!args.data?.productHandle) {    return null;  }
      const { product } = await storefront.query(`    query GetProduct($handle: String!) {      product(handle: $handle) {        id        title        handle        description        featuredImage {          url          altText          width          height        }        priceRange {          minVariantPrice {            amount            currencyCode          }        }      }    }  `, {    variables: { handle: args.data.productHandle }  });
      return { product };}
  2. Update component to use product data:

    interface HeroBannerProps extends HydrogenComponentProps {  // ... existing props  productHandle?: string;  loaderData?: {    product?: any;  };}
    function HeroBanner(props: HeroBannerProps) {  const { loaderData, productHandle, ...rest } = props;  const product = loaderData?.product;
      // Use product data if available  const displayHeading = product?.title || props.heading;  const displayDescription = product?.description || props.description;  const displayImage = product?.featuredImage || props.backgroundImage;
      return (    <section {...rest} className="relative min-h-[500px] flex items-center justify-center overflow-hidden">      {/* ... rest of component */}      <div className="relative z-10 text-center text-white max-w-4xl mx-auto px-6">        <h1 className="text-4xl md:text-6xl font-bold mb-6">          {displayHeading}        </h1>        <p className="text-lg md:text-xl mb-8 opacity-90">          {displayDescription}        </p>        {product && (          <p className="text-2xl font-bold mb-4">            From ${product.priceRange.minVariantPrice.amount}          </p>        )}        {/* ... button code */}      </div>    </section>  );}
  3. Add product selector to schema:

    export let schema = createSchema({  type: 'hero-banner',  title: 'Hero Banner',  settings: [    {      group: 'Content',      inputs: [        // ... existing inputs        {          type: 'product_picker',          name: 'productHandle',          label: 'Featured Product',        },      ],    },    // ... rest of schema  ],});

Performance Optimization

  1. Add caching to your loader:
    export async function loader(args: ComponentLoaderArgs<HeroBannerProps>) {  const { weaverse } = args;  const { storefront } = weaverse;
      if (!args.data?.productHandle) {    return null;  }
      const { product } = await storefront.query(    PRODUCT_QUERY,    {      variables: { handle: args.data.productHandle },      cache: storefront.CacheLong(), // Cache for 1 hour    }  );
      return { product };}

Pro Tips:

  • Always cache Shopify API calls for better performance
  • Use TypeScript for better development experience
  • Test components with different data states (empty, loading, error)

Part 6: Deployment (5 minutes)

Deploy to Shopify Oxygen

  1. Build your project:

    npm run build
  2. Deploy using Shopify CLI:

    npx shopify hydrogen deploy
  3. Follow the prompts to connect your Shopify store

  4. Update Weaverse Studio:

    • Go to Project Settings
    • Update Preview URL to your Oxygen deployment URL
    • Save changes

Production Checklist

Before going live, ensure:

  • Environment variables are set correctly
  • Images are optimized and loading properly
  • All sections work as expected
  • Mobile responsive design looks good
  • Performance scores are above 90 (check with Lighthouse)
  • SEO metadata is configured

Go Live

  1. Set your Oxygen deployment as your primary domain in Shopify admin
  2. Test thoroughly on the live site
  3. Train your team on using Weaverse Studio

🚀 Congratulations! Your Weaverse Hydrogen store is now live and ready for visual editing.


Next Steps

Expand Your Store

Add More Components:

  • Product grids with filtering
  • Customer testimonials
  • Newsletter signup forms
  • Collection showcases

Advanced Features:

  • Multi-language support
  • B2B customer groups
  • Advanced search and filtering
  • Custom checkout experiences

Performance Optimization:

  • Image optimization strategies
  • Caching best practices
  • Core Web Vitals improvements

Learning Resources

Common Issues

Component Not Showing in Studio?

  • Check component is exported correctly
  • Verify schema syntax
  • Ensure component is registered in components.ts

Preview Not Updating?

  • Check development server is running
  • Verify Preview URL in Studio settings
  • Clear browser cache

Deployment Issues?

  • Ensure all environment variables are set
  • Check build logs for errors
  • Verify Shopify app permissions

What You've Accomplished

In just 45 minutes, you've:

Built a modern Shopify storefront with React Router v7
Created custom components with visual editing capabilities
Connected Shopify data dynamically to your components
Deployed to production on Shopify Oxygen
Set up a workflow for continuous development and content updates

Your store is now ready for your team to manage visually through Weaverse Studio, while you focus on building amazing shopping experiences.

Ready to build something amazing? Join our Slack community and show us what you create!