Dynamic runtime config

This commit is contained in:
Travis Shivers 2020-07-21 16:28:48 -05:00
parent 3f8c68cef6
commit 091eee0363
No known key found for this signature in database
GPG Key ID: EE4CC2891B8FCD33
17 changed files with 99 additions and 61 deletions

2
.gitignore vendored
View File

@ -18,4 +18,4 @@ db.sqlite
# Optional npm cache directory
.npm
settings.json
public/config.json

View File

@ -5,14 +5,13 @@ COPY package*.json ./
RUN npm install
COPY . .
ARG SERVERS='{"name":"Local Server","location":"Local","url":"/","image":"synclounge-white.png"}'
RUN npm run build
# production environment
FROM node:current-alpine as production-stage
WORKDIR /app
COPY --from=build-stage /app/dist .
RUN npm install -g syncloungesocket@2.0.5
ARG BASE_URL
ENTRYPOINT ["syncloungesocket", "--static_path", "."]
COPY config config
COPY --from=build-stage /app/dist dist
RUN npm install -g syncloungesocket@2.0.5 nconf fs
ENTRYPOINT ["./docker-entrypoint.sh"]

6
config/clisaveconfig.js Executable file
View File

@ -0,0 +1,6 @@
#!/usr/bin/env node
const saveConfig = require('./index');
const config = saveConfig('dist/config.json');
console.log(config);

View File

@ -1,6 +1,4 @@
const defaults = {
base_url: '/',
servers: [
{
name: 'SyncLounge AU1',

View File

@ -1,33 +1,47 @@
const nconf = require('nconf');
const fs = require('fs');
const defaults = require('./defaults');
nconf
.argv({
separator: '__',
parseValues: true,
})
.env({
separator: '__',
lowerCase: true,
parseValues: true,
whitelist: Object.keys(defaults).concat([
'autojoin__server',
'autojoin__room',
'autojoin__password',
'authentication__mechanism',
'authentication__type',
'authentication__authorized',
// Parses, saves, and returns the config
const saveConfig = (file) => {
nconf
.argv({
separator: '__',
parseValues: true,
})
.env({
separator: '__',
lowerCase: true,
parseValues: true,
whitelist: Object.keys(defaults).concat([
'autojoin__server',
'autojoin__room',
'autojoin__password',
'authentication__mechanism',
'authentication__type',
'authentication__authorized',
'custom_server__name',
'custom_server__location',
'custom_server__url',
'custom_server__image',
'custom_server__name',
'custom_server__location',
'custom_server__url',
'custom_server__image',
'default_slplayer_quality',
]),
})
.file({ file: 'settings.json' });
'default_slplayer_quality',
]),
})
.file({ file });
nconf.defaults(defaults);
nconf.defaults(defaults);
module.exports = nconf;
// Filter out the weird stuff
const {
type, $0: firstArg, _: command, modern, ...config
} = nconf.get();
fs.writeFileSync(file, JSON.stringify(config));
return config;
};
module.exports = saveConfig;

4
docker-entrypoint.sh Executable file
View File

@ -0,0 +1,4 @@
#!/bin/sh
echo "Testtt"
./config/clisaveconfig.js
exec syncloungesocket --static_path dist

10
settings.json Normal file
View File

@ -0,0 +1,10 @@
{
"servers": [
{
"name": "Custom Server 1",
"location": "Custom Location",
"url": "http://vps.conicaw.me:9999",
"image": "https://mycustomserver.com/logo.png"
}
]
}

View File

@ -1,7 +1,7 @@
<template>
<v-app>
<leftsidebar />
<rightsidebar />
<rightsidebar v-if="IS_IN_ROOM" />
<v-app-bar
app
@ -108,7 +108,8 @@
fluid
>
<v-container
v-if="!IS_DONE_FETCHING_DEVICES && $route.matched.some((record) => record.meta.protected)"
v-if="!GET_CONFIG
|| !IS_DONE_FETCHING_DEVICES && $route.matched.some((record) => record.meta.protected)"
fill-height
>
<v-row
@ -292,15 +293,8 @@ export default {
},
},
mounted() {
fscreen.addEventListener('fullscreenchange', () => {
const isFullscreen = fscreen.fullscreenElement !== null;
this.appIsFullscreen = isFullscreen;
document.body.classList.toggle('is-fullscreen', isFullscreen);
});
},
async created() {
await this.FETCH_CONFIG();
if (this.IS_AUTHENTICATED) {
// Kick off a bunch of requests that we need for later
try {
@ -319,12 +313,21 @@ export default {
}
},
mounted() {
fscreen.addEventListener('fullscreenchange', () => {
const isFullscreen = fscreen.fullscreenElement !== null;
this.appIsFullscreen = isFullscreen;
document.body.classList.toggle('is-fullscreen', isFullscreen);
});
},
methods: {
...mapActions([
'SET_LEFT_SIDEBAR_OPEN',
'SET_RIGHT_SIDEBAR_OPEN',
'TOGGLE_RIGHT_SIDEBAR_OPEN',
'DISPLAY_NOTIFICATION',
'FETCH_CONFIG',
]),
...mapActions('plex', [

View File

@ -1,6 +1,5 @@
<template>
<v-navigation-drawer
v-if="IS_IN_ROOM"
:value="isRightSidebarOpen"
style="z-index: 6"
app
@ -268,7 +267,6 @@ export default {
'GET_HOST_USER',
'GET_HOST_ID',
'AM_I_HOST',
'IS_IN_ROOM',
'GET_SOCKET_ID',
]),

View File

@ -13,7 +13,8 @@ Vue.use(VueClipboard);
Vue.config.productionTip = false;
router.beforeEach((to, from, next) => {
if (!store.getters['plex/IS_AUTHENTICATED'] && to.matched.some((record) => record.meta.requiresAuth)) {
if (store.getters.GET_CONFIG && !store.getters['plex/IS_AUTHENTICATED']
&& to.matched.some((record) => record.meta.requiresAuth)) {
if (to.matched.some((record) => record.meta.redirectAfterAuth)) {
next({
name: 'Signin',

View File

@ -1,3 +1,5 @@
import { fetchJson } from '@/utils/fetchutils';
export default {
SET_LEFT_SIDEBAR_OPEN: ({ commit }, open) => {
commit('SET_LEFT_SIDEBAR_OPEN', open);
@ -15,4 +17,9 @@ export default {
commit('SET_SNACKBAR_MESSAGE', message);
commit('SET_SNACKBAR_OPEN', true);
},
FETCH_CONFIG: async ({ commit }) => {
const config = await fetchJson('config.json');
commit('SET_CONFIGURATION', config);
},
};

View File

@ -3,9 +3,6 @@ export default {
GET_UP_NEXT_TRIGGERED: (state) => state.upNextTriggered,
GET_UP_NEXT_POST_PLAY_DATA: (state) => state.upNextPostPlayData,
GET_CONFIG: (state) => state.configuration,
GET_AUTHENTICATION: (state) => state.configuration.authentication,
GET_CONFIGURATION_FETCHED: (state) => state.configurationFectched,
GET_CONFIGURATION_FETCHED_ERROR: (state) => state.configurationFetchedError,
GET_ACTIVE_METADATA: (state) => state.activeMetadata,
GET_SNACKBAR_MESSAGE: (state) => state.snackbarMessage,
GET_SNACKBAR_OPEN: (state) => state.snackbarOpen,

View File

@ -80,15 +80,14 @@ export default {
|| getters.IS_PLEX_USER_AUTHORIZED,
IS_PLEX_USER_AUTHORIZED: (state, getters, rootState, rootGetters) => rootGetters
.GET_AUTHENTICATION.type
&& rootGetters.GET_AUTHENTICATION.type.includes('user')
.GET_CONFIG?.authentication?.type.includes('user')
&& intersection(
[getters.GET_PLEX_USER.username, getters.GET_PLEX_USER.email],
rootGetters.GET_AUTHENTICATION.authorized,
).length > 0,
IS_AUTHENTICATION_TYPE_NONE: (state, getters, rootState, rootGetters) => rootGetters
.GET_AUTHENTICATION.mechanism === 'none',
.GET_CONFIG?.authentication.mechanism === 'none',
GET_PLEX_AUTH_TOKEN: (state) => state.plexAuthToken,
GET_CLIENT_IDENTIFIER: (state) => state.clientIdentifier,

View File

@ -24,10 +24,9 @@ export default {
GET_LAST_SERVER: (state, getters) => getters.GET_PLEX_SERVER(getters.GET_LAST_SERVER_ID),
DOES_USER_HAVE_AUTHORIZED_SERVER: (state, getters, rootState, rootGetters) => rootGetters
.GET_AUTHENTICATION.type
&& rootGetters.GET_AUTHENTICATION.type.includes('server')
.GET_CONFIG?.authentication?.type.includes('server')
&& intersection(
getters.GET_PLEX_SERVER_IDS, rootGetters.GET_AUTHENTICATION.authorized,
getters.GET_PLEX_SERVER_IDS, rootGetters.GET_CONFIG.authentication.authorized,
).length > 0,
GET_MEDIA_IMAGE_URL: (state, getters, rootState, rootGetters) => ({

View File

@ -30,4 +30,8 @@ export default {
SET_NAVIGATE_TO_PLAYER: (state, navigate) => {
state.navigateToPlayer = navigate;
},
SET_CONFIGURATION: (state, configuration) => {
state.configuration = configuration;
},
};

View File

@ -1,6 +1,6 @@
const state = () => ({
background: null,
configuration: JSON.parse(process.env.VUE_APP_CONFIGURATION),
configuration: null,
isLeftSidebarOpen: false,
isRightSidebarOpen: false,

View File

@ -1,11 +1,11 @@
const path = require('path');
const git = require('git-rev-sync');
const config = require('./config');
const saveConfig = require('./config');
console.log(config.get());
const config = saveConfig('public/config.json');
console.log(config);
process.env.VUE_APP_CONFIGURATION = JSON.stringify(config.get());
process.env.VUE_APP_VERSION = require('./package.json').version;
try {
@ -18,7 +18,6 @@ try {
}
module.exports = {
publicPath: config.get('base_url'),
lintOnSave: process.env.NODE_ENV !== 'production',
productionSourceMap: false,
transpileDependencies: ['vuetify'],