-
Notifications
You must be signed in to change notification settings - Fork 26
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
1383 add authorization header to getmap requests #1384
1383 add authorization header to getmap requests #1384
Conversation
…eader to GeoServer GetMap requests
…_GEOSERVER_PROXY variable in docker compose files
…orization-header-to-getmap-requests # Conflicts: # web/twa-vis-platform/code/package.json # web/twa-vis-platform/code/server.js # web/twa-vis-platform/code/src/ui/map/mapbox/mapbox-container.tsx # web/twa-vis-platform/resources/CHANGELOG.md # web/twa-vis-platform/resources/VERSION
…orization-header-to-getmap-requests # Conflicts: # web/twa-vis-platform/code/package.json # web/twa-vis-platform/code/server.js # web/twa-vis-platform/code/src/ui/map/mapbox/mapbox-container.tsx
… into 1383-add-authorization-header-to-getmap-requests
const serverUrl = `${window.location.protocol}//${window.location.host}`; | ||
const proxyUrl = `${serverUrl}/geoserver-proxy?url=${encodeURIComponent(url)}`; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this needs to change as we do not want to restrict viz and geoserver url to the same host as the viz url
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
agree with this
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
addressed by 1250573
web/twa-vis-platform/code/server.js
Outdated
if (useGeoServerProxy) { | ||
server.get('/geoserver-proxy', async (req, res) => { | ||
const targetUrl = req.query.url; | ||
let headers = { ...req.headers }; | ||
|
||
if (req.kauth?.grant) { | ||
headers['Authorization'] = 'Bearer ' + req.kauth.grant.access_token.token; | ||
} | ||
|
||
try { | ||
// Forward the request to the target URL with the modified headers | ||
const response = await axios({ | ||
url: targetUrl, | ||
method: req.method, | ||
headers: headers, | ||
responseType: 'stream', // To stream the response back | ||
}); | ||
|
||
// Pipe the response back to the client | ||
response.data.pipe(res); | ||
} catch (err) { | ||
// most of these errors can probably be ignored | ||
console.error(err); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we should get rid of this whole path and just save the req.kauth.grant.access_token
to the already existing /api/userinfo/path or somewhere else as a global variable. Then call that directly from the mapbox container url transformer
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The intention behind this design is that the token needs to be taken directly from the session store/server for each request, otherwise the token gets outdated and becomes invalid.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this design guarantees that each request is handled by the middleware
transformRequest: (url) => { | ||
if (process.env.REACT_APP_USE_GEOSERVER_PROXY === 'true') { | ||
try { | ||
const urlObject = new URL(url); | ||
const params = new URLSearchParams(urlObject.search); | ||
if (params.get('request') === 'GetMap') { | ||
// not sure if this will work across all conditions | ||
const serverUrl = `${window.location.protocol}//${window.location.host}`; | ||
const proxyUrl = `${serverUrl}/geoserver-proxy?url=${encodeURIComponent(url)}`; | ||
return { | ||
url: proxyUrl | ||
} | ||
} | ||
} catch { } | ||
} else { | ||
return { url: url } | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
transformRequest: (url) => { | |
if (process.env.REACT_APP_USE_GEOSERVER_PROXY === 'true') { | |
try { | |
const urlObject = new URL(url); | |
const params = new URLSearchParams(urlObject.search); | |
if (params.get('request') === 'GetMap') { | |
// not sure if this will work across all conditions | |
const serverUrl = `${window.location.protocol}//${window.location.host}`; | |
const proxyUrl = `${serverUrl}/geoserver-proxy?url=${encodeURIComponent(url)}`; | |
return { | |
url: proxyUrl | |
} | |
} | |
} catch { } | |
} else { | |
return { url: url } | |
} | |
} | |
transformRequest: (url, resourceType) => { | |
if (resourceType === 'Source' && url.startsWith('http://myHost')) { | |
return { | |
url: url.replace('http', 'https'), | |
headers: {'my-custom-header': true}, | |
credentials: 'include' // Include cookies for cross-origin requests | |
}; | |
} | |
} |
comes from here. Let's try just pass the header in this bit of code and use a variable to get the bearer token from /api/userinfo
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using resourceType does not seem to be robust enough, when I use MapBox vector tile, its value is 'Tile'
…ment variable REACT_APP_SERVER_URL
…VER_URL to docker compose files
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As discussed on call earlier, happy to merge this since it works well for the trajectories use case as demonstrated by @kok-foong and does not interfere with CReDo or other mapbox applications when the geoserver proxy setting is not set.
May revisit the application later with an improved resource server that authorises the token directly with keycloak using the spring adapter, or maybe uses a Requesting Party Token / Token exchange @gpeb2
Overview:
New environment variable
On server.js, a new API is added:
In mapbox-container.tsx