Added TTS integration and letsencrypt to make chat integration work

This commit is contained in:
GERBrowny 2022-08-16 17:46:21 +02:00
parent 9126f1518b
commit 1f87d1d027
12 changed files with 192 additions and 13 deletions

View File

@ -19,9 +19,16 @@ RUN pip3 install irc
RUN pip3 install obs-websocket-py RUN pip3 install obs-websocket-py
RUN pip3 install lxml RUN pip3 install lxml
RUN apt-get install -y supervisor coreutils RUN apt-get install -y supervisor coreutils dehydrated dos2unix
COPY ./supervisord/*.conf /etc/supervisor/conf.d/ COPY ./supervisord/*.conf /etc/supervisor/conf.d/
COPY ./nginx/nginx.conf /etc/nginx/nginx.conf COPY ./nginx/nginx.conf /etc/nginx/nginx.conf
COPY ./nginx/nginx_tmp.conf /etc/nginx/nginx_tmp.conf
COPY ./nginx/dhparams.pem /etc/nginx/dhparams.pem
COPY ./nginx/snakeoil.pem /etc/nginx/snakeoil.pem
COPY ./nginx/snakeoil.pem /etc/nginx/snakeoil.key
COPY ./nginx/domains.txt /etc/dehydrated/domains.txt
COPY ./nginx/dehydrated.conf /etc/dehydrated/config
RUN /usr/bin/dos2unix /etc/dehydrated/config
RUN mkdir -p /var/www/html/ RUN mkdir -p /var/www/html/
COPY ./www/* /var/www/html/ COPY ./www/* /var/www/html/

View File

@ -0,0 +1,15 @@
#############################################################
# This is the main config file for dehydrated #
# #
# This is the default configuration for the Debian package. #
# To see a more comprehensive example, see #
# /usr/share/doc/dehydrated/examples/config #
# #
# For details please read: #
# /usr/share/doc/dehydrated/README.Debian #
#############################################################
CONFIG_D=/etc/dehydrated/conf.d
BASEDIR=/var/lib/dehydrated
WELLKNOWN="/var/www/html/.well-known/acme-challenge"
DOMAINS_TXT="/etc/dehydrated/domains.txt"

8
build/nginx/dhparams.pem Normal file
View File

@ -0,0 +1,8 @@
-----BEGIN DH PARAMETERS-----
MIIBCAKCAQEA0d6RvH0nXLn1cU5A7TZfQKQE4aTJshF4ArHCn3KTokz/5U8xj6Bf
pnnsTFT1tLtBdXc/yPLgxaDwvDHC1EPPobqY+G3jdug30niZjZ9jbzY4PGr2pe1I
tu8Qi/rdW0g/QybEbVVvmEBmmabAgKtfaBYrfT13vXDTnm6ofh3YKHTPJzmBRHpU
6wDMS3bVb4eRqeXkbYIAwl0qfpj5ZtlKTWqU76leIjTwYgb84gsYiBKGiAvj52Yk
QYyxpBj2tZvuc9e0mt4R1X1gwUvoEjWCRSxhaDWFjNC4AQzm8O0sFfdR/HUmOe46
/DYINrlQtwMAnUseV9e+Of8Hu7HE0bjOcwIBAg==
-----END DH PARAMETERS-----

1
build/nginx/domains.txt Normal file
View File

@ -0,0 +1 @@
${LETSENCRYPT_DOMAIN}

View File

@ -17,10 +17,23 @@ http {
server { server {
listen 80; listen 80;
listen 443 ssl;
access_log /nginx_access.log; access_log /nginx_access.log;
error_log /nginx_error.log info; error_log /nginx_error.log info;
ssl_certificate /var/lib/dehydrated/certs/${LETSENCRYPT_DOMAIN}fullchain.pem;
ssl_certificate_key /var/lib/dehydrated/certs/${LETSENCRYPT_DOMAIN}/privkey.pem;
ssl_session_timeout 1d;
ssl_session_cache shared:MozSSL:10m;
ssl_session_tickets off;
ssl_dhparam /etc/nginx/dhparams.pem;
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384;
ssl_prefer_server_ciphers off;
gzip off;
location /stat { location /stat {
rtmp_stat all; rtmp_stat all;
rtmp_stat_stylesheet stat.xsl; rtmp_stat_stylesheet stat.xsl;
@ -36,17 +49,52 @@ http {
satisfy any; satisfy any;
} }
location /tts {
proxy_pass http://host.docker.internal:3000/;
proxy_redirect off;
proxy_buffering off;
}
location /bootstrap.min.css {
proxy_pass http://host.docker.internal:3000/bootstrap.min.css;
proxy_redirect off;
proxy_buffering off;
}
location /jquery.js {
proxy_pass http://host.docker.internal:3000/jquery.js;
proxy_redirect off;
proxy_buffering off;
}
location /tts.js {
proxy_pass http://host.docker.internal:3000/tts.js;
proxy_redirect off;
proxy_buffering off;
}
location /tts_queue {
proxy_pass http://host.docker.internal:3000/tts_queue;
proxy_redirect off;
proxy_buffering off;
}
location /tts_done {
proxy_pass http://host.docker.internal:3000/tts_done;
proxy_redirect off;
proxy_buffering off;
}
location /token {
proxy_pass http://host.docker.internal:3000/token;
proxy_redirect off;
proxy_buffering off;
}
location /favicon.ico {
proxy_pass http://host.docker.internal:3000/favicon.ico;
proxy_redirect off;
proxy_buffering off;
}
location / { location / {
root /var/www/html; root /var/www/html;
try_files $uri $uri/index.py; try_files $uri $uri/index.py;
} }
location /tts {
proxy_pass http://localhost:3000;
proxy_redirect off;
proxy_buffering off;
}
error_page 500 502 503 504 /50x.html; error_page 500 502 503 504 /50x.html;
location = /50x.html { location = /50x.html {
root /var/www/html; root /var/www/html;

View File

@ -0,0 +1,26 @@
user www-data;
worker_processes 1;
events {
worker_connections 1024;
}
http {
server_tokens off;
include mime.types;
default_type application/octet-stream;
sendfile on;
keepalive_timeout 65;
server {
listen 80;
access_log /nginx_access.log;
error_log /nginx_error.log info;
location / {
root /var/www/html/;
}
}
}

28
build/nginx/snakeoil.key Normal file
View File

@ -0,0 +1,28 @@
-----BEGIN PRIVATE KEY-----
MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQDT4/FqIz+sra/T
T4OGQZVUKhFgR9pEzugQCPymBluzj5HJLLY/6p3BzkXlVa5uZ8KjGAMdJpp5K3bz
EyDhsNRq518T34fELvR2KTxn96gPmpYcWffA2fkwbeqN1x5q+EJJFwtyPW7xmM6C
UgPNUhvqxGo8epQMk2KzpkVeDQZpnbDIaHfZ3f2PketnjldHMp0ckUf6+F3QFkWk
rnbYc8agjjOV2b3BKRf8p3rBKT2fHlLxLfsIxKYW9ue0KJnkuQNBGhiJi09fEcQs
dI39jR66DzX17/mTaDu1msqhBJbnVGEMUuQm1kRamLowFCp/En0pNrQIpP0YHNwP
cUUl19N9AgMBAAECggEAPWaNO3NxbSl7jOE6vLneeuAh3uOTZWMLrjHcfIPVKOhO
l5xER6tGAbYzXOyCOm4I4dgAdv8LvlcRBgkh+ySRuVTIoWqh3gC5SFBUt8/1PGhQ
XXDYsWK4qgb/9BBFOTwtgR6Ta4xPzOS52tvHTEUh39sA6fufUTGYZXSmH0Xo+Mt5
QPu3JHhqD+el7hQ59OUO2CQxYbM8d+oEG78+57wRDhDDpmKJ/aSjhn+FcxkoNt3z
EW0EaybNBbPiq5g6nWmBVA6YtXHOCMvBPQVh+uex8SFnuSWDY8beDp+1xOn0Qqje
c1UWodBBrfVMrilvekGdT1bb98VMGNwxbCaH2C+DBQKBgQDtLlnhpHUFluc+Qhup
Ux+kpMBHmXFSwaEWe7pvNnhRm2ipIywlTrGcbWFSXs2taP8tAa3idllQ9laBr2ID
tIzdYinWfGzNBiCDmz5yAVbSHWtS86iqDwTjzS6mN+qiKmLVNBkw59F3le/4HHUZ
KqfsaRel44IM6dOKp7XWI3AcUwKBgQDks+Kc8jfFzsZJJ6EvbYeCYUOFZ1smWgHL
Za0aNWMfJnjIuU+l2AfTMRaS5TbJFWBaJvuyZAgJNuImNgUQYFk+BQHaR/dbSZ5P
Eyae5lac8SReBUSYCTeaUUzuOcpCbczhBcD5IM+44dgGK/b9VFj+RtNLCh5slhQ6
y2QVNYDW7wKBgQCRvR+BpRo6+wTQnrJ8kxUoiAuWc1TM8ynWtORUHfZEvufKtlAU
BIzif9uDT7m2SoQx1YxRUUOEmjmBqpDhkfnUttLads4sFQ25kJUIXIZKycT+zbXf
+SaaC6QUgttsFftw4nhwMqHlh35SyLmzYyCYBeOADZIF+VABLRhwoonq/QKBgB1R
+pGIdCIF+mHSlNWRwzex5Igr0gG+tFAxPtoHUifiNMX3DAEFCyvGNVCr1jQ9a1bj
fI1IScd0o9WmQ0vwLkDHP4+OfmXTsFoO6HqiqSQBvlnXbw3W0KwWFDjOa+HMVeHb
bPwDet4HBjz0Ufv0XlxrFBegunnNW9aV0MTvUQ89AoGAKTsgvpChwne5n1KEU7T0
HYzRlwqtQiHfeyFoGW2uYh8Wuq4bJ9CDOUWGOuRenlct8r+e3Brnh+n1NsltuE4Z
W385wYAzQOWga6kj3hEjOcpcNayVnhAqKS54utV3d41nKmVchxJKPQq8pjuKBbYa
3SiDzZJMQ2X/l0gpsQ+7umY=
-----END PRIVATE KEY-----

22
build/nginx/snakeoil.pem Normal file
View File

@ -0,0 +1,22 @@
-----BEGIN CERTIFICATE-----
MIIDkzCCAnugAwIBAgIUJPU3Of7K0OuQ86sWD8DtKLJjkPcwDQYJKoZIhvcNAQEL
BQAwWTELMAkGA1UEBhMCQVUxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoM
GEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZDESMBAGA1UEAwwJbG9jYWxob3N0MB4X
DTIyMDgxNjEzNTYyOVoXDTMyMDgxMzEzNTYyOVowWTELMAkGA1UEBhMCQVUxEzAR
BgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoMGEludGVybmV0IFdpZGdpdHMgUHR5
IEx0ZDESMBAGA1UEAwwJbG9jYWxob3N0MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A
MIIBCgKCAQEA0+PxaiM/rK2v00+DhkGVVCoRYEfaRM7oEAj8pgZbs4+RySy2P+qd
wc5F5VWubmfCoxgDHSaaeSt28xMg4bDUaudfE9+HxC70dik8Z/eoD5qWHFn3wNn5
MG3qjdceavhCSRcLcj1u8ZjOglIDzVIb6sRqPHqUDJNis6ZFXg0GaZ2wyGh32d39
j5HrZ45XRzKdHJFH+vhd0BZFpK522HPGoI4zldm9wSkX/Kd6wSk9nx5S8S37CMSm
FvbntCiZ5LkDQRoYiYtPXxHELHSN/Y0eug819e/5k2g7tZrKoQSW51RhDFLkJtZE
Wpi6MBQqfxJ9KTa0CKT9GBzcD3FFJdfTfQIDAQABo1MwUTAdBgNVHQ4EFgQU30v/
MYsCsZn6DA1DcHdVlL/Lt6gwHwYDVR0jBBgwFoAU30v/MYsCsZn6DA1DcHdVlL/L
t6gwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0BAQsFAAOCAQEAKh0tmqZAiiRS
N9ZU7dnIxQaxcj/7FDQyK10HFOXZ0Bo7MdiaAhNPnpomPWbtFf97OCy+kgdkM4gB
aXyhjxKlMcIjWfy2h3KgWeXKsu8eg0tec6+ACNlunmyllXvnCBqT2tIrJJ1bG9ps
cHYWnqnIsOYcn2/r30i4Hw16eXPf4SRr6zbp8c0vPx1t1NjHzbtyS0klaRnYNMNA
ucO8FtPBOSQp4BSVwJstFJjIrVPt90kydPgk/JVLMnWO+j6q3ZLSHDGKxRd7QPUM
rkqdaTf8WkOY5YbLYqlJMUJEw1it0/vLdxWjlhz1ESBu+x+wz2gTdTG1UL7ijG1p
KIXg4HY9Ag==
-----END CERTIFICATE-----

View File

@ -61,7 +61,8 @@ vars = [
'DEBUG', 'DEBUG',
'EXTDATA', 'EXTDATA',
'TTS', 'TTS',
'TTS_URL' 'TTS_URL',
'TWITCH_CHAT_PARENT'
] ]
def get_config(): def get_config():
@ -90,6 +91,8 @@ def get_config():
if not conf['TTS_URL']: if not conf['TTS_URL']:
conf['TTS_URL'] = "http://localhost/tts" conf['TTS_URL'] = "http://localhost/tts"
if not conf['TWITCH_CHAT_PARENT']:
conf['TWITCH_CHAT_PARENT'] = "localhost"
if not conf['EXTDATA']: if not conf['EXTDATA']:
conf['EXTDATA'] = False conf['EXTDATA'] = False

View File

@ -2,8 +2,12 @@
cp /var/www/html/auth.php /tmp/auth.php cp /var/www/html/auth.php /tmp/auth.php
/usr/bin/envsubst '${STREAMKEY}' < /tmp/auth.php > /var/www/html/auth.php /usr/bin/envsubst '${STREAMKEY}' < /tmp/auth.php > /var/www/html/auth.php
cp /var/www/html/obs_settings.py /tmp/obs_settings.py #cp /var/www/html/obs_settings.py /tmp/obs_settings.py
/usr/bin/envsubst < /tmp/obs_settings.py > /var/www/html/obs_settings.py #/usr/bin/envsubst < /tmp/obs_settings.py > /var/www/html/obs_settings.py
cp /etc/nginx/nginx.conf /tmp/nginx.conf
/usr/bin/envsubst '${LETSENCRYPT_DOMAIN}' < /tmp/nginx.conf > /etc/nginx/nginx.conf
cp /etc/dehydrated/domains.txt /tmp/domains.txt
/usr/bin/envsubst '${LETSENCRYPT_DOMAIN}' < /tmp/domains.txt > /etc/dehydrated/domains.txt
echo ${OBS_PASSWORD} | /usr/bin/htpasswd -c -i /var/www/.htpasswd admin echo ${OBS_PASSWORD} | /usr/bin/htpasswd -c -i /var/www/.htpasswd admin
echo "Password for Admin-Interface: ${OBS_PASSWORD}" echo "Password for Admin-Interface: ${OBS_PASSWORD}"
@ -17,6 +21,21 @@ if [ ${LIVEU} != "True" ]; then
rm /etc/supervisor/conf.d/liveu_collector.conf rm /etc/supervisor/conf.d/liveu_collector.conf
fi fi
mkdir -p /var/www/html/.well-known/acme-challenge
mkdir -p /var/lib/dehydrated/certs/${LETSENCRYPT_DOMAIN}/
mv /etc/nginx/nginx.conf /etc/nginx/nginx.conf.full
mv /etc/nginx/nginx_tmp.conf /etc/nginx/nginx.conf
/usr/sbin/nginx
/usr/bin/dehydrated --register --accept-terms
/usr/bin/dehydrated -c
killall nginx
mv /etc/nginx/nginx.conf.full /etc/nginx/nginx.conf
if [ -z ${LETSENCRYPT_DOMAIN} ]; then
mv /etc/nginx/snakeoil.pem /var/lib/dehydrated/certs/${LETSENCRYPT_DOMAIN}/fullchain.pem
mv /etc/nginx/snakeoil.key /var/lib/dehydrated/certs/${LETSENCRYPT_DOMAIN}/privkey.pem
fi
touch /opt/scripts/vol/__init__.py touch /opt/scripts/vol/__init__.py
/usr/bin/supervisord -c /etc/supervisor/supervisord.conf /usr/bin/supervisord -c /etc/supervisor/supervisord.conf
/usr/bin/supervisorctl status /usr/bin/supervisorctl status

View File

@ -45,6 +45,7 @@ channel = obs_settings.channel
chat_height = obs_settings.chat_height chat_height = obs_settings.chat_height
tts = obs_settings.tts tts = obs_settings.tts
tts_url = obs_settings.tts_url tts_url = obs_settings.tts_url
twitch_parent = obs_settings.twitch_parent
if not chat_height: if not chat_height:
chat_height = int(500) chat_height = int(500)
@ -111,14 +112,14 @@ if connected:
if channel: if channel:
print('<div id="chat">') print('<div id="chat">')
print(' <iframe id="twitchchat" style="display:none;" scrolling="0" frameborder="0" src="https://www.twitch.tv/embed/{0}/chat?parent=localhost" height="500px" width="100%"></iframe>'.format(str(channel))) print(' <iframe id="twitchchat" scrolling="0" frameborder="0" src="https://www.twitch.tv/embed/{0}/chat?parent={1}" height="850px" width="100%"></iframe>'.format(str(channel), str(twitch_parent)))
print(' <div class="status" onClick="$(\'#twitchchat\').fadeToggle(\'slow\', \'linear\');">Show/Hide chat</div>') print(' <div class="status" onClick="$(\'#twitchchat\').fadeToggle(\'slow\', \'linear\');">Show/Hide chat</div>')
print('</div>') print('</div>')
if tts: if tts:
print('<div id="tts">') print('<div id="tts">')
print(' <iframe id="ttsframe" style="display:none;" scrolling="0" frameborder="0" src="{0]" height="500px" width="100%"></iframe>'.format(str(tts_url))) print(' <iframe id="ttsframe" style="display:none;" scrolling="0" frameborder="0" src="{0}" height="250px" width="100%"></iframe>'.format(str(tts_url)))
print(' <div class="status" onClick="$(\'#ttsframe\').fadeToggle(\'slow\', \'linear\');">Show/Hide chat</div>') print(' <div class="status" onClick="$(\'#ttsframe\').fadeToggle(\'slow\', \'linear\');">Show/Hide TTS</div>')
print('</div>') print('</div>')
print('<div id="stream">') print('<div id="stream">')

View File

@ -15,3 +15,4 @@ chat_height = os.environ.get('CHAT_HEIGHT', 500)
extdata = os.environ.get('EXTDATA', False) extdata = os.environ.get('EXTDATA', False)
tts = os.environ.get('TTS', False) tts = os.environ.get('TTS', False)
tts_url = os.environ.get('TTS_URL', 'http://localhost/tts') tts_url = os.environ.get('TTS_URL', 'http://localhost/tts')
twitch_parent = os.environ.get('TWITCH_CHAT_PARENT', 'localhost')