Unverified Commit d0b85f7d authored by Ruslan Konviser's avatar Ruslan Konviser Committed by GitHub
Browse files

Merge pull request #1323 from ever-co/feature/packages-updates

Feature/packages updates
parents 1fe5531f 2bacc543
Loading
Loading
Loading
Loading
+83 −75
Original line number Diff line number Diff line
version: 2.1

orbs:
    node: circleci/node@3.0.0
    node: circleci/node@4.1.0

aliases:
    - &install-node
      name: Install Node with NPM using NVM
      command: |
          echo 'export NVM_DIR="/opt/circleci/.nvm"' >> $BASH_ENV
          echo ' [ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"' >> $BASH_ENV
          nvm install v14
          nvm alias default v14
          source $BASH_ENV
          node --version

    - &install-gradle
      name: Install Gradle
      command: |
@@ -12,14 +22,18 @@ aliases:
          echo 'export GRADLE_HOME=/opt/gradle/gradle-4.0.2' >> $BASH_ENV
          echo 'export PATH=$PATH:/opt/gradle/gradle-4.0.2/bin' >> $BASH_ENV
          source $BASH_ENV

    - &install-deps
      name: Install Global Dependencies
      command: |
          sudo apt-get update
          sudo apt install npm
          sudo apt install build-essential
          sudo npm install --quiet node-gyp -g
          sudo npm install cordova -g
          sudo npm install ionic -g
          sudo npm config set python /usr/bin/python

    - &install-chrome
      name: Install Chrome
      command: |
@@ -28,14 +42,7 @@ aliases:
          sudo dpkg -i google-chrome.deb
          sudo sed -i 's|HERE/chrome\"|HERE/chrome\" --disable-setuid-sandbox|g' /opt/google/chrome/google-chrome
          rm google-chrome.deb
    - &install-gradle
      name: Install Gradle
      command: |
          wget https://services.gradle.org/distributions/gradle-4.0.2-bin.zip -P /tmp
          sudo unzip -d /opt/gradle /tmp/gradle-*.zip
          echo 'export GRADLE_HOME=/opt/gradle/gradle-4.0.2' >> $BASH_ENV
          echo 'export PATH=$PATH:/opt/gradle/gradle-4.0.2/bin' >> $BASH_ENV
          source $BASH_ENV

    - &install-yarn
      name: Install Latest Yarn
      command: |
@@ -45,17 +52,33 @@ aliases:
          rm -rf ~/.yarn
          curl -o- -L https://yarnpkg.com/install.sh | bash
          echo 'export PATH="${PATH}:${HOME}/.yarn/bin:${HOME}/.config/yarn/global/node_modules/.bin"' >> $BASH_ENV
          source $BASH_ENV

    - &install-android
      name: Install Android SDK
      command: |
          sudo apt update
          sudo apt install openjdk-8-jdk
          sudo apt-get update
          sudo apt-get remove openjdk*
          sudo apt-get clean
          sudo add-apt-repository -y ppa:openjdk-r/ppa
          sudo apt-get update
          sudo apt-get install -y openjdk-8-jdk
          sudo update-java-alternatives --set java-1.8.0-openjdk-amd64
          which java
          java -version
          sudo update-alternatives --install /usr/bin/java java /usr/lib/jvm/java-8-openjdk-amd64/jre/bin/java 1 --force
          sudo update-alternatives --set java /usr/lib/jvm/java-8-openjdk-amd64/jre/bin/java
          echo 'export JAVA_HOME=/usr/lib/jvm/java-8-openjdk-amd64' >> $BASH_ENV
          echo 'export PATH=$PATH:$JAVA_HOME/bin' >> $BASH_ENV
          source $BASH_ENV
          sudo apt install android-sdk
          export ANDROID_HOME=/usr/lib/android-sdk
          echo 'export ANDROID_SDK_ROOT="/usr/lib/android-sdk"' >> $BASH_ENV
          echo 'export ANDROID_HOME="/usr/lib/android-sdk"' >> $BASH_ENV
          source $BASH_ENV
          wget https://dl.google.com/android/repository/commandlinetools-linux-6609375_latest.zip
          unzip commandlinetools-linux-6609375_latest.zip -d cmdline-tools
          sudo mv cmdline-tools $ANDROID_HOME/
          export PATH=$ANDROID_HOME/cmdline-tools/tools/bin:$ANDROID_HOME/tools:$ANDROID_HOME/tools/bin:$ANDROID_HOME/platform-tools:$PATH
          echo 'export PATH=$ANDROID_HOME/cmdline-tools/tools/bin:$ANDROID_HOME/tools:$ANDROID_HOME/tools/bin:$ANDROID_HOME/platform-tools:$PATH' >> $BASH_ENV
          mkdir ~/.android && echo '### User Sources for Android SDK Manager' > ~/.android/repositories.cfg
          sudo chown -R $(whoami) $ANDROID_HOME
          echo "Installing SDK tools"
@@ -74,6 +97,13 @@ aliases:
          yes | sdkmanager --licenses --sdk_root=${ANDROID_HOME} || true
          echo "Updating SDK and accepting licenses"
          yes | sudo /usr/lib/android-sdk/cmdline-tools/tools/bin/sdkmanager --update --sdk_root=${ANDROID_HOME} || true
          source $BASH_ENV
          echo $JAVA_HOME
          echo $PATH
          echo $ANDROID_HOME
          echo $ANDROID_SDK_ROOT
          which java
          java -version

defaults: &defaults
    # put here anything which is common between all jobs
@@ -81,6 +111,7 @@ defaults: &defaults
    working_directory: /tmp/workspace
    environment:
        JVM_OPTS: -Xmx4096m
        JAVA_HOME: /usr/lib/jvm/java-8-openjdk-amd64
        ANDROID_HOME: /usr/lib/android-sdk

jobs:
@@ -88,12 +119,10 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/monorepo-root
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - checkout
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run:
@@ -107,6 +136,7 @@ jobs:
                      - yarn-packages-monorepo-root-{{ checksum "yarn.lock" }}
            - run:
                  name: Run Bootstrap
                  no_output_timeout: 60m
                  command: yarn bootstrap
                  no_output_timeout: 60m
            - run:
@@ -128,12 +158,10 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/backend/api
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - checkout
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run:
@@ -147,6 +175,7 @@ jobs:
                      - yarn-packages-backend-api-{{ checksum "yarn.lock" }}
            - run:
                  name: Run Bootstrap
                  no_output_timeout: 60m
                  command: yarn bootstrap
                  no_output_timeout: 60m
            - run:
@@ -170,12 +199,10 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/admin/website-angular
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - checkout
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run:
@@ -189,6 +216,7 @@ jobs:
                      - yarn-packages-admin-website-angular-{{ checksum "yarn.lock" }}
            - run:
                  name: Run Bootstrap
                  no_output_timeout: 60m
                  command: yarn bootstrap
                  no_output_timeout: 60m
            - run:
@@ -212,16 +240,12 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/carrier/mobile-ionic
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - checkout
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run:
                  name: Install Yarn
                  command: sudo npm install -g yarn --force
            - run: *install-yarn
            - run: *install-android
            - run: *install-gradle
            - run:
@@ -235,6 +259,7 @@ jobs:
                      - yarn-packages-carrier-mobile-ionic-{{ checksum "yarn.lock" }}
            - run:
                  name: Run Bootstrap
                  no_output_timeout: 60m
                  command: yarn bootstrap
                  no_output_timeout: 60m
            - run:
@@ -282,16 +307,12 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/shop/mobile-ionic
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - checkout
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run:
                  name: Install Yarn
                  command: sudo npm install -g yarn --force
            - run: *install-yarn
            - run: *install-android
            - run: *install-gradle
            - run:
@@ -305,6 +326,7 @@ jobs:
                      - yarn-packages-shop-mobile-ionic-{{ checksum "yarn.lock" }}
            - run:
                  name: Run Bootstrap
                  no_output_timeout: 60m
                  command: yarn bootstrap
                  no_output_timeout: 60m
            - run:
@@ -352,12 +374,10 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/shop/website-angular
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - checkout
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run:
@@ -371,6 +391,7 @@ jobs:
                      - yarn-packages-shop-website-angular-{{ checksum "yarn.lock" }}
            - run:
                  name: Run Bootstrap
                  no_output_timeout: 60m
                  command: yarn bootstrap
                  no_output_timeout: 60m
            - run:
@@ -394,16 +415,12 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/merchant/tablet-ionic
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - checkout
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run:
                  name: Install Yarn
                  command: sudo npm install -g yarn --force
            - run: *install-yarn
            - run: *install-android
            - run: *install-gradle
            - run:
@@ -417,6 +434,7 @@ jobs:
                      - yarn-packages-merchant-tablet-ionic-{{ checksum "yarn.lock" }}
            - run:
                  name: Run Bootstrap
                  no_output_timeout: 60m
                  command: yarn bootstrap
                  no_output_timeout: 60m
            - run:
@@ -464,11 +482,9 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/carrier/mobile-ionic
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run: *install-chrome
@@ -496,11 +512,9 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/shop/mobile-ionic
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run: *install-chrome
@@ -528,11 +542,9 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/shop/website-angular
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run: *install-chrome
@@ -560,11 +572,9 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/admin/website-angular
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run: *install-chrome
@@ -592,11 +602,9 @@ jobs:
        <<: *defaults
        working_directory: /tmp/workspace/backend/api
        machine:
            image: ubuntu-1604:202004-01
            image: ubuntu-2004:202010-01
        steps:
            - node/install:
                  install-yarn: true
                  node-version: latest
            - run: *install-node
            - run: *install-deps
            - run: *install-yarn
            - run: *install-chrome
+100 −29
Original line number Diff line number Diff line
FROM node:alpine AS development
# Ever Demand Platform Admin UI (Angular)

RUN apk update \
ARG API_BASE_URL
ARG API_HOST
ARG API_PORT
ARG CLIENT_BASE_URL
ARG SENTRY_DSN
ARG CHATWOOT_SDK_TOKEN
ARG CLOUDINARY_CLOUD_NAME
ARG CLOUDINARY_API_KEY
ARG GOOGLE_MAPS_API_KEY
ARG GOOGLE_PLACE_AUTOCOMPLETE
ARG DEFAULT_LATITUDE
ARG DEFAULT_LONGITUDE
ARG DEFAULT_CURRENCY
ARG DEMO
ARG WEB_HOST
ARG WEB_PORT

FROM node:16-alpine3.11 AS dependencies

LABEL maintainer="ever@ever.co"

ENV CI=true

RUN apk --update add bash \
	&& apk add libexecinfo libexecinfo-dev \
	&& npm i -g npm \
	&& apk --no-cache add --virtual builds-deps build-base \
	snappy g++ snappy-dev gcc libgcc libstdc++ linux-headers autoconf automake make nasm python git \
	&& apk add --no-cache --virtual build-dependencies build-base \
	snappy dos2unix g++ snappy-dev gcc libgcc libstdc++ linux-headers autoconf automake make nasm python2 py2-setuptools vips-dev git \
	&& npm install --quiet node-gyp -g \
	&& npm config set python /usr/bin/python \
	&& npm install yarn -g --force
	&& npm install yarn -g --force \
	&& mkdir /srv/ever && chown -R node:node /srv/ever

RUN mkdir /srv/ever && chown node:node /srv/ever
COPY wait .deploy/admin-web-angular/entrypoint.compose.sh .deploy/admin-web-angular/entrypoint.prod.sh /

USER node
RUN chmod +x /wait /entrypoint.compose.sh /entrypoint.prod.sh && dos2unix /entrypoint.compose.sh && dos2unix /entrypoint.prod.sh

USER node:node

WORKDIR /srv/ever

COPY --chown=node:node package.json yarn.lock lerna.json package.workspaces.json ./
COPY --chown=node:node package.json yarn.lock lerna.json package.workspaces.json tsconfig.base.json ./
COPY --chown=node:node packages/admin-web-angular/package.json ./packages/admin-web-angular/package.json
COPY --chown=node:node .snyk ./.snyk
COPY --chown=node:node packages/common ./packages/common
COPY --chown=node:node packages/common-angular ./packages/common-angular
COPY --chown=node:node packages/common/package.json ./packages/common/package.json
COPY --chown=node:node packages/common-angular/package.json ./packages/common-angular/package.json

RUN yarn bootstrap && yarn cache clean

RUN yarn install
FROM node:16-alpine3.11 AS development

FROM node:alpine AS production
USER node:node

RUN npm install cross-env -g
WORKDIR /srv/ever

RUN mkdir /srv/ever && chown node:node /srv/ever
RUN mkdir -p /srv/ever/packages/admin-web-angular && chown node:node /srv/ever/packages/admin-web-angular
RUN mkdir -p /srv/ever/packages/common && chown node:node /srv/ever/packages/common
RUN mkdir -p /srv/ever/packages/common-angular && chown node:node /srv/ever/packages/common-angular
COPY --chown=node:node --from=dependencies /wait /entrypoint.compose.sh /entrypoint.prod.sh /
COPY --chown=node:node --from=dependencies /srv/ever .
COPY . .

USER node
FROM node:16-alpine3.11 AS build

WORKDIR /srv/ever

ARG NODE_OPTIONS="--max-old-space-size=2048"
ENV NODE_OPTIONS $NODE_OPTIONS
ENV NODE_ENV production
RUN mkdir dist

COPY --from=development --chown=node:node /srv/ever/node_modules ./node_modules
COPY --from=development --chown=node:node /srv/ever/packages/common/node_modules ./packages/common/node_modules
COPY --from=development --chown=node:node /srv/ever/packages/common-angular/node_modules ./packages/common-angular/node_modules
COPY --from=development --chown=node:node /srv/ever/packages/admin-web-angular/node_modules ./packages/admin-web-angular/node_modules
COPY --chown=node:node package.json yarn.lock lerna.json package.workspaces.json tsconfig.base.json ./
COPY --chown=node:node packages/common ./packages/common
COPY --chown=node:node packages/common-angular ./packages/common-angular
COPY --chown=node:node packages/admin-web-angular ./packages/admin-web-angular
 No newline at end of file
COPY --chown=node:node --from=development /srv/ever .

ENV NODE_OPTIONS=${NODE_OPTIONS:-"--max-old-space-size=2048"}
ENV NODE_ENV=${NODE_ENV:-production}

ENV API_BASE_URL=${API_BASE_URL:-http://localhost:3000}
ENV CLIENT_BASE_URL=${CLIENT_BASE_URL:-http://localhost:4200}
ENV SENTRY_DSN=${SENTRY_DSN}

ENV CHATWOOT_SDK_TOKEN=${CHATWOOT_SDK_TOKEN}
ENV CLOUDINARY_CLOUD_NAME=${CLOUDINARY_CLOUD_NAME}
ENV CLOUDINARY_API_KEY=${CLOUDINARY_API_KEY}
ENV GOOGLE_MAPS_API_KEY=${GOOGLE_MAPS_API_KEY}
ENV GOOGLE_PLACE_AUTOCOMPLETE=${GOOGLE_PLACE_AUTOCOMPLETE:-false}
ENV DEFAULT_LATITUDE=${DEFAULT_LATITUDE:-42.6459136}
ENV DEFAULT_LONGITUDE=${DEFAULT_LONGITUDE:-23.3332736}
ENV DEFAULT_CURRENCY=${DEFAULT_CURRENCY:-USD}_DSN}

ENV DEMO=${DEMO:-false}

ENV IS_DOCKER=true

RUN yarn build:admin

FROM nginx:alpine AS production

# USER nginx:nginx

WORKDIR /srv/ever

COPY --chown=nginx:nginx --from=dependencies /wait /entrypoint.prod.sh /entrypoint.compose.sh ./
COPY --chown=nginx:nginx .deploy/admin-web-angular/nginx.compose.conf /etc/nginx/conf.d/compose.conf.template
COPY --chown=nginx:nginx .deploy/admin-web-angular/nginx.prod.conf /etc/nginx/conf.d/prod.conf.template
COPY --chown=nginx:nginx --from=build /srv/ever/packages/admin-web-angular/build .

RUN chmod +x wait entrypoint.compose.sh entrypoint.prod.sh && \
    chmod a+rw /etc/nginx/conf.d/compose.conf.template /etc/nginx/conf.d/prod.conf.template

ENV API_BASE_URL=${API_BASE_URL:-http://localhost:3000}
ENV CLIENT_BASE_URL=${CLIENT_BASE_URL:-http://localhost:4200}
ENV SENTRY_DSN=${SENTRY_DSN}

ENV API_HOST=${API_HOST:-api}
ENV API_PORT=${API_PORT:-3000}
ENV WEB_HOST=${WEB_HOST:-0.0.0.0}
ENV WEB_PORT=${WEB_PORT:-4200}

ENV DEMO=${DEMO:-false}

EXPOSE ${WEB_PORT}

ENTRYPOINT [ "./entrypoint.prod.sh" ]

CMD [ "nginx", "-g", "daemon off;" ]
+27 −0
Original line number Diff line number Diff line
#!/bin/sh
set -ex

# This Entrypoint used inside Docker Compose only

export WAIT_HOSTS=$API_HOST:$API_PORT

# In production we should replace some values in generated JS code
sed -i "s#DOCKER_API_BASE_URL#$API_BASE_URL#g" *.js
sed -i "s#DOCKER_CLIENT_BASE_URL#$CLIENT_BASE_URL#g" *.js
sed -i "s#DOCKER_SENTRY_DSN#$SENTRY_DSN#g" *.js
sed -i "s#DOCKER_CLOUDINARY_CLOUD_NAME#$CLOUDINARY_CLOUD_NAME#g" *.js
sed -i "s#DOCKER_CLOUDINARY_API_KEY#$CLOUDINARY_API_KEY#g" *.js
sed -i "s#DOCKER_GOOGLE_MAPS_API_KEY#$GOOGLE_MAPS_API_KEY#g" *.js
sed -i "s#DOCKER_GOOGLE_PLACE_AUTOCOMPLETE#$GOOGLE_PLACE_AUTOCOMPLETE#g" *.js
sed -i "s#DOCKER_DEFAULT_LATITUDE#$DEFAULT_LATITUDE#g" *.js
sed -i "s#DOCKER_DEFAULT_LONGITUDE#$DEFAULT_LONGITUDE#g" *.js
sed -i "s#DOCKER_DEFAULT_CURRENCY#$DEFAULT_CURRENCY#g" *.js
sed -i "s#DOCKER_CHATWOOT_SDK_TOKEN#$CHATWOOT_SDK_TOKEN#g" *.js
sed -i "s#DOCKER_DEMO#$DEMO#g" *.js

envsubst '${API_HOST} ${API_PORT}' < /etc/nginx/conf.d/compose.conf.template > /etc/nginx/nginx.conf

# in Docker Compose we should wait other services start
./wait

exec "$@"
 No newline at end of file
+24 −0
Original line number Diff line number Diff line
#!/bin/sh
set -ex

# This Entrypoint used when we run Docker container outside of Docker Compose (e.g. in k8s)

# In production we should replace some values in generated JS code
sed -i "s#DOCKER_API_BASE_URL#$API_BASE_URL#g" *.js
sed -i "s#DOCKER_CLIENT_BASE_URL#$CLIENT_BASE_URL#g" *.js
sed -i "s#DOCKER_SENTRY_DSN#$SENTRY_DSN#g" *.js
sed -i "s#DOCKER_CLOUDINARY_CLOUD_NAME#$CLOUDINARY_CLOUD_NAME#g" *.js
sed -i "s#DOCKER_CLOUDINARY_API_KEY#$CLOUDINARY_API_KEY#g" *.js
sed -i "s#DOCKER_GOOGLE_MAPS_API_KEY#$GOOGLE_MAPS_API_KEY#g" *.js
sed -i "s#DOCKER_GOOGLE_PLACE_AUTOCOMPLETE#$GOOGLE_PLACE_AUTOCOMPLETE#g" *.js
sed -i "s#DOCKER_DEFAULT_LATITUDE#$DEFAULT_LATITUDE#g" *.js
sed -i "s#DOCKER_DEFAULT_LONGITUDE#$DEFAULT_LONGITUDE#g" *.js
sed -i "s#DOCKER_DEFAULT_CURRENCY#$DEFAULT_CURRENCY#g" *.js
sed -i "s#DOCKER_CHATWOOT_SDK_TOKEN#$CHATWOOT_SDK_TOKEN#g" *.js
sed -i "s#DOCKER_DEMO#$DEMO#g" *.js

# We may not need to use that env vars now in nginx.config, but we may want later.
# Also we just need to copy nginx.conf to correct place anyway...
envsubst '' < /etc/nginx/conf.d/prod.conf.template > /etc/nginx/nginx.conf

exec "$@"
+37 −0
Original line number Diff line number Diff line
user  nginx;
error_log  /var/log/nginx/error.log warn;
pid        /var/run/nginx.pid;

events {
  worker_connections 1024;
}

http {
  include /etc/nginx/mime.types;

  log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

  access_log  /var/log/nginx/access.log  main;

  #gzip  on;

  upstream api {
    server ${API_HOST}:${API_PORT};
  }

  server {
    listen 4200;

    location / {
      root /srv/ever;
      try_files $uri $uri/ /index.html;
    }

    location /api/ {
      proxy_pass http://api;
      proxy_set_header Host $http_host;
    }
  }
}
Loading