代码之家  ›  专栏  ›  技术社区  ›  Dave

如何在服务器上验证Admob奖励的视频广告?

  •  0
  • Dave  · 技术社区  · 7 年前

    有没有办法验证客户是否在服务器上观看了奖励视频广告(OnadReveded)?我是否可以与Google云功能进行任何集成?

    我认为可以使用admob admin SDK验证客户端发送到服务器的令牌,但似乎不可能,我们只能验证客户端上的ad。

    0 回复  |  直到 7 年前
        1
  •  5
  •   Dave    7 年前

    现在可以使用 Server-Side Verification (SSV) Callbacks.

    服务器端验证回调是URL请求,由Google扩展查询参数,由Google发送到外部系统,通知其用户与奖励视频广告交互应获得奖励。奖励视频SSV(服务器端验证)回调提供了额外的一层保护,防止欺骗客户端回调以奖励用户。

        2
  •  2
  •   user1300214 user1300214    5 年前

    不确定这是否与Firebase相关,但以下是一些详细信息,以防有人使用Node/JS。可以使用节点的内置 crypto 图书馆第一 fetch 可用的Google AdMob verifier密钥来自 https://gstatic.com/admob/reward/verifier-keys.json 。

    然后需要遍历返回的JSON keys 阵列并抓住 pem 与 req.query.key_id 输入的参数 req.url 一串

    然后,我们希望验证签名的“消息”是传入的 需求。url地址 参数之间的子字符串 ? 符号和 &signature... 字符串。

    现在我们可以轻松验证:

       const verifier = crypto.createVerify("sha256");
       
       verifier.update(message);
       
       if(verifier.verify(pem, req.query.signature, "base64"))
          console.log("Ad was successfully verified.");
       else
          console.log("Ad could not be verified - quick call the cops !");
    
    

    需要注意的一点是,您可能需要 unescape(...) 你的 需求。url地址 字符串,因为某些字符可能已转义。我在这件事上纠结了好一两个小时。您可以使用节点的内置 querystring 图书馆

        3
  •  1
  •   pita    7 年前

    现在不行。根据我最近收集的信息,该功能已经在一段时间内处于封闭测试状态。我能找到的最后一个提及是在链接讨论中,据推测,谷歌的某个人表示,该功能将很快向公众推出。该职位从1月22日开始。

    https://groups.google.com/forum/#!topic/google-admob-ads-sdk/weXTAGZfYQ8

        4
  •  0
  •   Salam Hiyali    7 年前

    如果你们想为Admob SSV在Golang上寻找一种简单的方法。

    就用这个 hiyali/go-lib-ssv ,希望挽救您的生命:)

        5
  •  0
  •   postUp    5 年前

    我知道有点晚了,但这里有一段代码帮助了我。它是针对节点用户的javascript。 https://github.com/hypeben/admob-rewarded-ads-ssv

    const queryString = require('query-string');
    const crypto = require('crypto');
    const axios = require('axios');
    const GOOGLE_AD_KEY_URL = 'https://gstatic.com/admob/reward/verifier-keys.json';
    
    /**
     * Fetches the google public keys for the admob providers.
     * These keys changes time to time.
     */
     const getGoogleKeysMap = async () => {
     let googleKeyRes = await axios.get(GOOGLE_AD_KEY_URL);
     let {keys} = googleKeyRes.data;
     if (!keys) {
     throw new Error('No keys found from google keys');
     }
     /** For each of the keys array save it base 64 in decoded form in the key map */
     let keyMap = {};
     keys.forEach(k => {
     keyMap[`${k.keyId}`] = crypto.createPublicKey(k.pem);
     console.log(keyMap[`${k.keyId}`]);
     });
     return keyMap;
     };
    
    /**
     * Verifies the callback url query params string,
     * Resolves the promise if verification was successful, else fails.
     * Wanna 'debug' then pass the second parameter as true.
      * @param {String} queryUrl
      * @param {Boolean} debug 
     */
    async function verify(queryUrl, debug) {
    
    try {
    
    if (typeof queryUrl !== "string") throw new TypeError("URL needs to be string!");
    
    /**
     * Request coming as callback from admob must contain the 'signature' and the  'user_id'.
     * For more info https://developers.google.com/admob/android/rewarded-video-ssv
     */
    const {signature, key_id} = queryString.parse(queryUrl);
    if (!signature) {
      throw new Error('No signature value exist in the URL param');
    }
    
    if(debug) {
      console.debug('Signature and KeyId ---');
      console.debug(signature, key_id);
    //  console.log('Signature and KeyId ---');
    //  console.log(signature, key_id);
    }
    
    let queryParamsString = queryUrl;
    if (queryParamsString.indexOf('?') > -1) {
      queryParamsString = queryUrl.split('?')[1];
    }
    
    if(debug) {
      console.debug('Query param string ---');
     // console.log('Query param string ---');
      console.debug(queryParamsString);
     // console.log(queryParamsString);
    }
    
    /**
     * As per admob, 
     * The last two query parameters of rewarded video SSV callbacks are always signature and key_id, in that order.
     * The remaining query parameters specify the content to be verified. 
     */
    let contentToVerify = queryParamsString.substring(0, queryParamsString.indexOf('signature') -1);
    
    if(debug) {
      console.debug('Content to verify ---');
     // console.log(contentToVerify);
     // console.log('Content to verify ---');
      console.debug(contentToVerify);
    }
    
    let keyMap = await getGoogleKeysMap();
    
    if(keyMap[`${key_id}`]) {
      let publicKey = keyMap[`${key_id}`];
      const verifier = crypto.createVerify('RSA-SHA256');
      verifier.update(contentToVerify);
      let result = verifier.verify(publicKey, signature, 'base64');
      if (result) {
        console.debug('Result ---');
         console.debug(result);
        return true;
      } else {
        console.debug('Failure ---');
        console.debug(result);
        throw new Error('Invalid Signature Supplied');
      }
    } else {
      console.debug('Key id provided doesn\'t exist ---');
      throw new Error('Key id provided doesn\'t exist in the google public keys');
    }
    
    
      } catch (error) {
    
     }
    
    }
    
    module.exports.verify = verify;
    
    推荐文章