Skip to content

Commit

Permalink
Avoid building frontend for each environment and configure using env
Browse files Browse the repository at this point in the history
  • Loading branch information
limemloh committed Nov 4, 2024
1 parent 40ad591 commit 2b71a95
Show file tree
Hide file tree
Showing 15 changed files with 220 additions and 257 deletions.
10 changes: 10 additions & 0 deletions frontend/.env.mainnet
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Runtime configuration see comments in `nuxt.config.ts` for documentation.

NUXT_PUBLIC_API_URL=https://api-ccdscan.mainnet.concordium.software/graphql
NUXT_PUBLIC_WS_URL=wss://api-ccdscan.mainnet.concordium.software/graphql
NUXT_PUBLIC_EXPLORER_NAME=Mainnet
NUXT_PUBLIC_EXPLORER_EXTERNAL=Testnet@https://testnet.ccdscan.io

# Dev features, always disable in production.
NUXT_PUBLIC_ENABLE_URQL_DEVTOOLS=true
NUXT_PUBLIC_ENABLE_BREAKPOINT_HINT=true
10 changes: 10 additions & 0 deletions frontend/.env.stagenet
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Runtime configuration see comments in `nuxt.config.ts` for documentation.

NUXT_PUBLIC_API_URL=https://api-ccdscan.stagenet.concordium.com/graphql
NUXT_PUBLIC_WS_URL=wss://api-ccdscan.stagenet.concordium.com/graphql
NUXT_PUBLIC_EXPLORER_NAME=Stagenet
NUXT_PUBLIC_EXPLORER_EXTERNAL=Mainnet@https://ccdscan.io;Testnet@https://testnet.ccdscan.io

# Dev features, always disable in production.
NUXT_PUBLIC_ENABLE_URQL_DEVTOOLS=true
NUXT_PUBLIC_ENABLE_BREAKPOINT_HINT=true
10 changes: 10 additions & 0 deletions frontend/.env.testnet
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Runtime configuration see comments in `nuxt.config.ts` for documentation.

NUXT_PUBLIC_API_URL=https://api-ccdscan.testnet.concordium.com/graphql
NUXT_PUBLIC_WS_URL=wss://api-ccdscan.testnet.concordium.com/graphql
NUXT_PUBLIC_EXPLORER_NAME=Testnet
NUXT_PUBLIC_EXPLORER_EXTERNAL=Mainnet@https://ccdscan.io

# Dev features, always disable in production.
NUXT_PUBLIC_ENABLE_URQL_DEVTOOLS=true
NUXT_PUBLIC_ENABLE_BREAKPOINT_HINT=true
1 change: 1 addition & 0 deletions frontend/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ All notable changes to this project will be documented in this file.

- Migrate project to Nuxt `3.13`.
- Update NodeJS runtime version to `18.12.1`.
- Frontend image is now independent on the network being used, and can be configured at runtime.

### Removed

Expand Down
13 changes: 1 addition & 12 deletions frontend/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,26 +1,15 @@
ARG NODE_VERSION=18.12.1
ARG NODE_VERSION=18.18.2

FROM node:${NODE_VERSION} as build

ARG ENVIRONMENT

ENV ENVIRONMENT=$ENVIRONMENT

WORKDIR /app

COPY package.json yarn.lock ./
RUN yarn

COPY . .
RUN yarn build

FROM node:${NODE_VERSION}-slim

ENV PORT=3000
ENV HOST=0.0.0.0

EXPOSE 3000

COPY --from=build /app/.output .

CMD ["node", "server/index.mjs"]
2 changes: 0 additions & 2 deletions frontend/Jenkinsfile
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
// Params in JobDSL file
// 'https://github.com/Concordium/concordium-infra-jenkins-jobs/blob/master/ccdscan_frontend.groovy':
// - VERSION
// - TARGET_NET
pipeline {
agent any
environment {
Expand All @@ -21,7 +20,6 @@ pipeline {
steps {
sh '''\
docker build \
--build-arg ENVIRONMENT=${TARGET_NET} \
-f "frontend/Dockerfile" \
-t "${image_name}" \
./frontend
Expand Down
31 changes: 22 additions & 9 deletions frontend/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,11 @@ The frontend of CCDScan is a server-side rendered single page app, which consume

The frontend is built on some fundamental technologies:

- **[Vue](https://vuejs.org/)**
- **[Vue](https://vuejs.org/)**
JavaScript framework for building user interfaces for the web. It is reactive, declarative and very approachable to build and extend.
- **[Nuxt 3](https://v3.nuxtjs.org/)**
- **[Nuxt 3](https://v3.nuxtjs.org/)**
Application framework built on top of Vue. Out of the box it gives us some things that Vue itself lacks, such as routing, and it comes with a build system supporting code splitting and ohter optimisations.
- **[TypeScript](https://www.typescriptlang.org/)**
- **[TypeScript](https://www.typescriptlang.org/)**
A typed programming language, which compiles to JavaScript. This acts as an accelerator during development, and prevents most type errors at write-time and compile-time. [More on this in a later section](#typescript).

## Setup
Expand All @@ -23,25 +23,38 @@ yarn

### Run Development server

To run the development server a configuration can be provided using `.env` file, without it will assume the backend API is running locally.

```sh
yarn dev
```

Go to [http://localhost:3000](http://localhost:3000)
Go to [http://localhost:3000](http://localhost:3000).

To develop against our backend APIs already in production, specify the appropriate file with environment variables. Below is an example of using testnet backend API:

```sh
yarn dev --dotenv .env.testnet
```


### Build and serve locally

You can build and run the production image locally.

To build the image run
To build the image run:

```sh
docker build -t IMAGE_NAME:VERSION --build-arg ENVIRONMENT=<ENVIRONMENT> .
docker build -t IMAGE_NAME:VERSION .
```
where `IMAGE_NAME` and `VERSION` are some container name and version of your choice and `CHAIN_ENVIRONMENT` is which environment to run agains (`stagenet`, `testnet` or `mainnet`).

To run the image run
where `IMAGE_NAME` and `VERSION` are some container name.


The image can be run against Testnet by providing the `.env.testnet` configuration.

```sh
docker run -p 3000:3000 IMAGE_NAME:VERSION
docker run --public 3000:3000 --env-file .env.testnet IMAGE_NAME:VERSION
```

The application is now available at `http://localhost:3000/`.
Expand Down
95 changes: 46 additions & 49 deletions frontend/nuxt.config.ts
Original file line number Diff line number Diff line change
@@ -1,41 +1,43 @@
import { defineNuxtConfig } from 'nuxt/config'

type Environment = 'dev' | 'stagenet' | 'testnet' | 'mainnet'
type Config = {
apiUrl: string
wsUrl: string
}

const ENVIRONMENT = (process.env.ENVIRONMENT as Environment) || 'dev'

const VARS: Record<Environment, Config> = {
dev: {
apiUrl: 'http://localhost:5090/graphql',
wsUrl: 'ws://localhost:5090/graphql',
},
stagenet: {
apiUrl: 'https://api-ccdscan.stagenet.concordium.com/graphql',
wsUrl: 'wss://api-ccdscan.stagenet.concordium.com/graphql',
},
testnet: {
apiUrl: 'https://api-ccdscan.testnet.concordium.com/graphql',
wsUrl: 'wss://api-ccdscan.testnet.concordium.com/graphql',
},
mainnet: {
apiUrl: 'https://api-ccdscan.mainnet.concordium.software/graphql',
wsUrl: 'wss://api-ccdscan.mainnet.concordium.software/graphql',
},
}

const getConfig = (env: Environment): Config => {
return {
apiUrl: process.env.BACKEND_API_URL || VARS[env].apiUrl || '',
wsUrl: process.env.BACKEND_WS_URL || VARS[env].wsUrl || '',
}
}

export default defineNuxtConfig({
// Configuration available to the application at runtime, note the `public` object will be
// expose directly in the client-side code and therefore should not contain secrets.
// Below values are default and can be overwritten by environment variables at runtime.
runtimeConfig: {
public: {
version: process.env.npm_package_version,
// URL to use when sending GraphQL queries to the CCDscan API.
// (env NUXT_PUBLIC_API_URL)
apiUrl: 'http://localhost:5090/graphql',
// URL to use when using websockets in GraphQL CCDscan API.
// (env NUXT_PUBLIC_WS_URL)
wsUrl: 'ws://localhost:5090/graphql',
// Settings for how to display the explorer.
explorer: {
// The name to display for the explorer.
// (env NUXT_PUBLIC_EXPLORER_NAME)
name: 'Local',
// The list of external explorers to link in the explorer selector.
// Should be provided as `<name>@<url>` separated by `;`.
// Ex.: 'Mainnet@https://ccdscan.io;Testnet@https://testnet.ccdscan.io'
// (env NUXT_PUBLIC_EXPLORER_EXTERNAL).
external:
'Mainnet@https://ccdscan.io;Testnet@https://testnet.ccdscan.io;Stagenet@https://stagenet.ccdscan.io',
},
// When enabled a hint for the current breakpoint (related to screen size)
// is displayed in the bottom left corner. Enable only for development.
// (env NUXT_PUBLIC_ENABLE_BREAKPOINT_HINT)
enableBreakpointHint: false,
// Enabled the urql-devtools for debugging GraphQL (require browser extension).
// Enable only for development.
// (env NUXT_PUBLIC_ENABLE_URQL_DEVTOOLS)
enableUrqlDevtools: false,
},
},
// Directory for finding the source files.
srcDir: 'src/',
// Directories to search for components.
components: [
'~/components',
'~/components/atoms',
Expand All @@ -45,27 +47,22 @@ export default defineNuxtConfig({
'~/components/Drawer',
'~/components/BlockDetails',
],

runtimeConfig: {
public: {
...getConfig(ENVIRONMENT),
version: process.env.npm_package_version,
environment: ENVIRONMENT,
includeDevTools:
ENVIRONMENT === 'dev' ||
ENVIRONMENT === 'stagenet' ||
ENVIRONMENT === 'testnet',
},
},

// Global CSS files
css: ['~/assets/css/styles.css'],

// Enable postCSS
postcss: {
plugins: {
tailwindcss: {},
autoprefixer: {},
},
},

// Lock default values for Nuxt to what they were at this date.
compatibilityDate: '2024-11-01',
// TypeScript configurations.
// typescript: {
// // Enable strict checks.
// strict: true,
// // Enable type-checking at build time.
// typeCheck: true,
// },
})
6 changes: 3 additions & 3 deletions frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -65,10 +65,10 @@
"prettier": "^2.6.2",
"ts-jest": "^28",
"ts-node": "^10.8.0",
"typescript": "^4.7.2",
"vue-tsc": "^0.35.2"
"typescript": "^5.6.3",
"vue-tsc": "^2.1.10"
},
"volta": {
"node": "18.12.1"
"node": "18.18.2"
}
}
14 changes: 4 additions & 10 deletions frontend/src/components/molecules/GraphQLClient.vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,18 +12,12 @@ import {
provideClient,
} from '@urql/vue'
import { SubscriptionClient } from 'subscriptions-transport-ws'
import { composeBackendUrls } from '~/utils/composeBackendUrls'
const {
public: { apiUrl, wsUrl, includeDevTools },
public: { apiUrl, wsUrl, enableUrqlDevtools },
} = useRuntimeConfig()
const [composedApiUrl, composedWsUrl] = composeBackendUrls(
apiUrl,
wsUrl
)(location.host)
const subscriptionClient = new SubscriptionClient(composedWsUrl, {
const subscriptionClient = new SubscriptionClient(wsUrl, {
reconnect: true,
})
Expand All @@ -34,13 +28,13 @@ let exchanges = [
}),
]
if (includeDevTools) {
if (enableUrqlDevtools) {
const dtools = await import('@urql/devtools')
exchanges = [dtools.devtoolsExchange, ...exchanges]
}
const client = createClient({
url: composedApiUrl,
url: apiUrl,
exchanges,
})
Expand Down
Loading

0 comments on commit 2b71a95

Please sign in to comment.