cloudcommerce 0.33.2 → 0.33.4
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/CHANGELOG.md +23 -0
- package/ecomplus-stores/barra-doce/functions/many/package.json +3 -3
- package/ecomplus-stores/barra-doce/functions/ssr/package.json +6 -6
- package/ecomplus-stores/barra-doce/functions/with-apps/package.json +3 -3
- package/ecomplus-stores/barra-doce/package.json +2 -2
- package/ecomplus-stores/monocard/functions/many/package.json +3 -3
- package/ecomplus-stores/monocard/functions/ssr/package.json +6 -6
- package/ecomplus-stores/monocard/functions/with-apps/package.json +3 -3
- package/ecomplus-stores/monocard/package.json +2 -2
- package/package.json +2 -2
- package/packages/api/package.json +1 -1
- package/packages/apps/affilate-program/package.json +1 -1
- package/packages/apps/correios/package.json +1 -1
- package/packages/apps/custom-payment/package.json +1 -1
- package/packages/apps/custom-shipping/package.json +1 -1
- package/packages/apps/datafrete/package.json +1 -1
- package/packages/apps/discounts/package.json +1 -1
- package/packages/apps/emails/package.json +1 -1
- package/packages/apps/fb-conversions/package.json +1 -1
- package/packages/apps/flash-courier/package.json +1 -1
- package/packages/apps/frenet/package.json +1 -1
- package/packages/apps/galaxpay/package.json +1 -1
- package/packages/apps/google-analytics/package.json +1 -1
- package/packages/apps/jadlog/package.json +1 -1
- package/packages/apps/loyalty-points/package.json +1 -1
- package/packages/apps/mandae/package.json +1 -1
- package/packages/apps/melhor-envio/package.json +1 -1
- package/packages/apps/mercadopago/package.json +1 -1
- package/packages/apps/pagarme/package.json +1 -1
- package/packages/apps/pagarme-v5/package.json +1 -1
- package/packages/apps/paghiper/package.json +1 -1
- package/packages/apps/pix/package.json +1 -1
- package/packages/apps/tiny-erp/package.json +1 -1
- package/packages/apps/webhooks/package.json +1 -1
- package/packages/cli/package.json +1 -1
- package/packages/config/package.json +1 -1
- package/packages/emails/package.json +1 -1
- package/packages/eslint/package.json +1 -1
- package/packages/events/package.json +1 -1
- package/packages/feeds/package.json +1 -1
- package/packages/firebase/package.json +1 -1
- package/packages/i18n/lib/en_us/i19safeBuy.txt +1 -0
- package/packages/i18n/lib/en_us.d.ts +1 -0
- package/packages/i18n/lib/en_us.js +1 -0
- package/packages/i18n/lib/en_us.js.map +1 -1
- package/packages/i18n/lib/pt_br/i19safeBuy.txt +1 -0
- package/packages/i18n/lib/pt_br.d.ts +1 -0
- package/packages/i18n/lib/pt_br.js +1 -0
- package/packages/i18n/lib/pt_br.js.map +1 -1
- package/packages/i18n/package.json +1 -1
- package/packages/i18n/src/en_us.ts +1 -0
- package/packages/i18n/src/pt_br.ts +1 -0
- package/packages/modules/lib/firebase/checkout.js +1 -1
- package/packages/modules/lib/firebase/checkout.js.map +1 -1
- package/packages/modules/package.json +1 -1
- package/packages/modules/src/firebase/checkout.ts +2 -2
- package/packages/passport/package.json +1 -1
- package/packages/ssr/lib/analytics-events.js +33 -5
- package/packages/ssr/lib/analytics-events.js.map +1 -1
- package/packages/ssr/lib/analytics-providers/google-analytics.js +48 -0
- package/packages/ssr/lib/analytics-providers/google-analytics.js.map +1 -0
- package/packages/ssr/lib/analytics-providers/meta-conversions-api.js +44 -0
- package/packages/ssr/lib/analytics-providers/meta-conversions-api.js.map +1 -0
- package/packages/ssr/lib/firebase/serve-storefront.js +16 -12
- package/packages/ssr/lib/firebase/serve-storefront.js.map +1 -1
- package/packages/ssr/package.json +3 -1
- package/packages/ssr/src/analytics-events.ts +45 -5
- package/packages/ssr/src/analytics-providers/google-analytics.ts +67 -0
- package/packages/ssr/src/analytics-providers/meta-conversions-api.ts +57 -0
- package/packages/ssr/src/firebase/serve-storefront.ts +17 -12
- package/packages/storefront/package.json +1 -1
- package/packages/storefront/src/analytics/event-to-fbq.ts +3 -0
- package/packages/storefront/src/analytics/event-to-ttq.ts +89 -10
- package/packages/storefront/src/lib/scripts/push-analytics-events.ts +15 -0
- package/packages/storefront/src/lib/scripts/vbeta-app.ts +172 -0
- package/packages/storefront/src/lib/state/shopping-cart.ts +7 -5
- package/packages/test-base/package.json +1 -1
- package/packages/types/package.json +1 -1
|
@@ -9,6 +9,7 @@ import {
|
|
|
9
9
|
} from '@@sf/state/use-analytics';
|
|
10
10
|
import afetch from '../../helpers/afetch';
|
|
11
11
|
import parseGtagToFbq from '../../analytics/event-to-fbq';
|
|
12
|
+
import parseGtagToTtq from '../../analytics/event-to-ttq';
|
|
12
13
|
|
|
13
14
|
type AnalyticsEvent = {
|
|
14
15
|
type: 'gtag' | 'fbq' | 'ttq',
|
|
@@ -40,10 +41,12 @@ if (!import.meta.env.SSR) {
|
|
|
40
41
|
gtag,
|
|
41
42
|
dataLayer,
|
|
42
43
|
fbq,
|
|
44
|
+
ttq,
|
|
43
45
|
} = window as {
|
|
44
46
|
gtag?: Gtag.Gtag,
|
|
45
47
|
dataLayer?: Array<any>,
|
|
46
48
|
fbq?: (action: string, value: string, payload?: any) => any,
|
|
49
|
+
ttq?: { page: () => any, track: (value: string, payload?: any) => any },
|
|
47
50
|
};
|
|
48
51
|
if (typeof gtag === 'function') {
|
|
49
52
|
gtag('event', name, params);
|
|
@@ -60,6 +63,18 @@ if (!import.meta.env.SSR) {
|
|
|
60
63
|
fbq('track', fbqEvent.name, fbqEvent.params);
|
|
61
64
|
}
|
|
62
65
|
});
|
|
66
|
+
const ttqEvents = await parseGtagToTtq(evMessage);
|
|
67
|
+
ttqEvents.forEach((ttqEvent) => {
|
|
68
|
+
if (!ttqEvent.name) return;
|
|
69
|
+
sendServerEvent({ type: 'ttk', ...ttqEvent });
|
|
70
|
+
if (typeof ttq?.page === 'function') {
|
|
71
|
+
if (ttqEvent.name === 'PageView') {
|
|
72
|
+
ttq.page();
|
|
73
|
+
} else {
|
|
74
|
+
ttq.track(ttqEvent.name, ttqEvent.params);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
});
|
|
63
78
|
});
|
|
64
79
|
|
|
65
80
|
let lastPageLocation = '';
|
|
@@ -1,11 +1,182 @@
|
|
|
1
|
+
import type { Orders, Customers } from '@cloudcommerce/api/types';
|
|
1
2
|
import { watch } from 'vue';
|
|
3
|
+
import { phone as getPhone } from '@ecomplus/utils';
|
|
2
4
|
import {
|
|
3
5
|
session,
|
|
4
6
|
isAuthenticated,
|
|
5
7
|
customer,
|
|
8
|
+
customerName,
|
|
6
9
|
} from '@@sf/state/customer-session';
|
|
10
|
+
import { shoppingCart } from '@@sf/state/shopping-cart';
|
|
11
|
+
import { emitGtagEvent, getGtagItem } from '@@sf/state/use-analytics';
|
|
7
12
|
import utm from '@@sf/scripts/session-utm';
|
|
8
13
|
|
|
14
|
+
const watchAppRoutes = () => {
|
|
15
|
+
const router = (window as any).storefrontApp?.router;
|
|
16
|
+
if (router) {
|
|
17
|
+
const getCouponApplied = () => {
|
|
18
|
+
return sessionStorage.getItem('st_discount_coupon') || undefined;
|
|
19
|
+
};
|
|
20
|
+
const fixMoneyValue = (value: number) => {
|
|
21
|
+
return Math.round(value * 100) / 100;
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
const emittedCheckoutSteps: Array<
|
|
25
|
+
'view_cart' | 'begin_checkout' |
|
|
26
|
+
'add_payment_info' | 'add_shipping_info'
|
|
27
|
+
> = [];
|
|
28
|
+
const emitCheckout = (
|
|
29
|
+
evName: typeof emittedCheckoutSteps[0],
|
|
30
|
+
params?: Gtag.EventParams,
|
|
31
|
+
) => {
|
|
32
|
+
if (emittedCheckoutSteps.includes(evName)) return;
|
|
33
|
+
emittedCheckoutSteps.push(evName);
|
|
34
|
+
if (!params) {
|
|
35
|
+
params = {
|
|
36
|
+
value: fixMoneyValue(shoppingCart.value.subtotal),
|
|
37
|
+
items: shoppingCart.value.items.map(getGtagItem),
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
if (evName !== 'view_cart') {
|
|
41
|
+
params.coupon = getCouponApplied();
|
|
42
|
+
if (!emittedCheckoutSteps.includes('begin_checkout')) {
|
|
43
|
+
emitCheckout('begin_checkout');
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
emitGtagEvent(evName, params);
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
let isPurchaseSent = false;
|
|
50
|
+
const emitPurchase = (orderId: string, orderJson?: string) => {
|
|
51
|
+
if (!isPurchaseSent) {
|
|
52
|
+
if (localStorage.getItem('gtag.orderIdSent') !== orderId) {
|
|
53
|
+
let order: Orders | undefined;
|
|
54
|
+
if (orderJson) {
|
|
55
|
+
try {
|
|
56
|
+
order = JSON.parse(orderJson);
|
|
57
|
+
} catch {
|
|
58
|
+
//
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
const { amount } = (order || (window as any).storefrontApp) as {
|
|
62
|
+
amount?: Orders['amount'],
|
|
63
|
+
};
|
|
64
|
+
const params: Gtag.EventParams = {
|
|
65
|
+
transaction_id: orderId,
|
|
66
|
+
value: fixMoneyValue(amount?.total || shoppingCart.value.subtotal),
|
|
67
|
+
items: shoppingCart.value.items.map(getGtagItem),
|
|
68
|
+
coupon: order
|
|
69
|
+
? order.extra_discount?.discount_coupon
|
|
70
|
+
: getCouponApplied(),
|
|
71
|
+
};
|
|
72
|
+
if (amount) {
|
|
73
|
+
if (amount.freight !== undefined) {
|
|
74
|
+
params.shipping = fixMoneyValue(amount.freight);
|
|
75
|
+
}
|
|
76
|
+
if (amount.tax !== undefined) {
|
|
77
|
+
params.tax = fixMoneyValue(amount.tax);
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
let purchaseTimeout = 1;
|
|
81
|
+
const { dataLayer, __sendGTMExtraPurchaseData } = (window as any);
|
|
82
|
+
if (dataLayer && __sendGTMExtraPurchaseData) {
|
|
83
|
+
const extraPurchaseData: Record<string, any> = {};
|
|
84
|
+
let shippingAddr: Exclude<Customers['addresses'], undefined>[0] | undefined;
|
|
85
|
+
if (customer) {
|
|
86
|
+
extraPurchaseData.customerDisplayName = customerName.value;
|
|
87
|
+
let customerFullName = customer.value.name;
|
|
88
|
+
if (!customerFullName?.given_name) {
|
|
89
|
+
try {
|
|
90
|
+
const storedCustomer = sessionStorage.getItem('ecomCustomerAccount');
|
|
91
|
+
if (storedCustomer) {
|
|
92
|
+
const sessionCustomer = JSON.parse(storedCustomer);
|
|
93
|
+
if (typeof sessionCustomer === 'object' && sessionCustomer) {
|
|
94
|
+
customerFullName = sessionCustomer.name;
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
} catch {
|
|
98
|
+
//
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
if (customerFullName) {
|
|
102
|
+
extraPurchaseData.customerGivenName = customerFullName.given_name;
|
|
103
|
+
extraPurchaseData.customerFamilyName = customerFullName.family_name;
|
|
104
|
+
}
|
|
105
|
+
extraPurchaseData.customerEmail = customer.value.main_email;
|
|
106
|
+
extraPurchaseData.customerPhone = getPhone(customer.value);
|
|
107
|
+
shippingAddr = customer.value.addresses?.[0];
|
|
108
|
+
}
|
|
109
|
+
try {
|
|
110
|
+
const storedAddr = sessionStorage.getItem('ecomCustomerAddress');
|
|
111
|
+
if (storedAddr) {
|
|
112
|
+
const sessionShippingAddr = JSON.parse(storedAddr);
|
|
113
|
+
if (typeof shippingAddr === 'object' && shippingAddr) {
|
|
114
|
+
Object.assign(shippingAddr, sessionShippingAddr);
|
|
115
|
+
} else {
|
|
116
|
+
shippingAddr = sessionShippingAddr;
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
} catch {
|
|
120
|
+
//
|
|
121
|
+
}
|
|
122
|
+
if (shippingAddr && shippingAddr.zip) {
|
|
123
|
+
extraPurchaseData.shippingAddrZip = shippingAddr.zip;
|
|
124
|
+
extraPurchaseData.shippingAddrStreet = shippingAddr.street;
|
|
125
|
+
extraPurchaseData.shippingAddrNumber = shippingAddr.number;
|
|
126
|
+
if (shippingAddr.street && shippingAddr.number) {
|
|
127
|
+
extraPurchaseData.shippingAddrStreet += `, ${shippingAddr.number}`;
|
|
128
|
+
}
|
|
129
|
+
extraPurchaseData.shippingAddrCity = shippingAddr.city;
|
|
130
|
+
extraPurchaseData.shippingAddrProvinceCode = shippingAddr.province_code;
|
|
131
|
+
}
|
|
132
|
+
dataLayer.push({
|
|
133
|
+
event: 'purchaseExtraData',
|
|
134
|
+
...extraPurchaseData,
|
|
135
|
+
});
|
|
136
|
+
purchaseTimeout = 100;
|
|
137
|
+
}
|
|
138
|
+
setTimeout(() => emitGtagEvent('purchase', params), purchaseTimeout);
|
|
139
|
+
localStorage.setItem('gtag.orderIdSent', orderId);
|
|
140
|
+
}
|
|
141
|
+
isPurchaseSent = true;
|
|
142
|
+
}
|
|
143
|
+
};
|
|
144
|
+
|
|
145
|
+
let emitPurchaseTimer: NodeJS.Timeout | undefined;
|
|
146
|
+
const parseRouteToGtag = ({ name, params }) => {
|
|
147
|
+
switch (name) {
|
|
148
|
+
case 'cart':
|
|
149
|
+
emitCheckout('view_cart');
|
|
150
|
+
break;
|
|
151
|
+
case 'checkout':
|
|
152
|
+
if (!params.step) {
|
|
153
|
+
emitCheckout('begin_checkout');
|
|
154
|
+
} else if (Number(params.step) === 1) {
|
|
155
|
+
emitCheckout('add_shipping_info');
|
|
156
|
+
} else if (Number(params.step) === 2) {
|
|
157
|
+
emitCheckout('add_payment_info');
|
|
158
|
+
}
|
|
159
|
+
break;
|
|
160
|
+
case 'confirmation':
|
|
161
|
+
clearTimeout(emitPurchaseTimer);
|
|
162
|
+
if (params.json) {
|
|
163
|
+
emitPurchase(params.id, decodeURIComponent(params.json));
|
|
164
|
+
} else {
|
|
165
|
+
emitPurchaseTimer = setTimeout(() => {
|
|
166
|
+
emitPurchase(params.id);
|
|
167
|
+
}, 1500);
|
|
168
|
+
}
|
|
169
|
+
break;
|
|
170
|
+
default:
|
|
171
|
+
}
|
|
172
|
+
};
|
|
173
|
+
if (router.currentRoute) {
|
|
174
|
+
parseRouteToGtag(router.currentRoute);
|
|
175
|
+
}
|
|
176
|
+
router.afterEach(parseRouteToGtag);
|
|
177
|
+
}
|
|
178
|
+
};
|
|
179
|
+
|
|
9
180
|
// https://github.com/ecomplus/storefront/tree/master/%40ecomplus/storefront-app compat
|
|
10
181
|
if (!import.meta.env.SSR) {
|
|
11
182
|
if (Object.keys(utm).length) {
|
|
@@ -49,6 +220,7 @@ if (!import.meta.env.SSR) {
|
|
|
49
220
|
}, {
|
|
50
221
|
immediate: true,
|
|
51
222
|
});
|
|
223
|
+
setTimeout(watchAppRoutes, 400);
|
|
52
224
|
};
|
|
53
225
|
|
|
54
226
|
const appScript = document.createElement('script');
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import type { Products, CartSet, SearchItem } from '@cloudcommerce/api/types';
|
|
2
|
-
import { computed
|
|
2
|
+
import { computed } from 'vue';
|
|
3
|
+
import { watchDebounced } from '@vueuse/core';
|
|
3
4
|
import mitt from 'mitt';
|
|
4
5
|
import useStorage from '@@sf/state/use-storage';
|
|
5
6
|
import addItem from '@@sf/state/shopping-cart/add-cart-item';
|
|
@@ -107,7 +108,7 @@ type CartEvent = {
|
|
|
107
108
|
const cartEmitter = mitt<CartEvent>();
|
|
108
109
|
const cloneItems = () => shoppingCart.value.items.map((item) => ({ ...item }));
|
|
109
110
|
let oldItems = cloneItems();
|
|
110
|
-
|
|
111
|
+
watchDebounced(shoppingCart, ({ items }) => {
|
|
111
112
|
['addCartItem' as const, 'removeCartItem' as const].forEach((evName) => {
|
|
112
113
|
const isAdd = evName === 'addCartItem';
|
|
113
114
|
const baseItems = isAdd ? items : oldItems;
|
|
@@ -115,16 +116,17 @@ watch(shoppingCart, ({ items }) => {
|
|
|
115
116
|
baseItems.forEach((baseItem) => {
|
|
116
117
|
if (!baseItem.quantity) return;
|
|
117
118
|
const compareItem = compareItems.find(({ _id }) => _id === baseItem._id);
|
|
118
|
-
|
|
119
|
+
const compareQnt = compareItem?.quantity || 0;
|
|
120
|
+
if (baseItem.quantity > compareQnt) {
|
|
119
121
|
cartEmitter.emit(evName, {
|
|
120
122
|
...baseItem,
|
|
121
|
-
quantity: baseItem.quantity -
|
|
123
|
+
quantity: baseItem.quantity - compareQnt,
|
|
122
124
|
});
|
|
123
125
|
}
|
|
124
126
|
});
|
|
125
127
|
});
|
|
126
128
|
oldItems = cloneItems();
|
|
127
|
-
});
|
|
129
|
+
}, { debounce: 200 });
|
|
128
130
|
|
|
129
131
|
export const cartEvents = {
|
|
130
132
|
on: cartEmitter.on,
|