新卒研修を内製化してダミーSSPを作った話

この記事は、[Supershipグループ Advent Calendar 2021](https://qiita.com/advent-calendar/2021/supership)の13日目の記事になります。

今年度の新卒研修で[マーケティングテクノロジー事業](https://supership.jp/business/tech/)に配属予定のエンジニアを対象に、ダミーSSPを作る研修を実施したので、その内容について書いていきたいと思います。
アドテクに関する用語は本記事では詳しく解説しないので、[アドテク用語集](https://qiita.com/poly_soft/items/d743909ff799a58a8d39)等をご参照ください。

# 背景
昨年度までは、エンジニアの新卒研修では[Rails Tutorial](https://railstutorial.jp/)を自習した後、開発演習としてデータベースで管理されているデータに対して、ブラウザを通して各種検索、追加、更新、削除ができるWebアプリケーションを制作する研修を行っていました。

しかし、今年度の新卒はWebアプリケーションを制作した経験があったこと、配属前にアドテクに関する知識を手を動かして身に付けて欲しかったこと、任意の情報を設定できるBid Requestを簡単に自社のDSP（[ScaleOut](https://supership.jp/business/scaleout/)）に投げられるシステムが欲しかったこと等の背景から、ダミーSSPを制作する内製の研修を実施しました。

類似の事例として、CyberAgentさんでは「[ひとりDSP](https://developers.cyberagent.co.jp/blog/archives/7919/)」という研修が行われているそうです。

# ダミーSSPの制作
制作したダミーSSPの概要を説明します。
## RTBの仕組み
Real-Time-Bidding (RTB)とは、広告主と媒体をつなぐプロトコルであり、SSPとDSPとの間で、RTBで取引することによって広告が配信されます。ユーザーがサイトにアクセスすると、媒体はSSPに広告を出すためのリクエスト（Ad Request）を行い、SSPは提携している複数のDSPに広告枠を買うかリクエスト（Bid Request）を行い、DSPはSSPにこの広告枠をいくらで買いたいかの入札額（Bid Response）を返します。その後、SSPはDSPが返した入札額のうち最も高いDSPに落札通知を送り、SSPはAd Requestのレスポンスとして、落札したDSPの配信タグを媒体に埋め込みます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/205607/fc9ca90a-7ef0-6660-b122-ed456927304d.png)
[藪本晃輔. (2018). 稼げるエンジニアになるためのインターネット広告入門. 技術書典5.](https://booth.pm/ja/items/1044288) より

## Bid Requestの内容
多くのSSPは、[OpenRTB](https://iabtechlab.com/standards/openrtb/)に準拠したBid Requestを送ります。例として、[IndexExchange](https://www.indexexchange.com/)のバナー広告のBid Requestを挙げます。Bid Requestには、主にユーザーの端末の情報（User Agent、IPアドレス等）、広告枠のサイズ、掲載先の情報（ドメイン、カテゴリ等）、ユーザーの識別子等が含まれます。

```
{
 "device": {
     "ua": "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2272.101 Safari/537.36",
     "language": "EN",
     "ip": "207.34.112.154",
        "geo": {
            "lat": 40.7141667,
            "lon": -74.0063889,
            "country": "USA",
            "region": "NY",
            "regionfips104": "US36",
            "metro": "803",
            "city": "New York",
            "zip": "10001",
            "type": 2,
            "utcoffset": -300
         }
 },
 "imp": [
   {
     "banner": {
         "w": 728,
         "h": 90,
         "pos": 1,
         "topframe": 0
     },
     "secure":
	 "ext": {
		 "bcrid": ["5C7A9L","5G57H9"]
	 }, 			
     "pmp": {
         "deals": [{
             "bidfloor": 3.50,
             "at": 2,
             "id": "33CBCEYE0214"
         }
				]
     },
     "id": "1",
	 "tagid": "3447033_246891"
   }
 ],
 "bcat": ["IAB7-41", "IAB3-7", "IAB11-4", "IAB8-5", "IAB23", "IAB9-30", "IAB1-7", "IAB14", "IAB12", "IAB14-1", "IAB25-2", "IAB24"],
 "site": {
     "domain": "genericnews.ca",
     "cat": ["IAB12"]
     },
     "id": "3447033",
     "publisher": {
         "name": "News",
	     "id": "54321"
     }
 },
 "user": {
     "buyeruid": "79EB93BF-5BD9-8C24-385D-C3D3BECF5994",
     "id": "vE4OjdHt54QAAEhFcacAAACq"
 },
 "id": "112d66c0-d576-4c57-caf7-bbf94123326d",
 "ext": {
     "sdepth": 6,
     "edepth": 6
     "tz": 360,
 },
 "source": {
      "pchain": "50b1c356f2c5c8fc:2167"
      "ext": {
	  "schain":{
	     "complete":1,
         "ver": "1.0"
	     "nodes":[
		    {
		       "asi": "indexexchange.com",
		       "sid": "54321",
		       "hp": 1,
		       "rid": "A92AF4241C4A8FF6"
	        }  
	      ]
	    }
      }
    }
  }
}
```
https://kb.indexexchange.com/dsps/open-rtb/examples_of_openrtb_requests_and_responses.htm より

このjsonをDSPのエンドポイントにPOSTします。Bidに成功すると、HTTPコード 200が返り、以下のようなBid Responseが得られます。Bid Responseには、入札価格、広告配信タグ等が含まれます。

```
{
 "id":"112d66c0-d576-4c57-caf7-bbf94123326d",
 "seatbid": [{
     "bid": [{
         "id": "93587a2a-d0b3-11e4-9a5c-d5086b3235de",
         "impid": "1",
         "price": 300.0,
         "attr": [3],
         "adomain": ["www.genericcar.ca"],
         "adm": "<script type=\"text/javascript\" src=\"http://p3.location.com/ed/3/?5045740&cid=12622&tid=5045740&oid=A92AF4241C4A8FF6&vid=vE4OjdHt54QAAEhFcacAAACq&p=${AUCTION_PRICE}&bd=k1h6KtCzEeSaXNUIazI13gY9gN1dCbmXnCjTIg&rnd=-5462374893397372747\"></script>"
     }],
     "seat": "339"
 }]
}
```
https://kb.indexexchange.com/dsps/open-rtb/examples_of_openrtb_requests_and_responses.htm より

このjsonの `seatbid[0].bid[0].adm` が広告配信タグで、広告主へのリンクが貼られた画像を表示するimgタグ等が生成されます。これを媒体に埋め込むことによって、広告を表示できます。
DSPを用意できない場合は、Bid Requestの内容が正しければ入札額や広告配信タグ（imgタグ等）をランダムに返すWebサーバーを実装することで代用できます。

## Webアプリケーションの内容
以下の要件を満たすWebアプリケーションを制作することを課題としました。

* OpenRTB準拠のBid RequestをDSP（ScaleOut）に送信できる
* Bid Responseを表示し、Bidに成功した場合、広告を表示できる
* Bid Requestの内容を変更できる
    * 広告のサイズ、UserAgent、国情報などを指定できる
    * 広告の種類（バナー、VAST、インフィード等）を指定できる

インターネット広告業界やアドテクに興味のある皆さん、一度ダミーSSPを制作してみてはいかがでしょうか。

## 受講者の反応
DSP/SSPの仕組みを学べた、実際にScaleOutに触れることで理解が深まった、チーム開発を経験できた、各種要素技術について学べた、等の感想を頂きました。

## 感想
自身が新卒研修を受けていた時、DSPやSSPについて学びましたが、時間が経つとどちらかDSPなのか、Bid Requestを投げているのはどちらなのか曖昧になっていました。業務では主にDSPのダッシュボード部分に携わっているので配信周りはあまり見えないのですが、この業界にいる以上中途半端な理解ではいられないので、この研修を実施することで、自身のアドテクに関する知識も定着させることができました。
座学だけではなく、実際に手を動かすことで、知識はより定着すると思います。

# おわりに
最後に宣伝です。
Supershipではプロダクト開発やサービス開発に関わる人を絶賛募集しております。
ご興味がある方は以下リンクよりご確認ください。
[Supershipグループ 採用サイト](https://supership-hd.jp/recruit/)
是非ともよろしくお願いします。