-
Notifications
You must be signed in to change notification settings - Fork 2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat(store_pagespixel): add legacy analytics support #28
Conversation
This adds two new AnalyticsEvent types 'PAGE_VIEW' and 'CLICK_EVENT', which get directed to an alternate fetch request. Here is an example usage
Currently you have to pass everything into the event, but some of the stuff can be done automatically.
Additionally the config would need to be updated to take 1 of 2 config types, currently some answers values are required.
Additionally wanted to share our thoughts on the timeline of this. Once pages analytics are updated to the same system as answers, we'd like users to interact with yext analytics the same way regardless of product. This update aims to stand in and let us construct requests as if it that new system was ready so that when it is, |
const reporter = new PagesAnalyticsReporter(config, mockHttpRequesterService); | ||
reporter.pageView(); | ||
const expectedUrl = ''; | ||
expect(mockHttpRequesterService.get).toHaveBeenLastCalledWith(expectedUrl, expect.anything()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm getting a weird failure trying to run this:
FAIL tests/infra/PagesAnalyticsReporter.ts
● Test suite failed to run
TypeError: Cannot read properties of undefined (reading 'generatedLine')
at compareByGeneratedPositionsDeflated (node_modules/source-map-support/node_modules/source-map/lib/util.js:344:47)
at doQuickSort (node_modules/source-map-support/node_modules/source-map/lib/quick-sort.js:88:11)
at Object.<anonymous>.exports.quickSort (node_modules/source-map-support/node_modules/source-map/lib/quick-sort.js:113:3)
at BasicSourceMapConsumer.SourceMapConsumer_parseMappings [as _parseMappings] (node_modules/source-map-support/node_modules/source-map/lib/source-map-consumer.js:564:5)
at BasicSourceMapConsumer.get [as _generatedMappings] (node_modules/source-map-support/node_modules/source-map/lib/source-map-consumer.js:70:12)
at BasicSourceMapConsumer.SourceMapConsumer_originalPositionFor [as originalPositionFor] (node_modules/source-map-support/node_modules/source-map/lib/source-map-consumer.js:655:12)
at mapSourcePosition (node_modules/source-map-support/source-map-support.js:244:42)
at wrapCallSite (node_modules/source-map-support/source-map-support.js:397:20)
at Function.prepareStackTrace (node_modules/source-map-support/source-map-support.js:446:39)
README.md
Outdated
businessId: 123456, // this comes from the url of your Yext account | ||
featureId: 'My Locator', // the name of the feature in your features.json | ||
pageType: 'locator', // the type of page, can be 'entity', 'directory', 'locator', or 'static' | ||
product: 'storepages', |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What should product be? If it's always storepages
, is there a reason they need to specify it?
README.md
Outdated
featureId: 'My Locator', // the name of the feature in your features.json | ||
pageType: 'locator', // the type of page, can be 'entity', 'directory', 'locator', or 'static' | ||
product: 'storepages', | ||
production: false, // set to true if you are in the production environment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Production is a pretty overloaded term for us. Is this production as in the production vs staging deploy? Or production vs. sandbox? Could also see someone confusing this with the Production answers experience tag.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fair point... it's just that staging doesn't exist anymore so I figured it made sense to flip the bit
README.md
Outdated
|
||
```ts | ||
import { provideAnalytics } from '@yext/analytics'; | ||
|
||
const analytics = provideAnalytics({ | ||
experienceKey: '<your experience key>', | ||
experienceVersion: 'PRODUCTION', | ||
businessId: 123456, | ||
businessId: 123456, // this comes from the url of your Yext account | ||
featureId: 'My Locator', // the name of the feature in your features.json |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If you're using the react code features.json is autogenerated and you may never look at it, might need to specify that the name in that case is taken from the file name of your entry template
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ack
README.md
Outdated
product: 'storepages', | ||
production: false, // set to true if you are in the production environment | ||
siteId: 654321, // the id of your site, you can find this in the url of your deploy page | ||
ids: [90210], // if your pageType is 'entity' this is required, and it is the uid of the entity |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this required on directory pages (or if it's optional, is there a benefit to providing it?)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
in sites, it's necessary to identify the directory entity, since directory pages are entity pages
etc/analytics.api.md
Outdated
@@ -129,6 +119,61 @@ export interface CtaEvent { | |||
// @public | |||
export type EnumOrString<T extends string> = T | `${T}`; | |||
|
|||
// Warning: (ae-forgotten-export) The symbol "BaseAnalyticsConfig" needs to be exported by the entry point index.d.ts |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this warning something we need to do something about?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i think i've fixed this
src/models/PagesEventDetails.ts
Outdated
|
||
constructor(config: PagesAnalyticsConfig, event: PagesEvent) { | ||
this.eventType = event.eventType; | ||
this.product = 'storepages'; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this intentionally hardcoded instead of reading from the config?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
removed this from the config as it is only ever "storepages" in the context of this library
src/models/PagesEventDetails.ts
Outdated
this.ids = config.ids; | ||
this.pageType = config.pageType; | ||
|
||
if (this.pageType === 'entity' && !this.ids) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we want I believe this is enforceable at the type level. Do we also want to check the opposite, that entityIds aren't provided for non 'entity' page types?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i'm not 100% certain. I believe they are optional, for example if you click on a result on a locator i think we can pass the entity id. I haven't had a chance to check
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ok i've confirmed that if you set the id currently it treats it as an entity page
src/models/PagesEventDetails.ts
Outdated
|
||
this.featureId = config.featureId; | ||
this.pagesReferrer = config.pagesReferrer ? config.pagesReferrer : window.document.referrer; | ||
this.path = config.path ? config.path : window.location.pathname; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same question about references to window
|
||
/** | ||
* Reports a user interaction event. | ||
* Will perform a promis rejection if the API contains an error or if |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
* Will perform a promis rejection if the API contains an error or if | |
* Will perform a promise rejection if the API contains an error or if |
src/infra/HttpRequester.ts
Outdated
import fetch from 'cross-fetch'; | ||
|
||
/** | ||
* Responsible for making web requests. | ||
* | ||
* @public |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Does this need to be annotated as public
? Ideally it should just be an internal implementation detail.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So i did this because there was a warning in the auto-generated markdown file bc this is part of the method signature of the AnalyticsReporters
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the warning is:
// Warning: (ae-forgotten-export) The symbol "HttpRequesterService" needs to be exported by the entry point index.d.ts
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why do the various reporters need to be exported? We treated the AnalyticsReporter
as an implementation detail, IIRC. We did not export it, users could not instantiate it manually. They had to use the provide
method.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
let me look back at master, i thought I was following what it was doing but I may have over-exported things
src/services/HttpRequesterService.ts
Outdated
/** | ||
* A service for sending requests on the web. | ||
* | ||
* @public |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same thing about this being public.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
same thing about the method signatures
@@ -3,7 +3,7 @@ | |||
* | |||
* @public | |||
*/ | |||
export enum AnalyticsEventType { | |||
export enum SearchAnalyticsEventType { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If AnalyticsEventType
was exported by the library, we will need an alias.
J=CR-2409