{"version":3,"file":"EchoSrv.cjs","sources":["../../../src/services/EchoSrv.ts"],"sourcesContent":["/**\n * Describes a size with width/height\n *\n * @public\n */\nexport interface SizeMeta {\n  width: number;\n  height: number;\n}\n\n/**\n * Describes the meta information that are sent together with each event.\n *\n * @public\n */\nexport interface EchoMeta {\n  screenSize: SizeMeta;\n  windowSize: SizeMeta;\n  userAgent: string;\n  url?: string;\n  path?: string;\n  /**\n   * A unique browser session\n   */\n  sessionId: string;\n  /**\n   * The current user's username used to login into Grafana e.g. email.\n   */\n  userLogin: string;\n  /**\n   * The current user's unique identifier.\n   */\n  userId: number;\n  /**\n   * True when user is logged in into Grafana.\n   */\n  userSignedIn: boolean;\n  /**\n   * Current user's role\n   */\n  orgRole: string | '';\n  /**\n   * Current user's org\n   */\n  orgId: number;\n  /**\n   * A millisecond epoch\n   */\n  ts: number;\n  /**\n   * A highres timestamp since navigation start\n   */\n  timeSinceNavigationStart: number;\n}\n\n/**\n * Describes echo backends that can be registered to receive of events.\n *\n * @public\n */\nexport interface EchoBackend<T extends EchoEvent = any, O = any> {\n  options: O;\n  supportedEvents: EchoEventType[];\n  flush: () => void;\n  addEvent: (event: T) => void;\n}\n\n/**\n * Describes an echo event.\n *\n * @public\n */\nexport interface EchoEvent<T extends EchoEventType = any, P = any> {\n  type: EchoEventType;\n  /**\n   * Event payload containing event specific data.\n   */\n  payload: P;\n  meta: EchoMeta;\n}\n\n/**\n * Supported echo event types that can be sent via the {@link EchoSrv}.\n *\n * @public\n */\nexport enum EchoEventType {\n  Performance = 'performance',\n  MetaAnalytics = 'meta-analytics',\n  Pageview = 'pageview',\n  Interaction = 'interaction',\n  ExperimentView = 'experimentview',\n  GrafanaJavascriptAgent = 'grafana-javascript-agent',\n}\n\n/**\n * Used to send events to all the registered backends. This should be accessed via the\n * {@link getEchoSrv} function. Will, by default, flush events to the backends every\n * 10s or when the flush function is triggered.\n *\n * @public\n */\nexport interface EchoSrv {\n  /**\n   * Call this to flush current events to the echo backends.\n   */\n  flush(): void;\n  /**\n   * Add a new echo backend to the list of backends that will receive events.\n   */\n  addBackend(backend: EchoBackend): void;\n  /**\n   * Call this to add event that will be sent to the echo backends upon next\n   * flush.\n   *\n   * @param event - Object containing event information.\n   * @param meta - Object that will extend/override the default meta object.\n   */\n  addEvent<T extends EchoEvent>(event: Omit<T, 'meta'>, meta?: {}): void;\n  /**\n   * Subscribe to interaction events by name. The callback fires synchronously\n   * every time a matching interaction is reported via {@link reportInteraction}.\n   *\n   * Returns an unsubscribe function.\n   */\n  onInteraction(name: string, callback: (properties: Record<string, unknown>) => void): () => void;\n}\n\nlet singletonInstance: EchoSrv;\n\n/**\n * Used during startup by Grafana to set the EchoSrv so it is available\n * via the {@link getEchoSrv} to the rest of the application.\n *\n * @internal\n */\nexport function setEchoSrv(instance: EchoSrv) {\n  // Check if there were any events reported to the FakeEchoSrv (before the main EchoSrv was initialized), and track them\n  if (singletonInstance instanceof FakeEchoSrv) {\n    for (const item of singletonInstance.buffer) {\n      instance.addEvent(item.event, item.meta);\n    }\n  }\n\n  singletonInstance = instance;\n}\n\n/**\n * Used to retrieve the {@link EchoSrv} that can be used to report events to registered\n * echo backends.\n *\n * @public\n */\nexport function getEchoSrv(): EchoSrv {\n  if (!singletonInstance) {\n    singletonInstance = new FakeEchoSrv();\n  }\n\n  return singletonInstance;\n}\n\n/**\n * Used to register echo backends that will receive Grafana echo events during application\n * runtime.\n *\n * @public\n */\nexport const registerEchoBackend = (backend: EchoBackend) => {\n  getEchoSrv().addBackend(backend);\n};\n\nexport class FakeEchoSrv implements EchoSrv {\n  buffer: Array<{ event: Omit<EchoEvent, 'meta'>; meta?: {} | undefined }> = [];\n  private interactionSubscribers = new Map<string, Set<(properties: Record<string, unknown>) => void>>();\n\n  flush(): void {\n    this.buffer = [];\n  }\n\n  addBackend(backend: EchoBackend): void {}\n\n  addEvent<T extends EchoEvent>(event: Omit<T, 'meta'>, meta?: {} | undefined): void {\n    this.buffer.push({ event, meta });\n\n    // Dispatch to interaction subscribers\n    if (event.type === EchoEventType.Interaction) {\n      const payload: { interactionName?: string; properties?: Record<string, unknown> } = event.payload;\n      if (payload.interactionName) {\n        const subscribers = this.interactionSubscribers.get(payload.interactionName);\n        if (subscribers) {\n          for (const cb of subscribers) {\n            cb(payload.properties ?? {});\n          }\n        }\n      }\n    }\n  }\n\n  onInteraction(name: string, callback: (properties: Record<string, unknown>) => void): () => void {\n    let subscribers = this.interactionSubscribers.get(name);\n    if (!subscribers) {\n      subscribers = new Set();\n      this.interactionSubscribers.set(name, subscribers);\n    }\n    subscribers.add(callback);\n\n    return () => {\n      subscribers!.delete(callback);\n      if (subscribers!.size === 0) {\n        this.interactionSubscribers.delete(name);\n      }\n    };\n  }\n}\n"],"names":["EchoEventType"],"mappings":";;;;;AAsFO,IAAK,aAAA,qBAAAA,cAAAA,KAAL;AACL,EAAAA,eAAA,aAAA,CAAA,GAAc,aAAA;AACd,EAAAA,eAAA,eAAA,CAAA,GAAgB,gBAAA;AAChB,EAAAA,eAAA,UAAA,CAAA,GAAW,UAAA;AACX,EAAAA,eAAA,aAAA,CAAA,GAAc,aAAA;AACd,EAAAA,eAAA,gBAAA,CAAA,GAAiB,gBAAA;AACjB,EAAAA,eAAA,wBAAA,CAAA,GAAyB,0BAAA;AANf,EAAA,OAAAA,cAAAA;AAAA,CAAA,EAAA,aAAA,IAAA,EAAA;AA0CZ,IAAI,iBAAA;AAQG,SAAS,WAAW,QAAA,EAAmB;AAE5C,EAAA,IAAI,6BAA6B,WAAA,EAAa;AAC5C,IAAA,KAAA,MAAW,IAAA,IAAQ,kBAAkB,MAAA,EAAQ;AAC3C,MAAA,QAAA,CAAS,QAAA,CAAS,IAAA,CAAK,KAAA,EAAO,IAAA,CAAK,IAAI,CAAA;AAAA,IACzC;AAAA,EACF;AAEA,EAAA,iBAAA,GAAoB,QAAA;AACtB;AAQO,SAAS,UAAA,GAAsB;AACpC,EAAA,IAAI,CAAC,iBAAA,EAAmB;AACtB,IAAA,iBAAA,GAAoB,IAAI,WAAA,EAAY;AAAA,EACtC;AAEA,EAAA,OAAO,iBAAA;AACT;AAQO,MAAM,mBAAA,GAAsB,CAAC,OAAA,KAAyB;AAC3D,EAAA,UAAA,EAAW,CAAE,WAAW,OAAO,CAAA;AACjC;AAEO,MAAM,WAAA,CAA+B;AAAA,EAArC,WAAA,GAAA;AACL,IAAA,IAAA,CAAA,MAAA,GAA2E,EAAC;AAC5E,IAAA,IAAA,CAAQ,sBAAA,uBAA6B,GAAA,EAAgE;AAAA,EAAA;AAAA,EAErG,KAAA,GAAc;AACZ,IAAA,IAAA,CAAK,SAAS,EAAC;AAAA,EACjB;AAAA,EAEA,WAAW,OAAA,EAA4B;AAAA,EAAC;AAAA,EAExC,QAAA,CAA8B,OAAwB,IAAA,EAA6B;AArLrF,IAAA,IAAA,EAAA;AAsLI,IAAA,IAAA,CAAK,MAAA,CAAO,IAAA,CAAK,EAAE,KAAA,EAAO,MAAM,CAAA;AAGhC,IAAA,IAAI,KAAA,CAAM,SAAS,aAAA,oBAA2B;AAC5C,MAAA,MAAM,UAA8E,KAAA,CAAM,OAAA;AAC1F,MAAA,IAAI,QAAQ,eAAA,EAAiB;AAC3B,QAAA,MAAM,WAAA,GAAc,IAAA,CAAK,sBAAA,CAAuB,GAAA,CAAI,QAAQ,eAAe,CAAA;AAC3E,QAAA,IAAI,WAAA,EAAa;AACf,UAAA,KAAA,MAAW,MAAM,WAAA,EAAa;AAC5B,YAAA,EAAA,CAAA,CAAG,EAAA,GAAA,OAAA,CAAQ,UAAA,KAAR,IAAA,GAAA,EAAA,GAAsB,EAAE,CAAA;AAAA,UAC7B;AAAA,QACF;AAAA,MACF;AAAA,IACF;AAAA,EACF;AAAA,EAEA,aAAA,CAAc,MAAc,QAAA,EAAqE;AAC/F,IAAA,IAAI,WAAA,GAAc,IAAA,CAAK,sBAAA,CAAuB,GAAA,CAAI,IAAI,CAAA;AACtD,IAAA,IAAI,CAAC,WAAA,EAAa;AAChB,MAAA,WAAA,uBAAkB,GAAA,EAAI;AACtB,MAAA,IAAA,CAAK,sBAAA,CAAuB,GAAA,CAAI,IAAA,EAAM,WAAW,CAAA;AAAA,IACnD;AACA,IAAA,WAAA,CAAY,IAAI,QAAQ,CAAA;AAExB,IAAA,OAAO,MAAM;AACX,MAAA,WAAA,CAAa,OAAO,QAAQ,CAAA;AAC5B,MAAA,IAAI,WAAA,CAAa,SAAS,CAAA,EAAG;AAC3B,QAAA,IAAA,CAAK,sBAAA,CAAuB,OAAO,IAAI,CAAA;AAAA,MACzC;AAAA,IACF,CAAA;AAAA,EACF;AACF;;;;;;;;"}