mirror of
https://github.com/IT4Change/gradido.git
synced 2026-02-06 09:56:05 +00:00
Merge branch 'master' into 3427-feature-correct-user-data-transfer-to-gms
This commit is contained in:
commit
2e413fdc6c
3
.dockerignore
Normal file
3
.dockerignore
Normal file
@ -0,0 +1,3 @@
|
||||
**/node_modules
|
||||
**/build
|
||||
**/coverage
|
||||
2
.github/workflows/test_admin_interface.yml
vendored
2
.github/workflows/test_admin_interface.yml
vendored
@ -33,7 +33,7 @@ jobs:
|
||||
uses: actions/checkout@v3
|
||||
|
||||
- name: Admin Interface | Build 'test' image
|
||||
run: docker build --target test -t "gradido/admin:test" admin/ --build-arg NODE_ENV="test"
|
||||
run: docker build -f ./admin/Dockerfile --target test -t "gradido/admin:test" --build-arg NODE_ENV="test" .
|
||||
|
||||
unit_test:
|
||||
if: needs.files-changed.outputs.admin == 'true'
|
||||
|
||||
6
.github/workflows/test_backend.yml
vendored
6
.github/workflows/test_backend.yml
vendored
@ -44,7 +44,7 @@ jobs:
|
||||
uses: actions/checkout@v3
|
||||
|
||||
- name: Backend | docker-compose mariadb
|
||||
run: docker compose -f docker-compose.yml -f docker-compose.test.yml up --detach --no-deps mariadb
|
||||
run: docker compose -f docker-compose.yml -f docker-compose.test.yml up --detach --no-deps mariadb mailserver
|
||||
|
||||
- name: Sleep for 30 seconds
|
||||
run: sleep 30s
|
||||
@ -54,7 +54,7 @@ jobs:
|
||||
run: docker compose -f docker-compose.yml -f docker-compose.test.yml up --detach --no-deps database
|
||||
|
||||
- name: Backend | Unit tests
|
||||
run: cd database && yarn && yarn build && cd ../backend && yarn && yarn test
|
||||
run: cd database && yarn && yarn build && cd ../config && yarn install && cd ../backend && yarn && yarn test
|
||||
|
||||
lint:
|
||||
if: needs.files-changed.outputs.backend == 'true'
|
||||
@ -66,7 +66,7 @@ jobs:
|
||||
uses: actions/checkout@v3
|
||||
|
||||
- name: Backend | Lint
|
||||
run: cd database && yarn && cd ../backend && yarn && yarn run lint
|
||||
run: cd database && yarn && cd ../config && yarn install && cd ../backend && yarn && yarn run lint
|
||||
|
||||
locales:
|
||||
if: needs.files-changed.outputs.backend == 'true'
|
||||
|
||||
2
.github/workflows/test_dht_node.yml
vendored
2
.github/workflows/test_dht_node.yml
vendored
@ -51,7 +51,7 @@ jobs:
|
||||
uses: actions/checkout@v3
|
||||
|
||||
- name: Lint
|
||||
run: cd database && yarn && cd ../dht-node && yarn && yarn run lint
|
||||
run: cd database && yarn && cd ../config && yarn install && cd ../dht-node && yarn && yarn run lint
|
||||
|
||||
unit_test:
|
||||
name: Unit Tests - DHT Node
|
||||
|
||||
2
.github/workflows/test_e2e.yml
vendored
2
.github/workflows/test_e2e.yml
vendored
@ -21,6 +21,8 @@ jobs:
|
||||
sudo chown runner:docker -R *
|
||||
cd database
|
||||
yarn && yarn dev_reset
|
||||
cd ../config
|
||||
yarn install
|
||||
cd ../backend
|
||||
yarn && yarn seed
|
||||
|
||||
|
||||
2
.github/workflows/test_frontend.yml
vendored
2
.github/workflows/test_frontend.yml
vendored
@ -33,7 +33,7 @@ jobs:
|
||||
uses: actions/checkout@v3
|
||||
|
||||
- name: Frontend | Build 'test' image
|
||||
run: docker build --target test -t "gradido/frontend:test" frontend/ --build-arg NODE_ENV="test"
|
||||
run: docker build -f ./frontend/Dockerfile --target test -t "gradido/frontend:test" --build-arg NODE_ENV="test" .
|
||||
|
||||
unit_test:
|
||||
if: needs.files-changed.outputs.frontend == 'true'
|
||||
|
||||
@ -11,7 +11,7 @@ ENV BUILD_DATE="1970-01-01T00:00:00.00Z"
|
||||
## We cannot do $(npm run version).${BUILD_NUMBER} here so we default to 0.0.0.0
|
||||
ENV BUILD_VERSION="0.0.0.0"
|
||||
## We cannot do `$(git rev-parse --short HEAD)` here so we default to 0000000
|
||||
ENV BUILD_COMMIT="0000000"
|
||||
ENV BUILD_COMMIT_SHORT="0000000"
|
||||
## SET NODE_ENV
|
||||
ARG NODE_ENV="production"
|
||||
## App relevant Envs
|
||||
@ -42,6 +42,8 @@ EXPOSE ${PORT}
|
||||
RUN mkdir -p ${DOCKER_WORKDIR}
|
||||
WORKDIR ${DOCKER_WORKDIR}
|
||||
|
||||
RUN mkdir -p /config
|
||||
|
||||
##################################################################################
|
||||
# DEVELOPMENT (Connected to the local environment, to reload on demand) ##########
|
||||
##################################################################################
|
||||
@ -53,7 +55,7 @@ FROM base as development
|
||||
# Run command
|
||||
# (for development we need to execute yarn install since the
|
||||
# node_modules are on another volume and need updating)
|
||||
CMD /bin/sh -c "yarn install && yarn run dev"
|
||||
CMD /bin/sh -c "cd /config && yarn install && cd /app && yarn && yarn run dev"
|
||||
|
||||
##################################################################################
|
||||
# BUILD (Does contain all files and is therefore bloated) ########################
|
||||
@ -61,9 +63,16 @@ CMD /bin/sh -c "yarn install && yarn run dev"
|
||||
FROM base as build
|
||||
|
||||
# Copy everything
|
||||
COPY . .
|
||||
# yarn install
|
||||
COPY ./admin/ .
|
||||
# Copy everything from config
|
||||
COPY ./config/ ../config/
|
||||
|
||||
# yarn install and build config
|
||||
RUN cd ../config && yarn install --production=false --frozen-lockfile --non-interactive && yarn build
|
||||
|
||||
# yarn install admin
|
||||
RUN yarn install --production=false --frozen-lockfile --non-interactive
|
||||
|
||||
# yarn build
|
||||
RUN yarn run build
|
||||
|
||||
@ -85,6 +94,7 @@ FROM base as production
|
||||
|
||||
# Copy "binary"-files from build image
|
||||
COPY --from=build ${DOCKER_WORKDIR}/build ./build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/build ../config/build
|
||||
# We also copy the node_modules express and serve-static for the run script
|
||||
COPY --from=build ${DOCKER_WORKDIR}/node_modules ./node_modules
|
||||
# Copy static files
|
||||
|
||||
@ -74,6 +74,8 @@
|
||||
"eslint-plugin-prettier": "5.2.1",
|
||||
"eslint-plugin-promise": "^5.1.1",
|
||||
"eslint-plugin-vue": "8.7.1",
|
||||
"gradido-config": "../config",
|
||||
"joi": "^17.13.3",
|
||||
"jsdom": "^25.0.0",
|
||||
"mock-apollo-client": "^1.2.1",
|
||||
"postcss": "^8.4.8",
|
||||
|
||||
@ -21,6 +21,7 @@ vi.mock('@vue/apollo-composable', () => ({
|
||||
|
||||
vi.mock('vue-i18n', () => ({
|
||||
useI18n: () => ({
|
||||
locale: { value: 'en' },
|
||||
t: (key) => key,
|
||||
}),
|
||||
}))
|
||||
|
||||
@ -9,7 +9,13 @@
|
||||
</BFormGroup>
|
||||
<BFormGroup v-if="showResubmissionDate">
|
||||
<div class="d-flex my-2">
|
||||
<Datepicker v-model="resubmissionDate" :lower-limit="now" class="form-control" />
|
||||
<Datepicker
|
||||
v-model="resubmissionDate"
|
||||
:locale="dateLocale"
|
||||
input-format="P"
|
||||
:lower-limit="now"
|
||||
class="form-control"
|
||||
/>
|
||||
<time-picker v-model="resubmissionTime" class="ms-2" />
|
||||
</div>
|
||||
</BFormGroup>
|
||||
@ -80,9 +86,9 @@
|
||||
|
||||
<script setup>
|
||||
import { ref, computed } from 'vue'
|
||||
import { useDateLocale } from '@/composables/useDateLocale'
|
||||
import { useMutation } from '@vue/apollo-composable'
|
||||
import { useI18n } from 'vue-i18n'
|
||||
|
||||
import Datepicker from 'vue3-datepicker'
|
||||
import TimePicker from '@/components/input/TimePicker'
|
||||
import { adminCreateContributionMessage } from '@/graphql/adminCreateContributionMessage'
|
||||
@ -117,6 +123,7 @@ const emit = defineEmits([
|
||||
])
|
||||
|
||||
const { t } = useI18n()
|
||||
const dateLocale = useDateLocale()
|
||||
const { toastError, toastSuccess } = useAppToast()
|
||||
const form = ref({
|
||||
text: '',
|
||||
|
||||
@ -89,9 +89,9 @@
|
||||
<script setup>
|
||||
import { ref, computed, toRefs } from 'vue'
|
||||
import { useI18n } from 'vue-i18n'
|
||||
import { useDateLocale } from '@/composables/useDateLocale'
|
||||
import { useMutation } from '@vue/apollo-composable'
|
||||
import { formatDistanceToNow } from 'date-fns'
|
||||
import { de, enUS as en, fr, es, nl } from 'date-fns/locale'
|
||||
import EditableGroup from '@/components/input/EditableGroup.vue'
|
||||
import FederationVisualizeItem from './FederationVisualizeItem.vue'
|
||||
import { updateHomeCommunity } from '@/graphql/updateHomeCommunity'
|
||||
@ -99,15 +99,13 @@ import Coordinates from '../input/Coordinates.vue'
|
||||
import EditableGroupableLabel from '../input/EditableGroupableLabel.vue'
|
||||
import { useAppToast } from '@/composables/useToast'
|
||||
|
||||
const locales = { en, de, es, fr, nl }
|
||||
|
||||
const props = defineProps({
|
||||
item: { type: Object, required: true },
|
||||
})
|
||||
|
||||
const { item } = toRefs(props)
|
||||
|
||||
const { t, locale } = useI18n()
|
||||
const { t } = useI18n()
|
||||
|
||||
const { toastSuccess, toastError } = useAppToast()
|
||||
|
||||
@ -147,7 +145,7 @@ const lastAnnouncedAt = computed(() => {
|
||||
return formatDistanceToNow(lastAnnouncedAt, {
|
||||
includeSecond: true,
|
||||
addSuffix: true,
|
||||
locale: locales[locale.value],
|
||||
locale: useDateLocale(),
|
||||
})
|
||||
}
|
||||
return ''
|
||||
@ -158,7 +156,7 @@ const createdAt = computed(() => {
|
||||
return formatDistanceToNow(new Date(item.value.createdAt), {
|
||||
includeSecond: true,
|
||||
addSuffix: true,
|
||||
locale: locales[locale.value],
|
||||
locale: useDateLocale(),
|
||||
})
|
||||
}
|
||||
return ''
|
||||
|
||||
@ -30,11 +30,9 @@
|
||||
</template>
|
||||
<script>
|
||||
import { formatDistanceToNow } from 'date-fns'
|
||||
import { de, enUS as en, fr, es, nl } from 'date-fns/locale'
|
||||
import { useDateLocale } from '@/composables/useDateLocale'
|
||||
import VariantIcon from '@/components/VariantIcon.vue'
|
||||
|
||||
const locales = { en, de, es, fr, nl }
|
||||
|
||||
export default {
|
||||
name: 'FederationVisualizeItem',
|
||||
components: { VariantIcon },
|
||||
@ -58,7 +56,7 @@ export default {
|
||||
? formatDistanceToNow(new Date(dateString), {
|
||||
includeSecond: true,
|
||||
addSuffix: true,
|
||||
locale: locales[this.$i18n.locale],
|
||||
locale: useDateLocale,
|
||||
})
|
||||
: ''
|
||||
},
|
||||
|
||||
@ -114,7 +114,7 @@ describe('NavBar', () => {
|
||||
it('changes window location to wallet and dispatches logout', async () => {
|
||||
const dispatchSpy = vi.spyOn(store, 'dispatch')
|
||||
await wrapper.vm.handleWallet()
|
||||
expect(window.location).toBe(CONFIG.WALLET_AUTH_URL.replace('{token}', 'valid-token'))
|
||||
expect(window.location).toBe(CONFIG.WALLET_AUTH_URL + 'valid-token')
|
||||
expect(dispatchSpy).toHaveBeenCalledWith('logout')
|
||||
})
|
||||
})
|
||||
|
||||
@ -80,7 +80,7 @@ const handleLogout = async () => {
|
||||
}
|
||||
|
||||
const handleWallet = () => {
|
||||
window.location = CONFIG.WALLET_AUTH_URL.replace('{token}', store.state.token)
|
||||
window.location = CONFIG.WALLET_AUTH_URL + store.state.token
|
||||
store.dispatch('logout') // logout without redirect
|
||||
}
|
||||
|
||||
|
||||
10
admin/src/composables/useDateLocale.js
Normal file
10
admin/src/composables/useDateLocale.js
Normal file
@ -0,0 +1,10 @@
|
||||
import { useI18n } from 'vue-i18n'
|
||||
import { de, enUS as en, fr, es, nl } from 'date-fns/locale'
|
||||
|
||||
const locales = { en, de, es, fr, nl }
|
||||
|
||||
export function useDateLocale() {
|
||||
const { locale } = useI18n()
|
||||
const dateLocale = locales[locale.value] || en
|
||||
return dateLocale
|
||||
}
|
||||
@ -4,20 +4,12 @@
|
||||
// Load Package Details for some default values
|
||||
const pkg = require('../../package')
|
||||
|
||||
const constants = {
|
||||
CONFIG_VERSION: {
|
||||
DEFAULT: 'DEFAULT',
|
||||
EXPECTED: 'v3.2024-08-06',
|
||||
CURRENT: '',
|
||||
},
|
||||
}
|
||||
|
||||
const version = {
|
||||
ADMIN_MODULE_PROTOCOL: process.env.ADMIN_MODULE_PROTOCOL ?? 'http',
|
||||
ADMIN_MODULE_HOST: process.env.ADMIN_MODULE_HOST ?? 'localhost',
|
||||
ADMIN_MODULE_PORT: process.env.ADMIN_MODULE_PORT ?? '8080',
|
||||
APP_VERSION: pkg.version,
|
||||
BUILD_COMMIT: process.env.BUILD_COMMIT ?? null,
|
||||
BUILD_COMMIT: process.env.BUILD_COMMIT ?? undefined,
|
||||
// self reference of `version.BUILD_COMMIT` is not possible at this point, hence the duplicate code
|
||||
BUILD_COMMIT_SHORT: (process.env.BUILD_COMMIT ?? '0000000').slice(0, 7),
|
||||
}
|
||||
@ -47,11 +39,11 @@ const environment = {
|
||||
// const COMMUNITY_URL =
|
||||
// COMMUNITY_HOST && URL_PROTOCOL ? URL_PROTOCOL + '://' + COMMUNITY_HOST : undefined
|
||||
const COMMUNITY_URL = process.env.COMMUNITY_URL ?? ADMIN_MODULE_URL
|
||||
const WALLET_URL = process.env.WALLET_URL ?? COMMUNITY_URL ?? 'http://localhost'
|
||||
const WALLET_URL = process.env.WALLET_URL ?? COMMUNITY_URL ?? 'http://0.0.0.0'
|
||||
|
||||
const endpoints = {
|
||||
GRAPHQL_URI: process.env.GRAPHQL_URL ?? COMMUNITY_URL + (process.env.GRAPHQL_PATH ?? '/graphql'),
|
||||
WALLET_AUTH_URL: WALLET_URL + (process.env.WALLET_AUTH_PATH ?? '/authenticate?token={token}'),
|
||||
WALLET_AUTH_URL: WALLET_URL + (process.env.WALLET_AUTH_PATH ?? '/authenticate?token='),
|
||||
WALLET_LOGIN_URL: WALLET_URL + (process.env.WALLET_LOGIN_PATH ?? '/login'),
|
||||
}
|
||||
|
||||
@ -59,24 +51,13 @@ const debug = {
|
||||
DEBUG_DISABLE_AUTH: process.env.DEBUG_DISABLE_AUTH === 'true' ?? false,
|
||||
}
|
||||
|
||||
// Check config version
|
||||
constants.CONFIG_VERSION.CURRENT = process.env.CONFIG_VERSION ?? constants.CONFIG_VERSION.DEFAULT
|
||||
if (
|
||||
![constants.CONFIG_VERSION.EXPECTED, constants.CONFIG_VERSION.DEFAULT].includes(
|
||||
constants.CONFIG_VERSION.CURRENT,
|
||||
)
|
||||
) {
|
||||
throw new Error(
|
||||
`Fatal: Config Version incorrect - expected "${constants.CONFIG_VERSION.EXPECTED}" or "${constants.CONFIG_VERSION.DEFAULT}", but found "${constants.CONFIG_VERSION.CURRENT}"`,
|
||||
)
|
||||
}
|
||||
|
||||
const CONFIG = {
|
||||
...constants,
|
||||
...version,
|
||||
...environment,
|
||||
...endpoints,
|
||||
...debug,
|
||||
ADMIN_MODULE_URL,
|
||||
COMMUNITY_URL,
|
||||
}
|
||||
|
||||
module.exports = CONFIG
|
||||
|
||||
106
admin/src/config/schema.js
Normal file
106
admin/src/config/schema.js
Normal file
@ -0,0 +1,106 @@
|
||||
const {
|
||||
APP_VERSION,
|
||||
BUILD_COMMIT,
|
||||
BUILD_COMMIT_SHORT,
|
||||
COMMUNITY_URL,
|
||||
DEBUG,
|
||||
GRAPHQL_URI,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
} = require('gradido-config/build/src/commonSchema.js')
|
||||
const Joi = require('joi')
|
||||
|
||||
module.exports = Joi.object({
|
||||
APP_VERSION,
|
||||
BUILD_COMMIT,
|
||||
BUILD_COMMIT_SHORT,
|
||||
COMMUNITY_URL,
|
||||
DEBUG,
|
||||
GRAPHQL_URI,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
|
||||
ADMIN_HOSTING: Joi.string()
|
||||
.valid('nodejs', 'nginx')
|
||||
.description('set to `nodejs` if admin is hosted by vite with a own nodejs instance')
|
||||
.optional(),
|
||||
|
||||
ADMIN_MODULE_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.when('COMMUNITY_URL', {
|
||||
is: Joi.exist(),
|
||||
then: Joi.optional(), // not required if COMMUNITY_URL is provided
|
||||
otherwise: Joi.required(), // required if COMMUNITY_URL is missing
|
||||
})
|
||||
.description("Base Url for reaching admin in browser, only needed if COMMUNITY_URL wasn't set")
|
||||
.optional(), // optional in general, but conditionally required
|
||||
|
||||
ADMIN_MODULE_PROTOCOL: Joi.string()
|
||||
.when('ADMIN_HOSTING', {
|
||||
is: Joi.valid('nodejs'),
|
||||
then: Joi.valid('http').required(),
|
||||
otherwise: Joi.valid('http', 'https').required(),
|
||||
})
|
||||
.description(
|
||||
`
|
||||
Protocol for admin module hosting
|
||||
- it has to be the same as for backend api url and frontend to prevent mixed block errors,
|
||||
- if admin is served with nodejs:
|
||||
is have to be http or setup must be updated to include a ssl certificate
|
||||
`,
|
||||
)
|
||||
.default('http')
|
||||
.required(),
|
||||
|
||||
ADMIN_MODULE_HOST: Joi.alternatives()
|
||||
.try(
|
||||
Joi.string().valid('localhost').messages({ 'any.invalid': 'Must be localhost' }),
|
||||
Joi.string()
|
||||
.ip({ version: ['ipv4'] })
|
||||
.messages({ 'string.ip': 'Must be a valid IPv4 address' }),
|
||||
Joi.string().domain().messages({ 'string.domain': 'Must be a valid domain' }),
|
||||
)
|
||||
.when('ADMIN_HOSTING', {
|
||||
is: 'nodejs',
|
||||
then: Joi.required(),
|
||||
otherwise: Joi.optional(),
|
||||
})
|
||||
.when('COMMUNITY_URL', {
|
||||
is: null,
|
||||
then: Joi.required(),
|
||||
otherwise: Joi.optional(),
|
||||
})
|
||||
.description(
|
||||
'Host (domain, IPv4, or localhost) for the admin, default is 0.0.0.0 for local hosting during develop',
|
||||
)
|
||||
.default('0.0.0.0'),
|
||||
|
||||
ADMIN_MODULE_PORT: Joi.number()
|
||||
.integer()
|
||||
.min(1024)
|
||||
.max(49151)
|
||||
.description('Port for hosting Admin with Vite as a Node.js instance, default: 8080')
|
||||
.default(8080)
|
||||
.when('ADMIN_HOSTING', {
|
||||
is: 'nodejs',
|
||||
then: Joi.required(),
|
||||
otherwise: Joi.optional(),
|
||||
}),
|
||||
|
||||
WALLET_AUTH_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.description('Extern Url from wallet-frontend for forwarding from admin')
|
||||
.default('http://0.0.0.0/authenticate?token=')
|
||||
.required(),
|
||||
|
||||
WALLET_LOGIN_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.description('Extern Url from wallet-frontend for forwarding after logout')
|
||||
.default('http://0.0.0.0/login')
|
||||
.required(),
|
||||
|
||||
DEBUG_DISABLE_AUTH: Joi.boolean()
|
||||
.description('Flag for disable authorization during development')
|
||||
.default(false)
|
||||
.optional(), // true is only allowed in not-production setup
|
||||
})
|
||||
@ -6,6 +6,8 @@ import Components from 'unplugin-vue-components/vite'
|
||||
import IconsResolve from 'unplugin-icons/resolver'
|
||||
import { BootstrapVueNextResolver } from 'bootstrap-vue-next'
|
||||
import EnvironmentPlugin from 'vite-plugin-environment'
|
||||
import schema from './src/config/schema'
|
||||
import { validate, browserUrls } from 'gradido-config/build/src/index.js'
|
||||
|
||||
import dotenv from 'dotenv'
|
||||
|
||||
@ -15,56 +17,74 @@ const CONFIG = require('./src/config')
|
||||
|
||||
const path = require('path')
|
||||
|
||||
export default defineConfig({
|
||||
base: '/admin/',
|
||||
server: {
|
||||
host: CONFIG.ADMIN_MODULE_HOST, // '0.0.0.0',
|
||||
port: CONFIG.ADMIN_MODULE_PORT, // 8080,
|
||||
},
|
||||
resolve: {
|
||||
alias: {
|
||||
'@': path.resolve(__dirname, './src'),
|
||||
assets: path.join(__dirname, 'src/assets'),
|
||||
},
|
||||
extensions: ['.mjs', '.js', '.ts', '.jsx', '.tsx', '.json', '.vue'],
|
||||
},
|
||||
export default defineConfig(({ command }) => {
|
||||
if (command === 'serve') {
|
||||
CONFIG.ADMIN_HOSTING = 'nodejs'
|
||||
} else {
|
||||
CONFIG.ADMIN_HOSTING = 'nginx'
|
||||
}
|
||||
// Check config
|
||||
validate(schema, CONFIG)
|
||||
// make sure that all urls used in browser have the same protocol to prevent mixed content errors
|
||||
validate(browserUrls, [
|
||||
CONFIG.ADMIN_AUTH_URL,
|
||||
CONFIG.COMMUNITY_URL,
|
||||
CONFIG.COMMUNITY_REGISTER_URL,
|
||||
CONFIG.GRAPHQL_URI,
|
||||
CONFIG.FRONTEND_MODULE_URL,
|
||||
])
|
||||
|
||||
plugins: [
|
||||
vue({
|
||||
template: {
|
||||
compilerOptions: {
|
||||
compatConfig: {
|
||||
MODE: 2,
|
||||
return {
|
||||
base: '/admin/',
|
||||
server: {
|
||||
host: CONFIG.ADMIN_MODULE_HOST, // '0.0.0.0',
|
||||
port: CONFIG.ADMIN_MODULE_PORT, // 8080,
|
||||
},
|
||||
resolve: {
|
||||
alias: {
|
||||
'@': path.resolve(__dirname, './src'),
|
||||
assets: path.join(__dirname, 'src/assets'),
|
||||
},
|
||||
extensions: ['.mjs', '.js', '.ts', '.jsx', '.tsx', '.json', '.vue'],
|
||||
},
|
||||
|
||||
plugins: [
|
||||
vue({
|
||||
template: {
|
||||
compilerOptions: {
|
||||
compatConfig: {
|
||||
MODE: 2,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}),
|
||||
Components({
|
||||
resolvers: [IconsResolve(), BootstrapVueNextResolver()],
|
||||
dts: true,
|
||||
}),
|
||||
Icons({
|
||||
compiler: 'vue3',
|
||||
}),
|
||||
EnvironmentPlugin({
|
||||
BUILD_COMMIT: null,
|
||||
PORT: CONFIG.ADMIN_MODULE_PORT ?? null, // null,
|
||||
COMMUNITY_HOST: CONFIG.ADMIN_MODULE_HOST ?? null, // null,
|
||||
COMMUNITY_URL: CONFIG.COMMUNITY_URL ?? null,
|
||||
URL_PROTOCOL: CONFIG.ADMIN_MODULE_PROTOCOL ?? null, // null,
|
||||
WALLET_AUTH_URL: CONFIG.WALLET_AUTH_URL ?? null,
|
||||
GRAPHQL_URL: CONFIG.GRAPHQL_URI ?? null, // null,
|
||||
GRAPHQL_PATH: process.env.GRAPHQL_PATH ?? '/graphql', // null,
|
||||
WALLET_AUTH_PATH: CONFIG.WALLET_AUTH_PATH ?? null,
|
||||
WALLET_LOGIN_PATH: CONFIG.WALLET_LOGIN_URL ?? null, // null,
|
||||
DEBUG_DISABLE_AUTH: CONFIG.DEBUG_DISABLE_AUTH ?? null, // null,
|
||||
// CONFIG_VERSION: CONFIG.CONFIG_VERSION, // null,
|
||||
}),
|
||||
commonjs(),
|
||||
],
|
||||
build: {
|
||||
outDir: path.resolve(__dirname, './build'),
|
||||
chunkSizeWarningLimit: 1600,
|
||||
},
|
||||
publicDir: '/admin',
|
||||
}),
|
||||
Components({
|
||||
resolvers: [IconsResolve(), BootstrapVueNextResolver()],
|
||||
dts: true,
|
||||
}),
|
||||
Icons({
|
||||
compiler: 'vue3',
|
||||
}),
|
||||
EnvironmentPlugin({
|
||||
BUILD_COMMIT: null,
|
||||
PORT: CONFIG.ADMIN_MODULE_PORT ?? null, // null,
|
||||
COMMUNITY_HOST: CONFIG.ADMIN_MODULE_HOST ?? null, // null,
|
||||
COMMUNITY_URL: CONFIG.COMMUNITY_URL ?? null,
|
||||
URL_PROTOCOL: CONFIG.ADMIN_MODULE_PROTOCOL ?? null, // null,
|
||||
WALLET_AUTH_URL: CONFIG.WALLET_AUTH_URL ?? null,
|
||||
GRAPHQL_URL: CONFIG.GRAPHQL_URI ?? null, // null,
|
||||
GRAPHQL_PATH: process.env.GRAPHQL_PATH ?? '/graphql', // null,
|
||||
WALLET_AUTH_PATH: CONFIG.WALLET_AUTH_PATH ?? null,
|
||||
WALLET_LOGIN_PATH: CONFIG.WALLET_LOGIN_URL ?? null, // null,
|
||||
DEBUG_DISABLE_AUTH: CONFIG.DEBUG_DISABLE_AUTH ?? null, // null,
|
||||
// CONFIG_VERSION: CONFIG.CONFIG_VERSION, // null,
|
||||
}),
|
||||
commonjs(),
|
||||
],
|
||||
build: {
|
||||
outDir: path.resolve(__dirname, './build'),
|
||||
chunkSizeWarningLimit: 1600,
|
||||
},
|
||||
publicDir: '/admin',
|
||||
}
|
||||
})
|
||||
|
||||
@ -1072,6 +1072,18 @@
|
||||
resolved "https://registry.yarnpkg.com/@graphql-typed-document-node/core/-/core-3.2.0.tgz#5f3d96ec6b2354ad6d8a28bf216a1d97b5426861"
|
||||
integrity sha512-mB9oAsNCm9aM3/SOv4YtBMqZbYj10R7dkq8byBqxGY/ncFwhf2oQzMV+LCRlWoDSEBJ3COiR1yeDvMtsoOsuFQ==
|
||||
|
||||
"@hapi/hoek@^9.0.0", "@hapi/hoek@^9.3.0":
|
||||
version "9.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/hoek/-/hoek-9.3.0.tgz#8368869dcb735be2e7f5cb7647de78e167a251fb"
|
||||
integrity sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==
|
||||
|
||||
"@hapi/topo@^5.1.0":
|
||||
version "5.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/topo/-/topo-5.1.0.tgz#dc448e332c6c6e37a4dc02fd84ba8d44b9afb012"
|
||||
integrity sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@humanwhocodes/config-array@^0.11.14":
|
||||
version "0.11.14"
|
||||
resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.14.tgz#d78e481a039f7566ecc9660b4ea7fe6b1fec442b"
|
||||
@ -1471,6 +1483,23 @@
|
||||
resolved "https://registry.yarnpkg.com/@rtsao/scc/-/scc-1.1.0.tgz#927dd2fae9bc3361403ac2c7a00c32ddce9ad7e8"
|
||||
integrity sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==
|
||||
|
||||
"@sideway/address@^4.1.5":
|
||||
version "4.1.5"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/address/-/address-4.1.5.tgz#4bc149a0076623ced99ca8208ba780d65a99b9d5"
|
||||
integrity sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@sideway/formula@^3.0.1":
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/formula/-/formula-3.0.1.tgz#80fcbcbaf7ce031e0ef2dd29b1bfc7c3f583611f"
|
||||
integrity sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==
|
||||
|
||||
"@sideway/pinpoint@^2.0.0":
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/pinpoint/-/pinpoint-2.0.0.tgz#cff8ffadc372ad29fd3f78277aeb29e632cc70df"
|
||||
integrity sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==
|
||||
|
||||
"@types/estree@1.0.6", "@types/estree@^1.0.0":
|
||||
version "1.0.6"
|
||||
resolved "https://registry.yarnpkg.com/@types/estree/-/estree-1.0.6.tgz#628effeeae2064a1b4e79f78e81d87b7e5fc7b50"
|
||||
@ -4195,6 +4224,11 @@ graceful-fs@^4.1.6, graceful-fs@^4.2.0:
|
||||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3"
|
||||
integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==
|
||||
|
||||
gradido-config@../config:
|
||||
version "1.0.0"
|
||||
dependencies:
|
||||
joi "^17.13.3"
|
||||
|
||||
graphemer@^1.4.0:
|
||||
version "1.4.0"
|
||||
resolved "https://registry.yarnpkg.com/graphemer/-/graphemer-1.4.0.tgz#fb2f1d55e0e3a1849aeffc90c4fa0dd53a0e66c6"
|
||||
@ -4712,6 +4746,17 @@ jest-canvas-mock@~2.5.2:
|
||||
cssfontparser "^1.2.1"
|
||||
moo-color "^1.0.2"
|
||||
|
||||
joi@^17.13.3:
|
||||
version "17.13.3"
|
||||
resolved "https://registry.yarnpkg.com/joi/-/joi-17.13.3.tgz#0f5cc1169c999b30d344366d384b12d92558bcec"
|
||||
integrity sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.3.0"
|
||||
"@hapi/topo" "^5.1.0"
|
||||
"@sideway/address" "^4.1.5"
|
||||
"@sideway/formula" "^3.0.1"
|
||||
"@sideway/pinpoint" "^2.0.0"
|
||||
|
||||
js-beautify@^1.14.9:
|
||||
version "1.15.1"
|
||||
resolved "https://registry.yarnpkg.com/js-beautify/-/js-beautify-1.15.1.tgz#4695afb508c324e1084ee0b952a102023fc65b64"
|
||||
|
||||
@ -3,7 +3,7 @@ PORT=4000
|
||||
JWT_SECRET=secret123
|
||||
JWT_EXPIRES_IN=10m
|
||||
GRAPHIQL=false
|
||||
GDT_API_URL=https://gdt.gradido.net
|
||||
GDT_ACTIVE=false
|
||||
|
||||
# Database
|
||||
DB_HOST=localhost
|
||||
@ -45,7 +45,7 @@ EMAIL_TEST_RECEIVER=stage1@gradido.net
|
||||
EMAIL_USERNAME=gradido_email
|
||||
EMAIL_SENDER=info@gradido.net
|
||||
EMAIL_PASSWORD=xxx
|
||||
EMAIL_SMTP_URL=gmail.com
|
||||
EMAIL_SMTP_HOST=gmail.com
|
||||
EMAIL_SMTP_PORT=587
|
||||
EMAIL_LINK_VERIFICATION_PATH=/checkEmail/{optin}{code}
|
||||
EMAIL_LINK_SETPASSWORD_PATH=/reset-password/{optin}
|
||||
|
||||
@ -45,7 +45,7 @@ EMAIL_TEST_RECEIVER=stage1@gradido.net
|
||||
EMAIL_USERNAME=gradido_email
|
||||
EMAIL_SENDER=info@gradido.net
|
||||
EMAIL_PASSWORD=xxx
|
||||
EMAIL_SMTP_URL=gmail.com
|
||||
EMAIL_SMTP_HOST=gmail.com
|
||||
EMAIL_SMTP_PORT=587
|
||||
EMAIL_LINK_VERIFICATION_PATH=/checkEmail/{optin}{code}
|
||||
EMAIL_LINK_SETPASSWORD_PATH=/reset-password/{optin}
|
||||
|
||||
@ -49,7 +49,7 @@ EMAIL_TEST_RECEIVER=$EMAIL_TEST_RECEIVER
|
||||
EMAIL_USERNAME=$EMAIL_USERNAME
|
||||
EMAIL_SENDER=$EMAIL_SENDER
|
||||
EMAIL_PASSWORD=$EMAIL_PASSWORD
|
||||
EMAIL_SMTP_URL=$EMAIL_SMTP_URL
|
||||
EMAIL_SMTP_HOST=$EMAIL_SMTP_HOST
|
||||
EMAIL_SMTP_PORT=$EMAIL_SMTP_PORT
|
||||
EMAIL_LINK_VERIFICATION_PATH=$EMAIL_LINK_VERIFICATION_PATH
|
||||
EMAIL_LINK_SETPASSWORD_PATH=$EMAIL_LINK_SETPASSWORD_PATH
|
||||
|
||||
@ -1,6 +1,8 @@
|
||||
# Server
|
||||
JWT_EXPIRES_IN=2m
|
||||
|
||||
GDT_ACTIVE=false
|
||||
|
||||
# Email
|
||||
EMAIL=true
|
||||
EMAIL_TEST_MODUS=false
|
||||
|
||||
@ -43,6 +43,7 @@ RUN mkdir -p ${DOCKER_WORKDIR}
|
||||
WORKDIR ${DOCKER_WORKDIR}
|
||||
|
||||
RUN mkdir -p /database
|
||||
RUN mkdir -p /config
|
||||
|
||||
##################################################################################
|
||||
# DEVELOPMENT (Connected to the local environment, to reload on demand) ##########
|
||||
@ -55,7 +56,7 @@ FROM base as development
|
||||
# Run command
|
||||
# (for development we need to execute yarn install since the
|
||||
# node_modules are on another volume and need updating)
|
||||
CMD /bin/sh -c "cd /database && yarn install && yarn build && cd /app && yarn install && yarn run dev"
|
||||
CMD /bin/sh -c "cd /database && yarn install && yarn build && cd /config && yarn install && cd /app && yarn install && yarn run dev"
|
||||
|
||||
##################################################################################
|
||||
# BUILD (Does contain all files and is therefore bloated) ########################
|
||||
@ -66,6 +67,11 @@ FROM base as build
|
||||
COPY ./backend/ ./
|
||||
# Copy everything from database
|
||||
COPY ./database/ ../database/
|
||||
# Copy everything from config
|
||||
COPY ./config/ ../config/
|
||||
|
||||
# yarn install and build config
|
||||
RUN cd ../config && yarn install --production=false --frozen-lockfile --non-interactive && yarn build
|
||||
|
||||
# yarn install backend
|
||||
RUN yarn install --production=false --frozen-lockfile --non-interactive
|
||||
@ -74,10 +80,10 @@ RUN yarn install --production=false --frozen-lockfile --non-interactive
|
||||
RUN cd ../database && yarn install --production=false --frozen-lockfile --non-interactive
|
||||
|
||||
# yarn build
|
||||
RUN yarn run build
|
||||
RUN yarn build
|
||||
|
||||
# yarn build database
|
||||
RUN cd ../database && yarn run build
|
||||
RUN cd ../database && yarn build
|
||||
|
||||
##################################################################################
|
||||
# TEST ###########################################################################
|
||||
@ -95,9 +101,11 @@ FROM base as production
|
||||
# Copy "binary"-files from build image
|
||||
COPY --from=build ${DOCKER_WORKDIR}/build ./build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../database/build ../database/build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/build ../config/build
|
||||
# We also copy the node_modules express and serve-static for the run script
|
||||
COPY --from=build ${DOCKER_WORKDIR}/node_modules ./node_modules
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../database/node_modules ../database/node_modules
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/node_modules ../config/node_modules
|
||||
|
||||
# Copy static files
|
||||
# COPY --from=build ${DOCKER_WORKDIR}/public ./public
|
||||
|
||||
@ -7,7 +7,7 @@ module.exports = {
|
||||
collectCoverageFrom: ['src/**/*.ts', '!**/node_modules/**', '!src/seeds/**', '!build/**'],
|
||||
coverageThreshold: {
|
||||
global: {
|
||||
lines: 81,
|
||||
lines: 80,
|
||||
},
|
||||
},
|
||||
setupFiles: ['<rootDir>/test/testSetup.ts'],
|
||||
@ -39,5 +39,10 @@ module.exports = {
|
||||
process.env.NODE_ENV === 'development'
|
||||
? '<rootDir>/../database/src/$1'
|
||||
: '<rootDir>/../database/build/src/$1',
|
||||
'@config/(.*)':
|
||||
// eslint-disable-next-line n/no-process-env
|
||||
process.env.NODE_ENV === 'development'
|
||||
? '<rootDir>/../config/src/$1'
|
||||
: '<rootDir>/../config/build/$1',
|
||||
},
|
||||
}
|
||||
|
||||
@ -33,12 +33,14 @@
|
||||
"email-templates": "^10.0.1",
|
||||
"express": "^4.17.1",
|
||||
"express-slow-down": "^2.0.1",
|
||||
"gradido-config": "file:../config",
|
||||
"gradido-database": "file:../database",
|
||||
"graphql": "^15.5.1",
|
||||
"graphql-request": "5.0.0",
|
||||
"graphql-type-json": "0.3.2",
|
||||
"helmet": "^5.1.1",
|
||||
"i18n": "^0.15.1",
|
||||
"joi": "^17.13.3",
|
||||
"jose": "^4.14.4",
|
||||
"lodash.clonedeep": "^4.5.0",
|
||||
"log4js": "^6.4.6",
|
||||
@ -61,8 +63,9 @@
|
||||
"@types/faker": "^5.5.9",
|
||||
"@types/i18n": "^0.13.4",
|
||||
"@types/jest": "^27.0.2",
|
||||
"@types/joi": "^17.2.3",
|
||||
"@types/lodash.clonedeep": "^4.5.6",
|
||||
"@types/node": "^16.10.3",
|
||||
"@types/node": "^17.0.21",
|
||||
"@types/nodemailer": "^6.4.4",
|
||||
"@types/sodium-native": "^2.3.5",
|
||||
"@types/uuid": "^8.3.4",
|
||||
|
||||
@ -1,9 +1,14 @@
|
||||
// ATTENTION: DO NOT PUT ANY SECRETS IN HERE (or the .env)
|
||||
/* eslint-disable n/no-process-env */
|
||||
|
||||
// eslint-disable-next-line import/no-unresolved
|
||||
import { validate } from '@config/index'
|
||||
import { latestDbVersion } from '@dbTools/config/detectLastDBVersion'
|
||||
import { Decimal } from 'decimal.js-light'
|
||||
import dotenv from 'dotenv'
|
||||
|
||||
import { schema } from './schema'
|
||||
|
||||
dotenv.config()
|
||||
|
||||
Decimal.set({
|
||||
@ -12,16 +17,10 @@ Decimal.set({
|
||||
})
|
||||
|
||||
const constants = {
|
||||
DB_VERSION: '0087-add_index_on_user_roles',
|
||||
// DB_VERSION: '0087-add_index_on_user_roles',
|
||||
DB_VERSION: latestDbVersion,
|
||||
DECAY_START_TIME: new Date('2021-05-13 17:46:31-0000'), // GMT+0
|
||||
LOG4JS_CONFIG: 'log4js-config.json',
|
||||
// default log level on production should be info
|
||||
LOG_LEVEL: process.env.LOG_LEVEL ?? 'info',
|
||||
CONFIG_VERSION: {
|
||||
DEFAULT: 'DEFAULT',
|
||||
EXPECTED: 'v23.2024-04-04',
|
||||
CURRENT: '',
|
||||
},
|
||||
}
|
||||
|
||||
const server = {
|
||||
@ -29,8 +28,11 @@ const server = {
|
||||
JWT_SECRET: process.env.JWT_SECRET ?? 'secret123',
|
||||
JWT_EXPIRES_IN: process.env.JWT_EXPIRES_IN ?? '10m',
|
||||
GRAPHIQL: process.env.GRAPHIQL === 'true' || false,
|
||||
GDT_ACTIVE: process.env.GDT_ACTIVE === 'true' || false,
|
||||
GDT_API_URL: process.env.GDT_API_URL ?? 'https://gdt.gradido.net',
|
||||
PRODUCTION: process.env.NODE_ENV === 'production' || false,
|
||||
// default log level on production should be info
|
||||
LOG_LEVEL: process.env.LOG_LEVEL ?? 'info',
|
||||
}
|
||||
|
||||
const database = {
|
||||
@ -64,10 +66,9 @@ const dltConnector = {
|
||||
const community = {
|
||||
COMMUNITY_NAME: process.env.COMMUNITY_NAME ?? 'Gradido Entwicklung',
|
||||
COMMUNITY_URL,
|
||||
COMMUNITY_REGISTER_URL: COMMUNITY_URL + (process.env.COMMUNITY_REGISTER_PATH ?? '/register'),
|
||||
COMMUNITY_REDEEM_URL: COMMUNITY_URL + (process.env.COMMUNITY_REDEEM_PATH ?? '/redeem/{code}'),
|
||||
COMMUNITY_REDEEM_URL: COMMUNITY_URL + (process.env.COMMUNITY_REDEEM_PATH ?? '/redeem/'),
|
||||
COMMUNITY_REDEEM_CONTRIBUTION_URL:
|
||||
COMMUNITY_URL + (process.env.COMMUNITY_REDEEM_CONTRIBUTION_PATH ?? '/redeem/CL-{code}'),
|
||||
COMMUNITY_URL + (process.env.COMMUNITY_REDEEM_CONTRIBUTION_PATH ?? '/redeem/CL-'),
|
||||
COMMUNITY_DESCRIPTION:
|
||||
process.env.COMMUNITY_DESCRIPTION ?? 'Die lokale Entwicklungsumgebung von Gradido.',
|
||||
COMMUNITY_SUPPORT_MAIL: process.env.COMMUNITY_SUPPORT_MAIL ?? 'support@supportmail.com',
|
||||
@ -86,14 +87,14 @@ const email = {
|
||||
EMAIL_USERNAME: process.env.EMAIL_USERNAME ?? '',
|
||||
EMAIL_SENDER: process.env.EMAIL_SENDER ?? 'info@gradido.net',
|
||||
EMAIL_PASSWORD: process.env.EMAIL_PASSWORD ?? '',
|
||||
EMAIL_SMTP_URL: process.env.EMAIL_SMTP_URL ?? 'mailserver',
|
||||
EMAIL_SMTP_HOST: process.env.EMAIL_SMTP_HOST ?? 'mailserver',
|
||||
EMAIL_SMTP_PORT: Number(process.env.EMAIL_SMTP_PORT) || 1025,
|
||||
// eslint-disable-next-line no-unneeded-ternary
|
||||
EMAIL_TLS: process.env.EMAIL_TLS === 'false' ? false : true,
|
||||
EMAIL_LINK_VERIFICATION:
|
||||
COMMUNITY_URL + (process.env.EMAIL_LINK_VERIFICATION_PATH ?? '/checkEmail/{optin}{code}'),
|
||||
COMMUNITY_URL + (process.env.EMAIL_LINK_VERIFICATION_PATH ?? '/checkEmail/'),
|
||||
EMAIL_LINK_SETPASSWORD:
|
||||
COMMUNITY_URL + (process.env.EMAIL_LINK_SETPASSWORD_PATH ?? '/reset-password/{optin}'),
|
||||
COMMUNITY_URL + (process.env.EMAIL_LINK_SETPASSWORD_PATH ?? '/reset-password/'),
|
||||
EMAIL_LINK_FORGOTPASSWORD:
|
||||
COMMUNITY_URL + (process.env.EMAIL_LINK_FORGOTPASSWORD_PATH ?? '/forgot-password'),
|
||||
EMAIL_LINK_OVERVIEW: COMMUNITY_URL + (process.env.EMAIL_LINK_OVERVIEW_PATH ?? '/overview'),
|
||||
@ -115,18 +116,6 @@ const webhook = {
|
||||
// This is needed by graphql-directive-auth
|
||||
process.env.APP_SECRET = server.JWT_SECRET
|
||||
|
||||
// Check config version
|
||||
constants.CONFIG_VERSION.CURRENT = process.env.CONFIG_VERSION ?? constants.CONFIG_VERSION.DEFAULT
|
||||
if (
|
||||
![constants.CONFIG_VERSION.EXPECTED, constants.CONFIG_VERSION.DEFAULT].includes(
|
||||
constants.CONFIG_VERSION.CURRENT,
|
||||
)
|
||||
) {
|
||||
throw new Error(
|
||||
`Fatal: Config Version incorrect - expected "${constants.CONFIG_VERSION.EXPECTED}" or "${constants.CONFIG_VERSION.DEFAULT}", but found "${constants.CONFIG_VERSION.CURRENT}"`,
|
||||
)
|
||||
}
|
||||
|
||||
const federation = {
|
||||
FEDERATION_BACKEND_SEND_ON_API: process.env.FEDERATION_BACKEND_SEND_ON_API ?? '1_0',
|
||||
// ?? operator don't work here as expected
|
||||
@ -172,3 +161,5 @@ export const CONFIG = {
|
||||
...gms,
|
||||
...humhub,
|
||||
}
|
||||
|
||||
validate(schema, CONFIG)
|
||||
|
||||
355
backend/src/config/schema.ts
Normal file
355
backend/src/config/schema.ts
Normal file
@ -0,0 +1,355 @@
|
||||
// eslint-disable-next-line import/no-unresolved
|
||||
import {
|
||||
COMMUNITY_NAME,
|
||||
COMMUNITY_URL,
|
||||
COMMUNITY_DESCRIPTION,
|
||||
COMMUNITY_SUPPORT_MAIL,
|
||||
DB_HOST,
|
||||
DB_PASSWORD,
|
||||
DB_PORT,
|
||||
DB_USER,
|
||||
DB_VERSION,
|
||||
DB_DATABASE,
|
||||
DECAY_START_TIME,
|
||||
GDT_API_URL,
|
||||
GDT_ACTIVE,
|
||||
GMS_ACTIVE,
|
||||
GRAPHIQL,
|
||||
HUMHUB_ACTIVE,
|
||||
LOG4JS_CONFIG,
|
||||
LOGIN_APP_SECRET,
|
||||
LOGIN_SERVER_KEY,
|
||||
LOG_LEVEL,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
TYPEORM_LOGGING_RELATIVE_PATH,
|
||||
} from '@config/commonSchema'
|
||||
import Joi from 'joi'
|
||||
|
||||
export const schema = Joi.object({
|
||||
COMMUNITY_NAME,
|
||||
COMMUNITY_URL,
|
||||
COMMUNITY_DESCRIPTION,
|
||||
COMMUNITY_SUPPORT_MAIL,
|
||||
DB_HOST,
|
||||
DB_PASSWORD,
|
||||
DB_PORT,
|
||||
DB_USER,
|
||||
DB_VERSION,
|
||||
DB_DATABASE,
|
||||
DECAY_START_TIME,
|
||||
GDT_API_URL,
|
||||
GDT_ACTIVE,
|
||||
GMS_ACTIVE,
|
||||
GRAPHIQL,
|
||||
HUMHUB_ACTIVE,
|
||||
LOG4JS_CONFIG,
|
||||
LOGIN_APP_SECRET,
|
||||
LOGIN_SERVER_KEY,
|
||||
LOG_LEVEL,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
TYPEORM_LOGGING_RELATIVE_PATH,
|
||||
|
||||
COMMUNITY_REDEEM_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.description('The url for redeeming link transactions, must start with frontend base url')
|
||||
.default('http://0.0.0.0/redeem/')
|
||||
.custom((value: string, helpers: Joi.CustomHelpers<string>): string | Joi.ErrorReport => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument, @typescript-eslint/no-unsafe-member-access
|
||||
if (!value.startsWith(helpers.state.ancestors[0].COMMUNITY_URL)) {
|
||||
return helpers.error('string.pattern.base', { value, communityUrl: COMMUNITY_URL })
|
||||
}
|
||||
return value
|
||||
})
|
||||
.required(),
|
||||
|
||||
COMMUNITY_REDEEM_CONTRIBUTION_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.custom((value: string, helpers: Joi.CustomHelpers<string>): string | Joi.ErrorReport => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument, @typescript-eslint/no-unsafe-member-access
|
||||
if (!value.startsWith(helpers.state.ancestors[0].COMMUNITY_URL)) {
|
||||
return helpers.error('string.pattern.base', { value, communityUrl: COMMUNITY_URL })
|
||||
}
|
||||
return value
|
||||
})
|
||||
.description(
|
||||
'The url for redeeming contribution link transactions, must start with frontend base url.',
|
||||
)
|
||||
.default('http://0.0.0.0/redeem/CL-')
|
||||
.required(),
|
||||
|
||||
DLT_CONNECTOR: Joi.boolean()
|
||||
.description('Flag to indicate if DLT-Connector is used. (Still in development)')
|
||||
.default(false)
|
||||
.required(),
|
||||
|
||||
DLT_CONNECTOR_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.default('http://localhost:6010')
|
||||
.when('DLT_CONNECTOR', { is: true, then: Joi.required() })
|
||||
.description('The URL for GDT API endpoint'),
|
||||
|
||||
EMAIL: Joi.boolean()
|
||||
.default(false)
|
||||
.description('Enable or disable email functionality')
|
||||
.required(),
|
||||
|
||||
EMAIL_TEST_MODUS: Joi.boolean()
|
||||
.default(false)
|
||||
.description('When enabled, all emails are sended to EMAIL_TEST_RECEIVER')
|
||||
.optional(),
|
||||
|
||||
EMAIL_TEST_RECEIVER: Joi.string()
|
||||
.email()
|
||||
.default('stage1@gradido.net')
|
||||
.when('EMAIL_TEST_MODUS', { is: true, then: Joi.required() })
|
||||
.description('Email address used in test mode'),
|
||||
|
||||
EMAIL_USERNAME: Joi.alternatives().conditional(Joi.ref('EMAIL'), {
|
||||
is: true,
|
||||
then: Joi.alternatives().conditional(Joi.ref('NODE_ENV'), {
|
||||
is: 'development',
|
||||
then: Joi.string()
|
||||
.allow('')
|
||||
.description('Username for SMTP authentication (optional in development)'),
|
||||
otherwise: Joi.string()
|
||||
.pattern(/^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/)
|
||||
.description('Valid SMTP username required in production')
|
||||
.required(),
|
||||
}),
|
||||
otherwise: Joi.string().allow('').optional(),
|
||||
}),
|
||||
|
||||
EMAIL_SENDER: Joi.string()
|
||||
.email()
|
||||
.when('EMAIL', { is: true, then: Joi.required() })
|
||||
.default('info@gradido.net')
|
||||
.description('Email address used as sender'),
|
||||
|
||||
EMAIL_PASSWORD: Joi.alternatives().conditional(Joi.ref('EMAIL'), {
|
||||
is: true,
|
||||
then: Joi.alternatives().conditional(Joi.ref('NODE_ENV'), {
|
||||
is: 'development',
|
||||
then: Joi.string()
|
||||
.allow('')
|
||||
.description('Password for SMTP authentication (optional in development)'),
|
||||
otherwise: Joi.string()
|
||||
.min(8)
|
||||
.pattern(/^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[@$!%*?&#]).{8,}$/)
|
||||
.description(
|
||||
'Password must be at least 8 characters long, include uppercase and lowercase letters, a number, and a special character',
|
||||
)
|
||||
.required(),
|
||||
}),
|
||||
otherwise: Joi.string().allow('').optional(),
|
||||
}),
|
||||
|
||||
EMAIL_SMTP_HOST: Joi.string()
|
||||
.hostname()
|
||||
.when('EMAIL', { is: true, then: Joi.required() })
|
||||
.default('mailserver')
|
||||
.description('SMTP server hostname'),
|
||||
|
||||
EMAIL_SMTP_PORT: Joi.number()
|
||||
.integer()
|
||||
.positive()
|
||||
.when('EMAIL', { is: true, then: Joi.required() })
|
||||
.default(1025)
|
||||
.description('SMTP server port'),
|
||||
|
||||
EMAIL_TLS: Joi.boolean().default(true).description('Enable or disable TLS for SMTP').optional(),
|
||||
|
||||
EMAIL_LINK_VERIFICATION: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.custom((value: string, helpers: Joi.CustomHelpers<string>): string | Joi.ErrorReport => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument, @typescript-eslint/no-unsafe-member-access
|
||||
if (!value.startsWith(helpers.state.ancestors[0].COMMUNITY_URL)) {
|
||||
return helpers.error('string.pattern.base', { value, communityUrl: COMMUNITY_URL })
|
||||
}
|
||||
return value
|
||||
})
|
||||
.description('Email Verification link for activate Email.')
|
||||
.required(),
|
||||
|
||||
EMAIL_LINK_SETPASSWORD: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.custom((value: string, helpers: Joi.CustomHelpers<string>): string | Joi.ErrorReport => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument, @typescript-eslint/no-unsafe-member-access
|
||||
if (!value.startsWith(helpers.state.ancestors[0].COMMUNITY_URL)) {
|
||||
return helpers.error('string.pattern.base', { value, communityUrl: COMMUNITY_URL })
|
||||
}
|
||||
return value
|
||||
})
|
||||
.description('Email Verification link for set initial Password.')
|
||||
.required(),
|
||||
|
||||
EMAIL_LINK_FORGOTPASSWORD: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.custom((value: string, helpers: Joi.CustomHelpers<string>): string | Joi.ErrorReport => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument, @typescript-eslint/no-unsafe-member-access
|
||||
if (!value.startsWith(helpers.state.ancestors[0].COMMUNITY_URL)) {
|
||||
return helpers.error('string.pattern.base', { value, communityUrl: COMMUNITY_URL })
|
||||
}
|
||||
return value
|
||||
})
|
||||
.description('Email Verification link for set new Password, when old Password was forgotten.')
|
||||
.required(),
|
||||
|
||||
EMAIL_LINK_OVERVIEW: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.custom((value: string, helpers: Joi.CustomHelpers<string>): string | Joi.ErrorReport => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument, @typescript-eslint/no-unsafe-member-access
|
||||
if (!value.startsWith(helpers.state.ancestors[0].COMMUNITY_URL)) {
|
||||
return helpers.error('string.pattern.base', { value, communityUrl: COMMUNITY_URL })
|
||||
}
|
||||
return value
|
||||
})
|
||||
.description('Link to Wallet Overview')
|
||||
.required(),
|
||||
|
||||
EMAIL_CODE_VALID_TIME: Joi.number()
|
||||
.integer()
|
||||
.positive()
|
||||
.max(43200) // max at 30 days
|
||||
.default(1440)
|
||||
.description('Time in minutes a code is valid')
|
||||
.required(),
|
||||
|
||||
EMAIL_CODE_REQUEST_TIME: Joi.number()
|
||||
.integer()
|
||||
.positive()
|
||||
.max(43200) // max at 30 days
|
||||
.default(10)
|
||||
.description('Time in minutes before a new code can be requested')
|
||||
.required(),
|
||||
|
||||
FEDERATION_BACKEND_SEND_ON_API: Joi.string()
|
||||
.pattern(/^\d+_\d+$/)
|
||||
.default('1_0')
|
||||
.description('API Version of sending requests to another communities, e.g., "1_0"')
|
||||
.required(),
|
||||
|
||||
FEDERATION_VALIDATE_COMMUNITY_TIMER: Joi.number()
|
||||
.integer()
|
||||
.min(1000)
|
||||
.default(60000)
|
||||
.description('Timer interval in milliseconds for community validation')
|
||||
.required(),
|
||||
|
||||
FEDERATION_XCOM_SENDCOINS_ENABLED: Joi.boolean()
|
||||
.default(false)
|
||||
.description('Enable or disable the federation send coins feature')
|
||||
.optional(),
|
||||
|
||||
FEDERATION_XCOM_RECEIVER_COMMUNITY_UUID: Joi.string()
|
||||
.uuid()
|
||||
.default('56a55482-909e-46a4-bfa2-cd025e894ebc')
|
||||
.description(
|
||||
'UUID of the receiver community for federation cross-community transactions if the receiver is unknown',
|
||||
)
|
||||
.required(),
|
||||
|
||||
FEDERATION_XCOM_MAXREPEAT_REVERTSENDCOINS: Joi.number()
|
||||
.integer()
|
||||
.min(0)
|
||||
.default(3)
|
||||
.description('Maximum number of retries for reverting send coins transactions')
|
||||
.required(),
|
||||
|
||||
GMS_CREATE_USER_THROW_ERRORS: Joi.boolean()
|
||||
.default(false)
|
||||
.when('GMS_ACTIVE', { is: true, then: Joi.required(), otherwise: Joi.optional() })
|
||||
.description('Whether errors should be thrown when creating users in GMS'),
|
||||
|
||||
GMS_API_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.when('GMS_ACTIVE', { is: true, then: Joi.required(), otherwise: Joi.optional() })
|
||||
.default('http://localhost:4044/')
|
||||
.description('The API URL for the GMS service'),
|
||||
|
||||
GMS_DASHBOARD_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.when('GMS_ACTIVE', { is: true, then: Joi.required(), otherwise: Joi.optional() })
|
||||
.default('http://localhost:8080/')
|
||||
.description('The URL for the GMS dashboard'),
|
||||
|
||||
GMS_WEBHOOK_SECRET: Joi.string()
|
||||
.min(1)
|
||||
.default('secret')
|
||||
.when('GMS_ACTIVE', { is: true, then: Joi.required(), otherwise: Joi.optional() })
|
||||
.description('The secret postfix for the GMS webhook endpoint'),
|
||||
|
||||
HUMHUB_API_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.when('HUMHUB_ACTIVE', { is: true, then: Joi.required(), otherwise: Joi.optional() })
|
||||
.description('The API URL for HumHub integration'),
|
||||
|
||||
HUMHUB_JWT_KEY: Joi.string()
|
||||
.min(1)
|
||||
.when('HUMHUB_ACTIVE', {
|
||||
is: true,
|
||||
then: Joi.required(),
|
||||
otherwise: Joi.string().allow('').optional(),
|
||||
})
|
||||
.description('JWT key for HumHub integration, must be the same as configured in humhub'),
|
||||
|
||||
PORT: Joi.number()
|
||||
.integer()
|
||||
.min(1024)
|
||||
.max(49151)
|
||||
.description('Port for hosting backend, default: 4000')
|
||||
.default(4000)
|
||||
.required(),
|
||||
|
||||
KLICKTIPP: Joi.boolean()
|
||||
.default(false)
|
||||
.description("Indicates whether Klicktipp integration is enabled, 'true' or 'false'"),
|
||||
|
||||
KLICKTTIPP_API_URL: Joi.string()
|
||||
.uri({ scheme: ['https'] }) // Sicherstellen, dass es eine gültige HTTPS-URL ist
|
||||
.default('https://api.klicktipp.com')
|
||||
.description("The API URL for Klicktipp, must be a valid URL starting with 'https'"),
|
||||
|
||||
KLICKTIPP_USER: Joi.string().default('gradido_test').description('The username for Klicktipp'),
|
||||
|
||||
KLICKTIPP_PASSWORD: Joi.string()
|
||||
.min(6)
|
||||
.default('secret321')
|
||||
.description('The password for Klicktipp, should be at least 6 characters'),
|
||||
|
||||
KLICKTIPP_APIKEY_DE: Joi.string()
|
||||
.default('SomeFakeKeyDE')
|
||||
.description('The API key for Klicktipp (German version)'),
|
||||
|
||||
KLICKTIPP_APIKEY_EN: Joi.string()
|
||||
.default('SomeFakeKeyEN')
|
||||
.description('The API key for Klicktipp (English version)'),
|
||||
|
||||
USE_CRYPTO_WORKER: Joi.boolean()
|
||||
.default(false)
|
||||
.description(
|
||||
'Flag to enable or disable password encryption in separate thread, should be enabled if possible',
|
||||
),
|
||||
|
||||
// TODO: check format
|
||||
JWT_SECRET: Joi.string()
|
||||
.default('secret123')
|
||||
.description('jwt secret for jwt tokens used for login')
|
||||
.required(),
|
||||
|
||||
JWT_EXPIRES_IN: Joi.alternatives()
|
||||
.try(
|
||||
Joi.string()
|
||||
.pattern(/^\d+[smhdw]$/) // Time specification such as “10m”, “1h”, “2d”, etc.
|
||||
.description('Expiration time for JWT login token, in format like "10m", "1h", "1d"')
|
||||
.default('10m'),
|
||||
Joi.number()
|
||||
.positive() // positive number to accept seconds
|
||||
.description('Expiration time for JWT login token in seconds'),
|
||||
)
|
||||
.required()
|
||||
.description('Time for JWT token to expire, auto logout'),
|
||||
|
||||
WEBHOOK_ELOPAGE_SECRET: Joi.string().description("isn't really used any more").optional(),
|
||||
})
|
||||
@ -68,9 +68,9 @@ export class PublishNameLogic {
|
||||
*/
|
||||
public getUsername(publishNameType: PublishNameType): string {
|
||||
if (this.isUsernameFromInitials(publishNameType)) {
|
||||
return this.filterOutInvalidChar(
|
||||
this.firstUpperCaseSecondLowerCase(this.user.firstName) +
|
||||
this.firstUpperCaseSecondLowerCase(this.user.lastName),
|
||||
return (
|
||||
this.firstUpperCaseSecondLowerCase(this.filterOutInvalidChar(this.user.firstName)) +
|
||||
this.firstUpperCaseSecondLowerCase(this.filterOutInvalidChar(this.user.lastName))
|
||||
)
|
||||
} else if (this.isUsernameFromAlias(publishNameType)) {
|
||||
return this.filterOutInvalidChar(this.user.alias)
|
||||
|
||||
@ -7,9 +7,12 @@ import { CONFIG } from '@/config'
|
||||
|
||||
import { sendEmailTranslated } from './sendEmailTranslated'
|
||||
|
||||
const testMailServerHost = 'localhost'
|
||||
const testMailServerPort = 1025
|
||||
|
||||
CONFIG.EMAIL = false
|
||||
CONFIG.EMAIL_SMTP_URL = 'EMAIL_SMTP_URL'
|
||||
CONFIG.EMAIL_SMTP_PORT = 1234
|
||||
CONFIG.EMAIL_SMTP_HOST = testMailServerHost
|
||||
CONFIG.EMAIL_SMTP_PORT = testMailServerPort
|
||||
CONFIG.EMAIL_SENDER = 'info@gradido.net'
|
||||
CONFIG.EMAIL_USERNAME = 'user'
|
||||
CONFIG.EMAIL_PASSWORD = 'pwd'
|
||||
@ -73,8 +76,8 @@ describe('sendEmailTranslated', () => {
|
||||
|
||||
it('calls the transporter', () => {
|
||||
expect(createTransport).toBeCalledWith({
|
||||
host: 'EMAIL_SMTP_URL',
|
||||
port: 1234,
|
||||
host: testMailServerHost,
|
||||
port: testMailServerPort,
|
||||
secure: false,
|
||||
requireTLS: true,
|
||||
auth: {
|
||||
@ -87,11 +90,6 @@ describe('sendEmailTranslated', () => {
|
||||
describe('call of "sendEmailTranslated"', () => {
|
||||
it('has expected result', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['receiver@mail.org', 'support@gradido.net'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'receiver@mail.org',
|
||||
cc: 'support@gradido.net',
|
||||
@ -135,11 +133,6 @@ describe('sendEmailTranslated', () => {
|
||||
|
||||
it('call of "sendEmailTranslated" with faked "to"', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: CONFIG.EMAIL_SENDER,
|
||||
to: [CONFIG.EMAIL_TEST_RECEIVER, 'support@gradido.net'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: CONFIG.EMAIL_TEST_RECEIVER,
|
||||
cc: 'support@gradido.net',
|
||||
|
||||
@ -45,7 +45,7 @@ export const sendEmailTranslated = async ({
|
||||
receiver.to = CONFIG.EMAIL_TEST_RECEIVER
|
||||
}
|
||||
const transport = createTransport({
|
||||
host: CONFIG.EMAIL_SMTP_URL,
|
||||
host: CONFIG.EMAIL_SMTP_HOST,
|
||||
port: CONFIG.EMAIL_SMTP_PORT,
|
||||
secure: false, // true for 465, false for other ports
|
||||
requireTLS: CONFIG.EMAIL_TLS,
|
||||
@ -62,6 +62,7 @@ export const sendEmailTranslated = async ({
|
||||
message: {
|
||||
from: `Gradido (${i18n.__('emails.general.doNotAnswer')}) <${CONFIG.EMAIL_SENDER}>`,
|
||||
},
|
||||
send: CONFIG.EMAIL,
|
||||
transport,
|
||||
preview: false,
|
||||
// i18n, // is only needed if you don't install i18n
|
||||
|
||||
@ -25,7 +25,14 @@ import {
|
||||
sendContributionChangedByModeratorEmail,
|
||||
} from './sendEmailVariants'
|
||||
|
||||
const testMailServerHost = 'localhost'
|
||||
const testMailServerPort = 1025
|
||||
const testMailTLS = false
|
||||
|
||||
CONFIG.EMAIL_SENDER = 'info@gradido.net'
|
||||
CONFIG.EMAIL_SMTP_HOST = testMailServerHost
|
||||
CONFIG.EMAIL_SMTP_PORT = testMailServerPort
|
||||
CONFIG.EMAIL_TLS = testMailTLS
|
||||
|
||||
let con: Connection
|
||||
let testEnv: {
|
||||
@ -93,11 +100,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -151,11 +153,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -204,11 +201,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -267,11 +259,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -329,11 +316,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -389,11 +371,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('has expected result', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -449,11 +426,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -507,11 +479,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -571,11 +538,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
@ -633,11 +595,6 @@ describe('sendEmailVariants', () => {
|
||||
describe('result', () => {
|
||||
it('is the expected object', () => {
|
||||
expect(result).toMatchObject({
|
||||
envelope: {
|
||||
from: 'info@gradido.net',
|
||||
to: ['peter@lustig.de'],
|
||||
},
|
||||
message: expect.any(String),
|
||||
originalMessage: expect.objectContaining({
|
||||
to: 'Peter Lustig <peter@lustig.de>',
|
||||
from: 'Gradido (emails.general.doNotAnswer) <info@gradido.net>',
|
||||
|
||||
@ -19,7 +19,7 @@ export class ContributionLink {
|
||||
this.cycle = contributionLink.cycle
|
||||
this.maxPerCycle = contributionLink.maxPerCycle
|
||||
this.code = contributionLink.code
|
||||
this.link = CONFIG.COMMUNITY_REDEEM_CONTRIBUTION_URL.replace(/{code}/g, this.code)
|
||||
this.link = CONFIG.COMMUNITY_REDEEM_CONTRIBUTION_URL + this.code
|
||||
}
|
||||
|
||||
@Field(() => Int)
|
||||
|
||||
@ -20,7 +20,7 @@ export class TransactionLink {
|
||||
this.deletedAt = transactionLink.deletedAt
|
||||
this.redeemedAt = transactionLink.redeemedAt
|
||||
this.redeemedBy = redeemedBy
|
||||
this.link = CONFIG.COMMUNITY_REDEEM_URL.replace(/{code}/g, this.code)
|
||||
this.link = CONFIG.COMMUNITY_REDEEM_URL + this.code
|
||||
}
|
||||
|
||||
@Field(() => Int)
|
||||
|
||||
@ -24,6 +24,16 @@ export class GdtResolver {
|
||||
{ currentPage = 1, pageSize = 5, order = Order.DESC }: Paginated,
|
||||
@Ctx() context: Context,
|
||||
): Promise<GdtEntryList> {
|
||||
if (!CONFIG.GDT_ACTIVE) {
|
||||
return new GdtEntryList(
|
||||
'disabled',
|
||||
0,
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-call, @typescript-eslint/no-explicit-any
|
||||
[],
|
||||
0,
|
||||
0,
|
||||
)
|
||||
}
|
||||
const userEntity = getUser(context)
|
||||
|
||||
try {
|
||||
@ -51,6 +61,9 @@ export class GdtResolver {
|
||||
@Authorized([RIGHTS.GDT_BALANCE])
|
||||
@Query(() => Float, { nullable: true })
|
||||
async gdtBalance(@Ctx() context: Context): Promise<number | null> {
|
||||
if (!CONFIG.GDT_ACTIVE) {
|
||||
return null
|
||||
}
|
||||
const user = getUser(context)
|
||||
try {
|
||||
const resultGDTSum = await apiPost(`${CONFIG.GDT_API_URL}/GdtEntries/sumPerEmailApi`, {
|
||||
@ -71,6 +84,9 @@ export class GdtResolver {
|
||||
@Query(() => Int)
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
async existPid(@Arg('pid', () => Int) pid: number): Promise<number> {
|
||||
if (!CONFIG.GDT_ACTIVE) {
|
||||
return 0
|
||||
}
|
||||
// load user
|
||||
const resultPID = await apiGet(`${CONFIG.GDT_API_URL}/publishers/checkPidApi/${pid}`)
|
||||
if (!resultPID.success) {
|
||||
|
||||
@ -230,8 +230,11 @@ export class TransactionResolver {
|
||||
logger.addContext('user', user.id)
|
||||
logger.info(`transactionList(user=${user.firstName}.${user.lastName}, ${user.emailId})`)
|
||||
|
||||
const gdtResolver = new GdtResolver()
|
||||
const balanceGDTPromise = gdtResolver.gdtBalance(context)
|
||||
let balanceGDTPromise: Promise<number | null> = Promise.resolve(null)
|
||||
if (CONFIG.GDT_ACTIVE) {
|
||||
const gdtResolver = new GdtResolver()
|
||||
balanceGDTPromise = gdtResolver.gdtBalance(context)
|
||||
}
|
||||
|
||||
// find current balance
|
||||
const lastTransaction = await getLastTransaction(user.id)
|
||||
@ -418,8 +421,10 @@ export class TransactionResolver {
|
||||
).toDecimalPlaces(2, Decimal.ROUND_HALF_UP)
|
||||
}
|
||||
})
|
||||
const balanceGDT = await balanceGDTPromise
|
||||
context.balanceGDT = balanceGDT
|
||||
if (CONFIG.GDT_ACTIVE) {
|
||||
const balanceGDT = await balanceGDTPromise
|
||||
context.balanceGDT = balanceGDT
|
||||
}
|
||||
|
||||
// Construct Result
|
||||
return new TransactionList(await balanceResolver.balance(context), transactions)
|
||||
|
||||
@ -244,10 +244,10 @@ describe('UserResolver', () => {
|
||||
|
||||
describe('account activation email', () => {
|
||||
it('sends an account activation email', () => {
|
||||
const activationLink = CONFIG.EMAIL_LINK_VERIFICATION.replace(
|
||||
/{optin}/g,
|
||||
emailVerificationCode,
|
||||
).replace(/{code}/g, '')
|
||||
const activationLink = `${
|
||||
CONFIG.EMAIL_LINK_VERIFICATION
|
||||
}${emailVerificationCode.toString()}`
|
||||
|
||||
expect(sendAccountActivationEmail).toBeCalledWith({
|
||||
firstName: 'Peter',
|
||||
lastName: 'Lustig',
|
||||
@ -2230,14 +2230,13 @@ describe('UserResolver', () => {
|
||||
})
|
||||
|
||||
it('sends an account activation email', async () => {
|
||||
const userConatct = await UserContact.findOneOrFail({
|
||||
const userContact = await UserContact.findOneOrFail({
|
||||
where: { email: 'bibi@bloxberg.de' },
|
||||
relations: ['user'],
|
||||
})
|
||||
const activationLink = CONFIG.EMAIL_LINK_VERIFICATION.replace(
|
||||
/{optin}/g,
|
||||
userConatct.emailVerificationCode.toString(),
|
||||
).replace(/{code}/g, '')
|
||||
const activationLink = `${
|
||||
CONFIG.EMAIL_LINK_VERIFICATION
|
||||
}${userContact.emailVerificationCode.toString()}`
|
||||
expect(sendAccountActivationEmail).toBeCalledWith({
|
||||
firstName: 'Bibi',
|
||||
lastName: 'Bloxberg',
|
||||
@ -2252,14 +2251,14 @@ describe('UserResolver', () => {
|
||||
})
|
||||
|
||||
it('stores the EMAIL_ADMIN_CONFIRMATION event in the database', async () => {
|
||||
const userConatct = await UserContact.findOneOrFail({
|
||||
const userContact = await UserContact.findOneOrFail({
|
||||
where: { email: 'bibi@bloxberg.de' },
|
||||
relations: ['user'],
|
||||
})
|
||||
await expect(DbEvent.find()).resolves.toContainEqual(
|
||||
expect.objectContaining({
|
||||
type: EventType.EMAIL_ADMIN_CONFIRMATION,
|
||||
affectedUserId: userConatct.user.id,
|
||||
affectedUserId: userContact.user.id,
|
||||
actingUserId: admin.id,
|
||||
}),
|
||||
)
|
||||
|
||||
@ -109,7 +109,7 @@ const newEmailContact = (email: string, userId: number): DbUserContact => {
|
||||
// eslint-disable-next-line @typescript-eslint/ban-types
|
||||
export const activationLink = (verificationCode: string): string => {
|
||||
logger.debug(`activationLink(${verificationCode})...`)
|
||||
return CONFIG.EMAIL_LINK_SETPASSWORD.replace(/{optin}/g, verificationCode.toString())
|
||||
return CONFIG.EMAIL_LINK_SETPASSWORD + verificationCode.toString()
|
||||
}
|
||||
|
||||
const newGradidoID = async (): Promise<string> => {
|
||||
@ -371,10 +371,9 @@ export class UserResolver {
|
||||
throw new LogError('Error while updating dbUser', error)
|
||||
})
|
||||
|
||||
const activationLink = CONFIG.EMAIL_LINK_VERIFICATION.replace(
|
||||
/{optin}/g,
|
||||
emailContact.emailVerificationCode.toString(),
|
||||
).replace(/{code}/g, redeemCode ? '/' + redeemCode : '')
|
||||
const activationLink = `${
|
||||
CONFIG.EMAIL_LINK_VERIFICATION
|
||||
}${emailContact.emailVerificationCode.toString()}${redeemCode ? `/${redeemCode}` : ''}`
|
||||
|
||||
void sendAccountActivationEmail({
|
||||
firstName,
|
||||
|
||||
@ -15,6 +15,7 @@
|
||||
// "sourceMap": true, /* Generates corresponding '.map' file. */
|
||||
// "outFile": "./", /* Concatenate and emit output to single file. */
|
||||
"outDir": "./build", /* Redirect output structure to the directory. */
|
||||
// "rootDir" : ".",
|
||||
// "rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */
|
||||
// "composite": true, /* Enable project compilation */
|
||||
// "tsBuildInfoFile": "./", /* Specify file to store incremental compilation information */
|
||||
@ -60,7 +61,8 @@
|
||||
/* external */
|
||||
"@dbTools/*": ["../database/src/*", "../../database/build/src/*"],
|
||||
"@entity/*": ["../database/entity/*", "../../database/build/entity/*"],
|
||||
"@logging/*": ["../database/logging/*", "../../database/build/logging/*"]
|
||||
"@logging/*": ["../database/logging/*", "../../database/build/logging/*"],
|
||||
"@config/*": ["../config/src/*", "../../config/build/src/*"]
|
||||
},
|
||||
// "rootDirs": [], /* List of root folders whose combined content represents the structure of the project at runtime. */
|
||||
"typeRoots": ["@types", "node_modules/@types"], /* List of folders to include type definitions from. */
|
||||
@ -86,9 +88,12 @@
|
||||
},
|
||||
"references": [
|
||||
{
|
||||
"path": "../database/tsconfig.json",
|
||||
"path": "../database/tsconfig.json"
|
||||
// add 'prepend' if you want to include the referenced project in your output file
|
||||
// "prepend": true
|
||||
},
|
||||
{
|
||||
"path": "../config/tsconfig.json"
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@ -332,13 +332,6 @@
|
||||
core-js-pure "^3.30.2"
|
||||
regenerator-runtime "^0.14.0"
|
||||
|
||||
"@babel/runtime@^7.21.0":
|
||||
version "7.22.5"
|
||||
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.22.5.tgz#8564dd588182ce0047d55d7a75e93921107b57ec"
|
||||
integrity sha512-ecjvYlnAaZ/KVneE/OdKYBYfgXV3Ptu6zQWmgEF7vwKhQnvVS6bjMD2XYgj+SNvQ1GfK/pjgokfPkC/2CO8CuA==
|
||||
dependencies:
|
||||
regenerator-runtime "^0.13.11"
|
||||
|
||||
"@babel/template@^7.15.4", "@babel/template@^7.3.3":
|
||||
version "7.15.4"
|
||||
resolved "https://registry.yarnpkg.com/@babel/template/-/template-7.15.4.tgz#51898d35dcf3faa670c4ee6afcfd517ee139f194"
|
||||
@ -454,6 +447,18 @@
|
||||
resolved "https://registry.yarnpkg.com/@hapi/hoek/-/hoek-10.0.1.tgz#ee9da297fabc557e1c040a0f44ee89c266ccc306"
|
||||
integrity sha512-CvlW7jmOhWzuqOqiJQ3rQVLMcREh0eel4IBnxDx2FAcK8g7qoJRQK4L1CPBASoCY6y8e6zuCy3f2g+HWdkzcMw==
|
||||
|
||||
"@hapi/hoek@^9.0.0", "@hapi/hoek@^9.3.0":
|
||||
version "9.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/hoek/-/hoek-9.3.0.tgz#8368869dcb735be2e7f5cb7647de78e167a251fb"
|
||||
integrity sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==
|
||||
|
||||
"@hapi/topo@^5.1.0":
|
||||
version "5.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/topo/-/topo-5.1.0.tgz#dc448e332c6c6e37a4dc02fd84ba8d44b9afb012"
|
||||
integrity sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@humanwhocodes/config-array@^0.11.8":
|
||||
version "0.11.8"
|
||||
resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.8.tgz#03595ac2075a4dc0f191cc2131de14fbd7d410b9"
|
||||
@ -473,6 +478,18 @@
|
||||
resolved "https://registry.yarnpkg.com/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz#b520529ec21d8e5945a1851dfd1c32e94e39ff45"
|
||||
integrity sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA==
|
||||
|
||||
"@isaacs/cliui@^8.0.2":
|
||||
version "8.0.2"
|
||||
resolved "https://registry.yarnpkg.com/@isaacs/cliui/-/cliui-8.0.2.tgz#b37667b7bc181c168782259bab42474fbf52b550"
|
||||
integrity sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==
|
||||
dependencies:
|
||||
string-width "^5.1.2"
|
||||
string-width-cjs "npm:string-width@^4.2.0"
|
||||
strip-ansi "^7.0.1"
|
||||
strip-ansi-cjs "npm:strip-ansi@^6.0.1"
|
||||
wrap-ansi "^8.1.0"
|
||||
wrap-ansi-cjs "npm:wrap-ansi@^7.0.0"
|
||||
|
||||
"@istanbuljs/load-nyc-config@^1.0.0":
|
||||
version "1.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@istanbuljs/load-nyc-config/-/load-nyc-config-1.1.0.tgz#fd3db1d59ecf7cf121e80650bb86712f9b55eced"
|
||||
@ -750,6 +767,11 @@
|
||||
"@nodelib/fs.scandir" "2.1.5"
|
||||
fastq "^1.6.0"
|
||||
|
||||
"@pkgjs/parseargs@^0.11.0":
|
||||
version "0.11.0"
|
||||
resolved "https://registry.yarnpkg.com/@pkgjs/parseargs/-/parseargs-0.11.0.tgz#a77ea742fab25775145434eb1d2328cf5013ac33"
|
||||
integrity sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==
|
||||
|
||||
"@pkgr/utils@^2.3.1":
|
||||
version "2.3.1"
|
||||
resolved "https://registry.yarnpkg.com/@pkgr/utils/-/utils-2.3.1.tgz#0a9b06ffddee364d6642b3cd562ca76f55b34a03"
|
||||
@ -823,6 +845,23 @@
|
||||
domhandler "^4.2.0"
|
||||
selderee "^0.6.0"
|
||||
|
||||
"@sideway/address@^4.1.5":
|
||||
version "4.1.5"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/address/-/address-4.1.5.tgz#4bc149a0076623ced99ca8208ba780d65a99b9d5"
|
||||
integrity sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@sideway/formula@^3.0.1":
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/formula/-/formula-3.0.1.tgz#80fcbcbaf7ce031e0ef2dd29b1bfc7c3f583611f"
|
||||
integrity sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==
|
||||
|
||||
"@sideway/pinpoint@^2.0.0":
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/pinpoint/-/pinpoint-2.0.0.tgz#cff8ffadc372ad29fd3f78277aeb29e632cc70df"
|
||||
integrity sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==
|
||||
|
||||
"@sindresorhus/is@^0.14.0":
|
||||
version "0.14.0"
|
||||
resolved "https://registry.yarnpkg.com/@sindresorhus/is/-/is-0.14.0.tgz#9fb3a3cf3132328151f353de4632e01e52102bea"
|
||||
@ -1064,6 +1103,13 @@
|
||||
jest-diff "^27.0.0"
|
||||
pretty-format "^27.0.0"
|
||||
|
||||
"@types/joi@^17.2.3":
|
||||
version "17.2.3"
|
||||
resolved "https://registry.yarnpkg.com/@types/joi/-/joi-17.2.3.tgz#b7768ed9d84f1ebd393328b9f97c1cf3d2b94798"
|
||||
integrity sha512-dGjs/lhrWOa+eO0HwgxCSnDm5eMGCsXuvLglMghJq32F6q5LyyNuXb41DHzrg501CKNOSSAHmfB7FDGeUnDmzw==
|
||||
dependencies:
|
||||
joi "*"
|
||||
|
||||
"@types/json-schema@^7.0.9":
|
||||
version "7.0.11"
|
||||
resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.11.tgz#d421b6c527a3037f7c84433fd2c4229e016863d3"
|
||||
@ -1128,13 +1174,13 @@
|
||||
integrity sha512-Klz949h02Gz2uZCMGwDUSDS1YBlTdDDgbWHi+81l29tQALUtvz4rAYi5uoVhE5Lagoq6DeqAUlbrHvW/mXDgdQ==
|
||||
|
||||
"@types/mysql@^2.15.8":
|
||||
version "2.15.21"
|
||||
resolved "https://registry.yarnpkg.com/@types/mysql/-/mysql-2.15.21.tgz#7516cba7f9d077f980100c85fd500c8210bd5e45"
|
||||
integrity sha512-NPotx5CVful7yB+qZbWtXL2fA4e7aEHkihHLjklc6ID8aq7bhguHgeIoC1EmSNTAuCgI6ZXrjt2ZSaXnYX0EUg==
|
||||
version "2.15.26"
|
||||
resolved "https://registry.yarnpkg.com/@types/mysql/-/mysql-2.15.26.tgz#f0de1484b9e2354d587e7d2bd17a873cc8300836"
|
||||
integrity sha512-DSLCOXhkvfS5WNNPbfn2KdICAmk8lLc+/PNvnPnF7gOdMZCxopXduqv0OQ13y/yA/zXTSikZZqVgybUxOEg6YQ==
|
||||
dependencies:
|
||||
"@types/node" "*"
|
||||
|
||||
"@types/node@*", "@types/node@^16.10.3":
|
||||
"@types/node@*":
|
||||
version "16.10.3"
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-16.10.3.tgz#7a8f2838603ea314d1d22bb3171d899e15c57bd5"
|
||||
integrity sha512-ho3Ruq+fFnBrZhUYI46n/bV2GjwzSkwuT4dTf0GkuNFmnb8nq4ny2z9JEVemFi6bdEJanHLlYfy9c6FN9B9McQ==
|
||||
@ -1149,6 +1195,11 @@
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-14.17.21.tgz#6359d8cf73481e312a43886fa50afc70ce5592c6"
|
||||
integrity sha512-zv8ukKci1mrILYiQOwGSV4FpkZhyxQtuFWGya2GujWg+zVAeRQ4qbaMmWp9vb9889CFA8JECH7lkwCL6Ygg8kA==
|
||||
|
||||
"@types/node@^17.0.21":
|
||||
version "17.0.45"
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.45.tgz#2c0fafd78705e7a18b7906b5201a522719dc5190"
|
||||
integrity sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw==
|
||||
|
||||
"@types/nodemailer@*":
|
||||
version "6.4.6"
|
||||
resolved "https://registry.yarnpkg.com/@types/nodemailer/-/nodemailer-6.4.6.tgz#ce21b4b474a08f672f182e15982b7945dde1f288"
|
||||
@ -1528,6 +1579,11 @@ ansi-regex@^5.0.1:
|
||||
resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304"
|
||||
integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==
|
||||
|
||||
ansi-regex@^6.0.1:
|
||||
version "6.1.0"
|
||||
resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-6.1.0.tgz#95ec409c69619d6cb1b8b34f14b660ef28ebd654"
|
||||
integrity sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==
|
||||
|
||||
ansi-styles@^3.2.1:
|
||||
version "3.2.1"
|
||||
resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d"
|
||||
@ -1547,6 +1603,11 @@ ansi-styles@^5.0.0:
|
||||
resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-5.2.0.tgz#07449690ad45777d1924ac2abb2fc8895dba836b"
|
||||
integrity sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==
|
||||
|
||||
ansi-styles@^6.1.0:
|
||||
version "6.2.1"
|
||||
resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-6.2.1.tgz#0e62320cf99c21afff3b3012192546aacbfb05c5"
|
||||
integrity sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==
|
||||
|
||||
any-promise@^1.0.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/any-promise/-/any-promise-1.3.0.tgz#abc6afeedcea52e809cdc0376aed3ce39635d17f"
|
||||
@ -2396,6 +2457,15 @@ cross-spawn@^6.0.0:
|
||||
shebang-command "^1.2.0"
|
||||
which "^1.2.9"
|
||||
|
||||
cross-spawn@^7.0.0:
|
||||
version "7.0.6"
|
||||
resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.6.tgz#8a58fe78f00dcd70c370451759dfbfaf03e8ee9f"
|
||||
integrity sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==
|
||||
dependencies:
|
||||
path-key "^3.1.0"
|
||||
shebang-command "^2.0.0"
|
||||
which "^2.0.1"
|
||||
|
||||
cross-spawn@^7.0.1, cross-spawn@^7.0.2, cross-spawn@^7.0.3:
|
||||
version "7.0.3"
|
||||
resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6"
|
||||
@ -2469,18 +2539,16 @@ data-urls@^2.0.0:
|
||||
whatwg-mimetype "^2.3.0"
|
||||
whatwg-url "^8.0.0"
|
||||
|
||||
date-fns@^2.29.3:
|
||||
version "2.30.0"
|
||||
resolved "https://registry.yarnpkg.com/date-fns/-/date-fns-2.30.0.tgz#f367e644839ff57894ec6ac480de40cae4b0f4d0"
|
||||
integrity sha512-fnULvOpxnC5/Vg3NCiWelDsLiUc9bRwAPs/+LfTLNvetFCtCTN+yQz15C/fs4AwX1R9K5GLtLfn8QW+dWisaAw==
|
||||
dependencies:
|
||||
"@babel/runtime" "^7.21.0"
|
||||
|
||||
date-format@^4.0.9:
|
||||
version "4.0.9"
|
||||
resolved "https://registry.yarnpkg.com/date-format/-/date-format-4.0.9.tgz#4788015ac56dedebe83b03bc361f00c1ddcf1923"
|
||||
integrity sha512-+8J+BOUpSrlKLQLeF8xJJVTxS8QfRSuJgwxSVvslzgO3E6khbI0F5mMEPf5mTYhCCm4h99knYP6H3W9n3BQFrg==
|
||||
|
||||
dayjs@^1.11.9:
|
||||
version "1.11.13"
|
||||
resolved "https://registry.yarnpkg.com/dayjs/-/dayjs-1.11.13.tgz#92430b0139055c3ebb60150aa13e860a4b5a366c"
|
||||
integrity sha512-oaMBel6gjolK862uaPQOVTA7q3TZhuSvuMQAAglQDOWYO9A91IrAOUJEyKVlqJlHE0vq5p5UXxzdPfMH/x6xNg==
|
||||
|
||||
debug@2.6.9, debug@^2.2.0:
|
||||
version "2.6.9"
|
||||
resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f"
|
||||
@ -2714,15 +2782,20 @@ dotenv@^10.0.0:
|
||||
integrity sha512-rlBi9d8jpv9Sf1klPjNfFAuWDjKLwTIJJ/VxtoTwIR6hnZxcEOQCZg2oIL3MWBYw5GpUDKOEnND7LXTbIpQ03Q==
|
||||
|
||||
dotenv@^16.0.3:
|
||||
version "16.3.1"
|
||||
resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-16.3.1.tgz#369034de7d7e5b120972693352a3bf112172cc3e"
|
||||
integrity sha512-IPzF4w4/Rd94bA9imS68tZBaYyBWSCE47V1RGuMrB94iyTOIEwRmVL2x/4An+6mETpLrKJ5hQkB8W4kFAadeIQ==
|
||||
version "16.4.7"
|
||||
resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-16.4.7.tgz#0e20c5b82950140aa99be360a8a5f52335f53c26"
|
||||
integrity sha512-47qPchRCykZC03FhkYAhrvwU4xDBFIj1QPqaarj6mdM/hgUzfPHcpkHJOn3mJAufFeeAxAzeGsr5X0M4k6fLZQ==
|
||||
|
||||
duplexer3@^0.1.4:
|
||||
version "0.1.4"
|
||||
resolved "https://registry.yarnpkg.com/duplexer3/-/duplexer3-0.1.4.tgz#ee01dd1cac0ed3cbc7fdbea37dc0a8f1ce002ce2"
|
||||
integrity sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=
|
||||
|
||||
eastasianwidth@^0.2.0:
|
||||
version "0.2.0"
|
||||
resolved "https://registry.yarnpkg.com/eastasianwidth/-/eastasianwidth-0.2.0.tgz#696ce2ec0aa0e6ea93a397ffcf24aa7840c827cb"
|
||||
integrity sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==
|
||||
|
||||
ee-first@1.1.1:
|
||||
version "1.1.1"
|
||||
resolved "https://registry.yarnpkg.com/ee-first/-/ee-first-1.1.1.tgz#590c61156b0ae2f4f0255732a158b266bc56b21d"
|
||||
@ -2757,6 +2830,11 @@ emoji-regex@^8.0.0:
|
||||
resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37"
|
||||
integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==
|
||||
|
||||
emoji-regex@^9.2.2:
|
||||
version "9.2.2"
|
||||
resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-9.2.2.tgz#840c8803b0d8047f4ff0cf963176b32d4ef3ed72"
|
||||
integrity sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==
|
||||
|
||||
encodeurl@~1.0.2:
|
||||
version "1.0.2"
|
||||
resolved "https://registry.yarnpkg.com/encodeurl/-/encodeurl-1.0.2.tgz#ad3ff4c86ec2d029322f5a02c3a9a606c95b3f59"
|
||||
@ -3421,6 +3499,14 @@ for-each@^0.3.3:
|
||||
dependencies:
|
||||
is-callable "^1.1.3"
|
||||
|
||||
foreground-child@^3.1.0:
|
||||
version "3.3.0"
|
||||
resolved "https://registry.yarnpkg.com/foreground-child/-/foreground-child-3.3.0.tgz#0ac8644c06e431439f8561db8ecf29a7b5519c77"
|
||||
integrity sha512-Ld2g8rrAyMYFXBhEqMz8ZAHBi4J4uS1i/CxGMDnjyFWddMXLVcDp051DZfu+t7+ab7Wv6SMqpWmyFIj5UbfFvg==
|
||||
dependencies:
|
||||
cross-spawn "^7.0.0"
|
||||
signal-exit "^4.0.1"
|
||||
|
||||
form-data@^3.0.0:
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/form-data/-/form-data-3.0.1.tgz#ebd53791b78356a99af9a300d4282c4d5eb9755f"
|
||||
@ -3592,6 +3678,18 @@ glob-parent@^6.0.2:
|
||||
dependencies:
|
||||
is-glob "^4.0.3"
|
||||
|
||||
glob@^10.3.10:
|
||||
version "10.4.5"
|
||||
resolved "https://registry.yarnpkg.com/glob/-/glob-10.4.5.tgz#f4d9f0b90ffdbab09c9d77f5f29b4262517b0956"
|
||||
integrity sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg==
|
||||
dependencies:
|
||||
foreground-child "^3.1.0"
|
||||
jackspeak "^3.1.2"
|
||||
minimatch "^9.0.4"
|
||||
minipass "^7.1.2"
|
||||
package-json-from-dist "^1.0.0"
|
||||
path-scurry "^1.11.1"
|
||||
|
||||
glob@^7.1.1, glob@^7.1.2, glob@^7.1.3, glob@^7.1.4, glob@^7.1.6:
|
||||
version "7.2.0"
|
||||
resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.0.tgz#d15535af7732e02e948f4c41628bd910293f6023"
|
||||
@ -3604,17 +3702,6 @@ glob@^7.1.1, glob@^7.1.2, glob@^7.1.3, glob@^7.1.4, glob@^7.1.6:
|
||||
once "^1.3.0"
|
||||
path-is-absolute "^1.0.0"
|
||||
|
||||
glob@^8.1.0:
|
||||
version "8.1.0"
|
||||
resolved "https://registry.yarnpkg.com/glob/-/glob-8.1.0.tgz#d388f656593ef708ee3e34640fdfb99a9fd1c33e"
|
||||
integrity sha512-r8hpEjiQEYlF2QU0df3dS+nxxSIreXQS1qRhMJM0Q5NDdR386C7jb7Hwwod8Fgiuex+k0GFjgft18yvxm5XoCQ==
|
||||
dependencies:
|
||||
fs.realpath "^1.0.0"
|
||||
inflight "^1.0.4"
|
||||
inherits "2"
|
||||
minimatch "^5.0.1"
|
||||
once "^1.3.0"
|
||||
|
||||
global-dirs@^3.0.0:
|
||||
version "3.0.0"
|
||||
resolved "https://registry.yarnpkg.com/global-dirs/-/global-dirs-3.0.0.tgz#70a76fe84ea315ab37b1f5576cbde7d48ef72686"
|
||||
@ -3708,8 +3795,13 @@ graceful-fs@^4.1.6, graceful-fs@^4.2.0:
|
||||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.10.tgz#147d3a006da4ca3ce14728c7aefc287c367d7a6c"
|
||||
integrity sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==
|
||||
|
||||
"gradido-config@file:../config":
|
||||
version "1.0.0"
|
||||
dependencies:
|
||||
joi "^17.13.3"
|
||||
|
||||
"gradido-database@file:../database":
|
||||
version "2.4.1"
|
||||
version "2.4.4"
|
||||
dependencies:
|
||||
"@types/uuid" "^8.3.4"
|
||||
cross-env "^7.0.3"
|
||||
@ -4451,6 +4543,15 @@ iterall@^1.1.3, iterall@^1.2.1, iterall@^1.3.0:
|
||||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.3.0.tgz#afcb08492e2915cbd8a0884eb93a8c94d0d72fea"
|
||||
integrity sha512-QZ9qOMdF+QLHxy1QIpUHUU1D5pS2CG2P69LF6L6CPjPYA/XMOmKV3PZpawHoAjHNyB0swdVTRxdYT4tbBbxqwg==
|
||||
|
||||
jackspeak@^3.1.2:
|
||||
version "3.4.3"
|
||||
resolved "https://registry.yarnpkg.com/jackspeak/-/jackspeak-3.4.3.tgz#8833a9d89ab4acde6188942bd1c53b6390ed5a8a"
|
||||
integrity sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw==
|
||||
dependencies:
|
||||
"@isaacs/cliui" "^8.0.2"
|
||||
optionalDependencies:
|
||||
"@pkgjs/parseargs" "^0.11.0"
|
||||
|
||||
jest-changed-files@^27.2.5:
|
||||
version "27.2.5"
|
||||
resolved "https://registry.yarnpkg.com/jest-changed-files/-/jest-changed-files-27.2.5.tgz#9dfd550d158260bcb6fa80aff491f5647f7daeca"
|
||||
@ -4862,6 +4963,17 @@ jest@^27.2.4:
|
||||
import-local "^3.0.2"
|
||||
jest-cli "^27.2.5"
|
||||
|
||||
joi@*, joi@^17.13.3:
|
||||
version "17.13.3"
|
||||
resolved "https://registry.yarnpkg.com/joi/-/joi-17.13.3.tgz#0f5cc1169c999b30d344366d384b12d92558bcec"
|
||||
integrity sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.3.0"
|
||||
"@hapi/topo" "^5.1.0"
|
||||
"@sideway/address" "^4.1.5"
|
||||
"@sideway/formula" "^3.0.1"
|
||||
"@sideway/pinpoint" "^2.0.0"
|
||||
|
||||
jose@^4.14.4:
|
||||
version "4.14.4"
|
||||
resolved "https://registry.yarnpkg.com/jose/-/jose-4.14.4.tgz#59e09204e2670c3164ee24cbfe7115c6f8bff9ca"
|
||||
@ -5148,6 +5260,11 @@ lowercase-keys@^2.0.0:
|
||||
resolved "https://registry.yarnpkg.com/lowercase-keys/-/lowercase-keys-2.0.0.tgz#2603e78b7b4b0006cbca2fbcc8a3202558ac9479"
|
||||
integrity sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==
|
||||
|
||||
lru-cache@^10.2.0:
|
||||
version "10.4.3"
|
||||
resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-10.4.3.tgz#410fc8a17b70e598013df257c2446b7f3383f119"
|
||||
integrity sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==
|
||||
|
||||
lru-cache@^4.1.3:
|
||||
version "4.1.5"
|
||||
resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-4.1.5.tgz#8bbe50ea85bed59bc9e33dcab8235ee9bcf443cd"
|
||||
@ -5300,10 +5417,10 @@ minimatch@^3.0.5, minimatch@^3.1.2:
|
||||
dependencies:
|
||||
brace-expansion "^1.1.7"
|
||||
|
||||
minimatch@^5.0.1:
|
||||
version "5.1.6"
|
||||
resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.1.6.tgz#1cfcb8cf5522ea69952cd2af95ae09477f122a96"
|
||||
integrity sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g==
|
||||
minimatch@^9.0.4:
|
||||
version "9.0.5"
|
||||
resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-9.0.5.tgz#d74f9dd6b57d83d8e98cfb82133b03978bc929e5"
|
||||
integrity sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==
|
||||
dependencies:
|
||||
brace-expansion "^2.0.1"
|
||||
|
||||
@ -5317,6 +5434,11 @@ minimist@^1.2.6:
|
||||
resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.6.tgz#8637a5b759ea0d6e98702cfb3a9283323c93af44"
|
||||
integrity sha512-Jsjnk4bw3YJqYzbdyBiNsPWHPfO++UGG749Cxs6peCu5Xg4nrena6OVxOYxrQTqww0Jmwt+Ref8rggumkTLz9Q==
|
||||
|
||||
"minipass@^5.0.0 || ^6.0.2 || ^7.0.0", minipass@^7.1.2:
|
||||
version "7.1.2"
|
||||
resolved "https://registry.yarnpkg.com/minipass/-/minipass-7.1.2.tgz#93a9626ce5e5e66bd4db86849e7515e92340a707"
|
||||
integrity sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw==
|
||||
|
||||
mkdirp@^2.1.3:
|
||||
version "2.1.6"
|
||||
resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-2.1.6.tgz#964fbcb12b2d8c5d6fbc62a963ac95a273e2cc19"
|
||||
@ -5740,6 +5862,11 @@ p-wait-for@3.2.0:
|
||||
dependencies:
|
||||
p-timeout "^3.0.0"
|
||||
|
||||
package-json-from-dist@^1.0.0:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/package-json-from-dist/-/package-json-from-dist-1.0.1.tgz#4f1471a010827a86f94cfd9b0727e36d267de505"
|
||||
integrity sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==
|
||||
|
||||
package-json@^6.3.0:
|
||||
version "6.5.0"
|
||||
resolved "https://registry.yarnpkg.com/package-json/-/package-json-6.5.0.tgz#6feedaca35e75725876d0b0e64974697fed145b0"
|
||||
@ -5812,6 +5939,14 @@ path-parse@^1.0.6, path-parse@^1.0.7:
|
||||
resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735"
|
||||
integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==
|
||||
|
||||
path-scurry@^1.11.1:
|
||||
version "1.11.1"
|
||||
resolved "https://registry.yarnpkg.com/path-scurry/-/path-scurry-1.11.1.tgz#7960a668888594a0720b12a911d1a742ab9f11d2"
|
||||
integrity sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==
|
||||
dependencies:
|
||||
lru-cache "^10.2.0"
|
||||
minipass "^5.0.0 || ^6.0.2 || ^7.0.0"
|
||||
|
||||
path-to-regexp@0.1.7:
|
||||
version "0.1.7"
|
||||
resolved "https://registry.yarnpkg.com/path-to-regexp/-/path-to-regexp-0.1.7.tgz#df604178005f522f15eb4490e7247a1bfaa67f8c"
|
||||
@ -6173,10 +6308,10 @@ reflect-metadata@^0.1.13:
|
||||
resolved "https://registry.yarnpkg.com/reflect-metadata/-/reflect-metadata-0.1.13.tgz#67ae3ca57c972a2aa1642b10fe363fe32d49dc08"
|
||||
integrity sha512-Ts1Y/anZELhSsjMcU605fU9RE4Oi3p5ORujwbIKXfWa+0Zxs510Qrmrce5/Jowq3cHSZSJqBjypxmHarc+vEWg==
|
||||
|
||||
regenerator-runtime@^0.13.11:
|
||||
version "0.13.11"
|
||||
resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.13.11.tgz#f6dca3e7ceec20590d07ada785636a90cdca17f9"
|
||||
integrity sha512-kY1AZVr2Ra+t+piVaJ4gxaFaReZVH40AKNo7UCX6W+dEwBo/2oZJzqfuN1qLq1oL45o56cPaTXELwrTh8Fpggg==
|
||||
reflect-metadata@^0.2.1:
|
||||
version "0.2.2"
|
||||
resolved "https://registry.yarnpkg.com/reflect-metadata/-/reflect-metadata-0.2.2.tgz#400c845b6cba87a21f2c65c4aeb158f4fa4d9c5b"
|
||||
integrity sha512-urBwgfrvVP/eAyXx4hluJivBKzuEbSQs9rKWCrCkbSxNv8mxPcUZKeuoF3Uy4mJl3Lwprp6yy5/39VWigZ4K6Q==
|
||||
|
||||
regenerator-runtime@^0.14.0:
|
||||
version "0.14.1"
|
||||
@ -6479,6 +6614,11 @@ signal-exit@^3.0.2, signal-exit@^3.0.3:
|
||||
resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.5.tgz#9e3e8cc0c75a99472b44321033a7702e7738252f"
|
||||
integrity sha512-KWcOiKeQj6ZyXx7zq4YxSMgHRlod4czeBQZrPb8OKcohcqAXShm7E20kEMle9WBt26hFcAf0qLOcp5zmY7kOqQ==
|
||||
|
||||
signal-exit@^4.0.1:
|
||||
version "4.1.0"
|
||||
resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-4.1.0.tgz#952188c1cbd546070e2dd20d0f41c0ae0530cb04"
|
||||
integrity sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==
|
||||
|
||||
sisteransi@^1.0.5:
|
||||
version "1.0.5"
|
||||
resolved "https://registry.yarnpkg.com/sisteransi/-/sisteransi-1.0.5.tgz#134d681297756437cc05ca01370d3a7a571075ed"
|
||||
@ -6578,6 +6718,15 @@ string-length@^4.0.1:
|
||||
char-regex "^1.0.2"
|
||||
strip-ansi "^6.0.0"
|
||||
|
||||
"string-width-cjs@npm:string-width@^4.2.0":
|
||||
version "4.2.3"
|
||||
resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
|
||||
integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==
|
||||
dependencies:
|
||||
emoji-regex "^8.0.0"
|
||||
is-fullwidth-code-point "^3.0.0"
|
||||
strip-ansi "^6.0.1"
|
||||
|
||||
string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.2, string-width@^4.2.3:
|
||||
version "4.2.3"
|
||||
resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
|
||||
@ -6587,6 +6736,15 @@ string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2
|
||||
is-fullwidth-code-point "^3.0.0"
|
||||
strip-ansi "^6.0.1"
|
||||
|
||||
string-width@^5.0.1, string-width@^5.1.2:
|
||||
version "5.1.2"
|
||||
resolved "https://registry.yarnpkg.com/string-width/-/string-width-5.1.2.tgz#14f8daec6d81e7221d2a357e668cab73bdbca794"
|
||||
integrity sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==
|
||||
dependencies:
|
||||
eastasianwidth "^0.2.0"
|
||||
emoji-regex "^9.2.2"
|
||||
strip-ansi "^7.0.1"
|
||||
|
||||
string.prototype.trimend@^1.0.4:
|
||||
version "1.0.4"
|
||||
resolved "https://registry.yarnpkg.com/string.prototype.trimend/-/string.prototype.trimend-1.0.4.tgz#e75ae90c2942c63504686c18b287b4a0b1a45f80"
|
||||
@ -6628,6 +6786,13 @@ string_decoder@~1.1.1:
|
||||
dependencies:
|
||||
safe-buffer "~5.1.0"
|
||||
|
||||
"strip-ansi-cjs@npm:strip-ansi@^6.0.1":
|
||||
version "6.0.1"
|
||||
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
|
||||
integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==
|
||||
dependencies:
|
||||
ansi-regex "^5.0.1"
|
||||
|
||||
strip-ansi@^6.0.0, strip-ansi@^6.0.1:
|
||||
version "6.0.1"
|
||||
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
|
||||
@ -6635,6 +6800,13 @@ strip-ansi@^6.0.0, strip-ansi@^6.0.1:
|
||||
dependencies:
|
||||
ansi-regex "^5.0.1"
|
||||
|
||||
strip-ansi@^7.0.1:
|
||||
version "7.1.0"
|
||||
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-7.1.0.tgz#d5b6568ca689d8561370b0707685d22434faff45"
|
||||
integrity sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==
|
||||
dependencies:
|
||||
ansi-regex "^6.0.1"
|
||||
|
||||
strip-bom@^3.0.0:
|
||||
version "3.0.0"
|
||||
resolved "https://registry.yarnpkg.com/strip-bom/-/strip-bom-3.0.0.tgz#2334c18e9c759f7bdd56fdef7e9ae3d588e68ed3"
|
||||
@ -6874,9 +7046,9 @@ ts-jest@^27.0.5:
|
||||
yargs-parser "20.x"
|
||||
|
||||
ts-mysql-migrate@^1.0.2:
|
||||
version "1.0.2"
|
||||
resolved "https://registry.yarnpkg.com/ts-mysql-migrate/-/ts-mysql-migrate-1.0.2.tgz#736d37c3aa3fef92f226b869098e939950d0e18c"
|
||||
integrity sha512-zDW6iQsfPCJfQ3JMhfUGjhy8aK+VNTvPrXmJH66PB2EGEvyn4m7x2nBdhDNhKuwYU9LMxW1p+l39Ei+btXNpxA==
|
||||
version "1.1.2"
|
||||
resolved "https://registry.yarnpkg.com/ts-mysql-migrate/-/ts-mysql-migrate-1.1.2.tgz#6f280f4684cb95440ffa7254b926b494badb8cf3"
|
||||
integrity sha512-jwhVaMrYBNNhAoZ5XISxzqbnXTHqwazqu/r1UQ6kUaGNPGL43ZFnBiXVj4Gm3pfe3xtCGIaNInehDfdDuigPgw==
|
||||
dependencies:
|
||||
"@types/mysql" "^2.15.8"
|
||||
mysql "^2.18.1"
|
||||
@ -7033,21 +7205,21 @@ typedarray-to-buffer@^3.1.5:
|
||||
is-typedarray "^1.0.0"
|
||||
|
||||
typeorm@^0.3.16:
|
||||
version "0.3.17"
|
||||
resolved "https://registry.yarnpkg.com/typeorm/-/typeorm-0.3.17.tgz#a73c121a52e4fbe419b596b244777be4e4b57949"
|
||||
integrity sha512-UDjUEwIQalO9tWw9O2A4GU+sT3oyoUXheHJy4ft+RFdnRdQctdQ34L9SqE2p7LdwzafHx1maxT+bqXON+Qnmig==
|
||||
version "0.3.20"
|
||||
resolved "https://registry.yarnpkg.com/typeorm/-/typeorm-0.3.20.tgz#4b61d737c6fed4e9f63006f88d58a5e54816b7ab"
|
||||
integrity sha512-sJ0T08dV5eoZroaq9uPKBoNcGslHBR4E4y+EBHs//SiGbblGe7IeduP/IH4ddCcj0qp3PHwDwGnuvqEAnKlq/Q==
|
||||
dependencies:
|
||||
"@sqltools/formatter" "^1.2.5"
|
||||
app-root-path "^3.1.0"
|
||||
buffer "^6.0.3"
|
||||
chalk "^4.1.2"
|
||||
cli-highlight "^2.1.11"
|
||||
date-fns "^2.29.3"
|
||||
dayjs "^1.11.9"
|
||||
debug "^4.3.4"
|
||||
dotenv "^16.0.3"
|
||||
glob "^8.1.0"
|
||||
glob "^10.3.10"
|
||||
mkdirp "^2.1.3"
|
||||
reflect-metadata "^0.1.13"
|
||||
reflect-metadata "^0.2.1"
|
||||
sha.js "^2.4.11"
|
||||
tslib "^2.5.0"
|
||||
uuid "^9.0.0"
|
||||
@ -7193,9 +7365,9 @@ uuid@^8.0.0, uuid@^8.3.2:
|
||||
integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==
|
||||
|
||||
uuid@^9.0.0:
|
||||
version "9.0.0"
|
||||
resolved "https://registry.yarnpkg.com/uuid/-/uuid-9.0.0.tgz#592f550650024a38ceb0c562f2f6aa435761efb5"
|
||||
integrity sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==
|
||||
version "9.0.1"
|
||||
resolved "https://registry.yarnpkg.com/uuid/-/uuid-9.0.1.tgz#e188d4c8853cc722220392c424cd637f32293f30"
|
||||
integrity sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==
|
||||
|
||||
v8-to-istanbul@^8.1.0:
|
||||
version "8.1.0"
|
||||
@ -7374,6 +7546,15 @@ workerpool@^9.2.0:
|
||||
resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-9.2.0.tgz#f74427cbb61234708332ed8ab9cbf56dcb1c4371"
|
||||
integrity sha512-PKZqBOCo6CYkVOwAxWxQaSF2Fvb5Iv2fCeTP7buyWI2GiynWr46NcXSgK/idoV6e60dgCBfgYc+Un3HMvmqP8w==
|
||||
|
||||
"wrap-ansi-cjs@npm:wrap-ansi@^7.0.0":
|
||||
version "7.0.0"
|
||||
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43"
|
||||
integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==
|
||||
dependencies:
|
||||
ansi-styles "^4.0.0"
|
||||
string-width "^4.1.0"
|
||||
strip-ansi "^6.0.0"
|
||||
|
||||
wrap-ansi@^7.0.0:
|
||||
version "7.0.0"
|
||||
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43"
|
||||
@ -7383,6 +7564,15 @@ wrap-ansi@^7.0.0:
|
||||
string-width "^4.1.0"
|
||||
strip-ansi "^6.0.0"
|
||||
|
||||
wrap-ansi@^8.1.0:
|
||||
version "8.1.0"
|
||||
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-8.1.0.tgz#56dc22368ee570face1b49819975d9b9a5ead214"
|
||||
integrity sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==
|
||||
dependencies:
|
||||
ansi-styles "^6.1.0"
|
||||
string-width "^5.0.1"
|
||||
strip-ansi "^7.0.1"
|
||||
|
||||
wrappy@1:
|
||||
version "1.0.2"
|
||||
resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f"
|
||||
|
||||
4
config/.eslintignore
Normal file
4
config/.eslintignore
Normal file
@ -0,0 +1,4 @@
|
||||
node_modules
|
||||
**/*.min.js
|
||||
build
|
||||
coverage
|
||||
214
config/.eslintrc.js
Normal file
214
config/.eslintrc.js
Normal file
@ -0,0 +1,214 @@
|
||||
// eslint-disable-next-line import/no-commonjs, import/unambiguous
|
||||
module.exports = {
|
||||
root: true,
|
||||
env: {
|
||||
node: true,
|
||||
},
|
||||
parser: '@typescript-eslint/parser',
|
||||
plugins: ['prettier', '@typescript-eslint', 'type-graphql', 'import', 'n', 'promise'],
|
||||
extends: [
|
||||
'standard',
|
||||
'eslint:recommended',
|
||||
'plugin:prettier/recommended',
|
||||
'plugin:import/recommended',
|
||||
'plugin:import/typescript',
|
||||
'plugin:security/recommended',
|
||||
'plugin:@eslint-community/eslint-comments/recommended',
|
||||
],
|
||||
settings: {
|
||||
'import/parsers': {
|
||||
'@typescript-eslint/parser': ['.ts', '.tsx'],
|
||||
},
|
||||
'import/resolver': {
|
||||
typescript: {
|
||||
project: ['./tsconfig.json', '**/tsconfig.json'],
|
||||
},
|
||||
node: true,
|
||||
},
|
||||
// the parser cannot handle the split sodium import
|
||||
'import/ignore': ['sodium-native'],
|
||||
},
|
||||
rules: {
|
||||
'no-console': 'error',
|
||||
camelcase: ['error', { allow: ['crypto_*', 'randombytes_random'] }],
|
||||
'no-debugger': 'error',
|
||||
'prettier/prettier': [
|
||||
'error',
|
||||
{
|
||||
htmlWhitespaceSensitivity: 'ignore',
|
||||
},
|
||||
],
|
||||
// import
|
||||
'import/export': 'error',
|
||||
// 'import/no-deprecated': 'error',
|
||||
'import/no-empty-named-blocks': 'error',
|
||||
'import/no-extraneous-dependencies': 'error',
|
||||
'import/no-mutable-exports': 'error',
|
||||
'import/no-unused-modules': 'error',
|
||||
'import/no-named-as-default': 'error',
|
||||
'import/no-named-as-default-member': 'error',
|
||||
'import/no-amd': 'error',
|
||||
'import/no-commonjs': 'error',
|
||||
'import/no-import-module-exports': 'error',
|
||||
'import/no-nodejs-modules': 'off',
|
||||
'import/unambiguous': 'error',
|
||||
'import/default': 'error',
|
||||
'import/named': 'error',
|
||||
'import/namespace': 'error',
|
||||
'import/no-absolute-path': 'error',
|
||||
'import/no-cycle': 'error',
|
||||
'import/no-dynamic-require': 'error',
|
||||
'import/no-internal-modules': 'off',
|
||||
'import/no-relative-packages': 'error',
|
||||
'import/no-relative-parent-imports': [
|
||||
'error',
|
||||
{ ignore: ['@/*', 'random-bigint', 'sodium-native'] },
|
||||
],
|
||||
'import/no-self-import': 'error',
|
||||
'import/no-unresolved': 'error',
|
||||
'import/no-useless-path-segments': 'error',
|
||||
'import/no-webpack-loader-syntax': 'error',
|
||||
'import/consistent-type-specifier-style': 'error',
|
||||
'import/exports-last': 'off',
|
||||
'import/extensions': 'error',
|
||||
'import/first': 'error',
|
||||
'import/group-exports': 'off',
|
||||
'import/newline-after-import': 'error',
|
||||
'import/no-anonymous-default-export': 'error',
|
||||
'import/no-default-export': 'error',
|
||||
'import/no-duplicates': 'error',
|
||||
'import/no-named-default': 'error',
|
||||
'import/no-namespace': 'error',
|
||||
'import/no-unassigned-import': 'error',
|
||||
'import/order': [
|
||||
'error',
|
||||
{
|
||||
groups: ['builtin', 'external', 'internal', 'parent', 'sibling', 'index', 'object', 'type'],
|
||||
'newlines-between': 'always',
|
||||
pathGroups: [
|
||||
{
|
||||
pattern: '@?*/**',
|
||||
group: 'external',
|
||||
position: 'after',
|
||||
},
|
||||
{
|
||||
pattern: '@/**',
|
||||
group: 'external',
|
||||
position: 'after',
|
||||
},
|
||||
],
|
||||
alphabetize: {
|
||||
order: 'asc' /* sort in ascending order. Options: ['ignore', 'asc', 'desc'] */,
|
||||
caseInsensitive: true /* ignore case. Options: [true, false] */,
|
||||
},
|
||||
distinctGroup: true,
|
||||
},
|
||||
],
|
||||
'import/prefer-default-export': 'off',
|
||||
// n
|
||||
'n/handle-callback-err': 'error',
|
||||
'n/no-callback-literal': 'error',
|
||||
'n/no-exports-assign': 'error',
|
||||
'n/no-extraneous-import': 'error',
|
||||
'n/no-extraneous-require': 'error',
|
||||
'n/no-hide-core-modules': 'error',
|
||||
'n/no-missing-import': 'off', // not compatible with typescript
|
||||
'n/no-missing-require': 'error',
|
||||
'n/no-new-require': 'error',
|
||||
'n/no-path-concat': 'error',
|
||||
'n/no-process-exit': 'error',
|
||||
'n/no-unpublished-bin': 'error',
|
||||
'n/no-unpublished-import': 'off', // TODO need to exclude seeds
|
||||
'n/no-unpublished-require': 'error',
|
||||
'n/no-unsupported-features': ['error', { ignores: ['modules'] }],
|
||||
'n/no-unsupported-features/es-builtins': 'error',
|
||||
'n/no-unsupported-features/es-syntax': 'error',
|
||||
'n/no-unsupported-features/node-builtins': 'error',
|
||||
'n/process-exit-as-throw': 'error',
|
||||
'n/shebang': 'error',
|
||||
'n/callback-return': 'error',
|
||||
'n/exports-style': 'error',
|
||||
'n/file-extension-in-import': 'off',
|
||||
'n/global-require': 'error',
|
||||
'n/no-mixed-requires': 'error',
|
||||
'n/no-process-env': 'error',
|
||||
'n/no-restricted-import': 'error',
|
||||
'n/no-restricted-require': 'error',
|
||||
'n/no-sync': 'error',
|
||||
'n/prefer-global/buffer': 'error',
|
||||
'n/prefer-global/console': 'error',
|
||||
'n/prefer-global/process': 'error',
|
||||
'n/prefer-global/text-decoder': 'error',
|
||||
'n/prefer-global/text-encoder': 'error',
|
||||
'n/prefer-global/url': 'error',
|
||||
'n/prefer-global/url-search-params': 'error',
|
||||
'n/prefer-promises/dns': 'error',
|
||||
'n/prefer-promises/fs': 'error',
|
||||
// promise
|
||||
'promise/catch-or-return': 'error',
|
||||
'promise/no-return-wrap': 'error',
|
||||
'promise/param-names': 'error',
|
||||
'promise/always-return': 'error',
|
||||
'promise/no-native': 'off',
|
||||
'promise/no-nesting': 'warn',
|
||||
'promise/no-promise-in-callback': 'warn',
|
||||
'promise/no-callback-in-promise': 'warn',
|
||||
'promise/avoid-new': 'warn',
|
||||
'promise/no-new-statics': 'error',
|
||||
'promise/no-return-in-finally': 'warn',
|
||||
'promise/valid-params': 'warn',
|
||||
'promise/prefer-await-to-callbacks': 'error',
|
||||
'promise/no-multiple-resolved': 'error',
|
||||
// eslint comments
|
||||
'@eslint-community/eslint-comments/disable-enable-pair': ['error', { allowWholeFile: true }],
|
||||
'@eslint-community/eslint-comments/no-restricted-disable': 'error',
|
||||
'@eslint-community/eslint-comments/no-use': 'off',
|
||||
'@eslint-community/eslint-comments/require-description': 'off',
|
||||
},
|
||||
overrides: [
|
||||
// only for ts files
|
||||
{
|
||||
files: ['*.ts', '*.tsx'],
|
||||
extends: [
|
||||
'plugin:@typescript-eslint/recommended',
|
||||
'plugin:@typescript-eslint/recommended-requiring-type-checking',
|
||||
'plugin:@typescript-eslint/strict',
|
||||
'plugin:type-graphql/recommended',
|
||||
],
|
||||
rules: {
|
||||
// allow explicitly defined dangling promises
|
||||
'@typescript-eslint/no-floating-promises': ['error', { ignoreVoid: true }],
|
||||
'no-void': ['error', { allowAsStatement: true }],
|
||||
// ignore prefer-regexp-exec rule to allow string.match(regex)
|
||||
'@typescript-eslint/prefer-regexp-exec': 'off',
|
||||
// this should not run on ts files: https://github.com/import-js/eslint-plugin-import/issues/2215#issuecomment-911245486
|
||||
'import/unambiguous': 'off',
|
||||
// this is not compatible with typeorm, due to joined tables can be null, but are not defined as nullable
|
||||
'@typescript-eslint/no-unnecessary-condition': 'off',
|
||||
},
|
||||
parserOptions: {
|
||||
tsconfigRootDir: __dirname,
|
||||
project: ['./tsconfig.json', '**/tsconfig.json'],
|
||||
// this is to properly reference the referenced project database without requirement of compiling it
|
||||
// eslint-disable-next-line camelcase
|
||||
EXPERIMENTAL_useSourceOfProjectReferenceRedirect: true,
|
||||
},
|
||||
},
|
||||
{
|
||||
files: ['*.test.ts'],
|
||||
plugins: ['jest'],
|
||||
env: {
|
||||
jest: true,
|
||||
},
|
||||
rules: {
|
||||
'jest/no-disabled-tests': 'error',
|
||||
'jest/no-focused-tests': 'error',
|
||||
'jest/no-identical-title': 'error',
|
||||
'jest/prefer-to-have-length': 'error',
|
||||
'jest/valid-expect': 'error',
|
||||
'@typescript-eslint/unbound-method': 'off',
|
||||
'jest/unbound-method': 'error',
|
||||
},
|
||||
},
|
||||
],
|
||||
}
|
||||
14
config/.gitignore
vendored
Normal file
14
config/.gitignore
vendored
Normal file
@ -0,0 +1,14 @@
|
||||
node_modules/
|
||||
build/
|
||||
.cache/
|
||||
.yarn/install-state.gz
|
||||
|
||||
/.env
|
||||
/.env.bak
|
||||
|
||||
# coverage folder
|
||||
coverage/
|
||||
|
||||
# emacs
|
||||
*~
|
||||
|
||||
1
config/.nvmrc
Normal file
1
config/.nvmrc
Normal file
@ -0,0 +1 @@
|
||||
v18.7.0
|
||||
25
config/package.json
Normal file
25
config/package.json
Normal file
@ -0,0 +1,25 @@
|
||||
{
|
||||
"name": "gradido-config",
|
||||
"version": "1.0.0",
|
||||
"description": "Gradido Config for validate config",
|
||||
"main": "src/index.ts",
|
||||
"repository": "https://github.com/gradido/gradido/config",
|
||||
"author": "einhornimmond",
|
||||
"license": "Apache-2.0",
|
||||
"private": false,
|
||||
"scripts": {
|
||||
"build": "tsc --build",
|
||||
"clean": "tsc --build --clean",
|
||||
"test": "node test/index"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/joi": "^17.2.3",
|
||||
"@types/node": "^17.0.21",
|
||||
"typescript": "^4.3.5",
|
||||
"mkdirp": "^3.0.1",
|
||||
"ncp": "^2.0.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"joi": "^17.13.3"
|
||||
}
|
||||
}
|
||||
236
config/src/commonSchema.ts
Normal file
236
config/src/commonSchema.ts
Normal file
@ -0,0 +1,236 @@
|
||||
import Joi from 'joi'
|
||||
|
||||
export const browserUrls = Joi.array()
|
||||
.items(Joi.string().uri())
|
||||
.sparse(true)
|
||||
.custom((value: string[], helpers: Joi.CustomHelpers<string[]>) => {
|
||||
let protocol: string | undefined
|
||||
for (const url of value) {
|
||||
if (url === undefined) {
|
||||
continue
|
||||
}
|
||||
const urlObject = new URL(url)
|
||||
if(!protocol) {
|
||||
protocol = urlObject.protocol
|
||||
} else if(urlObject.protocol !== protocol) {
|
||||
return helpers.error('any.invalid')
|
||||
}
|
||||
}
|
||||
return value;
|
||||
})
|
||||
.required()
|
||||
.description('All URLs need to have same protocol to prevent mixed block errors')
|
||||
|
||||
export const DECAY_START_TIME = Joi.date()
|
||||
.iso() // ISO 8601 format for date validation
|
||||
.description('The start time for decay, expected in ISO 8601 format (e.g. 2021-05-13T17:46:31Z)')
|
||||
.default(new Date('2021-05-13T17:46:31Z')) // default to the specified date if not provided
|
||||
.required()
|
||||
|
||||
export const DB_VERSION = Joi.string()
|
||||
.pattern(/^\d{4}-[a-z0-9-_]+$/)
|
||||
.message('DB_VERSION must be in the format: YYYY-description, e.g. "0087-add_index_on_user_roles".')
|
||||
.description('db version string, last migration file name without ending or last folder in entity')
|
||||
.required()
|
||||
|
||||
export const COMMUNITY_URL = Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.custom((value: string, helpers: Joi.CustomHelpers<string>) => {
|
||||
if (value.endsWith('/')) {
|
||||
return helpers.error('any.invalid', { message: 'URL should not end with a slash (/)' })
|
||||
}
|
||||
return value;
|
||||
})
|
||||
.description('The base URL of the community, should have the same protocol as frontend, admin and backend api to prevent mixed contend issues.')
|
||||
.default('http://0.0.0.0')
|
||||
.required()
|
||||
|
||||
export const GRAPHQL_URI = Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.description(
|
||||
`
|
||||
The external URL of the backend service,
|
||||
accessible from outside the server (e.g., via Nginx or the server's public URL),
|
||||
should have the same protocol as frontend and admin to prevent mixed contend issues.
|
||||
`,
|
||||
)
|
||||
.default('http://0.0.0.0/graphql')
|
||||
.required()
|
||||
|
||||
export const COMMUNITY_NAME = Joi.string()
|
||||
.min(3)
|
||||
.max(40)
|
||||
.description('The name of the community')
|
||||
.default('Gradido Entwicklung')
|
||||
.required()
|
||||
|
||||
export const COMMUNITY_DESCRIPTION = Joi.string()
|
||||
.min(10)
|
||||
.max(255)
|
||||
.description('A short description of the community')
|
||||
.default('Die lokale Entwicklungsumgebung von Gradido.')
|
||||
.required()
|
||||
|
||||
export const COMMUNITY_SUPPORT_MAIL = Joi.string()
|
||||
.email()
|
||||
.description('The support email address for the community will be used in frontend and E-Mails')
|
||||
.default('support@supportmail.com')
|
||||
.required()
|
||||
|
||||
export const COMMUNITY_LOCATION = Joi.string()
|
||||
.pattern(/^[-+]?[0-9]{1,2}(\.[0-9]+)?,\s?[-+]?[0-9]{1,3}(\.[0-9]+)?$/)
|
||||
.when('GMS_ACTIVE', {
|
||||
is: true,
|
||||
then: Joi.string().required(),
|
||||
otherwise: Joi.string().optional()
|
||||
})
|
||||
.description('Geographical location of the community in "latitude, longitude" format')
|
||||
.default('49.280377, 9.690151')
|
||||
|
||||
export const GRAPHIQL = Joi.boolean()
|
||||
.description('Flag for enabling GraphQL playground for debugging.')
|
||||
.default(false)
|
||||
.when('NODE_ENV', {
|
||||
is: 'development',
|
||||
then: Joi.boolean().valid(true, false).required(), // only allow true in development mode
|
||||
otherwise: Joi.boolean().valid(false).required() // false in any other mode
|
||||
})
|
||||
|
||||
export const GMS_ACTIVE = Joi.boolean()
|
||||
.description('Flag to indicate if the GMS (Geographic Member Search) service is used.')
|
||||
.default(false)
|
||||
.required()
|
||||
|
||||
export const GDT_ACTIVE = Joi.boolean()
|
||||
.description('Flag to indicate if the GMS (Geographic Member Search) service is used.')
|
||||
.default(false)
|
||||
.required()
|
||||
|
||||
export const GDT_API_URL = Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.default('https://gdt.gradido.net')
|
||||
.when('GDT_ACTIVE', { is: true, then: Joi.required() })
|
||||
.description('The URL for GDT API endpoint')
|
||||
|
||||
export const HUMHUB_ACTIVE = Joi.boolean()
|
||||
.description('Flag to indicate if the HumHub based Community Server is used.')
|
||||
.default(false)
|
||||
.required()
|
||||
|
||||
export const LOG_LEVEL = Joi.string()
|
||||
.valid('all', 'mark', 'trace', 'debug', 'info', 'warn', 'error', 'fatal', 'off')
|
||||
.description('set log level')
|
||||
.default('info')
|
||||
.required()
|
||||
|
||||
export const LOG4JS_CONFIG = Joi.string()
|
||||
.pattern(/^[a-zA-Z0-9-_]+\.json$/)
|
||||
.message('LOG4JS_CONFIG must be a valid filename ending with .json')
|
||||
.description('config file name for log4js config file')
|
||||
.default('log4js-config.json')
|
||||
.required()
|
||||
|
||||
export const LOGIN_APP_SECRET = Joi.string()
|
||||
.pattern(/^[a-fA-F0-9]+$/)
|
||||
.message('need to be valid hex')
|
||||
.default('21ffbbc616fe')
|
||||
.description('App secret for salt component for libsodium crypto_pwhash')
|
||||
.required()
|
||||
|
||||
export const LOGIN_SERVER_KEY = Joi.string()
|
||||
.pattern(/^[a-fA-F0-9]+$/)
|
||||
.length(32)
|
||||
.message('need to be valid hex and 32 character')
|
||||
.default('a51ef8ac7ef1abf162fb7a65261acd7a')
|
||||
.description('Server key for password hashing as additional salt for libsodium crypto_shorthash_keygen')
|
||||
.required()
|
||||
|
||||
export const TYPEORM_LOGGING_RELATIVE_PATH = Joi.string()
|
||||
.pattern(/^[a-zA-Z0-9-_\.]+\.log$/)
|
||||
.message('TYPEORM_LOGGING_RELATIVE_PATH must be a valid filename ending with .log')
|
||||
.description('log file name for logging typeorm activities')
|
||||
.default('typeorm.log')
|
||||
.required()
|
||||
|
||||
export const DB_HOST = Joi.string()
|
||||
.hostname()
|
||||
.message('must be a valid host with alphanumeric characters, numbers, points and -')
|
||||
.description("database host like 'localhost' or 'mariadb' in docker setup")
|
||||
.default('localhost')
|
||||
.required()
|
||||
|
||||
export const DB_PORT = Joi.number()
|
||||
.integer()
|
||||
.min(1024)
|
||||
.max(49151)
|
||||
.description('database port, default: 3306')
|
||||
.default(3306)
|
||||
.required()
|
||||
|
||||
export const DB_USER = Joi.string()
|
||||
.pattern(/^[A-Za-z0-9]([A-Za-z0-9-_\.]*[A-Za-z0-9])?$/) // Validates MariaDB username rules
|
||||
.min(1) // Minimum length 1
|
||||
.max(16) // Maximum length 16
|
||||
.message(
|
||||
'Valid database username (letters, numbers, hyphens, underscores, dots allowed; no spaces, must not start or end with hyphen, dot, or underscore)'
|
||||
)
|
||||
.description('database username for mariadb')
|
||||
.default('root')
|
||||
.required()
|
||||
|
||||
export const DB_PASSWORD = Joi.string()
|
||||
.when(Joi.ref('NODE_ENV'), {
|
||||
is: 'development',
|
||||
then: Joi.string().allow(''),
|
||||
otherwise: Joi.string()
|
||||
.min(8)
|
||||
.max(32)
|
||||
.pattern(/^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[!@#$%^&*(),.?":{}|<>]).+$/)
|
||||
.message(
|
||||
'Password must be between 8 and 32 characters long, and contain at least one uppercase letter, one lowercase letter, one number, and one special character (e.g., !@#$%^&*).'
|
||||
)
|
||||
})
|
||||
.description(
|
||||
'Password for the database user. In development mode, an empty password is allowed. In other environments, a complex password is required.'
|
||||
)
|
||||
.default('')
|
||||
.required()
|
||||
|
||||
export const DB_DATABASE = Joi.string()
|
||||
.pattern(/^[a-zA-Z][a-zA-Z0-9_-]{1,63}$/)
|
||||
.description('Database name like gradido_community (must start with a letter, and can only contain letters, numbers, underscores, or dashes)')
|
||||
.default('gradido_community')
|
||||
.required()
|
||||
|
||||
export const APP_VERSION = Joi.string()
|
||||
.pattern(/^\d+\.\d+\.\d+$/)
|
||||
.message('Version must be in the format "major.minor.patch" (e.g., "2.4.1")')
|
||||
.description('App Version from package.json, alle modules share one version')
|
||||
.required()
|
||||
|
||||
export const BUILD_COMMIT = Joi.string()
|
||||
.pattern(/^[0-9a-f]{40}$/)
|
||||
.message('The commit hash must be a 40-character hexadecimal string.')
|
||||
.description('The full git commit hash.')
|
||||
.optional()
|
||||
|
||||
export const BUILD_COMMIT_SHORT = Joi.string()
|
||||
.pattern(/^[0-9a-f]{7}$/)
|
||||
.message('The first 7 hexadecimal character from git commit hash.')
|
||||
.description('A short version from the git commit hash.')
|
||||
.required()
|
||||
|
||||
export const NODE_ENV = Joi.string()
|
||||
.valid('production', 'development', 'test')
|
||||
.default('development')
|
||||
.description('Specifies the environment in which the application is running.')
|
||||
|
||||
export const DEBUG = Joi.boolean()
|
||||
.description('Indicates whether the application is in debugging mode. Set to true when NODE_ENV is not "production".')
|
||||
.default(false)
|
||||
.required()
|
||||
|
||||
export const PRODUCTION = Joi.boolean()
|
||||
.default(false)
|
||||
.description('Indicates whether the application is running in production mode. Set to true when NODE_ENV is "production".')
|
||||
.required()
|
||||
33
config/src/index.ts
Normal file
33
config/src/index.ts
Normal file
@ -0,0 +1,33 @@
|
||||
import { ObjectSchema } from 'joi'
|
||||
export * from './commonSchema'
|
||||
|
||||
export function validate(schema: ObjectSchema, data: any) {
|
||||
const { error } = schema.validate(data)
|
||||
const schemaJson = schema.describe()
|
||||
if (error) {
|
||||
error.details.forEach((err) => {
|
||||
const details = JSON.stringify(err, null, 2)
|
||||
if (!err.context) {
|
||||
throw new Error('missing context in config validation with joi: ' + details)
|
||||
}
|
||||
if (!schemaJson) {
|
||||
throw new Error('invalid schema in config validation with joi: ' + details)
|
||||
}
|
||||
const key = err.context.key
|
||||
if (key === undefined) {
|
||||
throw new Error('missing key in config validation with joi: ' + details)
|
||||
}
|
||||
const value = err.context.value
|
||||
const description = schemaJson.keys[key]
|
||||
? schema.describe().keys[key].flags.description
|
||||
: 'No description available'
|
||||
if (data[key] === undefined) {
|
||||
throw new Error(`Environment Variable '${key}' is missing. ${description}, details: ${details}`)
|
||||
} else {
|
||||
throw new Error(
|
||||
`Error on Environment Variable ${key} with value = ${value}: ${err.message}. ${description}`,
|
||||
)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
8
config/test/index.js
Normal file
8
config/test/index.js
Normal file
@ -0,0 +1,8 @@
|
||||
const Joi = require('joi')
|
||||
const commonSchema = require('../dist/commonSchema')
|
||||
|
||||
const schema = Joi.object({
|
||||
commonSchema
|
||||
})
|
||||
|
||||
// console.log(commonSchema.DECAY_START_TIME)
|
||||
73
config/tsconfig.json
Normal file
73
config/tsconfig.json
Normal file
@ -0,0 +1,73 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
/* Visit https://aka.ms/tsconfig.json to read more about this file */
|
||||
|
||||
/* Basic Options */
|
||||
// "incremental": true, /* Enable incremental compilation */
|
||||
"target": "es6", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', 'ES2021', or 'ESNEXT'. */
|
||||
"module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', 'es2020', or 'ESNext'. */
|
||||
// "lib": [], /* Specify library files to be included in the compilation. */
|
||||
// "allowJs": true, /* Allow javascript files to be compiled. */
|
||||
// "checkJs": true, /* Report errors in .js files. */
|
||||
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', 'react', 'react-jsx' or 'react-jsxdev'. */
|
||||
"declaration": true, /* Generates corresponding '.d.ts' file. */
|
||||
"declarationMap": true, /* Generates a sourcemap for each corresponding '.d.ts' file. */
|
||||
// "sourceMap": true, /* Generates corresponding '.map' file. */
|
||||
// "outFile": "./build/outfile.js", /* Concatenate and emit output to single file. */
|
||||
"outDir": "./build", /* Redirect output structure to the directory. */
|
||||
// "rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */
|
||||
"composite": true, /* Enable project compilation */
|
||||
// "tsBuildInfoFile": "./", /* Specify file to store incremental compilation information */
|
||||
// "removeComments": true, /* Do not emit comments to output. */
|
||||
// "noEmit": true, /* Do not emit outputs. */
|
||||
// "importHelpers": true, /* Import emit helpers from 'tslib'. */
|
||||
// "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */
|
||||
// "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */
|
||||
|
||||
/* Strict Type-Checking Options */
|
||||
"strict": true, /* Enable all strict type-checking options. */
|
||||
// "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */
|
||||
// "strictNullChecks": true, /* Enable strict null checks. */
|
||||
// "strictFunctionTypes": true, /* Enable strict checking of function types. */
|
||||
// "strictBindCallApply": true, /* Enable strict 'bind', 'call', and 'apply' methods on functions. */
|
||||
"strictPropertyInitialization": false, /* Enable strict checking of property initialization in classes. */
|
||||
// "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */
|
||||
// "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */
|
||||
|
||||
/* Additional Checks */
|
||||
// "noUnusedLocals": true, /* Report errors on unused locals. */
|
||||
// "noUnusedParameters": true, /* Report errors on unused parameters. */
|
||||
// "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */
|
||||
// "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */
|
||||
// "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */
|
||||
// "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an 'override' modifier. */
|
||||
// "noPropertyAccessFromIndexSignature": true, /* Require undeclared properties from index signatures to use element accesses. */
|
||||
|
||||
/* Module Resolution Options */
|
||||
// "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */
|
||||
// "baseUrl": ".", /* Base directory to resolve non-absolute module names. */
|
||||
// "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */
|
||||
// "rootDirs": [".", "../database"], /* List of root folders whose combined content represents the structure of the project at runtime. */
|
||||
// "typeRoots": [], /* List of folders to include type definitions from. */
|
||||
// "types": [], /* Type declaration files to be included in compilation. */
|
||||
// "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */
|
||||
"esModuleInterop": true, /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */
|
||||
// "preserveSymlinks": true, /* Do not resolve the real path of symlinks. */
|
||||
// "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */
|
||||
|
||||
/* Source Map Options */
|
||||
// "sourceRoot": "", /* Specify the location where debugger should locate TypeScript files instead of source locations. */
|
||||
// "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */
|
||||
// "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */
|
||||
// "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */
|
||||
|
||||
/* Experimental Options */
|
||||
"experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */
|
||||
"emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */
|
||||
|
||||
/* Advanced Options */
|
||||
"skipLibCheck": true, /* Skip type checking of declaration files. */
|
||||
"forceConsistentCasingInFileNames": true /* Disallow inconsistently-cased references to the same file. */
|
||||
},
|
||||
"references": [] /* Any project that is referenced must itself have a `references` array (which may be empty). */
|
||||
}
|
||||
70
config/yarn.lock
Normal file
70
config/yarn.lock
Normal file
@ -0,0 +1,70 @@
|
||||
# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
|
||||
# yarn lockfile v1
|
||||
|
||||
|
||||
"@hapi/hoek@^9.0.0", "@hapi/hoek@^9.3.0":
|
||||
version "9.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/hoek/-/hoek-9.3.0.tgz#8368869dcb735be2e7f5cb7647de78e167a251fb"
|
||||
integrity sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==
|
||||
|
||||
"@hapi/topo@^5.1.0":
|
||||
version "5.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/topo/-/topo-5.1.0.tgz#dc448e332c6c6e37a4dc02fd84ba8d44b9afb012"
|
||||
integrity sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@sideway/address@^4.1.5":
|
||||
version "4.1.5"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/address/-/address-4.1.5.tgz#4bc149a0076623ced99ca8208ba780d65a99b9d5"
|
||||
integrity sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@sideway/formula@^3.0.1":
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/formula/-/formula-3.0.1.tgz#80fcbcbaf7ce031e0ef2dd29b1bfc7c3f583611f"
|
||||
integrity sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==
|
||||
|
||||
"@sideway/pinpoint@^2.0.0":
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/pinpoint/-/pinpoint-2.0.0.tgz#cff8ffadc372ad29fd3f78277aeb29e632cc70df"
|
||||
integrity sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==
|
||||
|
||||
"@types/joi@^17.2.3":
|
||||
version "17.2.3"
|
||||
resolved "https://registry.yarnpkg.com/@types/joi/-/joi-17.2.3.tgz#b7768ed9d84f1ebd393328b9f97c1cf3d2b94798"
|
||||
integrity sha512-dGjs/lhrWOa+eO0HwgxCSnDm5eMGCsXuvLglMghJq32F6q5LyyNuXb41DHzrg501CKNOSSAHmfB7FDGeUnDmzw==
|
||||
dependencies:
|
||||
joi "*"
|
||||
|
||||
"@types/node@^17.0.21":
|
||||
version "17.0.45"
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.45.tgz#2c0fafd78705e7a18b7906b5201a522719dc5190"
|
||||
integrity sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw==
|
||||
|
||||
joi@*, joi@^17.13.3:
|
||||
version "17.13.3"
|
||||
resolved "https://registry.yarnpkg.com/joi/-/joi-17.13.3.tgz#0f5cc1169c999b30d344366d384b12d92558bcec"
|
||||
integrity sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.3.0"
|
||||
"@hapi/topo" "^5.1.0"
|
||||
"@sideway/address" "^4.1.5"
|
||||
"@sideway/formula" "^3.0.1"
|
||||
"@sideway/pinpoint" "^2.0.0"
|
||||
|
||||
mkdirp@^3.0.1:
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-3.0.1.tgz#e44e4c5607fb279c168241713cc6e0fea9adcb50"
|
||||
integrity sha512-+NsyUUAZDmo6YVHzL/stxSu3t9YS1iljliy3BSDrXJ/dkn1KYdmtZODGGjLcc9XLgVVpH4KshHB8XmZgMhaBXg==
|
||||
|
||||
ncp@^2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/ncp/-/ncp-2.0.0.tgz#195a21d6c46e361d2fb1281ba38b91e9df7bdbb3"
|
||||
integrity sha512-zIdGUrPRFTUELUvr3Gmc7KZ2Sw/h1PiVM0Af/oHB6zgnV1ikqSfRk+TOufi79aHYCW3NiOXmr1BP5nWbzojLaA==
|
||||
|
||||
typescript@^4.3.5:
|
||||
version "4.9.5"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.9.5.tgz#095979f9bcc0d09da324d58d03ce8f8374cbe65a"
|
||||
integrity sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==
|
||||
@ -22,7 +22,7 @@
|
||||
"@eslint-community/eslint-plugin-eslint-comments": "^3.2.1",
|
||||
"@types/faker": "^5.5.9",
|
||||
"@types/geojson": "^7946.0.13",
|
||||
"@types/node": "^16.10.3",
|
||||
"@types/node": "^17.0.21",
|
||||
"@typescript-eslint/eslint-plugin": "^5.57.1",
|
||||
"@typescript-eslint/parser": "^5.57.1",
|
||||
"eslint": "^8.37.0",
|
||||
|
||||
43
database/src/config/detectLastDBVersion.ts
Normal file
43
database/src/config/detectLastDBVersion.ts
Normal file
@ -0,0 +1,43 @@
|
||||
import path from 'path'
|
||||
import fs from 'fs'
|
||||
|
||||
// Define the regular expression pattern once
|
||||
const DB_VERSION_PATTERN = /^(\d{4}-[a-z0-9-_]+)/
|
||||
|
||||
// Define the paths to check
|
||||
const migrationsDir = path.join(__dirname, '..', '..', 'migrations')
|
||||
const entitiesDir = path.join(__dirname, '..', '..', 'entity')
|
||||
|
||||
// Helper function to get the highest version number from the directory
|
||||
function getLatestDbVersion(dir: string): string {
|
||||
// Read all files and folders in the directory
|
||||
const files = fs.readdirSync(dir)
|
||||
|
||||
// Filter out files/folders that don't match the pattern for DB_VERSION
|
||||
const dbVersionFiles = files.filter((file) => file.match(DB_VERSION_PATTERN))
|
||||
|
||||
if (dbVersionFiles.length === 0) {
|
||||
throw new Error(`couldn't found any file in ${dir} matching ${DB_VERSION_PATTERN}`)
|
||||
}
|
||||
|
||||
// Sort files by the version number (extract the version from the filename)
|
||||
const sortedFiles = dbVersionFiles.sort()
|
||||
|
||||
const lastFile = sortedFiles[sortedFiles.length - 1]
|
||||
const matches = lastFile.match(DB_VERSION_PATTERN)
|
||||
if (!matches || matches.length < 1) {
|
||||
throw new Error('invalid match')
|
||||
}
|
||||
// Return the latest version file or folder
|
||||
return matches[1]
|
||||
}
|
||||
|
||||
// Get the latest version from migrations and entities
|
||||
const latestMigrationVersion = getLatestDbVersion(migrationsDir)
|
||||
const latestEntityVersion = getLatestDbVersion(entitiesDir)
|
||||
|
||||
// Determine which directory has the latest version and return it
|
||||
export const latestDbVersion =
|
||||
latestMigrationVersion && (!latestEntityVersion || latestMigrationVersion > latestEntityVersion)
|
||||
? latestMigrationVersion
|
||||
: latestEntityVersion
|
||||
@ -170,10 +170,10 @@
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-16.7.1.tgz#c6b9198178da504dfca1fd0be9b2e1002f1586f0"
|
||||
integrity sha512-ncRdc45SoYJ2H4eWU9ReDfp3vtFqDYhjOsKlFFUDEn8V1Bgr2RjYal8YT5byfadWIRluhPFU6JiDOl0H6Sl87A==
|
||||
|
||||
"@types/node@^16.10.3":
|
||||
version "16.10.3"
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-16.10.3.tgz#7a8f2838603ea314d1d22bb3171d899e15c57bd5"
|
||||
integrity sha512-ho3Ruq+fFnBrZhUYI46n/bV2GjwzSkwuT4dTf0GkuNFmnb8nq4ny2z9JEVemFi6bdEJanHLlYfy9c6FN9B9McQ==
|
||||
"@types/node@^17.0.21":
|
||||
version "17.0.45"
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.45.tgz#2c0fafd78705e7a18b7906b5201a522719dc5190"
|
||||
integrity sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw==
|
||||
|
||||
"@types/semver@^7.3.12":
|
||||
version "7.5.0"
|
||||
|
||||
@ -9,7 +9,7 @@ EMAIL=true
|
||||
EMAIL_USERNAME=peter@lustig.de
|
||||
EMAIL_SENDER=peter@lustig.de
|
||||
EMAIL_PASSWORD=1234
|
||||
EMAIL_SMTP_URL=smtp.lustig.de
|
||||
EMAIL_SMTP_HOST=smtp.lustig.de
|
||||
EMAIL_SMTP_PORT=587
|
||||
|
||||
# if set to true allow sending gradidos to another communities
|
||||
@ -55,15 +55,15 @@ WEBHOOK_GITHUB_BRANCH=master
|
||||
# frontend and admin paths, usually don't need changes
|
||||
# used in nginx config and for links in emails
|
||||
COMMUNITY_REGISTER_PATH=/register
|
||||
COMMUNITY_REDEEM_PATH=/redeem/{code}
|
||||
COMMUNITY_REDEEM_CONTRIBUTION_PATH=/redeem/CL-{code}
|
||||
COMMUNITY_REDEEM_PATH=/redeem/
|
||||
COMMUNITY_REDEEM_CONTRIBUTION_PATH=/redeem/CL-
|
||||
WALLET_LOGIN_PATH=/login
|
||||
WALLET_AUTH_PATH=/authenticate?token={token}
|
||||
EMAIL_LINK_VERIFICATION_PATH=/checkEmail/{optin}{code}
|
||||
EMAIL_LINK_SETPASSWORD_PATH=/reset-password/{optin}
|
||||
WALLET_AUTH_PATH=/authenticate?token=
|
||||
EMAIL_LINK_VERIFICATION_PATH=/checkEmail/
|
||||
EMAIL_LINK_SETPASSWORD_PATH=/reset-password/
|
||||
EMAIL_LINK_FORGOTPASSWORD_PATH=/forgot-password
|
||||
EMAIL_LINK_OVERVIEW_PATH=/overview
|
||||
ADMIN_AUTH_PATH=/admin/authenticate?token={token}
|
||||
ADMIN_AUTH_PATH=/admin/authenticate?token=
|
||||
GRAPHQL_PATH=/graphql
|
||||
|
||||
# login expire time
|
||||
@ -82,7 +82,7 @@ FEDERATION_VALIDATE_COMMUNITY_TIMER=60000
|
||||
FEDERATION_COMMUNITY_APIS=1_0
|
||||
|
||||
# externe gradido services (more added in future)
|
||||
GDT_API_URL=https://gdt.gradido.net
|
||||
GDT_ACTIVE=false
|
||||
|
||||
# DLT-Connector (still in develop)
|
||||
DLT_CONNECTOR=false
|
||||
@ -117,7 +117,6 @@ NGINX_SSL_INCLUDE=/etc/letsencrypt/options-ssl-nginx.conf
|
||||
NGINX_REWRITE_LEGACY_URLS=false
|
||||
|
||||
# LEGACY
|
||||
DEFAULT_PUBLISHER_ID=2896
|
||||
WEBHOOK_ELOPAGE_SECRET=secret
|
||||
|
||||
# GMS
|
||||
|
||||
@ -47,6 +47,7 @@ RUN mkdir -p ${DOCKER_WORKDIR}
|
||||
WORKDIR ${DOCKER_WORKDIR}
|
||||
|
||||
RUN mkdir -p /database
|
||||
RUN mkdir -p /config
|
||||
|
||||
##################################################################################
|
||||
# DEVELOPMENT (Connected to the local environment, to reload on demand) ##########
|
||||
@ -59,7 +60,7 @@ FROM base as development
|
||||
# Run command
|
||||
# (for development we need to execute yarn install since the
|
||||
# node_modules are on another volume and need updating)
|
||||
CMD /bin/sh -c "cd /database && yarn install && yarn build && cd /app && yarn install && yarn run dev"
|
||||
CMD /bin/sh -c "cd /database && yarn install && yarn build && cd /config && yarn install && cd /app && yarn install && yarn run dev"
|
||||
|
||||
##################################################################################
|
||||
# BUILD (Does contain all files and is therefore bloated) ########################
|
||||
@ -70,6 +71,11 @@ FROM base as build
|
||||
COPY ./dht-node/ ./
|
||||
# Copy everything from database
|
||||
COPY ./database/ ../database/
|
||||
# Copy everything from config
|
||||
COPY ./config/ ../config/
|
||||
|
||||
# yarn install and build config
|
||||
RUN cd ../config && yarn install --production=false --frozen-lockfile --non-interactive && yarn run build
|
||||
|
||||
# yarn install dht-node
|
||||
RUN yarn install --production=false --frozen-lockfile --non-interactive
|
||||
@ -99,9 +105,11 @@ FROM base as production
|
||||
# Copy "binary"-files from build image
|
||||
COPY --from=build ${DOCKER_WORKDIR}/build ./build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../database/build ../database/build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/build ../config/build
|
||||
# We also copy the node_modules express and serve-static for the run script
|
||||
COPY --from=build ${DOCKER_WORKDIR}/node_modules ./node_modules
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../database/node_modules ../database/node_modules
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/node_modules ../config/node_modules
|
||||
|
||||
# Copy static files
|
||||
# COPY --from=build ${DOCKER_WORKDIR}/public ./public
|
||||
|
||||
@ -31,5 +31,10 @@ module.exports = {
|
||||
process.env.NODE_ENV === 'development'
|
||||
? '<rootDir>/../database/src/$1'
|
||||
: '<rootDir>/../database/build/src/$1',
|
||||
'@config/(.*)':
|
||||
// eslint-disable-next-line n/no-process-env
|
||||
process.env.NODE_ENV === 'development'
|
||||
? '<rootDir>/../config/src/$1'
|
||||
: '<rootDir>/../config/build/$1',
|
||||
},
|
||||
}
|
||||
|
||||
@ -20,6 +20,7 @@
|
||||
"cross-env": "^7.0.3",
|
||||
"dotenv": "10.0.0",
|
||||
"gradido-database": "file:../database",
|
||||
"joi": "^17.13.3",
|
||||
"log4js": "^6.7.1",
|
||||
"nodemon": "^2.0.20",
|
||||
"tsconfig-paths": "^4.1.2",
|
||||
@ -29,6 +30,7 @@
|
||||
"@eslint-community/eslint-plugin-eslint-comments": "^3.2.1",
|
||||
"@types/dotenv": "^8.2.0",
|
||||
"@types/jest": "^27.0.2",
|
||||
"@types/joi": "^17.2.3",
|
||||
"@types/node": "^18.11.18",
|
||||
"@types/uuid": "^8.3.4",
|
||||
"@typescript-eslint/eslint-plugin": "^5.57.1",
|
||||
@ -43,6 +45,7 @@
|
||||
"eslint-plugin-prettier": "^4.2.1",
|
||||
"eslint-plugin-promise": "^6.1.1",
|
||||
"eslint-plugin-security": "^1.7.1",
|
||||
"gradido-config": "../config",
|
||||
"jest": "^27.2.4",
|
||||
"prettier": "^2.8.7",
|
||||
"ts-jest": "^27.0.5",
|
||||
|
||||
@ -1,18 +1,17 @@
|
||||
/* eslint-disable n/no-process-env */
|
||||
import { validate } from '@config/index'
|
||||
import { latestDbVersion } from '@dbTools/config/detectLastDBVersion'
|
||||
import dotenv from 'dotenv'
|
||||
|
||||
import { schema } from './schema'
|
||||
|
||||
dotenv.config()
|
||||
|
||||
const constants = {
|
||||
DB_VERSION: '0087-add_index_on_user_roles',
|
||||
DB_VERSION: latestDbVersion,
|
||||
LOG4JS_CONFIG: 'log4js-config.json',
|
||||
// default log level on production should be info
|
||||
LOG_LEVEL: process.env.LOG_LEVEL ?? 'info',
|
||||
CONFIG_VERSION: {
|
||||
DEFAULT: 'DEFAULT',
|
||||
EXPECTED: 'v4.2024-01-17',
|
||||
CURRENT: '',
|
||||
},
|
||||
}
|
||||
|
||||
const server = {
|
||||
@ -46,18 +45,6 @@ const federation = {
|
||||
FEDERATION_COMMUNITY_APIS: process.env.FEDERATION_COMMUNITY_APIS ?? '1_0',
|
||||
}
|
||||
|
||||
// Check config version
|
||||
constants.CONFIG_VERSION.CURRENT = process.env.CONFIG_VERSION ?? constants.CONFIG_VERSION.DEFAULT
|
||||
if (
|
||||
![constants.CONFIG_VERSION.EXPECTED, constants.CONFIG_VERSION.DEFAULT].includes(
|
||||
constants.CONFIG_VERSION.CURRENT,
|
||||
)
|
||||
) {
|
||||
throw new Error(
|
||||
`Fatal: Config Version incorrect - expected "${constants.CONFIG_VERSION.EXPECTED}" or "${constants.CONFIG_VERSION.DEFAULT}", but found "${constants.CONFIG_VERSION.CURRENT}"`,
|
||||
)
|
||||
}
|
||||
|
||||
export const CONFIG = {
|
||||
...constants,
|
||||
...server,
|
||||
@ -65,3 +52,4 @@ export const CONFIG = {
|
||||
...community,
|
||||
...federation,
|
||||
}
|
||||
validate(schema, CONFIG)
|
||||
|
||||
64
dht-node/src/config/schema.ts
Normal file
64
dht-node/src/config/schema.ts
Normal file
@ -0,0 +1,64 @@
|
||||
import {
|
||||
COMMUNITY_NAME,
|
||||
COMMUNITY_DESCRIPTION,
|
||||
DB_DATABASE,
|
||||
DB_HOST,
|
||||
DB_PASSWORD,
|
||||
DB_PORT,
|
||||
DB_USER,
|
||||
DB_VERSION,
|
||||
LOG4JS_CONFIG,
|
||||
LOG_LEVEL,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
TYPEORM_LOGGING_RELATIVE_PATH,
|
||||
} from '@config/commonSchema'
|
||||
import Joi from 'joi'
|
||||
|
||||
export const schema = Joi.object({
|
||||
COMMUNITY_NAME,
|
||||
COMMUNITY_DESCRIPTION,
|
||||
DB_DATABASE,
|
||||
DB_HOST,
|
||||
DB_PASSWORD,
|
||||
DB_PORT,
|
||||
DB_USER,
|
||||
DB_VERSION,
|
||||
LOG4JS_CONFIG,
|
||||
LOG_LEVEL,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
TYPEORM_LOGGING_RELATIVE_PATH,
|
||||
|
||||
FEDERATION_DHT_TOPIC: Joi.string()
|
||||
.default('GRADIDO_HUB')
|
||||
.description('The topic for the DHT (Distributed Hash Table), defaults to GRADIDO_HUB')
|
||||
.required(),
|
||||
|
||||
FEDERATION_DHT_SEED: Joi.string()
|
||||
.when('NODE_ENV', {
|
||||
is: 'development',
|
||||
then: Joi.allow(null), // Allow empty for development
|
||||
otherwise: Joi.string()
|
||||
.hex()
|
||||
.length(64)
|
||||
.message('need to be valid hex with 64 character')
|
||||
.required(), // Valid hex and 64 characters for other environments
|
||||
})
|
||||
.description(
|
||||
'Seed for libsodium crypto_sign_seed_keypair. Valid hex with 64 characters in production',
|
||||
)
|
||||
.default(''), // Default to empty string
|
||||
|
||||
FEDERATION_COMMUNITY_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.default(Joi.ref('COMMUNITY_URL'))
|
||||
.description('Community URL for federation, defaults to COMMUNITY_URL')
|
||||
.required(),
|
||||
|
||||
FEDERATION_COMMUNITY_APIS: Joi.string()
|
||||
.valid('1_0', '1_1')
|
||||
.default('1_0')
|
||||
.description('Federation community API version, defaults to 1_0')
|
||||
.required(),
|
||||
})
|
||||
@ -53,7 +53,8 @@
|
||||
"@typeorm/*": ["../backend/src/typeorm/*", "../../backend/src/typeorm/*"],
|
||||
"@dbTools/*": ["../database/src/*", "../../database/build/src/*"],
|
||||
"@entity/*": ["../database/entity/*", "../../database/build/entity/*"],
|
||||
"@logging/*": ["../database/logging/*", "../../database/build/logging/*"]
|
||||
"@logging/*": ["../database/logging/*", "../../database/build/logging/*"],
|
||||
"@config/*": ["../config/src/*", "../../config/build/*"]
|
||||
},
|
||||
// "rootDirs": [], /* List of root folders whose combined content represents the structure of the project at runtime. */
|
||||
"typeRoots": ["src/dht_node/@types", "node_modules/@types"], /* List of folders to include type definitions from. */
|
||||
|
||||
@ -345,6 +345,18 @@
|
||||
resolved "https://registry.yarnpkg.com/@eslint/js/-/js-8.42.0.tgz#484a1d638de2911e6f5a30c12f49c7e4a3270fb6"
|
||||
integrity sha512-6SWlXpWU5AvId8Ac7zjzmIOqMOba/JWY8XZ4A7q7Gn1Vlfg/SFFIlrtHXt9nPn4op9ZPAkl91Jao+QQv3r/ukw==
|
||||
|
||||
"@hapi/hoek@^9.0.0", "@hapi/hoek@^9.3.0":
|
||||
version "9.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/hoek/-/hoek-9.3.0.tgz#8368869dcb735be2e7f5cb7647de78e167a251fb"
|
||||
integrity sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==
|
||||
|
||||
"@hapi/topo@^5.1.0":
|
||||
version "5.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/topo/-/topo-5.1.0.tgz#dc448e332c6c6e37a4dc02fd84ba8d44b9afb012"
|
||||
integrity sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@humanwhocodes/config-array@^0.11.10":
|
||||
version "0.11.10"
|
||||
resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.10.tgz#5a3ffe32cc9306365fb3fd572596cd602d5e12d2"
|
||||
@ -665,6 +677,23 @@
|
||||
picocolors "^1.0.0"
|
||||
tslib "^2.5.0"
|
||||
|
||||
"@sideway/address@^4.1.5":
|
||||
version "4.1.5"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/address/-/address-4.1.5.tgz#4bc149a0076623ced99ca8208ba780d65a99b9d5"
|
||||
integrity sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@sideway/formula@^3.0.1":
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/formula/-/formula-3.0.1.tgz#80fcbcbaf7ce031e0ef2dd29b1bfc7c3f583611f"
|
||||
integrity sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==
|
||||
|
||||
"@sideway/pinpoint@^2.0.0":
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/pinpoint/-/pinpoint-2.0.0.tgz#cff8ffadc372ad29fd3f78277aeb29e632cc70df"
|
||||
integrity sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==
|
||||
|
||||
"@sinonjs/commons@^1.7.0":
|
||||
version "1.8.6"
|
||||
resolved "https://registry.yarnpkg.com/@sinonjs/commons/-/commons-1.8.6.tgz#80c516a4dc264c2a69115e7578d62581ff455ed9"
|
||||
@ -783,6 +812,13 @@
|
||||
jest-matcher-utils "^27.0.0"
|
||||
pretty-format "^27.0.0"
|
||||
|
||||
"@types/joi@^17.2.3":
|
||||
version "17.2.3"
|
||||
resolved "https://registry.yarnpkg.com/@types/joi/-/joi-17.2.3.tgz#b7768ed9d84f1ebd393328b9f97c1cf3d2b94798"
|
||||
integrity sha512-dGjs/lhrWOa+eO0HwgxCSnDm5eMGCsXuvLglMghJq32F6q5LyyNuXb41DHzrg501CKNOSSAHmfB7FDGeUnDmzw==
|
||||
dependencies:
|
||||
joi "*"
|
||||
|
||||
"@types/json-schema@^7.0.9":
|
||||
version "7.0.11"
|
||||
resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.11.tgz#d421b6c527a3037f7c84433fd2c4229e016863d3"
|
||||
@ -2393,8 +2429,13 @@ graceful-fs@^4.2.4:
|
||||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3"
|
||||
integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==
|
||||
|
||||
gradido-config@../config:
|
||||
version "1.0.0"
|
||||
dependencies:
|
||||
joi "^17.13.3"
|
||||
|
||||
"gradido-database@file:../database":
|
||||
version "2.2.1"
|
||||
version "2.4.1"
|
||||
dependencies:
|
||||
"@types/uuid" "^8.3.4"
|
||||
cross-env "^7.0.3"
|
||||
@ -3226,6 +3267,17 @@ jest@^27.2.4:
|
||||
import-local "^3.0.2"
|
||||
jest-cli "^27.5.1"
|
||||
|
||||
joi@*, joi@^17.13.3:
|
||||
version "17.13.3"
|
||||
resolved "https://registry.yarnpkg.com/joi/-/joi-17.13.3.tgz#0f5cc1169c999b30d344366d384b12d92558bcec"
|
||||
integrity sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.3.0"
|
||||
"@hapi/topo" "^5.1.0"
|
||||
"@sideway/address" "^4.1.5"
|
||||
"@sideway/formula" "^3.0.1"
|
||||
"@sideway/pinpoint" "^2.0.0"
|
||||
|
||||
js-tokens@^4.0.0:
|
||||
version "4.0.0"
|
||||
resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499"
|
||||
|
||||
@ -9,7 +9,7 @@ services:
|
||||
build:
|
||||
target: development
|
||||
environment:
|
||||
- NODE_ENV="development"
|
||||
- NODE_ENV=development
|
||||
# - DEBUG=true
|
||||
volumes:
|
||||
# This makes sure the docker container has its own node modules.
|
||||
@ -27,7 +27,7 @@ services:
|
||||
build:
|
||||
target: development
|
||||
environment:
|
||||
- NODE_ENV="development"
|
||||
- NODE_ENV=development
|
||||
# - DEBUG=true
|
||||
volumes:
|
||||
# This makes sure the docker container has its own node modules.
|
||||
@ -55,9 +55,12 @@ services:
|
||||
- backend_node_modules:/app/node_modules
|
||||
- backend_database_node_modules:/database/node_modules
|
||||
- backend_database_build:/database/build
|
||||
- backend_config_node_modules:/config/node_modules
|
||||
- backend_config_build:/config/build
|
||||
# bind the local folder to the docker to allow live reload
|
||||
- ./backend:/app
|
||||
- ./database:/database
|
||||
- ./config:/config
|
||||
|
||||
########################################################
|
||||
# DHT-NODE #############################################
|
||||
@ -78,9 +81,12 @@ services:
|
||||
- dht_node_modules:/app/node_modules
|
||||
- dht_database_node_modules:/database/node_modules
|
||||
- dht_database_build:/database/build
|
||||
- dht_config_node_modules:/config/node_modules
|
||||
- dht_config_build:/config/build
|
||||
# bind the local folder to the docker to allow live reload
|
||||
- ./dht-node:/app
|
||||
- ./database:/database
|
||||
- ./config:/config
|
||||
|
||||
########################################################
|
||||
# DLT-CONNECTOR ########################################
|
||||
@ -122,9 +128,12 @@ services:
|
||||
- federation_node_modules:/app/node_modules
|
||||
- federation_database_node_modules:/database/node_modules
|
||||
- federation_database_build:/database/build
|
||||
- federation_config_node_modules:/config/node_modules
|
||||
- federation_config_build:/config/build
|
||||
# bind the local folder to the docker to allow live reload
|
||||
- ./federation:/app
|
||||
- ./database:/database
|
||||
- ./config:/config
|
||||
|
||||
########################################################
|
||||
# DATABASE ##############################################
|
||||
@ -216,13 +225,19 @@ volumes:
|
||||
backend_node_modules:
|
||||
backend_database_node_modules:
|
||||
backend_database_build:
|
||||
backend_config_node_modules:
|
||||
backend_config_build:
|
||||
dht_node_modules:
|
||||
dht_database_node_modules:
|
||||
dht_database_build:
|
||||
dht_config_node_modules:
|
||||
dht_config_build:
|
||||
dlt_connector_modules:
|
||||
federation_node_modules:
|
||||
federation_database_node_modules:
|
||||
federation_database_build:
|
||||
federation_config_node_modules:
|
||||
federation_config_build:
|
||||
database_node_modules:
|
||||
database_build:
|
||||
dlt-database_node_modules:
|
||||
|
||||
@ -7,7 +7,7 @@ services:
|
||||
build:
|
||||
target: test
|
||||
environment:
|
||||
- NODE_ENV="test"
|
||||
- NODE_ENV=test
|
||||
|
||||
########################################################
|
||||
# ADMIN INTERFACE ######################################
|
||||
@ -17,7 +17,7 @@ services:
|
||||
build:
|
||||
target: test
|
||||
environment:
|
||||
- NODE_ENV="test"
|
||||
- NODE_ENV=test
|
||||
|
||||
########################################################
|
||||
# BACKEND ##############################################
|
||||
@ -31,7 +31,7 @@ services:
|
||||
- external-net
|
||||
- internal-net
|
||||
environment:
|
||||
- NODE_ENV="test"
|
||||
- NODE_ENV=test
|
||||
- DB_HOST=mariadb
|
||||
|
||||
########################################################
|
||||
@ -46,7 +46,7 @@ services:
|
||||
- external-net
|
||||
- internal-net
|
||||
environment:
|
||||
- NODE_ENV="test"
|
||||
- NODE_ENV="test
|
||||
- DB_HOST=mariadb
|
||||
|
||||
########################################################
|
||||
@ -61,7 +61,7 @@ services:
|
||||
- external-net
|
||||
- internal-net
|
||||
environment:
|
||||
- NODE_ENV="test"
|
||||
- NODE_ENV=test
|
||||
- DB_HOST=mariadb
|
||||
|
||||
########################################################
|
||||
@ -73,7 +73,7 @@ services:
|
||||
context: ./database
|
||||
target: test_up
|
||||
environment:
|
||||
- NODE_ENV="test"
|
||||
- NODE_ENV=test
|
||||
# restart: always # this is very dangerous, but worth a test for the delayed mariadb startup at first run
|
||||
|
||||
########################################################
|
||||
@ -85,7 +85,7 @@ services:
|
||||
context: ./dlt-database
|
||||
target: test_up
|
||||
environment:
|
||||
- NODE_ENV="test"
|
||||
- NODE_ENV=test
|
||||
# restart: always # this is very dangerous, but worth a test for the delayed mariadb startup at first run
|
||||
|
||||
#########################################################
|
||||
|
||||
@ -12,7 +12,8 @@ services:
|
||||
# name the image so that it cannot be found in a DockerHub repository, otherwise it will not be built locally from the 'dockerfile' but pulled from there
|
||||
image: gradido/frontend:local-production
|
||||
build:
|
||||
context: ./frontend
|
||||
context: ./
|
||||
dockerfile: ./frontend/Dockerfile
|
||||
target: production
|
||||
networks:
|
||||
- external-net
|
||||
@ -26,7 +27,9 @@ services:
|
||||
# - BUILD_DATE="1970-01-01T00:00:00.00Z"
|
||||
# - BUILD_VERSION="0.0.0.0"
|
||||
# - BUILD_COMMIT="0000000"
|
||||
- NODE_ENV="production"
|
||||
- NODE_ENV=production
|
||||
volumes:
|
||||
- ./config:/config
|
||||
# env_file:
|
||||
# - ./.env
|
||||
# - ./frontend/.env
|
||||
@ -38,7 +41,8 @@ services:
|
||||
# name the image so that it cannot be found in a DockerHub repository, otherwise it will not be built locally from the 'dockerfile' but pulled from there
|
||||
image: gradido/admin:local-production
|
||||
build:
|
||||
context: ./admin
|
||||
context: ./
|
||||
dockerfile: ./admin/Dockerfile
|
||||
target: production
|
||||
networks:
|
||||
- external-net
|
||||
@ -52,7 +56,9 @@ services:
|
||||
# - BUILD_DATE="1970-01-01T00:00:00.00Z"
|
||||
# - BUILD_VERSION="0.0.0.0"
|
||||
# - BUILD_COMMIT="0000000"
|
||||
- NODE_ENV="production"
|
||||
- NODE_ENV=production
|
||||
volumes:
|
||||
- ./config:/config
|
||||
# env_file:
|
||||
# - ./.env
|
||||
# - ./admin/.env
|
||||
|
||||
@ -44,6 +44,7 @@ RUN mkdir -p ${DOCKER_WORKDIR}
|
||||
WORKDIR ${DOCKER_WORKDIR}
|
||||
|
||||
RUN mkdir -p /database
|
||||
RUN mkdir -p /config
|
||||
|
||||
##################################################################################
|
||||
# DEVELOPMENT (Connected to the local environment, to reload on demand) ##########
|
||||
@ -56,7 +57,7 @@ FROM base as development
|
||||
# Run command
|
||||
# (for development we need to execute yarn install since the
|
||||
# node_modules are on another volume and need updating)
|
||||
CMD /bin/sh -c "cd /database && yarn install && yarn build && cd /app && yarn install && yarn run dev"
|
||||
CMD /bin/sh -c "cd /database && yarn install && yarn build && cd /config && yarn install && cd /app && yarn install && yarn run dev"
|
||||
|
||||
##################################################################################
|
||||
# BUILD (Does contain all files and is therefore bloated) ########################
|
||||
@ -67,6 +68,11 @@ FROM base as build
|
||||
COPY ./federation/ ./
|
||||
# Copy everything from database
|
||||
COPY ./database/ ../database/
|
||||
# Copy everything from config
|
||||
COPY ./config/ ../config/
|
||||
|
||||
# yarn install and build config
|
||||
RUN cd ../config && yarn install --production=false --frozen-lockfile --non-interactive && yarn run build
|
||||
|
||||
# yarn install federation
|
||||
RUN yarn install --production=false --frozen-lockfile --non-interactive
|
||||
@ -96,9 +102,11 @@ FROM base as production
|
||||
# Copy "binary"-files from build image
|
||||
COPY --from=build ${DOCKER_WORKDIR}/build ./build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../database/build ../database/build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/build ../config/build
|
||||
# We also copy the node_modules express and serve-static for the run script
|
||||
COPY --from=build ${DOCKER_WORKDIR}/node_modules ./node_modules
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../database/node_modules ../database/node_modules
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/node_modules ../config/node_modules
|
||||
|
||||
# Copy static files
|
||||
# COPY --from=build ${DOCKER_WORKDIR}/public ./public
|
||||
|
||||
@ -33,5 +33,10 @@ module.exports = {
|
||||
process.env.NODE_ENV === 'development'
|
||||
? '<rootDir>/../database/src/$1'
|
||||
: '<rootDir>/../database/build/src/$1',
|
||||
'@config/(.*)':
|
||||
// eslint-disable-next-line n/no-process-env
|
||||
process.env.NODE_ENV === 'development'
|
||||
? '<rootDir>/../config/src/$1'
|
||||
: '<rootDir>/../config/build/$1',
|
||||
},
|
||||
}
|
||||
|
||||
@ -28,6 +28,7 @@
|
||||
"graphql": "15.5.1",
|
||||
"graphql-request": "5.0.0",
|
||||
"helmet": "^7.1.0",
|
||||
"joi": "^17.13.3",
|
||||
"lodash.clonedeep": "^4.5.0",
|
||||
"log4js": "^6.7.1",
|
||||
"reflect-metadata": "^0.1.13",
|
||||
@ -38,6 +39,7 @@
|
||||
"devDependencies": {
|
||||
"@types/express": "4.17.12",
|
||||
"@types/jest": "27.0.2",
|
||||
"@types/joi": "^17.2.3",
|
||||
"@types/lodash.clonedeep": "^4.5.6",
|
||||
"@types/node": "^16.10.3",
|
||||
"@types/sodium-native": "^2.3.5",
|
||||
@ -56,6 +58,7 @@
|
||||
"eslint-plugin-promise": "^6.1.1",
|
||||
"eslint-plugin-security": "^1.7.1",
|
||||
"eslint-plugin-type-graphql": "^1.0.0",
|
||||
"gradido-config": "../config",
|
||||
"graphql-tag": "^2.12.6",
|
||||
"jest": "^27.2.4",
|
||||
"nodemon": "^2.0.7",
|
||||
|
||||
@ -1,7 +1,12 @@
|
||||
// ATTENTION: DO NOT PUT ANY SECRETS IN HERE (or the .env)
|
||||
import { Decimal } from 'decimal.js-light'
|
||||
import { latestDbVersion } from '@dbTools/config/detectLastDBVersion'
|
||||
import dotenv from 'dotenv'
|
||||
|
||||
import { validate } from '@config/index'
|
||||
|
||||
import { schema } from './schema'
|
||||
|
||||
dotenv.config()
|
||||
|
||||
Decimal.set({
|
||||
@ -10,16 +15,11 @@ Decimal.set({
|
||||
})
|
||||
|
||||
const constants = {
|
||||
DB_VERSION: '0087-add_index_on_user_roles',
|
||||
DB_VERSION: latestDbVersion,
|
||||
DECAY_START_TIME: new Date('2021-05-13 17:46:31-0000'), // GMT+0
|
||||
LOG4JS_CONFIG: 'log4js-config.json',
|
||||
// default log level on production should be info
|
||||
LOG_LEVEL: process.env.LOG_LEVEL ?? 'info',
|
||||
CONFIG_VERSION: {
|
||||
DEFAULT: 'DEFAULT',
|
||||
EXPECTED: 'v2.2023-08-24',
|
||||
CURRENT: '',
|
||||
},
|
||||
}
|
||||
|
||||
const server = {
|
||||
@ -38,18 +38,6 @@ const database = {
|
||||
TYPEORM_LOGGING_RELATIVE_PATH: process.env.TYPEORM_LOGGING_RELATIVE_PATH ?? 'typeorm.backend.log',
|
||||
}
|
||||
|
||||
// Check config version
|
||||
constants.CONFIG_VERSION.CURRENT = process.env.CONFIG_VERSION ?? constants.CONFIG_VERSION.DEFAULT
|
||||
if (
|
||||
![constants.CONFIG_VERSION.EXPECTED, constants.CONFIG_VERSION.DEFAULT].includes(
|
||||
constants.CONFIG_VERSION.CURRENT,
|
||||
)
|
||||
) {
|
||||
throw new Error(
|
||||
`Fatal: Config Version incorrect - expected "${constants.CONFIG_VERSION.EXPECTED}" or "${constants.CONFIG_VERSION.DEFAULT}", but found "${constants.CONFIG_VERSION.CURRENT}"`,
|
||||
)
|
||||
}
|
||||
|
||||
const COMMUNITY_HOST = process.env.COMMUNITY_HOST ?? 'localhost'
|
||||
const URL_PROTOCOL = process.env.URL_PROTOCOL ?? 'http'
|
||||
const COMMUNITY_URL = process.env.COMMUNITY_URL ?? `${URL_PROTOCOL}://${COMMUNITY_HOST}`
|
||||
@ -74,4 +62,6 @@ export const CONFIG = {
|
||||
...federation,
|
||||
}
|
||||
|
||||
validate(schema, CONFIG)
|
||||
|
||||
export default CONFIG
|
||||
|
||||
75
federation/src/config/schema.ts
Normal file
75
federation/src/config/schema.ts
Normal file
@ -0,0 +1,75 @@
|
||||
import {
|
||||
DB_DATABASE,
|
||||
DB_HOST,
|
||||
DB_PASSWORD,
|
||||
DB_PORT,
|
||||
DB_USER,
|
||||
DB_VERSION,
|
||||
DECAY_START_TIME,
|
||||
GRAPHIQL,
|
||||
LOG4JS_CONFIG,
|
||||
LOG_LEVEL,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
TYPEORM_LOGGING_RELATIVE_PATH,
|
||||
} from '@config/commonSchema'
|
||||
import Joi from 'joi'
|
||||
|
||||
export const schema = Joi.object({
|
||||
DB_DATABASE,
|
||||
DB_HOST,
|
||||
DB_PASSWORD,
|
||||
DB_PORT,
|
||||
DB_USER,
|
||||
DB_VERSION,
|
||||
DECAY_START_TIME,
|
||||
GRAPHIQL,
|
||||
LOG4JS_CONFIG,
|
||||
LOG_LEVEL,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
TYPEORM_LOGGING_RELATIVE_PATH,
|
||||
|
||||
FEDERATION_API: Joi.string()
|
||||
.valid('1_0', '1_1')
|
||||
.default('1_0')
|
||||
.description('Federation API version, defaults to 1_0')
|
||||
.required(),
|
||||
|
||||
FEDERATION_PORT: Joi.number()
|
||||
.integer()
|
||||
.min(1024)
|
||||
.max(49151)
|
||||
.default(5010)
|
||||
.description('Port number for the federation service, defaults to 5010')
|
||||
.required(),
|
||||
|
||||
FEDERATION_COMMUNITY_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.default(Joi.ref('COMMUNITY_URL'))
|
||||
.description('Community URL for federation, defaults to COMMUNITY_URL')
|
||||
.required(),
|
||||
|
||||
FEDERATION_TRADING_LEVEL: Joi.object({
|
||||
RECEIVER_COMMUNITY_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.default('https://stage3.gradido.net/api/')
|
||||
.description('URL of the receiver community for trading')
|
||||
.required(),
|
||||
|
||||
SEND_COINS: Joi.boolean()
|
||||
.default(true)
|
||||
.description('Indicates if coins can be sent to the receiver community')
|
||||
.required(),
|
||||
|
||||
AMOUNT: Joi.number()
|
||||
.integer()
|
||||
.min(1)
|
||||
.default(100)
|
||||
.description('Maximum amount of coins allowed for trading')
|
||||
.required(),
|
||||
})
|
||||
.default()
|
||||
.description('Trading level configuration for federation')
|
||||
.optional(),
|
||||
})
|
||||
@ -61,7 +61,8 @@
|
||||
"@typeorm/*": ["../backend/src/typeorm/*", "../../backend/src/typeorm/*"],
|
||||
"@dbTools/*": ["../database/src/*", "../../database/build/src/*"],
|
||||
"@entity/*": ["../database/entity/*", "../../database/build/entity/*"],
|
||||
"@logging/*": ["../database/logging/*", "../../database/build/logging/*"]
|
||||
"@logging/*": ["../database/logging/*", "../../database/build/logging/*"],
|
||||
"@config/*": ["../config/src/*", "../../config/build/*"]
|
||||
},
|
||||
// "rootDirs": [], /* List of root folders whose combined content represents the structure of the project at runtime. */
|
||||
"typeRoots": ["node_modules/@types"], /* List of folders to include type definitions from. */
|
||||
|
||||
@ -379,6 +379,18 @@
|
||||
resolved "https://registry.yarnpkg.com/@graphql-typed-document-node/core/-/core-3.2.0.tgz#5f3d96ec6b2354ad6d8a28bf216a1d97b5426861"
|
||||
integrity sha512-mB9oAsNCm9aM3/SOv4YtBMqZbYj10R7dkq8byBqxGY/ncFwhf2oQzMV+LCRlWoDSEBJ3COiR1yeDvMtsoOsuFQ==
|
||||
|
||||
"@hapi/hoek@^9.0.0", "@hapi/hoek@^9.3.0":
|
||||
version "9.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/hoek/-/hoek-9.3.0.tgz#8368869dcb735be2e7f5cb7647de78e167a251fb"
|
||||
integrity sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==
|
||||
|
||||
"@hapi/topo@^5.1.0":
|
||||
version "5.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/topo/-/topo-5.1.0.tgz#dc448e332c6c6e37a4dc02fd84ba8d44b9afb012"
|
||||
integrity sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@humanwhocodes/config-array@^0.11.10":
|
||||
version "0.11.10"
|
||||
resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.10.tgz#5a3ffe32cc9306365fb3fd572596cd602d5e12d2"
|
||||
@ -722,6 +734,23 @@
|
||||
resolved "https://registry.yarnpkg.com/@protobufjs/utf8/-/utf8-1.1.0.tgz#a777360b5b39a1a2e5106f8e858f2fd2d060c570"
|
||||
integrity sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw==
|
||||
|
||||
"@sideway/address@^4.1.5":
|
||||
version "4.1.5"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/address/-/address-4.1.5.tgz#4bc149a0076623ced99ca8208ba780d65a99b9d5"
|
||||
integrity sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@sideway/formula@^3.0.1":
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/formula/-/formula-3.0.1.tgz#80fcbcbaf7ce031e0ef2dd29b1bfc7c3f583611f"
|
||||
integrity sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==
|
||||
|
||||
"@sideway/pinpoint@^2.0.0":
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/pinpoint/-/pinpoint-2.0.0.tgz#cff8ffadc372ad29fd3f78277aeb29e632cc70df"
|
||||
integrity sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==
|
||||
|
||||
"@sinonjs/commons@^1.7.0":
|
||||
version "1.8.6"
|
||||
resolved "https://registry.yarnpkg.com/@sinonjs/commons/-/commons-1.8.6.tgz#80c516a4dc264c2a69115e7578d62581ff455ed9"
|
||||
@ -941,6 +970,13 @@
|
||||
jest-diff "^27.0.0"
|
||||
pretty-format "^27.0.0"
|
||||
|
||||
"@types/joi@^17.2.3":
|
||||
version "17.2.3"
|
||||
resolved "https://registry.yarnpkg.com/@types/joi/-/joi-17.2.3.tgz#b7768ed9d84f1ebd393328b9f97c1cf3d2b94798"
|
||||
integrity sha512-dGjs/lhrWOa+eO0HwgxCSnDm5eMGCsXuvLglMghJq32F6q5LyyNuXb41DHzrg501CKNOSSAHmfB7FDGeUnDmzw==
|
||||
dependencies:
|
||||
joi "*"
|
||||
|
||||
"@types/json-schema@^7.0.9":
|
||||
version "7.0.12"
|
||||
resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.12.tgz#d70faba7039d5fca54c83c7dbab41051d2b6f6cb"
|
||||
@ -3027,6 +3063,11 @@ graceful-fs@^4.2.4:
|
||||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3"
|
||||
integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==
|
||||
|
||||
gradido-config@../config:
|
||||
version "1.0.0"
|
||||
dependencies:
|
||||
joi "^17.13.3"
|
||||
|
||||
grapheme-splitter@^1.0.4:
|
||||
version "1.0.4"
|
||||
resolved "https://registry.yarnpkg.com/grapheme-splitter/-/grapheme-splitter-1.0.4.tgz#9cf3a665c6247479896834af35cf1dbb4400767e"
|
||||
@ -3944,6 +3985,17 @@ jest@^27.2.4:
|
||||
import-local "^3.0.2"
|
||||
jest-cli "^27.5.1"
|
||||
|
||||
joi@*, joi@^17.13.3:
|
||||
version "17.13.3"
|
||||
resolved "https://registry.yarnpkg.com/joi/-/joi-17.13.3.tgz#0f5cc1169c999b30d344366d384b12d92558bcec"
|
||||
integrity sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.3.0"
|
||||
"@hapi/topo" "^5.1.0"
|
||||
"@sideway/address" "^4.1.5"
|
||||
"@sideway/formula" "^3.0.1"
|
||||
"@sideway/pinpoint" "^2.0.0"
|
||||
|
||||
js-tokens@^4.0.0:
|
||||
version "4.0.0"
|
||||
resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499"
|
||||
|
||||
@ -1,9 +1,6 @@
|
||||
# Environment
|
||||
DEFAULT_PUBLISHER_ID=2896
|
||||
|
||||
# Endpoints
|
||||
GRAPHQL_PATH=/graphql
|
||||
ADMIN_AUTH_PATH=/admin/authenticate?token={token}
|
||||
ADMIN_AUTH_PATH=/admin/authenticate?token=
|
||||
|
||||
# Community
|
||||
COMMUNITY_NAME=Gradido Entwicklung
|
||||
|
||||
@ -1,8 +1,5 @@
|
||||
CONFIG_VERSION=$FRONTEND_CONFIG_VERSION
|
||||
|
||||
# Environment
|
||||
DEFAULT_PUBLISHER_ID=$DEFAULT_PUBLISHER_ID
|
||||
|
||||
# Endpoints
|
||||
GRAPHQL_PATH=$GRAPHQL_PATH
|
||||
ADMIN_AUTH_PATH=$ADMIN_AUTH_PATH
|
||||
|
||||
@ -11,7 +11,7 @@ ENV BUILD_DATE="1970-01-01T00:00:00.00Z"
|
||||
## We cannot do $(npm run version).${BUILD_NUMBER} here so we default to 0.0.0.0
|
||||
ENV BUILD_VERSION="0.0.0.0"
|
||||
## We cannot do `$(git rev-parse --short HEAD)` here so we default to 0000000
|
||||
ENV BUILD_COMMIT="0000000"
|
||||
ENV BUILD_COMMIT_SHORT="0000000"
|
||||
## SET NODE_ENV
|
||||
ENV NODE_ENV="production"
|
||||
## App relevant Envs
|
||||
@ -42,6 +42,8 @@ EXPOSE ${PORT}
|
||||
RUN mkdir -p ${DOCKER_WORKDIR}
|
||||
WORKDIR ${DOCKER_WORKDIR}
|
||||
|
||||
RUN mkdir -p /config
|
||||
|
||||
##################################################################################
|
||||
# DEVELOPMENT (Connected to the local environment, to reload on demand) ##########
|
||||
##################################################################################
|
||||
@ -53,7 +55,7 @@ FROM base as development
|
||||
# Run command
|
||||
# (for development we need to execute npm install since the
|
||||
# node_modules are on another volume and need updating)
|
||||
CMD /bin/sh -c "yarn install && yarn run dev"
|
||||
CMD /bin/sh -c "cd /config && yarn install && yarn build && cd /app && yarn install && yarn run dev"
|
||||
|
||||
##################################################################################
|
||||
# BUILD (Does contain all files and is therefore bloated) ########################
|
||||
@ -61,9 +63,17 @@ CMD /bin/sh -c "yarn install && yarn run dev"
|
||||
FROM base as build
|
||||
|
||||
# Copy everything
|
||||
COPY . .
|
||||
COPY ./frontend ./
|
||||
|
||||
# Copy everything from config
|
||||
COPY ./config/ ../config/
|
||||
|
||||
# install and build config
|
||||
RUN cd ../config && yarn install --production=false --frozen-lockfile --non-interactive && yarn build
|
||||
|
||||
# npm install
|
||||
RUN yarn global add node-gyp && yarn install --production=false --frozen-lockfile --non-interactive
|
||||
|
||||
# npm build
|
||||
RUN yarn run build
|
||||
|
||||
@ -85,6 +95,7 @@ FROM base as production
|
||||
|
||||
# Copy "binary"-files from build image
|
||||
COPY --from=build ${DOCKER_WORKDIR}/build ./build
|
||||
COPY --from=build ${DOCKER_WORKDIR}/../config/build ../config/build
|
||||
# We also copy the node_modules express and serve-static for the run script
|
||||
COPY --from=build ${DOCKER_WORKDIR}/node_modules ./node_modules
|
||||
# Copy static files
|
||||
|
||||
@ -91,6 +91,8 @@
|
||||
"eslint-plugin-promise": "^5.1.1",
|
||||
"eslint-plugin-vitest": "^0.5.4",
|
||||
"eslint-plugin-vue": "8.7.1",
|
||||
"gradido-config": "../config",
|
||||
"joi": "^17.13.3",
|
||||
"jsdom": "^25.0.0",
|
||||
"mock-apollo-client": "^1.2.1",
|
||||
"postcss": "^8.4.8",
|
||||
|
||||
@ -6,11 +6,6 @@ const pkg = require('../../package')
|
||||
|
||||
const constants = {
|
||||
DECAY_START_TIME: new Date('2021-05-13 17:46:31-0000'), // GMT+0
|
||||
CONFIG_VERSION: {
|
||||
DEFAULT: 'DEFAULT',
|
||||
EXPECTED: 'v7.2024-08-06',
|
||||
CURRENT: '',
|
||||
},
|
||||
}
|
||||
|
||||
const version = {
|
||||
@ -18,12 +13,13 @@ const version = {
|
||||
FRONTEND_MODULE_HOST: process.env.FRONTEND_MODULE_HOST ?? '0.0.0.0',
|
||||
FRONTEND_MODULE_PORT: process.env.FRONTEND_MODULE_PORT ?? '3000',
|
||||
APP_VERSION: pkg.version,
|
||||
BUILD_COMMIT: process.env.BUILD_COMMIT ?? null,
|
||||
BUILD_COMMIT: process.env.BUILD_COMMIT ?? undefined,
|
||||
// self reference of `version.BUILD_COMMIT` is not possible at this point, hence the duplicate code
|
||||
BUILD_COMMIT_SHORT: (process.env.BUILD_COMMIT ?? '0000000').slice(0, 7),
|
||||
}
|
||||
|
||||
let FRONTEND_MODULE_URL
|
||||
|
||||
// in case of hosting the frontend module with a nodejs-instance
|
||||
if (process.env.FRONTEND_HOSTING === 'nodejs') {
|
||||
FRONTEND_MODULE_URL =
|
||||
@ -50,7 +46,6 @@ const environment = {
|
||||
NODE_ENV: process.env.NODE_ENV,
|
||||
DEBUG: process.env.NODE_ENV !== 'production' ?? false,
|
||||
PRODUCTION: process.env.NODE_ENV === 'production' ?? false,
|
||||
DEFAULT_PUBLISHER_ID: process.env.DEFAULT_PUBLISHER_ID ?? 2896,
|
||||
}
|
||||
|
||||
// const COMMUNITY_HOST = process.env.COMMUNITY_HOST ?? 'localhost'
|
||||
@ -61,7 +56,7 @@ const endpoints = {
|
||||
GRAPHQL_URI: process.env.GRAPHQL_URI ?? COMMUNITY_URL + (process.env.GRAPHQL_PATH ?? '/graphql'),
|
||||
ADMIN_AUTH_URL:
|
||||
process.env.ADMIN_AUTH_URL ??
|
||||
COMMUNITY_URL + (process.env.ADMIN_AUTH_PATH ?? '/admin/authenticate?token={token}'),
|
||||
COMMUNITY_URL + (process.env.ADMIN_AUTH_PATH ?? '/admin/authenticate?token='),
|
||||
}
|
||||
|
||||
const community = {
|
||||
@ -93,26 +88,15 @@ const meta = {
|
||||
META_AUTHOR: process.env.META_AUTHOR ?? 'Bernd Hückstädt - Gradido-Akademie',
|
||||
}
|
||||
|
||||
// Check config version
|
||||
constants.CONFIG_VERSION.CURRENT = process.env.CONFIG_VERSION ?? constants.CONFIG_VERSION.DEFAULT
|
||||
if (
|
||||
![constants.CONFIG_VERSION.EXPECTED, constants.CONFIG_VERSION.DEFAULT].includes(
|
||||
constants.CONFIG_VERSION.CURRENT,
|
||||
)
|
||||
) {
|
||||
throw new Error(
|
||||
`Fatal: Config Version incorrect - expected "${constants.CONFIG_VERSION.EXPECTED}" or "${constants.CONFIG_VERSION.DEFAULT}", but found "${constants.CONFIG_VERSION.CURRENT}"`,
|
||||
)
|
||||
}
|
||||
|
||||
const CONFIG = {
|
||||
...constants,
|
||||
...version,
|
||||
...features,
|
||||
...environment,
|
||||
...endpoints,
|
||||
...community,
|
||||
...meta,
|
||||
...constants,
|
||||
FRONTEND_MODULE_URL,
|
||||
}
|
||||
|
||||
module.exports = CONFIG
|
||||
|
||||
167
frontend/src/config/schema.js
Normal file
167
frontend/src/config/schema.js
Normal file
@ -0,0 +1,167 @@
|
||||
const {
|
||||
APP_VERSION,
|
||||
BUILD_COMMIT,
|
||||
BUILD_COMMIT_SHORT,
|
||||
COMMUNITY_DESCRIPTION,
|
||||
COMMUNITY_NAME,
|
||||
COMMUNITY_SUPPORT_MAIL,
|
||||
COMMUNITY_LOCATION,
|
||||
COMMUNITY_URL,
|
||||
DEBUG,
|
||||
DECAY_START_TIME,
|
||||
GMS_ACTIVE,
|
||||
GRAPHQL_URI,
|
||||
HUMHUB_ACTIVE,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
} = require('gradido-config/build/src/commonSchema.js')
|
||||
const Joi = require('joi')
|
||||
|
||||
// console.log(commonSchema)
|
||||
|
||||
module.exports = Joi.object({
|
||||
APP_VERSION,
|
||||
BUILD_COMMIT,
|
||||
BUILD_COMMIT_SHORT,
|
||||
COMMUNITY_DESCRIPTION,
|
||||
COMMUNITY_NAME,
|
||||
COMMUNITY_SUPPORT_MAIL,
|
||||
COMMUNITY_LOCATION,
|
||||
COMMUNITY_URL,
|
||||
DEBUG,
|
||||
DECAY_START_TIME,
|
||||
GMS_ACTIVE,
|
||||
GRAPHQL_URI,
|
||||
HUMHUB_ACTIVE,
|
||||
NODE_ENV,
|
||||
PRODUCTION,
|
||||
|
||||
ADMIN_AUTH_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.description('Extern Url for admin-frontend')
|
||||
.default('http://0.0.0.0/admin/authenticate?token=')
|
||||
.required(),
|
||||
|
||||
COMMUNITY_REGISTER_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.description('URL for Register a new Account in frontend.')
|
||||
.required(),
|
||||
|
||||
FRONTEND_HOSTING: Joi.string()
|
||||
.valid('nodejs', 'nginx')
|
||||
.description('set to `nodejs` if frontend is hosted by vite with a own nodejs instance')
|
||||
.optional(),
|
||||
|
||||
FRONTEND_MODULE_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.when('COMMUNITY_URL', {
|
||||
is: Joi.exist(),
|
||||
then: Joi.optional(), // not required if COMMUNITY_URL is provided
|
||||
otherwise: Joi.required(), // required if COMMUNITY_URL is missing
|
||||
})
|
||||
.description(
|
||||
"Base Url for reaching frontend in browser, only needed if COMMUNITY_URL wasn't set",
|
||||
)
|
||||
.optional(), // optional in general, but conditionally required
|
||||
|
||||
FRONTEND_MODULE_PROTOCOL: Joi.string()
|
||||
.when('FRONTEND_HOSTING', {
|
||||
is: Joi.valid('nodejs'),
|
||||
then: Joi.valid('http').required(),
|
||||
otherwise: Joi.valid('http', 'https').required(),
|
||||
})
|
||||
.description(
|
||||
`
|
||||
Protocol for frontend module hosting
|
||||
- it has to be the same as for backend api url and admin to prevent mixed block errors,
|
||||
- if frontend is served with nodejs:
|
||||
is have to be http or setup must be updated to include a ssl certificate
|
||||
`,
|
||||
)
|
||||
.default('http')
|
||||
.required(),
|
||||
|
||||
FRONTEND_MODULE_HOST: Joi.alternatives()
|
||||
.try(
|
||||
Joi.string().valid('localhost').messages({ 'any.invalid': 'Must be localhost' }),
|
||||
Joi.string()
|
||||
.ip({ version: ['ipv4'] })
|
||||
.messages({ 'string.ip': 'Must be a valid IPv4 address' }),
|
||||
Joi.string().domain().messages({ 'string.domain': 'Must be a valid domain' }),
|
||||
)
|
||||
.when('FRONTEND_HOSTING', {
|
||||
is: 'nodejs',
|
||||
then: Joi.required(),
|
||||
otherwise: Joi.optional(),
|
||||
})
|
||||
.when('COMMUNITY_URL', {
|
||||
is: null,
|
||||
then: Joi.required(),
|
||||
otherwise: Joi.optional(),
|
||||
})
|
||||
.description(
|
||||
'Host (domain, IPv4, or localhost) for the frontend, default is 0.0.0.0 for local hosting during development.',
|
||||
)
|
||||
.default('0.0.0.0'),
|
||||
|
||||
FRONTEND_MODULE_PORT: Joi.number()
|
||||
.integer()
|
||||
.min(1024)
|
||||
.max(49151)
|
||||
.description('Port for hosting Frontend with Vite as a Node.js instance, default: 3000')
|
||||
.default(3000)
|
||||
.when('FRONTEND_HOSTING', {
|
||||
is: 'nodejs',
|
||||
then: Joi.required(),
|
||||
otherwise: Joi.optional(),
|
||||
}),
|
||||
|
||||
META_URL: Joi.string()
|
||||
.uri({ scheme: ['http', 'https'] })
|
||||
.description('The base URL for the meta tags.')
|
||||
.default('http://localhost')
|
||||
.required(),
|
||||
|
||||
META_TITLE_DE: Joi.string()
|
||||
.description('Meta title in German.')
|
||||
.default('Gradido – Dein Dankbarkeitskonto')
|
||||
.required(),
|
||||
|
||||
META_TITLE_EN: Joi.string()
|
||||
.description('Meta title in English.')
|
||||
.default('Gradido - Your gratitude account')
|
||||
.required(),
|
||||
|
||||
META_DESCRIPTION_DE: Joi.string()
|
||||
.description('Meta description in German.')
|
||||
.default(
|
||||
'Dankbarkeit ist die Währung der neuen Zeit. Immer mehr Menschen entfalten ihr Potenzial und gestalten eine gute Zukunft für alle.',
|
||||
)
|
||||
.required(),
|
||||
|
||||
META_DESCRIPTION_EN: Joi.string()
|
||||
.description('Meta description in English.')
|
||||
.default(
|
||||
'Gratitude is the currency of the new age. More and more people are unleashing their potential and shaping a good future for all.',
|
||||
)
|
||||
.required(),
|
||||
|
||||
META_KEYWORDS_DE: Joi.string()
|
||||
.description('Meta keywords in German.')
|
||||
.default(
|
||||
'Grundeinkommen, Währung, Dankbarkeit, Schenk-Ökonomie, Natürliche Ökonomie des Lebens, Ökonomie, Ökologie, Potenzialentfaltung, Schenken und Danken, Kreislauf des Lebens, Geldsystem',
|
||||
)
|
||||
.required(),
|
||||
|
||||
META_KEYWORDS_EN: Joi.string()
|
||||
.description('Meta keywords in English.')
|
||||
.default(
|
||||
'Basic Income, Currency, Gratitude, Gift Economy, Natural Economy of Life, Economy, Ecology, Potential Development, Giving and Thanking, Cycle of Life, Monetary System',
|
||||
)
|
||||
.required(),
|
||||
|
||||
META_AUTHOR: Joi.string()
|
||||
.description('The author for the meta tags.')
|
||||
.default('Bernd Hückstädt - Gradido-Akademie')
|
||||
.required(),
|
||||
})
|
||||
@ -292,7 +292,7 @@ const getCommunityStatistics = async () => {
|
||||
}
|
||||
|
||||
const admin = () => {
|
||||
window.location.assign(CONFIG.ADMIN_AUTH_URL.replace('{token}', store.state.token))
|
||||
window.location.assign(CONFIG.ADMIN_AUTH_URL + store.state.token)
|
||||
store.dispatch('logout') // logout without redirect
|
||||
}
|
||||
|
||||
|
||||
@ -7,6 +7,8 @@ import Icons from 'unplugin-icons/vite'
|
||||
import IconsResolve from 'unplugin-icons/resolver'
|
||||
import EnvironmentPlugin from 'vite-plugin-environment'
|
||||
import { createHtmlPlugin } from 'vite-plugin-html'
|
||||
import schema from './src/config/schema'
|
||||
import { validate, browserUrls } from 'gradido-config/build/src/index.js'
|
||||
|
||||
import { BootstrapVueNextResolver } from 'bootstrap-vue-next'
|
||||
import dotenv from 'dotenv'
|
||||
@ -16,100 +18,120 @@ dotenv.config() // load env vars from .env
|
||||
const CONFIG = require('./src/config')
|
||||
|
||||
// https://vitejs.dev/config/
|
||||
export default defineConfig({
|
||||
server: {
|
||||
host: CONFIG.FRONTEND_MODULE_HOST, // '0.0.0.0',
|
||||
port: CONFIG.FRONTEND_MODULE_PORT, // 3000,
|
||||
},
|
||||
resolve: {
|
||||
alias: {
|
||||
'@': path.resolve(__dirname, './src'),
|
||||
assets: path.join(__dirname, 'src/assets'),
|
||||
'@vee-validate/i18n/dist/locale/en.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/en.json',
|
||||
'@vee-validate/i18n/dist/locale/de.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/de.json',
|
||||
'@vee-validate/i18n/dist/locale/es.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/es.json',
|
||||
'@vee-validate/i18n/dist/locale/fr.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/fr.json',
|
||||
'@vee-validate/i18n/dist/locale/nl.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/nl.json',
|
||||
'@vee-validate/i18n/dist/locale/tr.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/tr.json',
|
||||
export default defineConfig(({ command }) => {
|
||||
if (command === 'serve') {
|
||||
CONFIG.FRONTEND_HOSTING = 'nodejs'
|
||||
} else {
|
||||
CONFIG.FRONTEND_HOSTING = 'nginx'
|
||||
}
|
||||
// Check config
|
||||
validate(schema, CONFIG)
|
||||
// make sure that all urls used in browser have the same protocol to prevent mixed content errors
|
||||
validate(browserUrls, [
|
||||
CONFIG.ADMIN_AUTH_URL,
|
||||
CONFIG.COMMUNITY_URL,
|
||||
CONFIG.COMMUNITY_REGISTER_URL,
|
||||
CONFIG.GRAPHQL_URI,
|
||||
CONFIG.FRONTEND_MODULE_URL,
|
||||
])
|
||||
|
||||
return {
|
||||
server: {
|
||||
host: CONFIG.FRONTEND_MODULE_HOST, // '0.0.0.0',
|
||||
port: CONFIG.FRONTEND_MODULE_PORT, // 3000,
|
||||
https: CONFIG.FRONTEND_MODULE_PROTOCOL === 'https',
|
||||
fs: {
|
||||
strict: true,
|
||||
},
|
||||
esbuild: {
|
||||
minify: CONFIG.PRODUCTION === true,
|
||||
},
|
||||
},
|
||||
extensions: ['.mjs', '.js', '.ts', '.jsx', '.tsx', '.json', '.vue'],
|
||||
},
|
||||
plugins: [
|
||||
vue(),
|
||||
createHtmlPlugin({
|
||||
minify: true,
|
||||
inject: {
|
||||
data: {
|
||||
VITE_META_TITLE_DE: CONFIG.META_TITLE_DE,
|
||||
VITE_META_TITLE_EN: CONFIG.META_TITLE_EN,
|
||||
VITE_META_DESCRIPTION_DE: CONFIG.META_DESCRIPTION_DE,
|
||||
VITE_META_DESCRIPTION_EN: CONFIG.META_DESCRIPTION_EN,
|
||||
VITE_META_KEYWORDS_DE: CONFIG.META_KEYWORDS_DE,
|
||||
VITE_META_KEYWORDS_EN: CONFIG.META_KEYWORDS_EN,
|
||||
VITE_META_AUTHOR: CONFIG.META_AUTHOR,
|
||||
VITE_META_URL: CONFIG.META_URL,
|
||||
resolve: {
|
||||
alias: {
|
||||
'@': path.resolve(__dirname, './src'),
|
||||
assets: path.join(__dirname, 'src/assets'),
|
||||
'@vee-validate/i18n/dist/locale/en.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/en.json',
|
||||
'@vee-validate/i18n/dist/locale/de.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/de.json',
|
||||
'@vee-validate/i18n/dist/locale/es.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/es.json',
|
||||
'@vee-validate/i18n/dist/locale/fr.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/fr.json',
|
||||
'@vee-validate/i18n/dist/locale/nl.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/nl.json',
|
||||
'@vee-validate/i18n/dist/locale/tr.json':
|
||||
'/node_modules/@vee-validate/i18n/dist/locale/tr.json',
|
||||
},
|
||||
extensions: ['.mjs', '.js', '.ts', '.jsx', '.tsx', '.json', '.vue'],
|
||||
},
|
||||
plugins: [
|
||||
vue(),
|
||||
createHtmlPlugin({
|
||||
minify: CONFIG.PRODUCTION === true,
|
||||
inject: {
|
||||
data: {
|
||||
VITE_META_TITLE_DE: CONFIG.META_TITLE_DE,
|
||||
VITE_META_TITLE_EN: CONFIG.META_TITLE_EN,
|
||||
VITE_META_DESCRIPTION_DE: CONFIG.META_DESCRIPTION_DE,
|
||||
VITE_META_DESCRIPTION_EN: CONFIG.META_DESCRIPTION_EN,
|
||||
VITE_META_KEYWORDS_DE: CONFIG.META_KEYWORDS_DE,
|
||||
VITE_META_KEYWORDS_EN: CONFIG.META_KEYWORDS_EN,
|
||||
VITE_META_AUTHOR: CONFIG.META_AUTHOR,
|
||||
VITE_META_URL: CONFIG.META_URL,
|
||||
},
|
||||
},
|
||||
}),
|
||||
Components({
|
||||
resolvers: [BootstrapVueNextResolver(), IconsResolve()],
|
||||
dts: true,
|
||||
}),
|
||||
Icons({
|
||||
compiler: 'vue3',
|
||||
autoInstall: true,
|
||||
}),
|
||||
EnvironmentPlugin({
|
||||
GMS_ACTIVE: null,
|
||||
HUMHUB_ACTIVE: null,
|
||||
DEFAULT_PUBLISHER_ID: null,
|
||||
PORT: null,
|
||||
COMMUNITY_HOST: null,
|
||||
URL_PROTOCOL: null,
|
||||
COMMUNITY_URL: CONFIG.COMMUNITY_URL,
|
||||
GRAPHQL_PATH: null,
|
||||
GRAPHQL_URI: CONFIG.GRAPHQL_URI, // null,
|
||||
ADMIN_AUTH_PATH: CONFIG.ADMIN_AUTH_PATH ?? null, // it is the only env without exported default
|
||||
ADMIN_AUTH_URL: CONFIG.ADMIN_AUTH_URL, // null,
|
||||
COMMUNITY_NAME: null,
|
||||
COMMUNITY_REGISTER_PATH: null,
|
||||
COMMUNITY_REGISTER_URL: null,
|
||||
COMMUNITY_DESCRIPTION: null,
|
||||
COMMUNITY_SUPPORT_MAIL: null,
|
||||
META_URL: null,
|
||||
META_TITLE_DE: null,
|
||||
META_TITLE_EN: null,
|
||||
META_DESCRIPTION_DE: null,
|
||||
META_DESCRIPTION_EN: null,
|
||||
META_KEYWORDS_DE: null,
|
||||
META_KEYWORDS_EN: null,
|
||||
META_AUTHOR: null,
|
||||
}),
|
||||
commonjs(),
|
||||
],
|
||||
css: {
|
||||
extract: CONFIG.PRODUCTION === true,
|
||||
preprocessorOptions: {
|
||||
scss: {
|
||||
additionalData: `@use "@/assets/scss/custom/gradido-custom/color" as *;`,
|
||||
},
|
||||
},
|
||||
}),
|
||||
Components({
|
||||
resolvers: [BootstrapVueNextResolver(), IconsResolve()],
|
||||
dts: true,
|
||||
}),
|
||||
Icons({
|
||||
compiler: 'vue3',
|
||||
autoInstall: true,
|
||||
}),
|
||||
EnvironmentPlugin({
|
||||
BUILD_COMMIT: null,
|
||||
GMS_ACTIVE: null,
|
||||
HUMHUB_ACTIVE: null,
|
||||
NODE_ENV: null,
|
||||
DEFAULT_PUBLISHER_ID: null,
|
||||
PORT: null,
|
||||
COMMUNITY_HOST: null,
|
||||
URL_PROTOCOL: null,
|
||||
COMMUNITY_URL: null,
|
||||
GRAPHQL_PATH: null,
|
||||
GRAPHQL_URI: CONFIG.GRAPHQL_URI, // null,
|
||||
ADMIN_AUTH_PATH: CONFIG.ADMIN_AUTH_PATH ?? null, // it is the only env without exported default
|
||||
ADMIN_AUTH_URL: CONFIG.ADMIN_AUTH_URL, // null,
|
||||
COMMUNITY_NAME: null,
|
||||
COMMUNITY_REGISTER_PATH: null,
|
||||
COMMUNITY_REGISTER_URL: null,
|
||||
COMMUNITY_DESCRIPTION: null,
|
||||
COMMUNITY_SUPPORT_MAIL: null,
|
||||
META_URL: null,
|
||||
META_TITLE_DE: null,
|
||||
META_TITLE_EN: null,
|
||||
META_DESCRIPTION_DE: null,
|
||||
META_DESCRIPTION_EN: null,
|
||||
META_KEYWORDS_DE: null,
|
||||
META_KEYWORDS_EN: null,
|
||||
META_AUTHOR: null,
|
||||
CONFIG_VERSION: null,
|
||||
}),
|
||||
commonjs(),
|
||||
],
|
||||
css: {
|
||||
extract: true,
|
||||
preprocessorOptions: {
|
||||
scss: {
|
||||
additionalData: `@use "@/assets/scss/custom/gradido-custom/color" as *;`,
|
||||
},
|
||||
},
|
||||
},
|
||||
build: {
|
||||
outDir: path.resolve(__dirname, './build'),
|
||||
chunkSizeWarningLimit: 1600,
|
||||
},
|
||||
optimizeDeps: {
|
||||
include: ['vue', 'vue-router', 'bootstrap'],
|
||||
exclude: ['@popperjs/core'],
|
||||
},
|
||||
build: {
|
||||
outDir: path.resolve(__dirname, './build'),
|
||||
chunkSizeWarningLimit: 1600,
|
||||
minify: 'esbuild',
|
||||
sourcemap: false,
|
||||
},
|
||||
}
|
||||
})
|
||||
|
||||
@ -1073,6 +1073,18 @@
|
||||
resolved "https://registry.yarnpkg.com/@graphql-typed-document-node/core/-/core-3.2.0.tgz#5f3d96ec6b2354ad6d8a28bf216a1d97b5426861"
|
||||
integrity sha512-mB9oAsNCm9aM3/SOv4YtBMqZbYj10R7dkq8byBqxGY/ncFwhf2oQzMV+LCRlWoDSEBJ3COiR1yeDvMtsoOsuFQ==
|
||||
|
||||
"@hapi/hoek@^9.0.0", "@hapi/hoek@^9.3.0":
|
||||
version "9.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/hoek/-/hoek-9.3.0.tgz#8368869dcb735be2e7f5cb7647de78e167a251fb"
|
||||
integrity sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==
|
||||
|
||||
"@hapi/topo@^5.1.0":
|
||||
version "5.1.0"
|
||||
resolved "https://registry.yarnpkg.com/@hapi/topo/-/topo-5.1.0.tgz#dc448e332c6c6e37a4dc02fd84ba8d44b9afb012"
|
||||
integrity sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@humanwhocodes/config-array@^0.11.14":
|
||||
version "0.11.14"
|
||||
resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.14.tgz#d78e481a039f7566ecc9660b4ea7fe6b1fec442b"
|
||||
@ -1522,6 +1534,23 @@
|
||||
resolved "https://registry.yarnpkg.com/@rtsao/scc/-/scc-1.1.0.tgz#927dd2fae9bc3361403ac2c7a00c32ddce9ad7e8"
|
||||
integrity sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==
|
||||
|
||||
"@sideway/address@^4.1.5":
|
||||
version "4.1.5"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/address/-/address-4.1.5.tgz#4bc149a0076623ced99ca8208ba780d65a99b9d5"
|
||||
integrity sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.0.0"
|
||||
|
||||
"@sideway/formula@^3.0.1":
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/formula/-/formula-3.0.1.tgz#80fcbcbaf7ce031e0ef2dd29b1bfc7c3f583611f"
|
||||
integrity sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==
|
||||
|
||||
"@sideway/pinpoint@^2.0.0":
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/@sideway/pinpoint/-/pinpoint-2.0.0.tgz#cff8ffadc372ad29fd3f78277aeb29e632cc70df"
|
||||
integrity sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==
|
||||
|
||||
"@sindresorhus/merge-streams@^2.1.0":
|
||||
version "2.3.0"
|
||||
resolved "https://registry.yarnpkg.com/@sindresorhus/merge-streams/-/merge-streams-2.3.0.tgz#719df7fb41766bc143369eaa0dd56d8dc87c9958"
|
||||
@ -4173,6 +4202,11 @@ graceful-fs@^4.1.6, graceful-fs@^4.2.0:
|
||||
resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3"
|
||||
integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==
|
||||
|
||||
gradido-config@../config:
|
||||
version "1.0.0"
|
||||
dependencies:
|
||||
joi "^17.13.3"
|
||||
|
||||
graphemer@^1.4.0:
|
||||
version "1.4.0"
|
||||
resolved "https://registry.yarnpkg.com/graphemer/-/graphemer-1.4.0.tgz#fb2f1d55e0e3a1849aeffc90c4fa0dd53a0e66c6"
|
||||
@ -4739,6 +4773,17 @@ jiti@^2.3.0, jiti@^2.4.0, jiti@^2.4.1:
|
||||
resolved "https://registry.yarnpkg.com/jiti/-/jiti-2.4.2.tgz#d19b7732ebb6116b06e2038da74a55366faef560"
|
||||
integrity sha512-rg9zJN+G4n2nfJl5MW3BMygZX56zKPNVEYYqq7adpmMh4Jn2QNEwhvQlFy6jPVdcod7txZtKHWnyZiA3a0zP7A==
|
||||
|
||||
joi@^17.13.3:
|
||||
version "17.13.3"
|
||||
resolved "https://registry.yarnpkg.com/joi/-/joi-17.13.3.tgz#0f5cc1169c999b30d344366d384b12d92558bcec"
|
||||
integrity sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==
|
||||
dependencies:
|
||||
"@hapi/hoek" "^9.3.0"
|
||||
"@hapi/topo" "^5.1.0"
|
||||
"@sideway/address" "^4.1.5"
|
||||
"@sideway/formula" "^3.0.1"
|
||||
"@sideway/pinpoint" "^2.0.0"
|
||||
|
||||
js-beautify@^1.14.9:
|
||||
version "1.15.1"
|
||||
resolved "https://registry.yarnpkg.com/js-beautify/-/js-beautify-1.15.1.tgz#4695afb508c324e1084ee0b952a102023fc65b64"
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user