
Proposer un programme d’affiliation est l’un des canaux de marketing les plus efficaces pour développer votre activité SaaS (Software as a Service), en particulier dans les premiers temps.
L’idée est simple : vos utilisateurs existants (ou affiliés) recommandent votre produit à leur public au moyen d’un lien unique et, en retour, ils perçoivent une petite commission pour chaque nouveau client payant qu’ils amènent.
Avantages :
- Taux de conversion élevé (les gens achètent à des personnes qu’ils connaissent, qu’ils apprécient et en qui ils ont confiance)
- Vous dépensez de l’argent UNIQUEMENT lorsque vous en gagnez (contrairement aux publicités payantes, aux influenceurs et au référencement).
Les commissions varient, mais pour les logiciels libres, elles sont généralement récurrentes et représentent environ 30 % du montant payé par le client recommandé.
De nombreux fournisseurs tiers, tels que Rewardful, Tolt, FirstPromoter, PartnerStack et Dub Partners, vous permettent de lancer votre programme d’affiliation instantanément, mais si vous souhaitez créer un programme personnalisé en interne, poursuivez votre lecture.
Pourquoi créer un programme d’affiliation en interne ?
Si les solutions sans code sont excellentes, elles s’accompagnent souvent de frais et de nombreuses limitations.
L’un des principaux facteurs qui nous a amenés à créer notre programme d’affiliation à partir de zéro était l’incapacité d’adapter des solutions tierces à nos besoins.
Avantages pour la création d’un programme d’affiliation
- Pas de frais de tiers, donc des taux de commission plus élevés
- Hautement personnalisable, y compris un programme de récompenses pour les employés
Cons
- Construire l’infrastructure
- Gestion des paiements aux affiliés
Les inconvénients ne sont pas aussi graves qu’ils en ont l’air, alors plongeons dans le vif du sujet.
Créer des liens d’affiliation
Personnellement, je n’aime pas les liens d’affiliation qui ont l’air très génériques et/ou qui appartiennent à un (sous-)domaine différent du vôtre.
Au lieu de cela, je voulais que nos liens d’affiliation soient considérés comme faisant partie de notre site web et qu’ils soient personnalisables par l’utilisateur, de la même manière qu’une personne peut choisir son @ handle sur Instagram, X, ou tout autre réseau social.
Les noms d’utilisateur spécifiques que nous utilisons comme itinéraires pour notre site web, tels que /plans ou /blog, sont restreints, mais à part cela, les affiliés peuvent être aussi créatifs qu’ils le souhaitent, et le nom d’utilisateur peut être changé à tout moment.
Quelqu’un a choisi le nom d’utilisateur freetrial -> publer .com/freetrial
Notre objectif est de convertir nos clients existants en ambassadeurs de la marque, plutôt que de proposer un énième programme d’affiliation ; c’est pourquoi nous avons rendu obligatoire l’ouverture d’un compte sur Publer.

Nous sommes allés plus loin et approuvons désormais manuellement l’accès aux affiliés pour les utilisateurs du plan gratuit.
Liens d’affiliation multiples
Le partage de la page d’accueil du produit fonctionne généralement bien. Cependant, si vous avez une communauté de niche, il peut être plus efficace de partager une page d’atterrissage ou un article spécifique qui cible directement les points de douleur de votre communauté.
Bien que nous utilisions différentes technologies, telles que Framer, Vercel et WordPress, nous avons investi une somme importante pour permettre à chaque lien de notre site web d’être un lien d’affiliation.
Les affiliés peuvent partager n’importe quel lien de notre site web en tant que lien d’affiliation en ajoutant simplement /USERNAME à la fin de l’URL.
Voici le code WordPress 404.php qui attrape les liens de blog avec /USERNAME à la fin, vérifie que l’USERNAME est valide à travers une requête cURL, et redirige le visiteur vers le lien original en passant le paramètre ?referral=ID dans l’URL.
<?php
$url = rtrim(strtok($_SERVER["REQUEST_URI"], '?'), '/');
$LINK_WITHOUT_AMBASSADOR = "https://publer.com/blog" . substr($url, 0, strrpos($url, '/'));
// Don't honor clicks from ads
if (!$_GET['gclid'] && !$_GET['gad_source'] && !$_GET['via']) {
preg_match("/[^\/]+$/", $url, $matches);
$AMBASSADOR = $matches[0];
$referrer = isset($_GET['referrer']) ? $_GET['referrer'] : $_SERVER['HTTP_REFERER'];
// The data to send to the API
$postData = array(
'username' => $AMBASSADOR,
'link' => 'https://publer.com/blog' . $LINK_WITHOUT_AMBASSADOR,
'referrer' => $referrer
);
// Setup cURL
$ch = curl_init('https://app.publer.com/ambassador');
curl_setopt_array($ch, array(
CURLOPT_POST => TRUE,
CURLOPT_RETURNTRANSFER => TRUE,
CURLOPT_HTTPHEADER => array('Content-Type: application/json'),
CURLOPT_POSTFIELDS => json_encode($postData)
));
$response = curl_exec($ch);
if ($response) {
$data = json_decode($response, TRUE);
$ambassador_id = $data['id'];
header("Location: $LINK_WITHOUT_AMBASSADOR/?referral=$ambassador_id");
exit();
} else {
header("Location: $LINK_WITHOUT_AMBASSADOR/");
exit();
}
} else {
header("Location: $LINK_WITHOUT_AMBASSADOR/");
exit();
}
get_header();
?>
<div>
<h3>Oops! That page can’t be found.</h3>
<p>Try searching or go to the <a href="/blog">homepage</a></p>
</div>
Dans header.php, l’ID de référence, s’il existe, est stocké dans un cookie, qui est ensuite utilisé à des fins de suivi.
<?php
// Don't honor clicks from ads
if ($_GET['referral'] && !$_GET['gclid'] && !$_GET['gad_source'] && !$_GET['via']) {
$expiration = 30 * 24 * 60 * 60; // 30 days
echo "<script>document.cookie = 'referral=" . $_GET['referral'] . ";path=/;domain=.publer.com;max-age=$expiration;samesite=none;secure=true';</script>";
echo "<script>window.history.replaceState({}, document.title, window.location.href.split('?')[0]);</script>";
}
?>
Les solutions pour les routes Vercel et Framer diffèrent légèrement et/ou sont plus complexes, mais la logique sous-jacente reste la même. N’hésitez pas à m’envoyer un ping si vous souhaitez obtenir des extraits de code pour ces solutions.
Suivi des liens d’affiliation
La manière la plus simple de suivre les références est d’utiliser des cookies temporels, qui sont généralement valables pendant 30 ou 60 jours.
Les cookies sont de petits fichiers texte que les sites web envoient à votre navigateur pour stocker des informations sur votre visite.
Nous stockons le cookie de référence au niveau du domaine afin que le sous-domaine de l’application puisse y accéder.
Chaque fois qu’une personne s’inscrit sur notre plateforme, nous exécutons cette méthode d’aide Ruby pour vérifier si elle provient d’un lien d’affiliation, c’est-à-dire si le cookie de référence existe.
def check_referral(user)
referral = cookies[:referral]
return if referral.blank?
# Mark referred user as such and offer a sign up commission
Ambassador::CommissionsService.new(user, referral).registration_commission
cookies.delete(:referral)
end
Suivi des installations d’applications mobiles
Les cookies sont parfaits pour le suivi sur les plateformes web, mais les choses se compliquent si vous proposez une application mobile.
Il n’est pas possible de transmettre des paramètres de suivi personnalisés à Google Play ou à l’Apple App Store, c’est pourquoi nous avons opté pour cette solution de contournement :
- Avant de rediriger les visiteurs vers Google Play ou Apple App Store depuis notre site web
- Nous copions dans le presse-papiers le cookie de référence (s’il existe).
- Et utiliser l’identifiant copié lorsque le visiteur installe l’application et s’inscrit.
Bien que cette solution soit satisfaisante sur le papier, elle n’est pas à toute épreuve. Le visiteur peut copier quelque chose d’autre avant de s’inscrire via notre application mobile, ou le système d’exploitation peut ne pas autoriser la copie dans le presse-papiers sans permission.
Renvois manquants
Il est normal que quelqu’un clique sur un lien d’affiliation depuis son téléphone, mais décide d’en savoir plus et de s’inscrire sur le web.
Les cookies ne sont pas inter-appareils, ni inter-navigateurs.
Afin d’éviter des tickets de support client inutiles et des modifications manuelles de la base de données, nous permettons aux utilisateurs de spécifier volontairement si quelqu’un les a référés à Publer.
Mesures suivies
Bien que nous n’ayons pas mis l’accent sur les données chiffrées, nous suivons les indicateurs essentiels suivants :
- Nombre de clics quotidiens et totaux
- Nombre d’inscriptions quotidiennes et totales
- Nombre de mises à niveau quotidiennes
- Liens (affiliés) les plus cliqués
- Principaux sites de référence
Le tableau de bord des affiliés a été construit en 2016 en utilisant jQuery, Chartist, Bootstrap et DataTables. Rien d’extraordinaire, mais il fait toujours l’affaire 10 ans plus tard, sans aucune maintenance.
Commissions et paiements
Pour chaque paiement effectué par un client recommandé, l’affilié a droit à une commission d’environ 30 %.
Pour une personne payant 10 $/mois, l’affilié gagnerait 3 $/mois.
RATE = 0.3 # 30% commission
def payment_commission(payment, next_bill_date)
monthly_price = payment.unit_price.to_f
commission = (monthly_price * RATE).round(2)
Ambassador::Commission.create(created_at: Time.current, commission: commission, user: @user, ambassador: @ambassador, payment: payment)
Notification.create(reason: 'commission_pending', user_id: @ambassador.user.id.to_s)
end
Les commissions acquises sont généralement mises en attente pendant 30 jours afin de répondre aux éventuelles demandes de remboursement.
Il s’agit d’une tâche quotidienne qui marque automatiquement les commissions comme « approuvées » ou « refusées » en fonction de l’état du paiement, et une fois que 30 jours se sont écoulés.
scheduler.cron '7 18 * * *' do # Every day at 18:07 UTC
Ambassador::CommissionsTask.new.execute
end
module Ambassador
class CommissionsTask
def execute
pipeline = [
{ '$match': { state: 'pending', created_at: { '$lte': 30.days.ago.beginning_of_day } } },
{ '$project': { _id: 1 } }
]
ids = Ambassador::Commission.collection.aggregate(pipeline).map { |oid| oid.as_json['_id']['$oid'] }
ids.each_slice(BATCH_SIZE) do |bulk|
# Mark as 'approved' or 'declined' depending on the payment status
Ambassador::CommissionsWorker.perform_async(bulk)
end
end
end
end
Les commissions approuvées sont ensuite regroupées et payées lorsque la somme atteint un seuil spécifique, généralement 20 ou 50 dollars.
Suivi des commissions
Les affiliés peuvent voir en temps réel toutes les commissions gagnées et tous les clients payants qu’ils ont apportés, ainsi que certains détails concernant leur plan.

Rémunérer les affiliés
C’est probablement le plus grand inconvénient lorsqu’il s’agit de gérer un programme d’affiliation interne :
- Vous devez déterminer comment payer les affiliés (PayPal, Stripe, etc.).
- Votre entreprise doit être enregistrée dans un pays supporté par PayPal ou Stripe.
- Vous devez vous occuper des formulaires fiscaux, des retenues à la source, de la comptabilité et des déclarations.
Cependant, en utilisant des services en ligne tels que FirstBase et Online Taxman, il est très facile de constituer une société aux États-Unis et de conserver son statut juridique.
👉 Comment constituer une société et ouvrir un compte bancaire aux États-Unis ?
Les paiements peuvent être entièrement automatisés sur une base mensuelle ou bihebdomadaire.
scheduler.cron '7 13 1 * *' # First day of the month at 13:07 UTC
Ambassador::PayoutsTask.new.execute
end
Paiements PayPal
PayPal est la méthode la plus simple, car l’affilié n’a qu’à fournir son adresse électronique PayPal.
module Ambassador
class PaypalPayoutsWorker
include Sidekiq::Worker
def perform(params)
commission_ids = []
payout_items = params.map do |item|
ambassador = Ambassador::Detail.find(item['ambassador'])
receiver = ambassador.payout_method&.[](:email)
next unless receiver
commission_ids.concat(item['commissions'])
{
recipient_type: 'EMAIL',
amount: {
value: item['total'].round(2),
currency: 'USD'
},
note: <<~NOTE,
Thank you for being an Ambassador of #PublerNation.
Login to your dashboard: <a href='https://app.publer.com/ambassador'>https://app.publer.com/ambassador</a><br>
NOTE
sender_item_id: ambassador.username,
receiver: receiver
}
end
payout_params = {
sender_batch_header: {
sender_batch_id: SecureRandom.hex(8),
email_subject: 'Your payment from the Publer Ambassador program!'
},
items: payout_items.compact
}
payout = PayPal::SDK::REST::DataTypes::Payout.new(payout_params)
Ambassador::Commission.in(id: commission_ids.map { |id| BSON::ObjectId(id) }).update_all(state: 'sending')
payout.create
rescue => ex
Sentry.capture_exception(ex, extra: { params: params })
end
end
end
Le seul inconvénient de PayPal est que vous devez configurer un point de terminaison et écouter les webhooks de PayPal, qui vous informent de la réussite ou de l’échec des paiements.
Stripe Connect
Stripe est une autre excellente alternative pour ceux qui ne peuvent pas ou préfèrent ne pas utiliser PayPal.
Contrairement à PayPal, les affiliés utilisant Stripe doivent suivre quelques étapes d’intégration pour fournir leurs informations personnelles et leurs coordonnées bancaires.
Une fois que l’affilié a terminé son inscription, le paiement des commissions approuvées se fait en une seule étape.
module Ambassador
class StripePayoutsWorker
include Sidekiq::Worker
include AmbassadorHelpers
def perform(payout)
ambassador = Ambassador::Detail.find(payout['ambassador'])
commissions = Ambassador::Commission.where(_id: { '$in': payout['commissions'] })
commissions.update_all(state: 'sending')
params = { currency: 'usd',
amount: (payout['total'] * 100).to_i,
destination: ambassador.payout_method[:id],
description: 'Thank you for being an Ambassador of #PublerNation!' }
transfer = Stripe::Transfer.create(params)
notify_payout(payout['total'], transfer.id, ambassador, :stripe)
rescue => ex
commissions&.update_all(state: 'approved')
Sentry.capture_exception(ex, extra: { payout: payout })
end
end
end
Alors que les paiements PayPal sont envoyés via PayPal, les paiements Stripe sont déposés directement sur le compte bancaire connecté de l’affilié.
Incitation au programme d’affiliation
Si vous pensez qu’il suffit de mettre en place un programme d’affiliation pour que les influenceurs et les clients commencent à promouvoir votre produit, vous allez être déçu.
Vous trouverez ci-dessous quelques-unes des incitations personnalisées que nous avons mises en place pour notre programme d’affiliation.
Taux de commission progressifs
Les taux de commission standard commencent comme suit :
- 0,25 $ pour chaque nouvelle inscription légitime, qu’il s’agisse ou non d’une mise à niveau de leur plan
- 50% de commission sur la première mensualité de chaque nouveau client payant
- 20% de commission sur les paiements récurrents pour les clients qui paient activement
En fonction des ventes réalisées par l’affilié le mois précédent, les taux de commission peuvent augmenter :
- 0 $ – 500 $ → 50 % de commission pour le premier paiement, 20 % pour les paiements récurrents
- 500 $ – 1 000 $ → 60 % et 25 % respectivement
- > 1 000 $ → 70 % et 30 % respectivement
Pour les grands influenceurs, nous proposons des taux de commission fixes, mais plus élevés.
Accès anticipé aux nouvelles fonctionnalités
Ceux qui promeuvent activement Publer, quel que soit leur succès, ont la possibilité de tester les nouvelles fonctionnalités avant tout le monde, de laisser des commentaires et, ainsi, de participer directement au processus de décision.
Fréquence de paiement
Comme pour l’accès anticipé aux nouvelles fonctionnalités, les affiliés les plus assidus sont payés toutes les deux semaines plutôt que tous les mois.
Récompenses
Nous avons alloué un budget mensuel de 175 $ aux trois premiers affiliés (sur la base des revenus mensuels générés par les nouveaux clients payants).
Fenêtre contextuelle de témoignage
Les gens achètent auprès de personnes (ou de marques) qu’ils connaissent, qu’ils apprécient et en qui ils ont confiance. Nous voulions donc que nos affiliés fassent partie intégrante de notre site web – littéralement.
Pro-tip : les popups prennent en charge le markdown, ce qui permet aux affiliés de lier leur entreprise ou leur site web personnel à leur témoignage, pour une meilleure connaissance de la marque.
Partage des réductions
Pourquoi une personne s’inscrirait-elle à un service en utilisant un lien d’affiliation au lieu d’aller directement sur le site web ? Les réductions sont toujours un excellent motif !

Créer une communauté autour du programme d’affiliation
Enfin, vous devez établir des canaux de communication entre vous et vos affiliés.
- Envoi automatique d’e-mails pour partager les rapports et les classements
- Groupe Facebook dédié pour partager les mises à jour et les nouvelles sur les produits
Et c’est toujours une bonne idée de préparer des graphiques, des tutoriels et des articles prêts à l’emploi.
Conseils en matière de référencement
Le fait d’intégrer des liens d’affiliation à votre domaine principal constitue un avantage considérable en termes de référencement, mais cela peut aussi se retourner contre vous.
Indexation
Vous ne voulez pas que des liens d’affiliation apparaissent dans les résultats de recherche de Google lorsque quelqu’un recherche votre produit, n’est-ce pas ?
Vous devez vous assurer que les moteurs de recherche n’indexent pas les liens d’affiliation.
<Header image={image} description={description} title={title} url={url}>
<meta name="robots" content="noindex" />
</Header>
URL canonique
Vous ne devez pas non plus avoir plusieurs liens pour la même page de destination, car cela entraînerait une cannibalisation des mots clés (les liens se battent les uns contre les autres pour obtenir du trafic).
Au contraire, l’URL canonique doit toujours être celle qui n’est pas affiliée.
<link rel="canonical" href="https://publer.com"> ✅
<link rel="canonical" href="https://publer.com/affiliate"> ❌
<link rel="canonical" href="https://publer.com/anotherone"> ❌
<link rel="canonical" href="https://publer.com/random123"> ❌
Nettoyage de l’URL
Une fois que vous avez stocké le cookie d’affiliation dans le navigateur, il est toujours bon d’effacer les paramètres de suivi de l’URL de la barre d’adresse.
removeURLParameter('username');
removeURLParameter('referrer');
const removeURLParameter = useCallback(
(parameter) => {
let params = new URLSearchParams(window.location.search);
params.delete(parameter);
const url = constructURL(params.toString());
window.history.replaceState({}, document.title, url);
},
[constructURL]
);
Sinon, les visiteurs risquent de partager accidentellement le lien d’affiliation et de vous faire payer des frais d’affiliation inutiles, à moins que vous ne proposiez un programme d’affiliation à plusieurs niveaux (une structure de commission dans laquelle un affilié gagne non seulement sur ses ventes directes, mais aussi sur les ventes générées par ses ventes directes).
Empêcher les publicités
Dans presque tous les programmes d’affiliation, le premier terme sur lequel vous devez vous mettre d’accord est le suivant :
En continuant, vous acceptez de ne pas utiliser de publicités payantes pour promouvoir vos liens d’affiliation, notre site web ou nos mots-clés de marque.
En effet, vous ne voulez pas que les affiliés enchérissent pour obtenir du trafic par mot-clé vers votre site web ou votre marque.
Vous ne voulez pas non plus que des publicités d’affiliation aléatoires apparaissent sur Google lorsque quelqu’un recherche votre produit. Vous perdez en enchères sur les mots clés et vous perdez en commissions d’affiliation.
Mais les règles sont faites pour être transgressées, et le seul moyen d’empêcher totalement les affiliés de diffuser des publicités est de ne pas honorer les clics et les commissions provenant de ces publicités.
const router = useRouter();
const { ambassador, referrer, gclid, gad_source, via } = router.query;
const isAffiliateMarketingNetwork = (referrer) => {
return /shareasale\.com|googleadservices\.com|google\.com/.test(referrer || '');
};
useEffect(() => {
// Don't honor clicks from ads
router.push({
pathname: '/',
query:
gclid || gad_source || via || isAffiliateMarketingNetwork(referrer)
? {}
: { username: ambassador, referrer },
});
}, [ambassador, referrer, gclid, gad_source, via, router]);
Transformer le programme d’affiliation en un programme de récompenses pour les employés
Quel que soit le montant des commissions, les meilleurs ambassadeurs d’une marque seront toujours ses employés
Il serait dommage de ne pas offrir des commissions similaires à votre équipe de marketing et d’assistance, surtout si vous disposez déjà de l’infrastructure nécessaire.
Lorsque quelqu’un décide de mettre à jour son plan sur Publer, cette fenêtre apparaît.
L’employé sélectionné, à l’exception de moi, recevra une commission de 10 % sur les paiements pendant une période maximale d’un an, ce qui constitue une excellente incitation à faire un effort supplémentaire.
Tout comme n’importe quel autre affilié, en utilisant le même tableau de bord, les employés peuvent également partager leur lien unique pour attirer de nouveaux clients à partir des médias sociaux et au-delà.
Un prix supplémentaire de 50 dollars est attribué au meilleur employé du mois (sur la base des revenus générés par les nouveaux clients payants).
Retour sur investissement
Bien que ce programme d’affiliation ait 10 ans, son développement initial n’a pris que quelques semaines, avec quelques mises à jour mineures au fil des ans. Il s’agit d’une machine génératrice de revenus entièrement autonome.
À ce jour, nous avons versé à nos affiliés, y compris les employés, plus de 208 000 dollars de commissions.
En retour, nous avons réalisé un bénéfice de 742 000 dollars (à l’exclusion des recettes provenant de ma stratégie de marque personnelle).
Avec un retour sur investissement de 355 %, ce programme d’affiliation surpasse largement tous les autres canaux de commercialisation que nous avons testés jusqu’à présent.
Projets pour l’avenir
Vu le succès de ces quelques lignes de code, j’envisage sérieusement de proposer ce que nous avons construit comme un produit SaaS autonome.
Ce serait un excellent complément à notre mission qui consiste à renforcer votre présence en ligne.
N’hésitez pas à me faire savoir si cela vous intéresse.
Et si vous avez lu jusqu’ici, j’espère que cela en valait la peine.
Merci de votre attention !
Autres mises à jour que vous avez peut-être manquées :