ホームページ  >  記事  >  ウェブフロントエンド  >  埋設ポイントシステムの予備調査

埋設ポイントシステムの予備調査

coldplay.xixi
coldplay.xixi転載
2020-09-15 16:24:552542ブラウズ

埋設ポイントシステムの予備調査

関連する学習に関する推奨事項: JavaScript ビデオ チュートリアル

序文

雑多 最近、前シリーズの埋め合わせに時間をかけることは少なく、ポイントを貯めているシリーズも本格的に動き始めています

ポイント制度が必要な理由

映画

フロントエンド開発攻囲戦のShi Kaiは楽しそうにコードを書いており、ビジネスとUIを別々に開発していることに非常に誇りを持っています。さまざまなデザインパターンとアルゴリズムの最適化が順番に実装されています。コードは完璧です(世界最高の労働コード)、バグはなく、プログラムは完璧で、互換性はNo.1です。コードは高品質で入力およびレジストできます。仕事を終えて帰宅して赤ちゃんの世話をした後も簡単に打刻できます。

実際には

実際には、開発環境と本番環境は同じではなく、テストプロセスがどれほど完璧であっても、テスト漏れは依然として存在します。ユーザーのクライアント環境、ネットワーク環境など、一連の不確定要素の存在を考慮します。 したがって、開発プロセスでは 3 つの主要な原則を覚えておく必要があります (

私のナンセンス

)

    完璧なコードなど存在せず、存在するのは未発見のバグだけです
  1. #テスト環境を決して信頼しないでください
  2. 、すべてのオンライン状況をカバーできるテスト環境はありません
  3. オンラインでフィードバックがない場合は、疑わないでください。問題は次のとおりです。非常に深く、非常に深く隠されています
  4. 埋め込みポイント システムとは
埋め込みポイントは街にあるカメラのようなもので、製品の観点から見ると、製品内でのユーザーの動きを監視できます。その中の行動の軌跡は、製品の反復とプロジェクトの安定性の基礎を提供します。

誰が、いつ、どこで、どのように、何を行うかがデータ収集の基本的な側面です

フロントエンド開発の場合、ページ リソースの読み込みパフォーマンス、例外などを監視し、ページ エクスペリエンスと健全性インデックスを提供し、その後のパフォーマンス最適化の基礎を提供し、例外と発生シナリオをタイムリーにレポートできます。 。これにより、問題をタイムリーに修正し、プロジェクトの品質を向上させることができます。

埋められたポイントは、大きく 3 つのカテゴリに分類できます。

痕跡のない埋められたポイント
    - ページの入口と出口を含む、ページ上のすべての情報が無差別に収集されます。イベントのクリックなど。有用な情報を取得するにはデータのフラッシュが必要です。
  1. 視覚的な埋め込みポイント
  2. - 生成されたページ構造に基づいて特定のポイントを取得し、ポイントを個別に分析します
  3. 業務コード手動埋め込み
  4. - 特定の複雑なビジネスに応じて、カバーできない上記 2 つの領域を削除し、業務コードを埋め込みます
視覚的な埋め込みポイントトレースレス埋め込みポイント典型的なシナリオビジネス データが必要な場合など、目に見えない埋もれたポイントはカバーできませんシンプルで標準化されたページ シナリオシンプルで標準化されたページ シナリオ,利点 明確なビジネスデータ低開発コスト、オペレータは関連する埋め込みポイントを直接設定可能設定不要、データを追跡可能不十分ですデータを遡ることができず、開発コストが高額ですビジネスデータと関連付けることができず、データを遡ることができませんデータ量が多く、業務データの関連付けができない
コード埋め込みポイント
#

ほとんどの場合、痕跡のない埋設点を通じてすべての情報データを収集し、視覚的な埋設点と連携して特定の点を特定し、それに応じてほとんどの埋設点情報を分析できます。

特殊な状況では、ビジネス コードを追加して、特殊なシナリオに対処するポイントを手動で埋め込むことができます (ほとんどの場合、強力なビジネスは、通常のクリックや更新イベント、および必要な情報とは何の関係もありません)報告済み)

埋没点 SDK 開発

埋没点データの収集と分析

  • 基本的なイベント データ
    • イベント発生時間
    • 発生時のページ情報のスナップショット
  • ページ
    • ページPV、UV
    • ユーザーページ滞在時間
    • ページジャンプイベント
    • ページがバックグラウンドに入る
    • ユーザーがページを離れる
  • ユーザー情報
    • ユーザーuid
    • ユーザーデバイスのフィンガープリント
    • デバイス情報
    • ip
    • ポジショニング
  • ユーザー操作の動作
    • ユーザーのクリック
      • ターゲットをクリックします
  • ##ページ AJAX リクエスト
    • リクエスト成功
    • リクエスト失敗
    • リクエスト タイムアウト
    # ページ エラー
  • リソース読み込みエラー
    • JS 実行エラー
    新しいリソース読み込みパフォーマンス
  • 画像
  • スクリプト
  • ページ読み込みパフォーマンス
  • 上記のデータは、
3 次元を通じて非表示のイベントを定義します

·
    LEVEL
  • : 埋め込まれたデータのログ レベルを記述します。
      INFO
    • : 一部のユーザー操作、リクエストの成功、リソースの読み込みなど、通常のデータ レコード
    • ERROR
    • : JS エラー、インターフェイス エラーなどのデータ レコード。
    • DEBUG
    • : 開発者が手動でバグを排除するためにデータ レコードを返すために予約されています。呼び出し
    • WARN
    • : 開発者が手動呼び出しを通じて異常なユーザー動作のデータ レコードを返すために予約されています
  • CATEGORY
  • : 説明埋め込みポイント データの分類
      TRACK
    • : 埋め込みポイント SDK オブジェクトのライフ サイクルによって、埋め込みポイント データ全体が管理されます。
        WILL_MOUNT
      • : SDK オブジェクトが初期化およびロードされようとしており、デフォルト ID が生成され、関連するすべてのイベントが追跡されます
      • DID_MOUNTED
      • :SDKオブジェクトが初期化され、本体のデバイスフィンガープリント等の非同期操作が完了
    • #AJAX
    • :AJAX関連データ
    • ERROR
    • : ページ内の例外に関するデータ
    • PERFORMANCE
    • : パフォーマンス関連のデータ
    • OPERATION
    • : ユーザー操作関連data
  • EVENT_NAME
  • : 特定のイベント名
上記の次元に従って、次のアーキテクチャを簡単に設計できます

埋設ポイントシステムの予備調査
#上図のアーキテクチャに従って、次の特定のコード開発に進みます

プロキシ リクエスト

ブラウザには現在 2 つの主なタイプがあります。リクエスト メソッドは 3 つあり、1 つは

XMLHttpRequest

、もう 1 つは

Fetch です。 Agent XMLHttpRequest

function NewXHR() {  var realXHR: any = new OldXHR(); // 代理模式里面有提到过
  realXHR.id = guid()  const oldSend = realXHR.send;

  realXHR.send = function (body) {
    oldSend.call(this, body)    //记录埋点
  }
  realXHR.addEventListener('load', function () {    //记录埋点
  }, false);
  realXHR.addEventListener('abort', function () {    //记录埋点
  }, false);

  realXHR.addEventListener('error', function () {    //记录埋点
  }, false);
  realXHR.addEventListener('timeout', function () {    //记录埋点
  }, false);  return realXHR;
}复制代码

Agent Fetch

 const oldFetch = window.fetch;  function newFetch(url, init) {    const fetchObj = {      url: url,      method: method,      body: body,
    }
    ajaxEventTrigger.call(fetchObj, AJAX_START);    return oldFetch.apply(this, arguments).then(function (response) {      if (response.ok) {       //记录埋点
      } else {       //上报错误
      }      return response
    }).catch(function (error) {
      fetchObj.error = error        //记录埋点      
        throw error
    })
  }复制代码

ページの

PV

をリッスンします、

UV ページに入る前に、アルゴリズムを使用して一意の セッション ID

を生成します。これは、この埋め込み動作のグローバル ID として機能し、ユーザー ID、デバイスの指紋、およびデバイス情報を報告します。ユーザーがログインしていない場合、

UV はデバイスのフィンガープリントを通じて計算され、PVセッション ID を通じて計算されます。 例外キャプチャ

例外は、プログラムの通常のフローを妨げる異常な事故です。

実行時エラー

JS で渡すことができます。

window.onerror および window.addEventListener('error', callback) は、ランタイム例外をキャプチャします。通常、window.onerror が使用されます。互換性。

window.onerror = function(message, url, lineno, columnNo, error) {    const lowCashMessage = message.toLowerCase()    if(lowCashMessage.indexOf('script error') > -1) {      return
    }    const detail = {      url: url    
      filename: filename,      columnNo: columnNo,      lineno: lineno,      stack: error.stack,      message: message
    }    //记录埋点}复制代码
スクリプト エラー

ここでは、

スクリプト エラー

をフィルター処理します。これは主に、ページに読み込まれたサードパーティのクロスドメイン スクリプトによって報告されるエラーによって発生します。サードパーティ CDN の

js スクリプトでホストされます。このタイプの問題は、トラブルシューティングがより困難です。解決策は次のとおりです。

CORS
    (クロスオリジン リソース共有、クロスドメイン リソース共有) を開き、次の手順に従います。
  • aabe02b7c09859a7420c688c19aeb5c62cacc6d41bbb37262a98f745aa00fbf0
    • ModifyAccess-Control-Allow-Origin: * | ドメイン名を指定
    • 使用
    try catch
  •   <script scr="crgt.js"></script> //加载crgt脚本,window.crgt = {getUser: () => string}
      try{      window.crgt.getUser();
      }catch(error) {      throw error // 输出正确的错误堆栈
      }复制代码
  • プロミス拒否

js

パスできません非同期例外

onerror メソッド キャプチャの場合、Promise オブジェクトが拒否され、同時に処理されなかった場合 unhandledrejection エラーがスローされ、上記のメソッドでは捕捉されないため、別の処理イベントを追加する必要があります。

window.addEventListener("unhandledrejection", event => {  throw event.reason
});复制代码

资源加载异常

在浏览器中,可以通过 window.addEventListener('error', callback) 的方式监听资源加载异常,比如 js 或者 css 脚本文件丢失。

window.addEventListener(&#39;error&#39;, (event) => {  if (event.target instanceof HTMLElement) {    const target = parseDom(event.target, [&#39;src&#39;]);    const detail = {      target: target,      path: parseXPath(target),
    }    //  记录埋点
  }
}, true)复制代码

监听用户行为

通过 addEventListener click 监听 click 事件

window.addEventListener(&#39;click&#39;, (event) => {    //记录埋点}, true)复制代码

在这里通过组件的 displaName 来定位元素的位置,displaName 表示组件的文件目录,比如 src/components/Form.js 文件导出的组件 FormItem 通过 babel plugin 自动添加属性 @components/Form.FormItem,或者使用者主动给组件添加 static 属性 displayName

页面路由变化

  • hashRouter 监听页面hash变化,对hash进行解析
window.addEventListener(&#39;hashchange&#39;, event => {  const { oldURL, newURL } = event;  const oldURLObj = url.parseUrl(oldURL);  const newURLObj = url.parseUrl(newURL);  const from = oldURLObj.hash && url.parseHash(oldURLObj.hash);  const to = newURLObj.hash && url.parseHash(newURLObj.hash);  if(!from && !to ) return;  // 记录埋点})复制代码

监听页面离开

通过 addEventListener beforeunload 监听离开页面事件

window.addEventListener(&#39;beforeunload&#39;, (event) => {    //记录埋点})复制代码

SDK 架构

class Observable {    constructor(observer) {
        observer(this.emit)
    }
    emit = (data) => {        this.listeners.forEach(listener => {
            listener(data)
        })
    }
    listeners = [];
    
    subscribe = (listener) => {        this.listeners.push(listeners);        return () => {            const index = this.listeners.indexOf(listener);            if(index === -1) {                return false
            }            
            this.listeners.splice(index, 1);            return true;
        }
     }
}复制代码
const clickObservable = new Observable((emit) => {    window.addEventListener(&#39;click&#39;, emit)
})复制代码

然而在处理 ajax,需要将多种数据组合在一起,需要进行 merg 操作,则显得没有那么优雅,也很难适应后续复杂的数据流的操作。

const ajaxErrorObservable = new Observable((emit) => {    window.addEventListener(AJAX_ERROR, emit)
})const ajaxSuccessObservable = new Observable((emit) => {    window.addEventListener(AJAX_SUCCESS, emit)
})const ajaxTimeoutObservable = new Observable((emit) => {    window.addEventListener(AJAX_TIMEOUT, emit)
})复制代码

可以选择 RxJS 来优化代码

export const ajaxError$ = fromEvent(window, &#39;AJAX_ERROR&#39;, true)export const ajaxSuccess$ = fromEvent(window, &#39;AJAX_SUCCESS&#39;, true)export const ajaxTimeout$ = fromEvent(window, &#39;AJAX_TIMEOUT&#39;, true)复制代码
ajaxError$.pipe(
    merge(ajaxSuccess$, ajaxTimeout$), 
    map(data=> (data) => ({category: &#39;ajax&#39;, data; data}))
    subscribe(data => console.log(data))复制代码

通过 merge, map 两个操作符完成对数据的合并和处理。

数据流

埋設ポイントシステムの予備調査

项目结构

  • core
    • event$ 数据流合并
    • snapshot 获取当前设备快照,例如urluserIDrouter
    • track 埋点类,组合数据流和日志。
  • logger
    • logger 日志类
      • info
      • warn
      • debug
      • error
  • observable
    • ajax
    • beforeUpload
    • opeartion
    • routerChange
    • logger
    • track

参考

  • www.alibabacloud.com/help/zh/doc…

结尾

自建埋点系统是一个需要前后端一起合作的事情,如果人力不足的情况下,建议使用第三方分析插件,例如 Sentry 就能足够满足大部分日常使用

但还是建议多了解,在第三方插件出现不能满足业务需求的时候,可以顶上。

想了解更多编程学习,敬请关注php培训栏目!

以上が埋設ポイントシステムの予備調査の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はjuejin.imで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。