Skip to content
Learni
View all tutorials
Marketing Numérique

How to Create and Optimize YouTube Ads in 2026

Lire en français

Introduction

In 2026, YouTube remains the dominant video platform with over 2.5 billion monthly users, perfect for immersive video ads. YouTube Ads, managed via Google Ads, offer precise targeting by interests, demographics, and behavior, with average CPCs of $0.10-$0.30 for ROIs over 300% in e-commerce and SaaS sectors. This intermediate tutorial guides you step-by-step: from manual setup in the Google Ads interface to automation with the Google Ads API using Python. You'll learn to create video campaigns (In-Stream, Discovery), upload assets, target lookalike audiences, and monitor performance. Why it matters: YouTube ads grab attention in 5 seconds, boosting views and conversions. By the end, you'll have working scripts to scale your campaigns, saving hours of manual work. Ready to turn views into revenue? (128 words)

Prerequisites

  • Active Google Ads account with billing set up.
  • Verified YouTube channel (at least 1 video uploaded).
  • Python 3.10+ installed.
  • Google Ads API access: GCP Console to create a project and service account.
  • Basic knowledge of digital marketing and JSON.

Install Python Dependencies

setup.sh
#!/bin/bash
pip install google-ads==23.0.0 google-auth google-auth-oauthlib google-auth-httplib2
pip install pandas matplotlib
mkdir -p ~/.google-ads
chmod +x setup.sh

This Bash script installs the official Google Ads Python library (version 23.0.0, compatible with 2026) and its dependencies for authentication and data analysis. Run it in a terminal to set up your environment. It creates a config folder and avoids version conflicts—use a virtualenv.

Set Up API Authentication

The Google Ads API requires service account authentication for automated scripts. In the Google Cloud Console, enable the Ads API and generate a JSON key. Download it as google-ads.yaml. Link your Ads account to the service account via Manager permissions. Analogy: It's like giving an API key to a robot to act on your behalf, without risking your main account. Place the file in ~/.google-ads/ for global config.

API Configuration File

google-ads.yaml
developer_token: "ABCD-EFGH-IJKL-MNOP-QRST-UVWX-YZ01-2345"
login_customer_id: "1234567890"
use_proto_plus: true
client_id: "your-client-id.googleusercontent.com"
client_secret: "your-client-secret"
refresh_token: "your-refresh-token"

# Pour service account (recommandé pour prod)
json_key_file: "/path/to/service-account-key.json"
login_customer_id: "1234567890"

This YAML file defines essential credentials: developer_token (from Google Ads > Tools > API), login_customer_id (MCC ID for multi-accounts), and service account for secure automation. Replace placeholders with your real values. Pitfall: Check service account permissions, or API calls fail with 403 Forbidden.

Create a YouTube Video Campaign

create_video_campaign.py
from google.ads.googleads.client import GoogleAdsClient
from google.ads.googleads.errors import GoogleAdsException

client = GoogleAdsClient.load_from_storage(path="~/.google_ads.yaml")
googleads_service = client.get_service("GoogleAdsService")

campaign_service = client.get_service("CampaignService")
operation = client.get_type("CampaignOperation")
campaign = operation.create
campaign.name = "Ma Campagne YouTube 2026"
campaign.status = client.enums.CampaignStatusEnum.PAUSED
campaign.advertising_channel_type = client.enums.AdvertisingChannelTypeEnum.VIDEO
campaign.advertising_channel_sub_type = client.enums.AdvertisingChannelSubTypeEnum.VIDEO_REACH

budget_service = client.get_service("CampaignBudgetService")
budget_operation = client.get_type("CampaignBudgetOperation")
budget = budget_operation.create
budget.name = "Budget Quotidien 50€"
budget.amount_micros = 50_000_000  # 50 EUR

response = budget_service.mutate_campaign_budgets(customer_id="1234567890", operations=[budget_operation])
budget_resource_name = response.results[0].resource_name

campaign.campaign_budget = budget_resource_name

campaign_response = campaign_service.mutate_campaigns(customer_id="1234567890", operations=[operation])
print(f"Nouvelle campagne créée: {campaign_response.results[0].resource_name}")

This Python script creates a YouTube video campaign of type 'Reach' (In-Stream/Discovery) with a 50€ daily budget, initially paused for testing. It uses the official client to mutate budgets and campaigns. Replace customer_id with your Ads ID. Pitfall: Always specify amount_micros (x1,000,000 for EUR) to avoid currency errors.

Add an Ad Group and Targeting

An ad group defines targeting: audiences, keywords, YouTube placements. In the Google Ads interface, select 'Views' as the goal. For the API, link to the video channel. Practical example: Target 25-34 year-olds, 'tech' interests, France, with remarketing on your existing videos. Use lookalike audiences to scale (similar to your converters). Check placements to avoid sensitive content via 'Appropriate content'.

Create Ad Group with Geo Targeting

create_ad_group.py
from google.ads.googleads.client import GoogleAdsClient
client = GoogleAdsClient.load_from_storage()
ad_group_service = client.get_service("AdGroupService")
operation = client.get_type("AdGroupOperation")
ad_group = operation.create
ad_group.name = "Groupe France Tech"
ad_group.campaign = "customers/1234567890/campaigns/1234567891"
ad_group.status = client.enums.AdGroupStatusEnum.ENABLED
ad_group.type = client.enums.AdGroupAdTypeEnum.VIDEO_RESPONSIVE
ad_group.cpc_bid_micros = 20_000_000  # 20 EUR CPC

# Targeting géo France
geo_target_constant_service = client.get_service("GeoTargetConstantService")
location = client.get_type("LocationInfo")
location.geo_target_constant = "21137"  # France
ad_group.targeting_setting = client.get_type("TargetingSetting")
ad_group.targeting_setting.targeting_resources.append(location)

response = ad_group_service.mutate_ad_groups(customer_id="1234567890", operations=[operation])
print(f"Groupe créé: {response.results[0].resource_name}")

This code adds a responsive video ad group with 20€ CPC and France targeting (geo code 21137). It links to the previous campaign. Use VIDEO_BUMPER for short formats. Pitfall: cpc_bid_micros must be realistic, or Google rejects with 'INVALID_ARGUMENT'.

Create a Responsive Video Ad

create_responsive_video_ad.py
from google.ads.googleads.client import GoogleAdsClient
client = GoogleAdsClient.load_from_storage()
ad_group_ad_service = client.get_service("AdGroupAdService")
operation = client.get_type("AdGroupAdOperation")
responsive_search_ad = operation.create
responsive_search_ad.ad_group = "customers/1234567890/adGroups/1234567892"
responsive_search_ad.status = client.enums.AdGroupAdStatusEnum.PAUSED
responsive_video_ad_info = client.get_type("ResponsiveVideoAdInfo")
responsive_video_ad_info.headlines.add(headlines="Titre Impactant !")
responsive_video_ad_info.descriptions.add(descriptions="Découvrez notre produit révolutionnaire.")
responsive_video_ad_info.format_setting = client.enums.VideoFormatEnum.ALL_FORMATS
responsive_video_ad_info.youtube_video_asset = "customers/1234567890/youtubeVideoAssets/VIDEO_ID"  # Remplacez par votre vidéo YouTube ID
responsive_search_ad.responsive_video_ad = responsive_video_ad_info

response = ad_group_ad_service.mutate_ad_group_ads(customer_id="1234567890", operations=[operation])
print(f"Annonce créée: {response.results[0].resource_name}")

This script creates a responsive video ad with headline, description, and link to your YouTube video (ID from the URL). Formats auto-adapt (skippable/non-skippable). Upload the video first via YouTube Studio. Pitfall: Without a valid youtube_video_asset, the API returns 400 Bad Request.

Launch and Monitor the Campaign

Activate the campaign in Google Ads > Campaigns > Status 'Enabled'. Monitor metrics: Views, CTR (target >1%), View-through conversions. Use Google Analytics for UTM tracking. Analogy: Like a pilot adjusting sails in real-time. In the interface, optimize with A/B testing on headlines.

Performance Reporting Script

report_performance.py
from google.ads.googleads.client import GoogleAdsClient
import pandas as pd
client = GoogleAdsClient.load_from_storage()
GAQS = client.get_service("GoogleAdsService")
query = """
SELECT
  campaign.name,
  metrics.impressions,
  metrics.clicks,
  metrics.video_views,
  metrics.cost_micros
FROM campaign
WHERE segments.date DURING LAST_7_DAYS
AND campaign.advertising_channel_type = VIDEO
"""
response = GAQS.search(customer_id="1234567890", query=query)

data = []
for row in response:
    data.append({
        'Campagne': row.campaign.name,
        'Impressions': row.metrics.impressions,
        'Clics': row.metrics.clicks,
        'Vues Vidéo': row.metrics.video_views,
        'Coût (€)': row.metrics.cost_micros / 1_000_000
    })
df = pd.DataFrame(data)
print(df)
df.to_csv('youtube_ads_report.csv', index=False)

This script uses a GAQL query for the last 7 days' performance on video campaigns and exports to CSV with Pandas. Run it daily via cron. Add metrics.ctr for ratios. Pitfall: Limit to LAST_7_DAYS to avoid timeouts on large accounts.

Best Practices

  • Always test paused: Validate assets before activation to avoid waste.
  • Target precisely: Use In-Market + Remarketing audiences (4x ROI).
  • Optimize creatives: 3s hooks, clear CTA, 16:9 formats.
  • Progressive budget: Start at 20-50€/day, scale on data.
  • Track conversions: Integrate Google Tag Manager for view-through.

Common Errors to Avoid

  • Missing developer_token: API returns 401 Unauthorized; generate it once.
  • Too broad targeting: CPM skyrockets without conversions; refine with geo + interests.
  • Unapproved video: YouTube rejects policy-violating content (copyrighted music).
  • Ignoring mobile: 70% YouTube views on mobile; test vertical ads.

Next Steps

Dive deeper with the Google Ads API docs and YouTube Analytics. Automate further with Google Ads Scripts in JS. Check out our Learni digital marketing courses to master advanced Google Ads and AI for ads.