Skip to content

Commit

Permalink
Added support for AMP linker
Browse files Browse the repository at this point in the history
  • Loading branch information
parth-mahajan authored and sayan-mitra committed Jan 13, 2021
1 parent ea49ea0 commit c2c2a8b
Show file tree
Hide file tree
Showing 6 changed files with 138 additions and 5 deletions.
33 changes: 33 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -192,6 +192,39 @@ rudderanalytics.ready(
```

# [](https://github.com/rudderlabs/rudder-sdk-js/blob/master/README.md#adding-callbacks-to-standard-methods)Adding callbacks to standard methods
| **For detailed technical documentation and troubleshooting guide on the RudderStack’s JavaScript SDK, check out our [docs](https://docs.rudderlabs.com/sdk-integration-guide/getting-started-with-javascript-sdk).** |
|:------|

# [](https://github.com/rudderlabs/rudder-sdk-js/blob/master/README.md#querystring-api)Querystring API

RudderStack's Querystring API allows you to trigger `track`, `identify` calls using query parameters. If you pass the following parameters in the URL, then it will trigger the corresponding SDK API call.

For example:

```
http://hostname.com/?ajs_uid=12345&ajs_event=test%20event&ajs_aid=abcde&ajs_prop_testProp=prop1&ajs_trait_name=Firstname+Lastname
```
For the above URL, the below SDK calls will be triggered:

```
rudderanalytics.identify("12345", {name: "Firstname Lastname"});
rudderanalytics.track("test event", {testProp: "prop1"});
rudderanalytics.setAnonymousId("abcde");
rudderanalytics.setAnonymousId(null, "<version>*<checkSum>*<idName1>*<idValue1>*<idName2>*<idValue2>...");
```

You may use the below parameters as querystring parameter and trigger the corresponding call.

`ajs_uid` : Makes a `rudderanalytics.identify()` call with `userId` having the value of the parameter value.

`ajs_aid` : Makes a `rudderanalytics.setAnonymousId()` call with `anonymousId` having the value of the parameter value or call with `rudderAmpLinkerParm` having the value of `rudderstack` from the query param.

`ajs_event` : Makes a `rudderanalytics.track()` call with `event` name as parameter value.

`ajs_prop_<property>` : If `ajs_event` is passed as querystring, value of this parameter will populate the `properties` of the corresponding event in the `track` call.

`ajs_trait_<trait>` : If `ajs_uid` is provided as querysting, value of this parameter will populate the `traits` of the `identify` call made.


One can also define callbacks to common methods of `rudderanalytics` object. _**Note**_: For now, the functionality is supported for `syncPixel` method which is called in Rudder SDK when making sync calls in integrations for relevant destinations.

Expand Down
16 changes: 14 additions & 2 deletions analytics.js
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ import { EventRepository } from "./utils/EventRepository";
import logger from "./utils/logUtil";
import { addDomEventHandlers } from "./utils/autotrack.js";
import ScriptLoader from "./integrations/ScriptLoader";
import parseLinker from "./utils/linker";

const queryDefaults = {
trait: "ajs_trait_",
Expand Down Expand Up @@ -830,9 +831,20 @@ class Analytics {
return this.anonymousId;
}

setAnonymousId(anonymousId) {
/**
* Sets anonymous id in the followin precedence:
* 1. anonymousId: Id directly provided to the function.
* 2. rudderAmpLinkerParm: value generated from linker query parm (rudderstack)
* using praseLinker util.
* 3. generateUUID: A new uniquie id is generated and assigned.
*
* @param {string} anonymousId
* @param {string} rudderAmpLinkerParm
*/
setAnonymousId(anonymousId, rudderAmpLinkerParm) {
// if (!this.loaded) return;
this.anonymousId = anonymousId || generateUUID();
const parsedAnonymousId = rudderAmpLinkerParm ? parseLinker(rudderAmpLinkerParm) : null;
this.anonymousId = anonymousId || parsedAnonymousId || generateUUID();
this.storage.setAnonymousId(this.anonymousId);
}

Expand Down
26 changes: 26 additions & 0 deletions utils/linker/base64decoder.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
/**
* @description This is utility function for decoding from base 64 to utf8
* @version v1.0.0
*/

/**
* @param {string} str base64
* @returns {string} utf8
*/
function b64DecodeUnicode(str) {
// Going backwards: from bytestream, to percent-encoding, to original string.
return decodeURIComponent(atob(str).split('').map(function (c) {
return '%' + ('00' + c.charCodeAt(0).toString(16)).slice(-2);
}).join(''));
}

/**
* @param {string} value
* @return {string}
*/
function decode(data = "") {
data = data.endsWith("..") ? data.substr(0, data.length - 2) : data;
return b64DecodeUnicode(data);
}

export default decode
42 changes: 42 additions & 0 deletions utils/linker/crc32.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
/**
* @description This is utility function for crc32 algorithm
* @version v1.0.0
*/

/**
* @description generate crc table
* @params none
* @returns arrray of CRC table
*/

const makeCRCTable = function () {
const crcTable = []
let c
for (var n = 0; n < 256; n++) {
c = n
for (var k = 0; k < 8; k++) {
c = c & 1 ? 0xedb88320 ^ (c >>> 1) : c >>> 1
}
crcTable[n] = c
}
return crcTable
}


/**
*
* @param {string} str
* @returns {Bystream} crc32
*/
const crc32 = function (str) {
const crcTable = makeCRCTable()
let crc = 0 ^ -1

for (let i = 0; i < str.length; i++) {
crc = (crc >>> 8) ^ crcTable[(crc ^ str.charCodeAt(i)) & 0xff]
}

return (crc ^ -1) >>> 0
}

export default crc32
6 changes: 3 additions & 3 deletions utils/linker/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@
* @author Parth Mahajan, Ayush Mehra
*/

import crc32 from "./utils/crc32";
import USER_INTERFACE from "./utils/userLib";
import decode from "./utils/base64decoder";
import crc32 from "./crc32";
import USER_INTERFACE from "./userLib";
import decode from "./base64decoder";

const KEY_VALIDATOR = /^[a-zA-Z0-9\-_.]+$/;
const CHECKSUM_OFFSET_MAX_MIN = 1;
Expand Down
20 changes: 20 additions & 0 deletions utils/linker/userLib.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
/**
* @description An interface to fetch user device details.
* @version v1.0.0
*/

const USER_INTERFACE = {
/**
* @param {*} req
* @returns {string} user language
*/
getUserLanguage: () => navigator && navigator.language,

/**
* @param {*} req
* @returns {string} userAgent
*/
getUserAgent: () => navigator && navigator.userAgent
}

export default USER_INTERFACE;

0 comments on commit c2c2a8b

Please sign in to comment.