From 03129d9dfa10852a72feea129dac08646ed0d9df Mon Sep 17 00:00:00 2001 From: Jakob Scheid Date: Sun, 8 Mar 2026 14:43:48 +0100 Subject: [PATCH] Added support for CORS --- NOTICE | 7 +------ README.md | 3 +++ api.conf | 18 ++++++++++++++++++ default_configuration.conf | 1 + src/api.py | 18 ++++++++++++++---- 5 files changed, 37 insertions(+), 10 deletions(-) diff --git a/NOTICE b/NOTICE index d0f6ac1..6795733 100644 --- a/NOTICE +++ b/NOTICE @@ -289,9 +289,4 @@ This software uses the following third-party libraries. Full license texts are a Author: Graham Dumpleton License: BSD 2-Clause License URL: https://github.com/GrahamDumpleton/wrapt - See licenses/wrapt.txt for full license text. - -55. word-language-detector-ai - Author: Johannes D. Vos - License: MIT License - See licenses/word-language-detector-ai.txt for full license text. \ No newline at end of file + See licenses/wrapt.txt for full license text. \ No newline at end of file diff --git a/README.md b/README.md index b62ca4b..f7e44de 100644 --- a/README.md +++ b/README.md @@ -54,6 +54,9 @@ For the full API documentation, see the docs path of the API. ## Changelog +### Version 0.2.0 +- support for CORS + ### Version 0.1.1 - added `--break-system-packages` to `pip install ...` - bug fix: create model directory before downloading the model diff --git a/api.conf b/api.conf index c7f7b4e..ba32642 100644 --- a/api.conf +++ b/api.conf @@ -5,6 +5,24 @@ # The port to listen. Default is 3000. # port= +# The Access-Control-Allow-Origin HTTP Header. It controls which origin +# is allowed to access the API. You can allow all origins by setting it +# to '*'. Default is '*'. +# Note: This only affects access via JavaScript in browsers. Moreover, +# a HTTP request is always sent when JavaScript in browsers attempts to +# access the API, even when it runs on a domain that is not allowed in +# 'allowOrigin'. In this case, however, the response is simply not made +# accessible for JavaScript. +# If the API is intended for access via a specific website, setting the +# property to the domain of the site is strongly recommended. +# Furthermore, note that this is not a protection for the API. It is +# simply a note for the browser to control which websites can access it. +# In a non-browser context, this has no effect. +# For an example, set it to 'http://example.com:8000' (NOT +# 'http://example.com:8000/') if you want to access the API from +# 'http://example.com:8000'. +# allowOrigin= + [docs] # The path for the Swagger UI documentation. If an empty path is # specified, no Swagger UI documentation will be available. Default is diff --git a/default_configuration.conf b/default_configuration.conf index a44a7dd..1f807d9 100644 --- a/default_configuration.conf +++ b/default_configuration.conf @@ -4,6 +4,7 @@ [server] host=0.0.0.0 port=3000 +allowOrigin=* [docs] swagger=/docs diff --git a/src/api.py b/src/api.py index c1ebd3b..92b985a 100755 --- a/src/api.py +++ b/src/api.py @@ -5,7 +5,8 @@ import os # disable TensorFlow output os.environ['TF_CPP_MIN_LOG_LEVEL'] = '3' -from fastapi import FastAPI +from fastapi import FastAPI, Response +from fastapi.middleware.cors import CORSMiddleware import uvicorn from pydantic import BaseModel, Field import json @@ -322,6 +323,7 @@ if ai_modules_lazy_import.lower() not in ('true', 'false'): ai_modules_lazy_import = ai_modules_lazy_import.lower() == 'true' +allow_origin = configuration.server.allowOrigin # Initialize cache @@ -365,16 +367,25 @@ app = FastAPI( openapi_url=configuration.docs.openapi ) +app.add_middleware( + CORSMiddleware, + allow_origins=[allow_origin], + allow_credentials=False, + allow_methods=['GET', 'POST'], + allow_headers=['*'] +) + if not ai_modules_lazy_import: load_ai() # predict word language @app.post('/prediction', response_model=LanguagesResponse) -async def predict_language(words: Words): +async def predict_language(words: Words, response: Response): if not ai_loaded: load_ai(model_dir) - + response.headers['Access-Control-Allow-Origin'] = allow_origin + response.headers['Access-Control-Allow-Origin'] = allow_origin return { 'words': { w.word: { @@ -393,7 +404,6 @@ async def get_languages(): ] } - # run Uvicorn if __name__ == '__main__': uvicorn.run(