@happyvertical/analytics 0.74.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENT.md +33 -0
- package/LICENSE +7 -0
- package/dist/chunks/ga4-6gyDPZRn.js +863 -0
- package/dist/chunks/ga4-6gyDPZRn.js.map +1 -0
- package/dist/chunks/matomo-Ds_oRmZ6.js +1043 -0
- package/dist/chunks/matomo-Ds_oRmZ6.js.map +1 -0
- package/dist/chunks/plausible-BxpNa6qF.js +479 -0
- package/dist/chunks/plausible-BxpNa6qF.js.map +1 -0
- package/dist/cli/claude-context.d.ts +3 -0
- package/dist/cli/claude-context.d.ts.map +1 -0
- package/dist/cli/claude-context.js +21 -0
- package/dist/cli/claude-context.js.map +1 -0
- package/dist/index.d.ts +37 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +135 -0
- package/dist/index.js.map +1 -0
- package/dist/shared/factory.d.ts +48 -0
- package/dist/shared/factory.d.ts.map +1 -0
- package/dist/shared/providers/ga4.d.ts +68 -0
- package/dist/shared/providers/ga4.d.ts.map +1 -0
- package/dist/shared/providers/matomo-admin.d.ts +56 -0
- package/dist/shared/providers/matomo-admin.d.ts.map +1 -0
- package/dist/shared/providers/matomo.d.ts +49 -0
- package/dist/shared/providers/matomo.d.ts.map +1 -0
- package/dist/shared/providers/plausible.d.ts +50 -0
- package/dist/shared/providers/plausible.d.ts.map +1 -0
- package/dist/shared/types.d.ts +1235 -0
- package/dist/shared/types.d.ts.map +1 -0
- package/metadata.json +30 -0
- package/package.json +57 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ga4-6gyDPZRn.js","sources":["../../src/shared/providers/ga4.ts"],"sourcesContent":["/**\n * Google Analytics 4 provider implementation\n *\n * Uses three APIs internally:\n * - Admin API: Property management, data streams, custom definitions\n * - Data API: Reports and analytics queries\n * - Measurement Protocol: Server-side event tracking\n */\n\nimport { readFile } from 'node:fs/promises';\nimport {\n type analyticsadmin_v1beta,\n type analyticsdata_v1beta,\n google,\n} from 'googleapis';\n\nimport type {\n AnalyticsCapabilities,\n AnalyticsInterface,\n ConfigOptions,\n CreateDataStreamOptions,\n CreatePropertyOptions,\n CustomDimension,\n CustomDimensionOptions,\n CustomMetric,\n CustomMetricOptions,\n DataStream,\n DimensionMetadata,\n GA4Options,\n KeyEvent,\n KeyEventOptions,\n ListPropertiesOptions,\n MetricMetadata,\n PageviewEvent,\n Property,\n RealtimeReportOptions,\n ReportOptions,\n ReportResult,\n ServiceAccountCredentials,\n SnippetOptions,\n TrackEvent,\n TrackingSnippet,\n UpdatePropertyOptions,\n} from '../types.js';\nimport {\n AnalyticsError,\n AuthenticationError,\n PropertyNotFoundError,\n QuotaExceededError,\n RateLimitError,\n} from '../types.js';\n\n/**\n * Measurement Protocol endpoint\n */\nconst MEASUREMENT_PROTOCOL_URL = 'https://www.google-analytics.com/mp/collect';\nconst PROPERTY_HYDRATION_CONCURRENCY = 5;\n\n/**\n * Convert null to undefined for optional fields\n * Google APIs return null for missing fields, but our types use undefined\n */\nfunction _nullToUndefined<T>(value: T | null | undefined): T | undefined {\n return value === null ? undefined : value;\n}\n\n/**\n * Google Analytics 4 provider\n */\nexport class GA4Provider implements AnalyticsInterface {\n private adminClient: analyticsadmin_v1beta.Analyticsadmin | null = null;\n private dataClient: analyticsdata_v1beta.Analyticsdata | null = null;\n private options: GA4Options;\n private credentials: ServiceAccountCredentials | null = null;\n\n constructor(options: GA4Options) {\n this.options = {\n timeout: 30000,\n maxRetries: 3,\n cacheTTL: 3600000, // 1 hour\n ...options,\n };\n }\n\n /**\n * Initialize Google API clients with service account credentials\n */\n private async ensureClients(): Promise<void> {\n if (this.adminClient && this.dataClient) {\n return;\n }\n\n // Load credentials if needed\n if (!this.credentials && this.options.serviceAccountKey) {\n if (typeof this.options.serviceAccountKey === 'string') {\n // It's a file path, read and parse\n const content = await readFile(this.options.serviceAccountKey, 'utf-8');\n this.credentials = JSON.parse(content) as ServiceAccountCredentials;\n } else {\n this.credentials = this.options.serviceAccountKey;\n }\n }\n\n if (!this.credentials) {\n throw new AuthenticationError('ga4');\n }\n\n // Create auth client\n const auth = new google.auth.GoogleAuth({\n credentials: this.credentials,\n scopes: [\n 'https://www.googleapis.com/auth/analytics.readonly',\n 'https://www.googleapis.com/auth/analytics.edit',\n ],\n });\n\n // Initialize Admin API client\n this.adminClient = google.analyticsadmin({\n version: 'v1beta',\n auth,\n });\n\n // Initialize Data API client\n this.dataClient = google.analyticsdata({\n version: 'v1beta',\n auth,\n });\n }\n\n /**\n * Normalize property ID to numeric format\n */\n private normalizePropertyId(propertyId: string): string {\n // Remove 'properties/' prefix if present\n return propertyId.replace(/^properties\\//, '');\n }\n\n /**\n * Get full property resource name\n */\n private getPropertyName(propertyId: string): string {\n const id = this.normalizePropertyId(propertyId);\n return `properties/${id}`;\n }\n\n /**\n * Map a Google Analytics property resource to the public Property shape\n */\n private mapProperty(\n property: analyticsadmin_v1beta.Schema$GoogleAnalyticsAdminV1betaProperty,\n ): Property {\n return {\n id: property.name?.replace('properties/', '') || '',\n name: property.name || '',\n displayName: property.displayName || '',\n createTime: property.createTime || '',\n updateTime: property.updateTime ?? undefined,\n timeZone: property.timeZone ?? undefined,\n currencyCode: property.currencyCode ?? undefined,\n industryCategory: property.industryCategory ?? undefined,\n serviceLevel: property.serviceLevel as 'STANDARD' | 'PREMIUM' | undefined,\n };\n }\n\n /**\n * Hydrate discovered properties without firing unbounded concurrent requests\n */\n private async hydrateProperties(properties: Property[]): Promise<Property[]> {\n const hydrated: Property[] = [];\n\n for (\n let index = 0;\n index < properties.length;\n index += PROPERTY_HYDRATION_CONCURRENCY\n ) {\n const batch = properties.slice(\n index,\n index + PROPERTY_HYDRATION_CONCURRENCY,\n );\n const hydratedBatch = await Promise.all(\n batch.map(async (property) => {\n const response = await this.adminClient!.properties.get({\n name: property.name,\n });\n\n return this.mapProperty(response.data);\n }),\n );\n\n hydrated.push(...hydratedBatch);\n }\n\n return hydrated;\n }\n\n /**\n * Map Google API errors to our error types\n */\n private mapError(error: unknown): AnalyticsError {\n if (error instanceof AnalyticsError) {\n return error;\n }\n\n const err = error as { code?: number; message?: string; status?: number };\n const status = err.code || err.status;\n const message = err.message || 'Unknown error';\n\n switch (status) {\n case 401:\n case 403:\n return new AuthenticationError('ga4');\n case 404:\n return new PropertyNotFoundError(message, 'ga4');\n case 429:\n return new RateLimitError('ga4');\n case 402:\n return new QuotaExceededError('ga4');\n default:\n return new AnalyticsError(message, 'API_ERROR', 'ga4');\n }\n }\n\n // ===========================================================================\n // Property Management\n // ===========================================================================\n\n async createProperty(options: CreatePropertyOptions): Promise<Property> {\n await this.ensureClients();\n\n if (!options.parent) {\n throw new AnalyticsError(\n 'Parent account is required for creating GA4 properties',\n 'MISSING_PARENT',\n 'ga4',\n );\n }\n\n try {\n const response = await this.adminClient!.properties.create({\n requestBody: {\n displayName: options.displayName,\n timeZone: options.timeZone || 'America/Los_Angeles',\n currencyCode: options.currencyCode || 'USD',\n industryCategory: options.industryCategory,\n parent: options.parent,\n },\n });\n\n const property = this.mapProperty(response.data);\n\n if (!property.createTime) {\n property.createTime = new Date().toISOString();\n }\n\n return property;\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async listProperties(options?: ListPropertiesOptions): Promise<Property[]> {\n await this.ensureClients();\n\n try {\n const properties = new Map<string, Property>();\n let pageToken: string | undefined;\n\n do {\n const response = await this.adminClient!.accountSummaries.list({\n pageSize: 200,\n pageToken,\n });\n\n for (const accountSummary of response.data.accountSummaries || []) {\n for (const propertySummary of accountSummary.propertySummaries ||\n []) {\n const propertyName = propertySummary.property || '';\n\n if (!propertyName || properties.has(propertyName)) {\n continue;\n }\n\n properties.set(propertyName, {\n id: propertyName.replace('properties/', ''),\n name: propertyName,\n displayName: propertySummary.displayName || '',\n createTime: '',\n });\n }\n }\n\n pageToken = response.data.nextPageToken ?? undefined;\n } while (pageToken);\n\n const listedProperties = [...properties.values()];\n\n if (options?.hydrate === false) {\n return listedProperties;\n }\n\n return this.hydrateProperties(listedProperties);\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async getProperty(propertyId: string): Promise<Property> {\n await this.ensureClients();\n\n try {\n const response = await this.adminClient!.properties.get({\n name: this.getPropertyName(propertyId),\n });\n\n return this.mapProperty(response.data);\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async updateProperty(\n propertyId: string,\n data: UpdatePropertyOptions,\n ): Promise<Property> {\n await this.ensureClients();\n\n const updateMask: string[] = [];\n if (data.displayName) updateMask.push('displayName');\n if (data.timeZone) updateMask.push('timeZone');\n if (data.currencyCode) updateMask.push('currencyCode');\n if (data.industryCategory) updateMask.push('industryCategory');\n\n try {\n const response = await this.adminClient!.properties.patch({\n name: this.getPropertyName(propertyId),\n updateMask: updateMask.join(','),\n requestBody: {\n displayName: data.displayName,\n timeZone: data.timeZone,\n currencyCode: data.currencyCode,\n industryCategory: data.industryCategory,\n },\n });\n\n return this.mapProperty(response.data);\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async deleteProperty(propertyId: string): Promise<void> {\n await this.ensureClients();\n\n try {\n await this.adminClient!.properties.delete({\n name: this.getPropertyName(propertyId),\n });\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n // ===========================================================================\n // Data Streams\n // ===========================================================================\n\n async getDataStreams(propertyId: string): Promise<DataStream[]> {\n await this.ensureClients();\n\n try {\n const response = await this.adminClient!.properties.dataStreams.list({\n parent: this.getPropertyName(propertyId),\n });\n\n return (response.data.dataStreams || []).map(\n (\n ds: analyticsadmin_v1beta.Schema$GoogleAnalyticsAdminV1betaDataStream,\n ) => ({\n id: ds.name?.split('/').pop() || '',\n type: ds.type as DataStream['type'],\n displayName: ds.displayName || '',\n measurementId: ds.webStreamData?.measurementId ?? undefined,\n firebaseAppId:\n ds.androidAppStreamData?.firebaseAppId ??\n ds.iosAppStreamData?.firebaseAppId ??\n undefined,\n defaultUri: ds.webStreamData?.defaultUri ?? undefined,\n createTime: ds.createTime || '',\n updateTime: ds.updateTime ?? undefined,\n }),\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async createDataStream(\n propertyId: string,\n options: CreateDataStreamOptions,\n ): Promise<DataStream> {\n await this.ensureClients();\n\n try {\n const requestBody: analyticsadmin_v1beta.Schema$GoogleAnalyticsAdminV1betaDataStream =\n {\n type: options.type,\n displayName: options.displayName,\n };\n\n if (options.type === 'WEB_DATA_STREAM') {\n requestBody.webStreamData = {\n defaultUri: options.defaultUri,\n };\n } else if (options.type === 'ANDROID_APP_DATA_STREAM') {\n requestBody.androidAppStreamData = {\n packageName: options.packageName,\n };\n } else if (options.type === 'IOS_APP_DATA_STREAM') {\n requestBody.iosAppStreamData = {\n bundleId: options.bundleId,\n };\n }\n\n const response = await this.adminClient!.properties.dataStreams.create({\n parent: this.getPropertyName(propertyId),\n requestBody,\n });\n\n const ds = response.data;\n return {\n id: ds.name?.split('/').pop() || '',\n type: ds.type as DataStream['type'],\n displayName: ds.displayName || '',\n measurementId: ds.webStreamData?.measurementId ?? undefined,\n firebaseAppId:\n ds.androidAppStreamData?.firebaseAppId ??\n ds.iosAppStreamData?.firebaseAppId ??\n undefined,\n defaultUri: ds.webStreamData?.defaultUri ?? undefined,\n createTime: ds.createTime || '',\n updateTime: ds.updateTime ?? undefined,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async deleteDataStream(propertyId: string, streamId: string): Promise<void> {\n await this.ensureClients();\n\n try {\n await this.adminClient!.properties.dataStreams.delete({\n name: `${this.getPropertyName(propertyId)}/dataStreams/${streamId}`,\n });\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n // ===========================================================================\n // Custom Definitions\n // ===========================================================================\n\n async getCustomDimensions(propertyId: string): Promise<CustomDimension[]> {\n await this.ensureClients();\n\n try {\n const response = await this.adminClient!.properties.customDimensions.list(\n {\n parent: this.getPropertyName(propertyId),\n },\n );\n\n return (response.data.customDimensions || []).map(\n (\n cd: analyticsadmin_v1beta.Schema$GoogleAnalyticsAdminV1betaCustomDimension,\n ) => ({\n id: cd.name?.split('/').pop() || '',\n name: cd.name || '',\n parameterName: cd.parameterName || '',\n displayName: cd.displayName || '',\n description: cd.description ?? undefined,\n scope: cd.scope as CustomDimension['scope'],\n disallowAdsPersonalization:\n cd.disallowAdsPersonalization ?? undefined,\n }),\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async createCustomDimension(\n propertyId: string,\n options: CustomDimensionOptions,\n ): Promise<CustomDimension> {\n await this.ensureClients();\n\n try {\n const response =\n await this.adminClient!.properties.customDimensions.create({\n parent: this.getPropertyName(propertyId),\n requestBody: {\n parameterName: options.parameterName,\n displayName: options.displayName,\n description: options.description,\n scope: options.scope,\n disallowAdsPersonalization: options.disallowAdsPersonalization,\n },\n });\n\n const cd = response.data;\n return {\n id: cd.name?.split('/').pop() || '',\n name: cd.name || '',\n parameterName: cd.parameterName || '',\n displayName: cd.displayName || '',\n description: cd.description ?? undefined,\n scope: cd.scope as CustomDimension['scope'],\n disallowAdsPersonalization: cd.disallowAdsPersonalization ?? undefined,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async archiveCustomDimension(\n propertyId: string,\n dimensionId: string,\n ): Promise<void> {\n await this.ensureClients();\n\n try {\n await this.adminClient!.properties.customDimensions.archive({\n name: `${this.getPropertyName(propertyId)}/customDimensions/${dimensionId}`,\n });\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async getCustomMetrics(propertyId: string): Promise<CustomMetric[]> {\n await this.ensureClients();\n\n try {\n const response = await this.adminClient!.properties.customMetrics.list({\n parent: this.getPropertyName(propertyId),\n });\n\n return (response.data.customMetrics || []).map(\n (\n cm: analyticsadmin_v1beta.Schema$GoogleAnalyticsAdminV1betaCustomMetric,\n ) => ({\n id: cm.name?.split('/').pop() || '',\n name: cm.name || '',\n parameterName: cm.parameterName || '',\n displayName: cm.displayName || '',\n description: cm.description ?? undefined,\n scope: 'EVENT' as const,\n measurementUnit:\n cm.measurementUnit as CustomMetric['measurementUnit'],\n restrictedMetricType:\n (cm\n .restrictedMetricType?.[0] as CustomMetric['restrictedMetricType']) ??\n undefined,\n }),\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async createCustomMetric(\n propertyId: string,\n options: CustomMetricOptions,\n ): Promise<CustomMetric> {\n await this.ensureClients();\n\n try {\n const response = await this.adminClient!.properties.customMetrics.create({\n parent: this.getPropertyName(propertyId),\n requestBody: {\n parameterName: options.parameterName,\n displayName: options.displayName,\n description: options.description,\n measurementUnit: options.measurementUnit,\n restrictedMetricType: options.restrictedMetricType\n ? [options.restrictedMetricType]\n : undefined,\n scope: 'EVENT',\n },\n });\n\n const cm = response.data!;\n return {\n id: cm.name?.split('/').pop() || '',\n name: cm.name || '',\n parameterName: cm.parameterName || '',\n displayName: cm.displayName || '',\n description: cm.description ?? undefined,\n scope: 'EVENT' as const,\n measurementUnit: cm.measurementUnit as CustomMetric['measurementUnit'],\n restrictedMetricType:\n (cm\n .restrictedMetricType?.[0] as CustomMetric['restrictedMetricType']) ??\n undefined,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async archiveCustomMetric(\n propertyId: string,\n metricId: string,\n ): Promise<void> {\n await this.ensureClients();\n\n try {\n await this.adminClient!.properties.customMetrics.archive({\n name: `${this.getPropertyName(propertyId)}/customMetrics/${metricId}`,\n });\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n // ===========================================================================\n // Key Events (Conversions)\n // ===========================================================================\n\n async getKeyEvents(propertyId: string): Promise<KeyEvent[]> {\n await this.ensureClients();\n\n try {\n const response = await this.adminClient!.properties.keyEvents.list({\n parent: this.getPropertyName(propertyId),\n });\n\n return (response.data.keyEvents || []).map(\n (\n ke: analyticsadmin_v1beta.Schema$GoogleAnalyticsAdminV1betaKeyEvent,\n ) => ({\n id: ke.name?.split('/').pop() || '',\n name: ke.name || '',\n eventName: ke.eventName || '',\n createTime: ke.createTime || '',\n countingMethod: ke.countingMethod as KeyEvent['countingMethod'],\n defaultValue: ke.defaultValue\n ? {\n numericValue: ke.defaultValue.numericValue ?? undefined,\n currencyCode: ke.defaultValue.currencyCode ?? undefined,\n }\n : undefined,\n }),\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async createKeyEvent(\n propertyId: string,\n options: KeyEventOptions,\n ): Promise<KeyEvent> {\n await this.ensureClients();\n\n try {\n const response = await this.adminClient!.properties.keyEvents.create({\n parent: this.getPropertyName(propertyId),\n requestBody: {\n eventName: options.eventName,\n countingMethod: options.countingMethod,\n defaultValue: options.defaultValue,\n },\n });\n\n const ke = response.data;\n return {\n id: ke.name?.split('/').pop() || '',\n name: ke.name || '',\n eventName: ke.eventName || '',\n createTime: ke.createTime || '',\n countingMethod: ke.countingMethod as KeyEvent['countingMethod'],\n defaultValue: ke.defaultValue\n ? {\n numericValue: ke.defaultValue.numericValue ?? undefined,\n currencyCode: ke.defaultValue.currencyCode ?? undefined,\n }\n : undefined,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async deleteKeyEvent(propertyId: string, eventId: string): Promise<void> {\n await this.ensureClients();\n\n try {\n await this.adminClient!.properties.keyEvents.delete({\n name: `${this.getPropertyName(propertyId)}/keyEvents/${eventId}`,\n });\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n // ===========================================================================\n // Reporting\n // ===========================================================================\n\n async runReport(\n propertyId: string,\n options: ReportOptions,\n ): Promise<ReportResult> {\n await this.ensureClients();\n\n try {\n const response = await this.dataClient!.properties.runReport({\n property: this.getPropertyName(propertyId),\n requestBody: {\n dateRanges: options.dateRanges,\n dimensions: options.dimensions,\n metrics: options.metrics,\n dimensionFilter: options.dimensionFilter,\n metricFilter: options.metricFilter,\n offset: options.offset ? String(options.offset) : undefined,\n limit: options.limit ? String(options.limit) : undefined,\n orderBys: options.orderBys,\n keepEmptyRows: options.keepEmptyRows,\n returnPropertyQuota: options.returnPropertyQuota,\n },\n });\n\n const data = response.data;\n return {\n dimensionHeaders: (data.dimensionHeaders || []).map(\n (h: analyticsdata_v1beta.Schema$DimensionHeader) => ({\n name: h.name || '',\n }),\n ),\n metricHeaders: (data.metricHeaders || []).map(\n (h: analyticsdata_v1beta.Schema$MetricHeader) => ({\n name: h.name || '',\n type: h.type || '',\n }),\n ),\n rows: (data.rows || []).map((r: analyticsdata_v1beta.Schema$Row) => ({\n dimensionValues: (r.dimensionValues || []).map(\n (v: analyticsdata_v1beta.Schema$DimensionValue) => ({\n value: v.value || '',\n }),\n ),\n metricValues: (r.metricValues || []).map(\n (v: analyticsdata_v1beta.Schema$MetricValue) => ({\n value: v.value || '',\n }),\n ),\n })),\n rowCount: data.rowCount ?? undefined,\n metadata: data.metadata\n ? {\n currencyCode: data.metadata.currencyCode ?? undefined,\n timeZone: data.metadata.timeZone ?? undefined,\n dataLossFromOtherRow:\n data.metadata.dataLossFromOtherRow ?? undefined,\n emptyReason: data.metadata.emptyReason ?? undefined,\n }\n : undefined,\n propertyQuota: data.propertyQuota\n ? {\n tokensPerDay: {\n consumed: data.propertyQuota.tokensPerDay?.consumed || 0,\n remaining: data.propertyQuota.tokensPerDay?.remaining || 0,\n },\n tokensPerHour: {\n consumed: data.propertyQuota.tokensPerHour?.consumed || 0,\n remaining: data.propertyQuota.tokensPerHour?.remaining || 0,\n },\n concurrentRequests: {\n consumed: data.propertyQuota.concurrentRequests?.consumed || 0,\n remaining:\n data.propertyQuota.concurrentRequests?.remaining || 0,\n },\n }\n : undefined,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async runRealtimeReport(\n propertyId: string,\n options?: RealtimeReportOptions,\n ): Promise<ReportResult> {\n await this.ensureClients();\n\n try {\n const response = await this.dataClient!.properties.runRealtimeReport({\n property: this.getPropertyName(propertyId),\n requestBody: {\n dimensions: options?.dimensions,\n metrics: options?.metrics || [{ name: 'activeUsers' }],\n dimensionFilter: options?.dimensionFilter,\n metricFilter: options?.metricFilter,\n limit: options?.limit ? String(options.limit) : undefined,\n minuteRanges: options?.minuteRanges,\n },\n });\n\n const data = response.data;\n return {\n dimensionHeaders: (data.dimensionHeaders || []).map(\n (h: analyticsdata_v1beta.Schema$DimensionHeader) => ({\n name: h.name || '',\n }),\n ),\n metricHeaders: (data.metricHeaders || []).map(\n (h: analyticsdata_v1beta.Schema$MetricHeader) => ({\n name: h.name || '',\n type: h.type || '',\n }),\n ),\n rows: (data.rows || []).map((r: analyticsdata_v1beta.Schema$Row) => ({\n dimensionValues: (r.dimensionValues || []).map(\n (v: analyticsdata_v1beta.Schema$DimensionValue) => ({\n value: v.value || '',\n }),\n ),\n metricValues: (r.metricValues || []).map(\n (v: analyticsdata_v1beta.Schema$MetricValue) => ({\n value: v.value || '',\n }),\n ),\n })),\n rowCount: data.rowCount ?? undefined,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async getMetrics(propertyId: string): Promise<MetricMetadata[]> {\n await this.ensureClients();\n\n try {\n const response = await this.dataClient!.properties.getMetadata({\n name: `${this.getPropertyName(propertyId)}/metadata`,\n });\n\n return (response.data.metrics || []).map(\n (m: analyticsdata_v1beta.Schema$MetricMetadata) => ({\n apiName: m.apiName || '',\n uiName: m.uiName || '',\n description: m.description || '',\n deprecatedApiNames: m.deprecatedApiNames ?? undefined,\n type: m.type as MetricMetadata['type'],\n expression: m.expression ?? undefined,\n customDefinition: m.customDefinition ?? undefined,\n blockedReasons: m.blockedReasons ?? undefined,\n category: m.category ?? undefined,\n }),\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async getDimensions(propertyId: string): Promise<DimensionMetadata[]> {\n await this.ensureClients();\n\n try {\n const response = await this.dataClient!.properties.getMetadata({\n name: `${this.getPropertyName(propertyId)}/metadata`,\n });\n\n return (response.data.dimensions || []).map(\n (d: analyticsdata_v1beta.Schema$DimensionMetadata) => ({\n apiName: d.apiName || '',\n uiName: d.uiName || '',\n description: d.description || '',\n deprecatedApiNames: d.deprecatedApiNames ?? undefined,\n customDefinition: d.customDefinition ?? undefined,\n category: d.category ?? undefined,\n }),\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n // ===========================================================================\n // Event Tracking (Measurement Protocol)\n // ===========================================================================\n\n async track(event: TrackEvent): Promise<void> {\n if (!this.options.measurementId || !this.options.apiSecret) {\n throw new AnalyticsError(\n 'Measurement ID and API Secret are required for server-side tracking',\n 'MISSING_CREDENTIALS',\n 'ga4',\n );\n }\n\n const clientId = event.clientId || this.generateClientId();\n const url = `${MEASUREMENT_PROTOCOL_URL}?measurement_id=${this.options.measurementId}&api_secret=${this.options.apiSecret}`;\n\n const payload = {\n client_id: clientId,\n user_id: event.userId,\n timestamp_micros: event.timestamp,\n non_personalized_ads: event.nonPersonalizedAds,\n events: [\n {\n name: event.name,\n params: event.params,\n },\n ],\n };\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify(payload),\n });\n\n if (!response.ok) {\n throw new AnalyticsError(\n `Measurement Protocol error: ${response.status}`,\n 'TRACKING_ERROR',\n 'ga4',\n );\n }\n } catch (error) {\n if (error instanceof AnalyticsError) {\n throw error;\n }\n throw this.mapError(error);\n }\n }\n\n async trackPageview(pageview: PageviewEvent): Promise<void> {\n await this.track({\n name: 'page_view',\n params: {\n page_path: pageview.pagePath,\n page_title: pageview.pageTitle || '',\n page_location: pageview.pageLocation || '',\n ...pageview.params,\n },\n clientId: pageview.clientId,\n userId: pageview.userId,\n });\n }\n\n async trackBatch(events: TrackEvent[]): Promise<void> {\n if (!this.options.measurementId || !this.options.apiSecret) {\n throw new AnalyticsError(\n 'Measurement ID and API Secret are required for server-side tracking',\n 'MISSING_CREDENTIALS',\n 'ga4',\n );\n }\n\n // GA4 Measurement Protocol supports up to 25 events per request\n const batchSize = 25;\n for (let i = 0; i < events.length; i += batchSize) {\n const batch = events.slice(i, i + batchSize);\n\n // Group by client_id\n const byClient = new Map<string, TrackEvent[]>();\n for (const event of batch) {\n const clientId = event.clientId || this.generateClientId();\n const existing = byClient.get(clientId) || [];\n existing.push(event);\n byClient.set(clientId, existing);\n }\n\n // Send one request per client\n for (const [clientId, clientEvents] of byClient) {\n const url = `${MEASUREMENT_PROTOCOL_URL}?measurement_id=${this.options.measurementId}&api_secret=${this.options.apiSecret}`;\n\n const payload = {\n client_id: clientId,\n events: clientEvents.map((e) => ({\n name: e.name,\n params: e.params,\n })),\n };\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify(payload),\n });\n\n if (!response.ok) {\n throw new AnalyticsError(\n `Measurement Protocol error: ${response.status}`,\n 'TRACKING_ERROR',\n 'ga4',\n );\n }\n } catch (error) {\n if (error instanceof AnalyticsError) {\n throw error;\n }\n throw this.mapError(error);\n }\n }\n }\n }\n\n async identify(\n userId: string,\n traits?: Record<string, unknown>,\n ): Promise<void> {\n // GA4 uses user_id and user properties\n // Send a synthetic event to associate user properties\n await this.track({\n name: 'user_engagement',\n userId,\n params: traits as Record<string, string | number | boolean> | undefined,\n });\n }\n\n /**\n * Generate a random client ID for Measurement Protocol\n */\n private generateClientId(): string {\n return `${Math.floor(Math.random() * 2147483647)}.${Math.floor(Date.now() / 1000)}`;\n }\n\n // ===========================================================================\n // Client-Side Helpers\n // ===========================================================================\n\n generateTrackingSnippet(\n propertyId: string,\n options?: SnippetOptions,\n ): TrackingSnippet {\n const measurementId = this.options.measurementId || `G-${propertyId}`;\n\n const configOptions: Record<string, unknown> = {};\n if (options?.anonymizeIp) {\n configOptions.anonymize_ip = true;\n }\n if (options?.sendPageView === false) {\n configOptions.send_page_view = false;\n }\n if (options?.cookieFlags) {\n configOptions.cookie_flags = options.cookieFlags;\n }\n if (options?.customConfig) {\n Object.assign(configOptions, options.customConfig);\n }\n\n const configStr =\n Object.keys(configOptions).length > 0\n ? `, ${JSON.stringify(configOptions)}`\n : '';\n\n const html = `<!-- Google Analytics -->\n<script async src=\"https://www.googletagmanager.com/gtag/js?id=${measurementId}\"></script>\n<script>\n window.dataLayer = window.dataLayer || [];\n function gtag(){dataLayer.push(arguments);}\n gtag('js', new Date());\n gtag('config', '${measurementId}'${configStr});\n</script>`;\n\n return {\n html,\n config: {\n measurementId,\n ...configOptions,\n },\n scripts: [`https://www.googletagmanager.com/gtag/js?id=${measurementId}`],\n };\n }\n\n generateConfig(\n propertyId: string,\n options?: ConfigOptions,\n ): Record<string, unknown> {\n const measurementId = this.options.measurementId || `G-${propertyId}`;\n\n const config: Record<string, unknown> = {\n measurement_id: measurementId,\n };\n\n if (options?.anonymizeIp) {\n config.anonymize_ip = true;\n }\n if (options?.sendPageView === false) {\n config.send_page_view = false;\n }\n if (options?.userId) {\n config.user_id = options.userId;\n }\n if (options?.customDimensions) {\n Object.entries(options.customDimensions).forEach(([key, value]) => {\n config[key] = value;\n });\n }\n\n return config;\n }\n\n // ===========================================================================\n // Provider Info\n // ===========================================================================\n\n async getCapabilities(): Promise<AnalyticsCapabilities> {\n return {\n propertyManagement: true,\n dataStreams: true,\n customDimensions: true,\n customMetrics: true,\n keyEvents: true,\n reporting: true,\n realtimeReporting: true,\n serverSideTracking: true,\n clientSideSnippet: true,\n userIdentification: true,\n batchTracking: true,\n };\n }\n}\n"],"names":[],"mappings":"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"}
|