mirror of
https://github.com/zoffline/zwift-offline.git
synced 2026-04-28 11:53:14 -07:00
Merge auth_server into zwift_offline
This commit is contained in:
@@ -1,10 +0,0 @@
|
|||||||
#!/usr/bin/python
|
|
||||||
import os
|
|
||||||
import sys
|
|
||||||
import logging
|
|
||||||
logging.basicConfig(stream=sys.stderr)
|
|
||||||
SCRIPT_DIR = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
sys.path.insert(0, SCRIPT_DIR)
|
|
||||||
|
|
||||||
from auth_server import app as application
|
|
||||||
application.debug = True
|
|
||||||
50
auth_server.py → tokens.py
Executable file → Normal file
50
auth_server.py → tokens.py
Executable file → Normal file
@@ -1,14 +1,5 @@
|
|||||||
#!/usr/bin/env python
|
# Tokens to be imported for auth server
|
||||||
|
# Not very pythonic, but don't want this cluttering main source
|
||||||
import os
|
|
||||||
import time
|
|
||||||
from flask import Flask, request, jsonify, redirect
|
|
||||||
|
|
||||||
app = Flask(__name__)
|
|
||||||
|
|
||||||
SCRIPT_DIR = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
AUTOLAUNCH_FILE = "%s/storage/auto_launch.txt" % SCRIPT_DIR
|
|
||||||
NOAUTO_EMBED = "http://cdn.zwift.com/static/web/launcher/embed-noauto.html"
|
|
||||||
|
|
||||||
# Token expires at INT32_MAX... because apparently Zwift or the library they're
|
# Token expires at INT32_MAX... because apparently Zwift or the library they're
|
||||||
# using thinks time can be negative.
|
# using thinks time can be negative.
|
||||||
@@ -19,40 +10,3 @@ REFRESH_TOKEN = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJqdGkiOiJiYjQ4czgyOS03ND
|
|||||||
ID_TOKEN = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJqdGkiOiJiYjQ4czgyOS03NDgzLTQzbzEtbzg1NC01ZDc5M3E1bjAwbjciLCJleHAiOjIxNDc0ODM2NDcsIm5iZiI6MCwiaWF0IjoxNTM1NTA4MDg3LCJpc3MiOiJodHRwczovL3NlY3VyZS56d2lmdC5jb20vYXV0aC9yZWFsbXMvendpZnQiLCJhdWQiOiJHYW1lX0xhdW5jaGVyIiwic3ViIjoiMDJyM2RlYjUtbnE5cS00NzZzLTlzczAtMDM0cTk3N3NwMnIxIiwidHlwIjoiSUQiLCJhenAiOiJHYW1lX0xhdW5jaGVyIiwiYXV0aF90aW1lIjoxNTM1NTA3MjQ5LCJzZXNzaW9uX3N0YXRlIjoiMDg0Nm5vOW4tNzY1cS00cDNzLW4yMHAtNnBucDlyODZyNXMzIiwiYWNyIjoiMCIsIm5hbWUiOiJad2lmdCBPZmZsaW5lIiwicHJlZmVycmVkX3VzZXJuYW1lIjoiem9mZmxpbmVAdHV0YW5vdGEuY29tIiwiZ2l2ZW5fbmFtZSI6Ilp3aWZ0IiwiZmFtaWx5X25hbWUiOiJPZmZsaW5lIiwiZW1haWwiOiJ6b2ZmbGluZUB0dXRhbm90YS5jb20ifQ.rWGSvv5TFO-i6LKczHNUUcB87Hfd5ow9IMG9O5EGR4Y"
|
ID_TOKEN = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJqdGkiOiJiYjQ4czgyOS03NDgzLTQzbzEtbzg1NC01ZDc5M3E1bjAwbjciLCJleHAiOjIxNDc0ODM2NDcsIm5iZiI6MCwiaWF0IjoxNTM1NTA4MDg3LCJpc3MiOiJodHRwczovL3NlY3VyZS56d2lmdC5jb20vYXV0aC9yZWFsbXMvendpZnQiLCJhdWQiOiJHYW1lX0xhdW5jaGVyIiwic3ViIjoiMDJyM2RlYjUtbnE5cS00NzZzLTlzczAtMDM0cTk3N3NwMnIxIiwidHlwIjoiSUQiLCJhenAiOiJHYW1lX0xhdW5jaGVyIiwiYXV0aF90aW1lIjoxNTM1NTA3MjQ5LCJzZXNzaW9uX3N0YXRlIjoiMDg0Nm5vOW4tNzY1cS00cDNzLW4yMHAtNnBucDlyODZyNXMzIiwiYWNyIjoiMCIsIm5hbWUiOiJad2lmdCBPZmZsaW5lIiwicHJlZmVycmVkX3VzZXJuYW1lIjoiem9mZmxpbmVAdHV0YW5vdGEuY29tIiwiZ2l2ZW5fbmFtZSI6Ilp3aWZ0IiwiZmFtaWx5X25hbWUiOiJPZmZsaW5lIiwiZW1haWwiOiJ6b2ZmbGluZUB0dXRhbm90YS5jb20ifQ.rWGSvv5TFO-i6LKczHNUUcB87Hfd5ow9IMG9O5EGR4Y"
|
||||||
|
|
||||||
FAKE_JWT = """{"access_token":"%s","expires_in":1000021600,"refresh_expires_in":611975560,"refresh_token":"%s","token_type":"bearer","id_token":"%s","not-before-policy":1408478984,"session_state":"0846ab9a-765d-4c3f-a20c-6cac9e86e5f3","scope":""}""" % (ACCESS_TOKEN, REFRESH_TOKEN, ID_TOKEN)
|
FAKE_JWT = """{"access_token":"%s","expires_in":1000021600,"refresh_expires_in":611975560,"refresh_token":"%s","token_type":"bearer","id_token":"%s","not-before-policy":1408478984,"session_state":"0846ab9a-765d-4c3f-a20c-6cac9e86e5f3","scope":""}""" % (ACCESS_TOKEN, REFRESH_TOKEN, ID_TOKEN)
|
||||||
|
|
||||||
|
|
||||||
@app.route('/auth/rb_bf03269xbi', methods=['POST'])
|
|
||||||
def api_auth():
|
|
||||||
return 'OK(Java)'
|
|
||||||
|
|
||||||
|
|
||||||
@app.route('/launcher', methods=['GET'])
|
|
||||||
@app.route('/auth/realms/zwift/protocol/openid-connect/auth', methods=['GET'])
|
|
||||||
@app.route('/auth/realms/zwift/login-actions/request/login', methods=['GET', 'POST'])
|
|
||||||
@app.route('/auth/realms/zwift/protocol/openid-connect/registrations', methods=['GET'])
|
|
||||||
@app.route('/auth/realms/zwift/login-actions/startriding', methods=['GET']) # Unused as it's a direct redirect now from auth/login
|
|
||||||
@app.route('/auth/realms/zwift/tokens/login', methods=['GET']) # Called by Mac, but not Windows
|
|
||||||
@app.route('/auth/realms/zwift/tokens/registrations', methods=['GET']) # Called by Mac, but not Windows
|
|
||||||
@app.route('/ride', methods=['GET'])
|
|
||||||
def launch_zwift():
|
|
||||||
if request.path != "/ride" and not os.path.exists(AUTOLAUNCH_FILE):
|
|
||||||
return redirect(NOAUTO_EMBED, 302)
|
|
||||||
else:
|
|
||||||
return redirect("http://zwift/?code=zwift_refresh_token%s" % REFRESH_TOKEN, 302)
|
|
||||||
|
|
||||||
|
|
||||||
@app.route('/auth/realms/zwift/protocol/openid-connect/token', methods=['POST'])
|
|
||||||
def auth_realms_zwift_protocol_openid_connect_token():
|
|
||||||
return FAKE_JWT, 200
|
|
||||||
|
|
||||||
|
|
||||||
# Called by Mac, but not Windows
|
|
||||||
@app.route('/auth/realms/zwift/tokens/access/codes', methods=['POST'])
|
|
||||||
def auth_realms_zwift_tokens_access_codes():
|
|
||||||
return FAKE_JWT, 200
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
app.run(ssl_context=('ssl/cert-secure-zwift.pem', 'ssl/key-secure-zwift.pem'),
|
|
||||||
port=9000,
|
|
||||||
host='0.0.0.0',
|
|
||||||
debug=True)
|
|
||||||
57
zwift_offline.py
Executable file → Normal file
57
zwift_offline.py
Executable file → Normal file
@@ -11,7 +11,7 @@ from copy import copy
|
|||||||
from datetime import timedelta
|
from datetime import timedelta
|
||||||
from io import BytesIO
|
from io import BytesIO
|
||||||
|
|
||||||
from flask import Flask, request, jsonify, g
|
from flask import Flask, request, jsonify, g, redirect
|
||||||
from google.protobuf.descriptor import FieldDescriptor
|
from google.protobuf.descriptor import FieldDescriptor
|
||||||
from protobuf_to_dict import protobuf_to_dict, TYPE_CALLABLE_MAP
|
from protobuf_to_dict import protobuf_to_dict, TYPE_CALLABLE_MAP
|
||||||
|
|
||||||
@@ -32,6 +32,10 @@ DATABASE_PATH = "%s/zwift-offline.db" % STORAGE_DIR
|
|||||||
DATABASE_INIT_SQL = "%s/initialize_db.sql" % SCRIPT_DIR
|
DATABASE_INIT_SQL = "%s/initialize_db.sql" % SCRIPT_DIR
|
||||||
DATABASE_CUR_VER = 0
|
DATABASE_CUR_VER = 0
|
||||||
|
|
||||||
|
# For auth server
|
||||||
|
AUTOLAUNCH_FILE = "%s/storage/auto_launch.txt" % SCRIPT_DIR
|
||||||
|
NOAUTO_EMBED = "http://cdn.zwift.com/static/web/launcher/embed-noauto.html"
|
||||||
|
from tokens import *
|
||||||
|
|
||||||
####
|
####
|
||||||
# Set up protobuf_to_dict call map
|
# Set up protobuf_to_dict call map
|
||||||
@@ -104,6 +108,7 @@ def get_id(table_name):
|
|||||||
|
|
||||||
@app.route('/api/auth', methods=['GET'])
|
@app.route('/api/auth', methods=['GET'])
|
||||||
def api_auth():
|
def api_auth():
|
||||||
|
print "api_auth"
|
||||||
return '{"realm":"zwift","url":"https://secure.zwift.com/auth/"}'
|
return '{"realm":"zwift","url":"https://secure.zwift.com/auth/"}'
|
||||||
|
|
||||||
|
|
||||||
@@ -478,8 +483,50 @@ def init_database():
|
|||||||
# Migrate database if necessary
|
# Migrate database if necessary
|
||||||
|
|
||||||
|
|
||||||
|
####################
|
||||||
|
#
|
||||||
|
# Auth server (secure.zwift.com) routes below here
|
||||||
|
#
|
||||||
|
####################
|
||||||
|
|
||||||
|
@app.route('/auth/rb_bf03269xbi', methods=['POST'])
|
||||||
|
def auth_rb():
|
||||||
|
return 'OK(Java)'
|
||||||
|
|
||||||
|
|
||||||
|
@app.route('/launcher', methods=['GET'])
|
||||||
|
@app.route('/auth/realms/zwift/protocol/openid-connect/auth', methods=['GET'])
|
||||||
|
@app.route('/auth/realms/zwift/login-actions/request/login', methods=['GET', 'POST'])
|
||||||
|
@app.route('/auth/realms/zwift/protocol/openid-connect/registrations', methods=['GET'])
|
||||||
|
@app.route('/auth/realms/zwift/login-actions/startriding', methods=['GET']) # Unused as it's a direct redirect now from auth/login
|
||||||
|
@app.route('/auth/realms/zwift/tokens/login', methods=['GET']) # Called by Mac, but not Windows
|
||||||
|
@app.route('/auth/realms/zwift/tokens/registrations', methods=['GET']) # Called by Mac, but not Windows
|
||||||
|
@app.route('/ride', methods=['GET'])
|
||||||
|
def launch_zwift():
|
||||||
|
if request.path != "/ride" and not os.path.exists(AUTOLAUNCH_FILE):
|
||||||
|
return redirect(NOAUTO_EMBED, 302)
|
||||||
|
else:
|
||||||
|
return redirect("http://zwift/?code=zwift_refresh_token%s" % REFRESH_TOKEN, 302)
|
||||||
|
|
||||||
|
|
||||||
|
@app.route('/auth/realms/zwift/protocol/openid-connect/token', methods=['POST'])
|
||||||
|
def auth_realms_zwift_protocol_openid_connect_token():
|
||||||
|
return FAKE_JWT, 200
|
||||||
|
|
||||||
|
|
||||||
|
# Called by Mac, but not Windows
|
||||||
|
@app.route('/auth/realms/zwift/tokens/access/codes', methods=['POST'])
|
||||||
|
def auth_realms_zwift_tokens_access_codes():
|
||||||
|
return FAKE_JWT, 200
|
||||||
|
|
||||||
|
|
||||||
|
def run_standalone():
|
||||||
|
app.run(ssl_context=('ssl/cert-zwift-com.pem', 'ssl/key-zwift-com.pem'),
|
||||||
|
port=443,
|
||||||
|
threaded=True,
|
||||||
|
host='0.0.0.0')
|
||||||
|
# debug=True, use_reload=False)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
app.run(#ssl_context=('ssl/cert-us-or.pem', 'ssl/key-us-or.pem'),
|
run_standalone()
|
||||||
port=8000,
|
|
||||||
host='0.0.0.0',
|
|
||||||
debug=True)
|
|
||||||
|
|||||||
Reference in New Issue
Block a user