@akinon/projectzero 1.28.0-rc.0 → 1.29.0-rc.2

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 CHANGED
@@ -1,5 +1,13 @@
1
1
  # @akinon/projectzero
2
2
 
3
+ ## 1.29.0-rc.2
4
+
5
+ ### Minor Changes
6
+
7
+ - 495d155: ZERO-2563: The create command cli now doesnt get it from bitbucket but clones the repository from a localized clone version
8
+
9
+ ## 1.28.0-rc.1
10
+
3
11
  ## 1.28.0-rc.0
4
12
 
5
13
  ### Minor Changes
@@ -1,5 +1,44 @@
1
1
  # projectzeronext
2
2
 
3
+ ## 1.29.0-rc.2
4
+
5
+ ### Minor Changes
6
+
7
+ - aafd9fe: BRDG-9228: Removed the inside of the catch blocks that has console.errors
8
+ - 42320c2: ZERO-2516: Add if there are errors in the OTP login
9
+ - 091d7ad: ZERO-2480: Refactor carousel component
10
+ - 495d155: ZERO-2563: The create command cli now doesnt get it from bitbucket but clones the repository from a localized clone version
11
+ - a892946: ZERO-2501: Update next.config.js to ES module compatible next.config.mjs format
12
+ - f76f079: ZERO-2493: Add redirect util function
13
+ - ce60543: ZERO-2517: Make metadata alternate languages ​​values ​​dynamic
14
+
15
+ ### Patch Changes
16
+
17
+ - 95686ad: ZERO-2582: Fix dependency versions
18
+ - Updated dependencies [a7e432f]
19
+ - Updated dependencies [42320c2]
20
+ - Updated dependencies [495d155]
21
+ - Updated dependencies [495d155]
22
+ - Updated dependencies [f76f079]
23
+ - @akinon/next@1.29.0-rc.2
24
+ - @akinon/pz-otp@1.29.0-rc.2
25
+ - @akinon/pz-b2b@1.29.0-rc.2
26
+ - @akinon/pz-gpay@1.29.0-rc.2
27
+ - @akinon/pz-masterpass@1.29.0-rc.2
28
+ - @akinon/pz-one-click-checkout@1.29.0-rc.2
29
+
30
+ ## 1.28.0-rc.1
31
+
32
+ ### Patch Changes
33
+
34
+ - 95686ad: ZERO-2582: Fix dependency versions
35
+ - @akinon/next@1.28.0-rc.1
36
+ - @akinon/pz-b2b@1.28.0-rc.1
37
+ - @akinon/pz-gpay@1.28.0-rc.1
38
+ - @akinon/pz-masterpass@1.28.0-rc.1
39
+ - @akinon/pz-one-click-checkout@1.28.0-rc.1
40
+ - @akinon/pz-otp@1.28.0-rc.1
41
+
3
42
  ## 1.28.0-rc.0
4
43
 
5
44
  ### Minor Changes
@@ -1,9 +1,6 @@
1
- const withPWA = require('next-pwa')({
2
- dest: 'public',
3
- disable: process.env.NODE_ENV === 'development'
4
- });
5
- const { withSentryConfig } = require('@sentry/nextjs');
6
- const withPzConfig = require('@akinon/next/with-pz-config');
1
+ import withPWA from 'next-pwa';
2
+ import { withSentryConfig } from '@sentry/nextjs';
3
+ import withPzConfig from '@akinon/next/with-pz-config.js';
7
4
 
8
5
  /** @type {import('next').NextConfig} */
9
6
  const nextConfig = {
@@ -22,9 +19,16 @@ const nextConfig = {
22
19
  }
23
20
  };
24
21
 
25
- const enhancedConfig = withPzConfig(nextConfig);
22
+ const withPwaConfig = withPWA({
23
+ dest: 'public',
24
+ disable: process.env.NODE_ENV === 'development'
25
+ });
26
26
 
27
- module.exports = withSentryConfig(withPWA(enhancedConfig), {
27
+ const sentryConfig = {
28
28
  silent: true,
29
29
  dryRun: !process.env.SENTRY_DSN
30
- });
30
+ };
31
+
32
+ const enhancedConfig = withPzConfig(nextConfig);
33
+
34
+ export default withSentryConfig(withPwaConfig(enhancedConfig), sentryConfig);
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "projectzeronext",
3
- "version": "1.28.0-rc.0",
3
+ "version": "1.29.0-rc.2",
4
4
  "private": true,
5
5
  "license": "MIT",
6
6
  "scripts": {
@@ -22,12 +22,12 @@
22
22
  "prestart": "pz-prestart"
23
23
  },
24
24
  "dependencies": {
25
- "@akinon/next": "1.26.0",
26
- "@akinon/pz-b2b": "1.26.0",
27
- "@akinon/pz-gpay": "1.26.0",
28
- "@akinon/pz-masterpass": "1.26.0",
29
- "@akinon/pz-one-click-checkout": "1.26.0",
30
- "@akinon/pz-otp": "1.26.0",
25
+ "@akinon/next": "1.29.0-rc.2",
26
+ "@akinon/pz-b2b": "1.29.0-rc.2",
27
+ "@akinon/pz-gpay": "1.29.0-rc.2",
28
+ "@akinon/pz-masterpass": "1.29.0-rc.2",
29
+ "@akinon/pz-one-click-checkout": "1.29.0-rc.2",
30
+ "@akinon/pz-otp": "1.29.0-rc.2",
31
31
  "@hookform/resolvers": "2.9.0",
32
32
  "@next/third-parties": "14.1.0",
33
33
  "@react-google-maps/api": "2.17.1",
@@ -51,7 +51,7 @@
51
51
  "yup": "0.32.11"
52
52
  },
53
53
  "devDependencies": {
54
- "@akinon/eslint-plugin-projectzero": "1.26.0",
54
+ "@akinon/eslint-plugin-projectzero": "1.29.0-rc.2",
55
55
  "@semantic-release/changelog": "6.0.2",
56
56
  "@semantic-release/exec": "6.0.3",
57
57
  "@semantic-release/git": "10.0.1",
@@ -91,5 +91,10 @@
91
91
  "submit": "Sign In",
92
92
  "quick_login": "Quick Login"
93
93
  }
94
+ },
95
+ "otp_login": {
96
+ "form": {
97
+ "error_code": "The verification code you entered is incorrect."
98
+ }
94
99
  }
95
100
  }
@@ -91,5 +91,10 @@
91
91
  "submit": "Giriş Yap",
92
92
  "quick_login": "Hızlı Giriş"
93
93
  }
94
+ },
95
+ "otp_login": {
96
+ "form": {
97
+ "error_code": "Girdiğiniz doğrulama kodu hatalıdır."
98
+ }
94
99
  }
95
100
  }
@@ -1,12 +1,8 @@
1
1
  import AccountBackButton from '@theme/views/account/back-button';
2
2
  import AccountMenu from '@theme/views/account/account-menu';
3
3
  import { getServerSession } from 'next-auth/next';
4
- import { redirect } from 'next/navigation';
5
4
  import { ROUTES } from 'routes';
6
- import { headers } from 'next/headers';
7
- import { ServerVariables } from '@akinon/next/utils/server-variables';
8
- import { getUrlPathWithLocale } from '@akinon/next/utils/localization';
9
- import Settings from 'settings';
5
+ import { redirect } from '@akinon/next/utils/redirect';
10
6
 
11
7
  export default async function AccountLayout({
12
8
  children
@@ -15,25 +11,8 @@ export default async function AccountLayout({
15
11
  }) {
16
12
  const session = await getServerSession();
17
13
 
18
- const nextHeaders = headers();
19
- const pageUrl = new URL(
20
- nextHeaders.get('pz-url') ?? process.env.NEXT_PUBLIC_URL
21
- );
22
-
23
- const currentLocale = Settings.localization.locales.find(
24
- (locale) => locale.value === ServerVariables.locale
25
- );
26
-
27
14
  if (!session?.user) {
28
- const callbackUrl = pageUrl.pathname;
29
- const authRoute = getUrlPathWithLocale(
30
- ROUTES.AUTH,
31
- currentLocale.localePath ?? currentLocale.value
32
- );
33
-
34
- const redirectUrl = `${authRoute}?callbackUrl=${callbackUrl}`;
35
-
36
- return redirect(redirectUrl);
15
+ return redirect(ROUTES.AUTH);
37
16
  }
38
17
 
39
18
  return (
@@ -12,6 +12,7 @@ import PzRoot from '@akinon/next/components/pz-root';
12
12
  import MobileAppToggler from '@akinon/next/components/mobile-app-toggler';
13
13
  import pwaTags from '@theme/components/pwa-tags';
14
14
  import type { Viewport } from 'next';
15
+ import settings from '@theme/settings';
15
16
 
16
17
  export const viewport: Viewport = {
17
18
  width: 'device-width',
@@ -22,12 +23,15 @@ export const viewport: Viewport = {
22
23
  };
23
24
 
24
25
  export async function generateMetadata() {
26
+ const { locales } = settings.localization;
27
+
28
+ const languages = locales.map(({ localePath }) => ({
29
+ [localePath]: `/${localePath}`
30
+ }));
31
+
25
32
  let result: Metadata = {
26
33
  alternates: {
27
- languages: {
28
- en: '/en',
29
- tr: '/tr'
30
- }
34
+ languages: languages.reduce((acc, cur) => ({ ...acc, ...cur }), {})
31
35
  }
32
36
  };
33
37
 
@@ -177,6 +177,10 @@ const CheckoutCompleted = ({
177
177
  swipeable={true}
178
178
  arrows={false}
179
179
  itemClass="pr-[50px]"
180
+ containerAspectRatio={{
181
+ mobile: 460 / 88,
182
+ desktop: 637 / 88
183
+ }}
180
184
  >
181
185
  {data.order.orderitem_set.map((item) => (
182
186
  <div key={`order-item-${item.id}`} className="flex">
@@ -1,3 +1,42 @@
1
+ 'use client';
2
+
3
+ import { useEffect, useState } from 'react';
1
4
  import 'react-multi-carousel/lib/styles.css';
5
+ import Carousel, {
6
+ CarouselProps as BaseCarouselProps
7
+ } from 'react-multi-carousel';
8
+ import { forwardRef } from 'react';
9
+ import { useMediaQuery } from '@akinon/next/hooks';
10
+
11
+ type ContainerAspectRatioType = {
12
+ mobile: number;
13
+ desktop: number;
14
+ };
15
+
16
+ interface CarouselProps extends BaseCarouselProps {
17
+ containerAspectRatio: ContainerAspectRatioType;
18
+ }
19
+
20
+ const CarouselCore = forwardRef<Carousel, CarouselProps>((props, ref) => {
21
+ const { containerAspectRatio } = props;
22
+ const matches = useMediaQuery('(min-width: 768px)');
23
+ const [aspectRatio, setAspectRatio] = useState(containerAspectRatio.mobile);
24
+
25
+ useEffect(() => {
26
+ if (matches) {
27
+ setAspectRatio(containerAspectRatio.desktop);
28
+ } else {
29
+ setAspectRatio(containerAspectRatio.mobile);
30
+ }
31
+ }, [matches]);
32
+
33
+ return (
34
+ <div className="w-full" style={{ aspectRatio }}>
35
+ <Carousel {...props} ref={ref} />
36
+ </div>
37
+ );
38
+ });
39
+
40
+ CarouselCore.displayName = 'CarouselCore';
2
41
 
3
- export { default as CarouselCore } from 'react-multi-carousel';
42
+ export { CarouselCore };
@@ -72,7 +72,7 @@ export default function AccountMenu() {
72
72
  callbackUrl: '/'
73
73
  });
74
74
  })
75
- .catch((error) => console.error(error));
75
+ .catch();
76
76
  };
77
77
 
78
78
  return (
@@ -88,7 +88,7 @@ const AddressBox = ({
88
88
  .then((editAddressResponse) => {
89
89
  handleAddressClick(addressType, editAddressResponse);
90
90
  })
91
- .catch((error) => console.error(error));
91
+ .catch();
92
92
 
93
93
  setIsEditAddressModalOpen(false);
94
94
  };
@@ -84,7 +84,7 @@ const Addresses = () => {
84
84
  setSelectAddresses(addAddressResponse.pk);
85
85
  }
86
86
  })
87
- .catch((error) => console.error(error));
87
+ .catch();
88
88
 
89
89
  setIsModalOpen(false);
90
90
  };
@@ -12,6 +12,7 @@ import { useLocalization } from '@akinon/next/hooks';
12
12
  import { useOtpLoginMutation } from '@akinon/next/data/client/user';
13
13
  import { useAppSelector } from '@akinon/next/redux/hooks';
14
14
  import PluginModule, { Component } from '@akinon/next/components/plugin-module';
15
+ import { AuthError } from '@akinon/next/types';
15
16
 
16
17
  const loginFormSchema = (t) =>
17
18
  yup.object().shape({
@@ -42,11 +43,34 @@ export const OtpLogin = () => {
42
43
  const [formError, setFormError] = useState(null);
43
44
 
44
45
  const loginHandler: SubmitHandler<OtpLoginFormType> = async (data) => {
45
- return await signIn('default', {
46
+ const loginResponse = await signIn('default', {
46
47
  redirect: false,
47
48
  callbackUrl: '/',
48
49
  ...data
49
50
  } as SignInOptions);
51
+
52
+ if (loginResponse.error) {
53
+ const errors: AuthError[] = JSON.parse(loginResponse.error);
54
+
55
+ const fieldErrors = errors.find((error) => error.type === 'field_errors')
56
+ ?.data as { name: string; value: string[] }[];
57
+
58
+ const nonFieldErrors = errors.find(
59
+ (error) => error.type === 'non_field_errors'
60
+ )?.data as string[];
61
+
62
+ fieldErrors?.forEach((item) => {
63
+ if (item.name === 'error_code') {
64
+ setFormError(t('auth.otp_login.form.error_code'));
65
+ }
66
+ });
67
+
68
+ if (nonFieldErrors?.length) {
69
+ setFormError(nonFieldErrors.join(', '));
70
+ }
71
+
72
+ return;
73
+ }
50
74
  };
51
75
 
52
76
  const onSubmit = async (data: OtpLoginFormType) => {
@@ -118,7 +142,8 @@ export const OtpLogin = () => {
118
142
  props={{
119
143
  setShowPopup: setShowOtpModal,
120
144
  data: getValues(),
121
- submitAction: loginHandler
145
+ submitAction: loginHandler,
146
+ error: formError
122
147
  }}
123
148
  />
124
149
  )}
@@ -69,6 +69,7 @@ export default function ProductInfoSlider({ product }: ProductSliderItem) {
69
69
  arrows={false}
70
70
  swipeable={true}
71
71
  ref={carouselRef}
72
+ containerAspectRatio={{ mobile: 520 / 798, desktop: 372 / 573 }}
72
73
  className="w-full"
73
74
  >
74
75
  {product?.productimage_set?.map((item, i) => (
@@ -3,65 +3,52 @@
3
3
  import React from 'react';
4
4
  import { CarouselCore } from '@theme/components/carousel-core';
5
5
  import { Image, Link } from '@akinon/next/components';
6
- import { useMediaQuery } from '@akinon/next/hooks';
7
6
 
8
7
  export default function HomeHeroSliderContent({ data }) {
9
8
  const imageRatio = {
10
9
  mobile: 375 / 540,
11
10
  desktop: 1540 / 540
12
11
  };
13
- const matches = useMediaQuery('(min-width: 768px)');
14
- const [aspectRatio, setAspectRatio] = React.useState(imageRatio.mobile);
15
-
16
- React.useEffect(() => {
17
- if (matches) {
18
- setAspectRatio(imageRatio.desktop);
19
- } else {
20
- setAspectRatio(imageRatio.mobile);
21
- }
22
- }, [matches]);
23
12
 
24
13
  return (
25
- <div
26
- style={{
27
- aspectRatio
14
+ <CarouselCore
15
+ responsive={{
16
+ all: {
17
+ breakpoint: { max: 5000, min: 0 },
18
+ items: 1
19
+ }
20
+ }}
21
+ arrows={false}
22
+ swipeable={true}
23
+ containerAspectRatio={{
24
+ mobile: imageRatio.mobile,
25
+ desktop: imageRatio.desktop
28
26
  }}
29
27
  >
30
- <CarouselCore
31
- responsive={{
32
- all: {
33
- breakpoint: { max: 5000, min: 0 },
34
- items: 1
35
- }
36
- }}
37
- arrows={false}
38
- swipeable={true}
39
- >
40
- {data?.attributes?.hero_slider?.map((item, i) => (
41
- <div key={i}>
42
- <Link href={item.value.url}>
43
- <Image
44
- src={item.kwargs.value.mobile_image.url}
45
- alt={item.value.alt}
46
- aspectRatio={imageRatio.mobile}
47
- draggable={false}
48
- sizes="375px"
49
- fill
50
- className="block md:hidden"
51
- />
52
- <Image
53
- src={item.kwargs.value.image.url}
54
- alt={item.value.alt}
55
- aspectRatio={imageRatio.desktop}
56
- draggable={false}
57
- sizes="1540px"
58
- fill
59
- className="hidden md:block"
60
- />
61
- </Link>
62
- </div>
63
- ))}
64
- </CarouselCore>
65
- </div>
28
+ {data?.attributes?.hero_slider?.map((item, i) => (
29
+ <div key={i}>
30
+ <Link href={item.value.url}>
31
+ <Image
32
+ src={item.kwargs.value.mobile_image.url}
33
+ alt={item.value.alt}
34
+ aspectRatio={imageRatio.mobile}
35
+ draggable={false}
36
+ sizes="375px"
37
+ fill
38
+ className="block md:hidden"
39
+ />
40
+ <Image
41
+ src={item.kwargs.value.image.url}
42
+ alt={item.value.alt}
43
+ aspectRatio={imageRatio.desktop}
44
+ draggable={false}
45
+ sizes="1540px"
46
+ fill
47
+ className="hidden md:block"
48
+ />
49
+ </Link>
50
+ </div>
51
+ ))}
52
+ </CarouselCore>
66
53
  );
67
54
  }
@@ -57,6 +57,7 @@ export default function RecommendationContent({ data }) {
57
57
  responsive={responsive}
58
58
  arrows={false}
59
59
  itemClass="pr-2.5"
60
+ containerAspectRatio={{ mobile: 484 / 431, desktop: 1278 / 453 }}
60
61
  >
61
62
  {data?.products?.map((product, index) => (
62
63
  <div key={product.pk}>
@@ -30,6 +30,7 @@ export function SpecialPageCarousel(props: Props) {
30
30
  swipeable={true}
31
31
  showDots={true}
32
32
  itemClass="pr-2.5"
33
+ containerAspectRatio={{ mobile: 608 / 166, desktop: 1370 / 294 }}
33
34
  >
34
35
  {data.attributes.special_page_category.map((item, i) => (
35
36
  <div key={i.toString()}>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@akinon/projectzero",
3
- "version": "1.28.0-rc.0",
3
+ "version": "1.29.0-rc.2",
4
4
  "private": false,
5
5
  "description": "CLI tool to manage your Project Zero Next project",
6
6
  "bin": {