Merge pull request #424 from dannyrb/docs/last-bits
Note regarding different repositories
This commit is contained in:
commit
12eefb3108
16
docker/OpenResty-Orthanc/.dockerignore
Normal file
16
docker/OpenResty-Orthanc/.dockerignore
Normal file
@ -0,0 +1,16 @@
|
||||
# Output
|
||||
dist/
|
||||
|
||||
# Dependencies
|
||||
node_modules/
|
||||
|
||||
# Root
|
||||
README.md
|
||||
Dockerfile
|
||||
|
||||
# Misc. Config
|
||||
.git
|
||||
.DS_Store
|
||||
.gitignore
|
||||
.vscode
|
||||
.circleci
|
||||
5
docker/OpenResty-Orthanc/.env
Normal file
5
docker/OpenResty-Orthanc/.env
Normal file
@ -0,0 +1,5 @@
|
||||
# Docker ENV and ARG Variables
|
||||
# ----------------------------
|
||||
# https://vsupalov.com/docker-arg-env-variable-guide/
|
||||
#
|
||||
#
|
||||
135
docker/OpenResty-Orthanc/config/nginx.conf
Normal file
135
docker/OpenResty-Orthanc/config/nginx.conf
Normal file
@ -0,0 +1,135 @@
|
||||
worker_processes 2;
|
||||
error_log /var/logs/nginx/mydomain.error.log;
|
||||
pid /var/run/nginx.pid;
|
||||
include /usr/share/nginx/modules/*.conf; # See /usr/share/doc/nginx/README.dynamic.
|
||||
|
||||
events {
|
||||
worker_connections 1024; ## Default: 1024
|
||||
use epoll; # http://nginx.org/en/docs/events.html
|
||||
multi_accept on; # http://nginx.org/en/docs/ngx_core_module.html#multi_accept
|
||||
}
|
||||
|
||||
# Core Modules Docs:
|
||||
# http://nginx.org/en/docs/http/ngx_http_core_module.html
|
||||
http {
|
||||
include '/usr/local/openresty/nginx/conf/mime.types';
|
||||
default_type application/octet-stream;
|
||||
|
||||
keepalive_timeout 65;
|
||||
keepalive_requests 100000;
|
||||
tcp_nopush on;
|
||||
tcp_nodelay on;
|
||||
|
||||
# lua_ settings
|
||||
#
|
||||
lua_package_path '/usr/local/openresty/lualib/?.lua;;';
|
||||
lua_shared_dict discovery 1m; # cache for discovery metadata documents
|
||||
lua_shared_dict jwks 1m; # cache for JWKs
|
||||
# lua_ssl_trusted_certificate /etc/ssl/certs/ca-certificates.crt;
|
||||
|
||||
variables_hash_max_size 2048;
|
||||
server_names_hash_bucket_size 128;
|
||||
server_tokens off;
|
||||
|
||||
resolver 8.8.8.8 valid=30s ipv6=off;
|
||||
resolver_timeout 11s;
|
||||
|
||||
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
|
||||
'$status $body_bytes_sent "$http_referer" '
|
||||
'"$http_user_agent" "$http_x_forwarded_for"';
|
||||
|
||||
# Nginx `listener` block
|
||||
server {
|
||||
listen [::]:80 default_server;
|
||||
listen 80;
|
||||
# listen 443 ssl;
|
||||
access_log /var/logs/nginx/mydomain.access.log;
|
||||
|
||||
# Domain to protect
|
||||
server_name 127.0.0.1 localhost; # mydomain.com;
|
||||
proxy_intercept_errors off;
|
||||
# ssl_certificate /etc/letsencrypt/live/mydomain.co.uk/fullchain.pem;
|
||||
# ssl_certificate_key /etc/letsencrypt/live/mydomain.co.uk/privkey.pem;
|
||||
gzip on;
|
||||
gzip_types text/css application/javascript application/json image/svg+xml;
|
||||
gzip_comp_level 9;
|
||||
etag on;
|
||||
|
||||
# https://github.com/bungle/lua-resty-session/issues/15
|
||||
set $session_check_ssi off;
|
||||
lua_code_cache off;
|
||||
set $session_secret Eeko7aeb6iu5Wohch9Loo1aitha0ahd1;
|
||||
set $session_storage cookie;
|
||||
|
||||
server_tokens off; # Hides server version num
|
||||
|
||||
# Reverse Proxy for `orthanc` admin
|
||||
#
|
||||
location /pacs-admin/ {
|
||||
|
||||
proxy_http_version 1.1;
|
||||
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
|
||||
expires 0;
|
||||
add_header Cache-Control private;
|
||||
|
||||
proxy_pass http://orthanc:8042/;
|
||||
}
|
||||
|
||||
# Reverse Proxy for `orthanc` APIs (including DICOMWeb)
|
||||
#
|
||||
location /pacs/ {
|
||||
|
||||
proxy_http_version 1.1;
|
||||
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
|
||||
expires 0;
|
||||
add_header Cache-Control private;
|
||||
|
||||
proxy_pass http://orthanc:8042/;
|
||||
|
||||
# By default, this endpoint is protected by CORS (cross-origin-resource-sharing)
|
||||
# You can add headers to allow other domains to request this resource.
|
||||
# See the "Updating CORS Settings" example below
|
||||
}
|
||||
|
||||
# Do not cache sw.js, required for offline-first updates.
|
||||
location /sw.js {
|
||||
add_header Cache-Control "no-cache";
|
||||
proxy_cache_bypass $http_pragma;
|
||||
proxy_cache_revalidate on;
|
||||
expires off;
|
||||
access_log off;
|
||||
}
|
||||
|
||||
# Single Page App
|
||||
# Try files, fallback to index.html
|
||||
#
|
||||
location / {
|
||||
alias /var/www/html/;
|
||||
index index.html;
|
||||
try_files $uri $uri/ /index.html;
|
||||
add_header Cache-Control "no-store, no-cache, must-revalidate";
|
||||
}
|
||||
|
||||
# EXAMPLE: Redirect server error pages to the static page /40x.html
|
||||
#
|
||||
# error_page 404 /404.html;
|
||||
# location = /40x.html {
|
||||
# }
|
||||
|
||||
# EXAMPLE: Redirect server error pages to the static page /50x.html
|
||||
#
|
||||
# error_page 500 502 503 504 /50x.html;
|
||||
# location = /50x.html {
|
||||
# }
|
||||
}
|
||||
}
|
||||
89
docker/OpenResty-Orthanc/config/orthanc.json
Normal file
89
docker/OpenResty-Orthanc/config/orthanc.json
Normal file
@ -0,0 +1,89 @@
|
||||
{
|
||||
"Name": "Orthanc inside Docker",
|
||||
"StorageDirectory": "/var/lib/orthanc/db",
|
||||
"IndexDirectory": "/var/lib/orthanc/db",
|
||||
"StorageCompression": false,
|
||||
"MaximumStorageSize": 0,
|
||||
"MaximumPatientCount": 0,
|
||||
"LuaScripts": [],
|
||||
"Plugins": ["/usr/share/orthanc/plugins", "/usr/local/share/orthanc/plugins"],
|
||||
"ConcurrentJobs": 2,
|
||||
"HttpServerEnabled": true,
|
||||
"HttpPort": 8042,
|
||||
"HttpDescribeErrors": true,
|
||||
"HttpCompressionEnabled": true,
|
||||
"DicomServerEnabled": true,
|
||||
"DicomAet": "ORTHANC",
|
||||
"DicomCheckCalledAet": false,
|
||||
"DicomPort": 4242,
|
||||
"DefaultEncoding": "Latin1",
|
||||
"DeflatedTransferSyntaxAccepted": true,
|
||||
"JpegTransferSyntaxAccepted": true,
|
||||
"Jpeg2000TransferSyntaxAccepted": true,
|
||||
"JpegLosslessTransferSyntaxAccepted": true,
|
||||
"JpipTransferSyntaxAccepted": true,
|
||||
"Mpeg2TransferSyntaxAccepted": true,
|
||||
"RleTransferSyntaxAccepted": true,
|
||||
"UnknownSopClassAccepted": false,
|
||||
"DicomScpTimeout": 30,
|
||||
|
||||
"RemoteAccessAllowed": true,
|
||||
"SslEnabled": false,
|
||||
"SslCertificate": "certificate.pem",
|
||||
"AuthenticationEnabled": false,
|
||||
"RegisteredUsers": {
|
||||
"test": "test"
|
||||
},
|
||||
"DicomModalities": {},
|
||||
"DicomModalitiesInDatabase": false,
|
||||
"DicomAlwaysAllowEcho": true,
|
||||
"DicomAlwaysAllowStore": true,
|
||||
"DicomCheckModalityHost": false,
|
||||
"DicomScuTimeout": 10,
|
||||
"OrthancPeers": {},
|
||||
"OrthancPeersInDatabase": false,
|
||||
"HttpProxy": "",
|
||||
|
||||
"HttpVerbose": true,
|
||||
|
||||
"HttpTimeout": 10,
|
||||
"HttpsVerifyPeers": true,
|
||||
"HttpsCACertificates": "",
|
||||
"UserMetadata": {},
|
||||
"UserContentType": {},
|
||||
"StableAge": 60,
|
||||
"StrictAetComparison": false,
|
||||
"StoreMD5ForAttachments": true,
|
||||
"LimitFindResults": 0,
|
||||
"LimitFindInstances": 0,
|
||||
"LimitJobs": 10,
|
||||
"LogExportedResources": false,
|
||||
"KeepAlive": true,
|
||||
"TcpNoDelay": true,
|
||||
"HttpThreadsCount": 50,
|
||||
"StoreDicom": true,
|
||||
"DicomAssociationCloseDelay": 5,
|
||||
"QueryRetrieveSize": 10,
|
||||
"CaseSensitivePN": false,
|
||||
"LoadPrivateDictionary": true,
|
||||
"Dictionary": {},
|
||||
"SynchronousCMove": true,
|
||||
"JobsHistorySize": 10,
|
||||
"SaveJobs": true,
|
||||
"OverwriteInstances": false,
|
||||
"MediaArchiveSize": 1,
|
||||
"StorageAccessOnFind": "Always",
|
||||
"MetricsEnabled": true,
|
||||
|
||||
"DicomWeb": {
|
||||
"Enable": true,
|
||||
"Root": "/dicom-web/",
|
||||
"EnableWado": true,
|
||||
"WadoRoot": "/wado",
|
||||
"Host": "127.0.0.1",
|
||||
"Ssl": false,
|
||||
"StowMaxInstances": 10,
|
||||
"StowMaxSize": 10,
|
||||
"QidoCaseSensitive": false
|
||||
}
|
||||
}
|
||||
45
docker/OpenResty-Orthanc/docker-compose.yml
Normal file
45
docker/OpenResty-Orthanc/docker-compose.yml
Normal file
@ -0,0 +1,45 @@
|
||||
# Reference:
|
||||
# - https://docs.docker.com/compose/compose-file
|
||||
# - https://eclipsesource.com/blogs/2018/01/11/authenticating-reverse-proxy-with-keycloak/
|
||||
|
||||
version: '3.5'
|
||||
|
||||
services:
|
||||
# Exposed server that's handling incoming web requests
|
||||
# Underlying image: openresty/openresty:alpine-fat
|
||||
ohif_viewer:
|
||||
build:
|
||||
# Project root
|
||||
context: ./../../
|
||||
# Relative to context
|
||||
dockerfile: ./docker/OpenResty-Orthanc/dockerfile
|
||||
image: webapp:latest
|
||||
container_name: webapp
|
||||
volumes:
|
||||
# Nginx config
|
||||
- ./config/nginx.conf:/usr/local/openresty/nginx/conf/nginx.conf:ro
|
||||
# Logs
|
||||
- ./logs/nginx:/var/logs/nginx
|
||||
# Let's Encrypt
|
||||
# - letsencrypt_certificates:/etc/letsencrypt
|
||||
# - letsencrypt_challenges:/var/www/letsencrypt
|
||||
ports:
|
||||
- '443:443' # SSL
|
||||
- '80:80' # Web
|
||||
depends_on:
|
||||
- orthanc
|
||||
restart: on-failure
|
||||
|
||||
# LINK: https://hub.docker.com/r/jodogne/orthanc-plugins/
|
||||
# TODO: Update to use Postgres
|
||||
# https://github.com/mrts/docker-postgresql-multiple-databases
|
||||
orthanc:
|
||||
image: jodogne/orthanc-plugins:1.5.6
|
||||
hostname: orthanc
|
||||
container_name: orthanc
|
||||
volumes:
|
||||
# Config
|
||||
- ./config/orthanc.json:/etc/orthanc/orthanc.json:ro
|
||||
# Persist data
|
||||
- ./volumes/orthanc-db/:/var/lib/orthanc/db/
|
||||
restart: unless-stopped
|
||||
65
docker/OpenResty-Orthanc/dockerfile
Normal file
65
docker/OpenResty-Orthanc/dockerfile
Normal file
@ -0,0 +1,65 @@
|
||||
# docker-compose
|
||||
# --------------
|
||||
# This dockerfile is used by the `docker-compose.yml` adjacent file. When
|
||||
# running `docker-compose build`, this dockerfile helps build the "webapp" image.
|
||||
# All paths are relative to the `context`, which is the project root directory.
|
||||
#
|
||||
# docker build
|
||||
# --------------
|
||||
# If you would like to use this dockerfile to build and tag an image, make sure
|
||||
# you set the context to the project's root directory:
|
||||
# https://docs.docker.com/engine/reference/commandline/build/
|
||||
#
|
||||
#
|
||||
# SUMMARY
|
||||
# --------------
|
||||
# This dockerfile has two stages:
|
||||
#
|
||||
# 1. Building the React application for production
|
||||
# 2. Setting up our Nginx (OpenResty*) image w/ step one's output
|
||||
#
|
||||
# * OpenResty is functionally identical to Nginx with the addition of Lua out of
|
||||
# the box.
|
||||
|
||||
|
||||
# Stage 1: Build the application
|
||||
FROM node:11.2.0-slim as builder
|
||||
|
||||
RUN mkdir /usr/src/app
|
||||
WORKDIR /usr/src/app
|
||||
|
||||
ENV REACT_APP_CONFIG=config/docker_openresty-orthanc.js
|
||||
ENV PATH /usr/src/app/node_modules/.bin:$PATH
|
||||
|
||||
COPY package.json /usr/src/app/package.json
|
||||
COPY yarn.lock /usr/src/app/yarn.lock
|
||||
|
||||
ADD . /usr/src/app/
|
||||
RUN yarn install
|
||||
RUN yarn run build:web
|
||||
|
||||
# Stage 2: Bundle the built application into a Docker container
|
||||
# which runs openresty (nginx) using Alpine Linux
|
||||
# LINK: https://hub.docker.com/r/openresty/openresty
|
||||
FROM openresty/openresty:1.15.8.1rc1-0-alpine-fat
|
||||
|
||||
RUN mkdir /var/log/nginx
|
||||
RUN apk add --no-cache openssl
|
||||
RUN apk add --no-cache openssl-dev
|
||||
RUN apk add --no-cache git
|
||||
RUN apk add --no-cache gcc
|
||||
# !!!
|
||||
RUN luarocks install lua-resty-openidc
|
||||
|
||||
#
|
||||
RUN luarocks install lua-resty-jwt
|
||||
RUN luarocks install lua-resty-session
|
||||
RUN luarocks install lua-resty-http
|
||||
# !!!
|
||||
RUN luarocks install lua-resty-openidc
|
||||
RUN luarocks install luacrypto
|
||||
|
||||
# Copy build output to image
|
||||
COPY --from=builder /usr/src/app/build /var/www/html
|
||||
|
||||
ENTRYPOINT ["/usr/local/openresty/nginx/sbin/nginx", "-g", "daemon off;"]
|
||||
2
docker/OpenResty-Orthanc/volumes/orthanc-db/.gitignore
vendored
Normal file
2
docker/OpenResty-Orthanc/volumes/orthanc-db/.gitignore
vendored
Normal file
@ -0,0 +1,2 @@
|
||||
*
|
||||
!.gitignore
|
||||
BIN
docs/latest/assets/designs/nginx-image-archive.fig
Normal file
BIN
docs/latest/assets/designs/nginx-image-archive.fig
Normal file
Binary file not shown.
BIN
docs/latest/assets/designs/scope-of-project.fig
Normal file
BIN
docs/latest/assets/designs/scope-of-project.fig
Normal file
Binary file not shown.
BIN
docs/latest/assets/img/nginx-image-archive.png
Normal file
BIN
docs/latest/assets/img/nginx-image-archive.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 27 KiB |
BIN
docs/latest/assets/img/scope-of-project.png
Normal file
BIN
docs/latest/assets/img/scope-of-project.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 60 KiB |
@ -4,18 +4,23 @@
|
||||
|
||||
Fork the repository, make your change and submit a pull request.
|
||||
|
||||
- The OHIF Viewer consists of code from three different repositories. Make sure
|
||||
your change is modifying the appropriate one:
|
||||
- `ohif-core`: Business Logic
|
||||
- `react-viewerbase`: Reusable React Component Library
|
||||
- `Viewers`: The glue, PWA, and primary extension point
|
||||
- At a minimum, you may want to read the following documentation:
|
||||
- [Essentials: Getting Started](./essentials/getting-started.md)
|
||||
- [Advanced: Architecture](./advanced/architecture.md)
|
||||
|
||||
## Any guidance on submitting changes?
|
||||
|
||||
While we do appreciate code contributions, triaging and integrating contributed
|
||||
code changes can be very time consuming. Please consider the following tips when
|
||||
working on your pull requests:
|
||||
|
||||
- Functionality is appropriate for the repository. Consider posting on the forum
|
||||
if you are not sure.
|
||||
- Code quality is acceptable. We don't have coding standards defined, but make
|
||||
sure it passes ESLint and looks like the rest of the code in the repository.
|
||||
- Quality of design is acceptable. This is a bit subjective so you should
|
||||
consider posting on the forum for specific guidance.
|
||||
- Functionality is appropriate for the repository. Consider creating a GitHub
|
||||
issue to discuss your suggested changes.
|
||||
- The scope of the pull request is not too large. Please consider separate pull
|
||||
requests for each feature as big pull requests are very time consuming to
|
||||
understand.
|
||||
@ -35,14 +40,14 @@ Replacing the number 237 in the link below with your pull request number should
|
||||
let you test it as well and you can use this link for discussions on github
|
||||
without requiring reviewers to download and build your branch.
|
||||
|
||||
```
|
||||
```bash
|
||||
https://deploy-preview-237--ohif.netlify.com/viewer/?url=https://s3.eu-central-1.amazonaws.com/ohif-viewer/sampleDICOM.json
|
||||
```
|
||||
|
||||
If you have made a documentation change, a link like this will let you preview
|
||||
the gitbook generated by the pull request:
|
||||
|
||||
```
|
||||
```bash
|
||||
https://deploy-preview-237--ohif.netlify.com/contributing.html
|
||||
```
|
||||
|
||||
|
||||
4
docs/latest/deployment/_nginx-image-archive-diagram.md
Normal file
4
docs/latest/deployment/_nginx-image-archive-diagram.md
Normal file
@ -0,0 +1,4 @@
|
||||
<div style="text-align: center;">
|
||||
<img src="/assets/img/nginx-image-archive.png" alt="request flow example" style="margin: 0 auto;" />
|
||||
<div><i>simplified request flow diagram</i></div>
|
||||
</div>
|
||||
@ -182,6 +182,7 @@ to secure access to your Image Archive as well.
|
||||
|
||||
We've included a few recipes for common deployment scenarios. There are many,
|
||||
many possible configurations, so please don't feel limited to these setups.
|
||||
Please feel free to suggest or contribute your own recipes.
|
||||
|
||||
- Script Include
|
||||
- [Embedding the Viewer](deployment/recipes/embedded-viewer.md)
|
||||
|
||||
@ -1 +1,245 @@
|
||||
# Nginx + Image Archive
|
||||
|
||||
> DISCLAIMER! We make no claims or guarantees of this approach's security. If in
|
||||
> doubt, enlist the help of an expert and conduct proper audits.
|
||||
|
||||
At a certain point, you may want others to have access to your instance of the
|
||||
OHIF Viewer and its medical imaging data. This post covers one of many potential
|
||||
setups that accomplish that. Please note, noticably absent is user account
|
||||
control.
|
||||
|
||||
Do not use this recipe to host sensitive medical data on the open web. Depending
|
||||
on your company's policies, this may be an appropriate setup on an internal
|
||||
network when protected with a server's basic authentication. For a more robust
|
||||
setup, check out our [user account control recpie](./user-account-control.md)
|
||||
that builds on the lessons learned here.
|
||||
|
||||
## Overview
|
||||
|
||||
Our two biggest hurdles when hosting our image archive and web client are:
|
||||
|
||||
- Risks related to exposing our PACS to the netowrk
|
||||
- Cross-Origin Resource Sharing (CORS) requests
|
||||
|
||||
### Handling Web Requests
|
||||
|
||||
We mittigate our first issue by allowing [Nginx][nginx] to handle incoming web
|
||||
requests. Nginx is open source software for web serving, reverse proxying,
|
||||
caching, and more. It's designed for maximum performance and stability --
|
||||
allowing us to more reliably serve content than Orthanc's built-in server can.
|
||||
|
||||
More specifically, we accomplish this by using a
|
||||
[`reverse proxy`](https://en.wikipedia.org/wiki/Reverse_proxy) to retrieve
|
||||
resources from our image archive (Orthanc), and when accessing its web admin.
|
||||
|
||||
> A reverse proxy is a type of proxy server that retrieves resources on behalf
|
||||
> of a client from one or more servers. These resources are then returned to the
|
||||
> client, appearing as if they originated from the proxy server itself.
|
||||
|
||||
### CORS Issues
|
||||
|
||||
Cross-Origin Resource Sharing (CORS) is a mechanism that uses HTTP headers to
|
||||
tell a browser which web applications have permission to access selected
|
||||
resources from a server at a different origin (domain, protocol, port). IE. By
|
||||
default, a Web App located at `http://my-website.com` can't access resources
|
||||
hosted at `http://not-my-website.com`
|
||||
|
||||
We can solve this one of two ways:
|
||||
|
||||
1. Have our Image Archive located at the same domain as our Web App
|
||||
2. Add appropriate `Access-Control-Allow-*` HTTP headers
|
||||
|
||||
This solution uses the first approach, but you can see an example of the second
|
||||
in the `docker-compose` bundled with this project for local development:
|
||||
[HERE](#)
|
||||
|
||||
You can read more about CORS in this Medium article: [Understanding
|
||||
CORS][understanding-cors]
|
||||
|
||||
### Diagram
|
||||
|
||||
This setup allows us to create a setup similar to the one pictured below:
|
||||
|
||||
{% include "./../_nginx-image-archive-diagram.md" %}
|
||||
|
||||
- All web requests are routed through `nginx` on our `OpenResty` image
|
||||
- `/pacs` is a reverse proxy for `orthanc`'s `DICOM Web` endpoints
|
||||
- `/pacs-admin` is a reverse proxy for `orthanc`'s Web Admin
|
||||
- All static resources for OHIF Viewer are served up by `nginx` when a matching
|
||||
route for that resource is requested
|
||||
|
||||
## Getting Started
|
||||
|
||||
### Requirements
|
||||
|
||||
- Docker
|
||||
- [Docker for Mac](https://docs.docker.com/docker-for-mac/)
|
||||
- [Docker for Windows](https://docs.docker.com/docker-for-windows/)
|
||||
|
||||
_Not sure if you have `docker` installed already? Try running `docker --version`
|
||||
in command prompt or terminal_
|
||||
|
||||
### Setup
|
||||
|
||||
_Spin Things Up_
|
||||
|
||||
- Navigate to `<project-root>/docker/OpenResty-Orthanc` in your shell
|
||||
- Run `docker-compose up`
|
||||
|
||||
_Upload Your First Study_
|
||||
|
||||
- Navigate to `http://127.0.0.1/pacs-admin`
|
||||
- From the top right, select "Upload"
|
||||
- Click "Select files to upload..." (DICOM)
|
||||
- Click "Start the upload"
|
||||
- Navigate back to `http://127.0.0.1/` to view your studies in the Study List
|
||||
|
||||
### Troubleshooting
|
||||
|
||||
_Exit code 137_
|
||||
|
||||
This means Docker ran out of memory. Open Docker Desktop, go to the `advanced`
|
||||
tab, and increase the amount of Memory available.
|
||||
|
||||
_Cannot create container for service X_
|
||||
|
||||
Use this one with caution: `docker system prune`
|
||||
|
||||
_X is already running_
|
||||
|
||||
Stop running all containers:
|
||||
|
||||
- Win: `docker ps -a -q | ForEach { docker stop $_ }`
|
||||
- Linux: `docker stop $(docker ps -a -q)`
|
||||
|
||||
### Configuration
|
||||
|
||||
After verifying that everything runs with default configuration values, you will
|
||||
likely want to update:
|
||||
|
||||
- The domain: `http://127.0.0.1`
|
||||
|
||||
#### OHIF Viewer
|
||||
|
||||
The OHIF Viewer's configuration is imported from a static `.js` file and made
|
||||
available globally at `window.config`. The configuration we use is set to a
|
||||
specific file when we build the viewer, and determined by the env variable:
|
||||
`REACT_APP_CONFIG`. You can see where we set its value in the `dockerfile` for
|
||||
this solution:
|
||||
|
||||
`ENV REACT_APP_CONFIG=config/docker_openresty-orthanc.js`
|
||||
|
||||
You can find the configuration we're using here:
|
||||
`/public/config/docker_openresty-orthanc.js`
|
||||
|
||||
To rebuild the `webapp` image created by our `dockerfile` after updating the
|
||||
Viewer's configuration, you can run:
|
||||
|
||||
- `docker-compose build` OR
|
||||
- `docker-compose up --build`
|
||||
|
||||
#### Other
|
||||
|
||||
All other files are found in: `/docker/OpenResty-Orthanc/`
|
||||
|
||||
| Service | Configuration | Docs |
|
||||
| ----------------- | ---------------------------------------------- | ------------------------------------------- |
|
||||
| OHIF Viewer | [dockerfile][dockerfile] / [config.js][config] | You're reading them now! |
|
||||
| OpenResty (Nginx) | [`/nginx.conf`][config-nginx] | [lua-resty-openidc][lua-resty-openidc-docs] |
|
||||
| Orthanc | [`/orthanc.json`][config-orthanc] | [Here][orthanc-docs] |
|
||||
|
||||
## Next Steps
|
||||
|
||||
### Deploying to Production
|
||||
|
||||
While these configuration and docker-compose files model an environment suitable
|
||||
for production, they are not easy to deploy "as is". You can either:
|
||||
|
||||
- Manually recreate this environment and deploy built application files **OR**
|
||||
- Deploy to a cloud kubernetes provider like
|
||||
[Digital Ocean](https://www.digitalocean.com/products/kubernetes/) **OR**
|
||||
- [See a full list of cloud providers here](https://landscape.cncf.io/category=cloud&format=card-mode&grouping=category)
|
||||
- Find and follow your preferred provider's guide on setting up
|
||||
[swarms and stacks](https://docs.docker.com/get-started/)
|
||||
|
||||
### Adding SSL
|
||||
|
||||
Adding SSL registration and renewal for your domain with Let's Encrypt that
|
||||
terminates at Nginx is an incredibly important step toward securing your data.
|
||||
Here are some resources, specific to this setup, that may be helpful:
|
||||
|
||||
- [lua-resty-auto-ssl](https://github.com/GUI/lua-resty-auto-ssl)
|
||||
- [Let's Encrypt + Nginx](https://www.nginx.com/blog/using-free-ssltls-certificates-from-lets-encrypt-with-nginx/)
|
||||
|
||||
While we terminate SSL at Nginx, it may be worth using self signed certificates
|
||||
for communication between services.
|
||||
|
||||
- [SSL Termination for TCP Upstream Servers](https://docs.nginx.com/nginx/admin-guide/security-controls/terminating-ssl-tcp/)
|
||||
|
||||
### Use PostgresSQL w/ Orthanc
|
||||
|
||||
Orthanc can handle a large amount of data and requests, but if you find that
|
||||
requests start to slow as you add more and more studies, you may want to
|
||||
configure your Orthanc instance to use PostgresSQL. Instructions on how to do
|
||||
that can be found in the
|
||||
[`Orthanc Server Book`](http://book.orthanc-server.com/users/docker.html), under
|
||||
"PostgreSQL and Orthanc inside Docker"
|
||||
|
||||
### Improving This Guide
|
||||
|
||||
Here are some improvements this guide would benefit from, and that we would be
|
||||
more than happy to accept Pull Requests for:
|
||||
|
||||
- SSL Support
|
||||
- Complete configuration with `.env` file (or something similar)
|
||||
- Any security issues
|
||||
- One-click deploy to a cloud provider
|
||||
|
||||
## Resources
|
||||
|
||||
### Misc. Helpful Commands
|
||||
|
||||
_Check if `nginx.conf` is valid:_
|
||||
|
||||
```bash
|
||||
docker run --rm -t -a stdout --name my-openresty -v $PWD/config/:/usr/local/openresty/nginx/conf/:ro openresty/openresty:alpine-fat openresty -c /usr/local/openresty/nginx/conf/nginx.conf -t
|
||||
```
|
||||
|
||||
_Interact w/ running container:_
|
||||
|
||||
`docker exec -it CONTAINER_NAME bash`
|
||||
|
||||
_List running containers:_
|
||||
|
||||
`docker ps`
|
||||
|
||||
### Referenced Articles
|
||||
|
||||
For more documentation on the software we've chosen to use, you may find the
|
||||
following resources helpful:
|
||||
|
||||
- [Orthanc for Docker](http://book.orthanc-server.com/users/docker.html)
|
||||
- [OpenResty Guide](http://www.staticshin.com/programming/definitely-an-open-resty-guide/)
|
||||
- [Lua Ngx API](https://openresty-reference.readthedocs.io/en/latest/Lua_Nginx_API/)
|
||||
|
||||
For a different take on this setup, check out the repository one of our
|
||||
community members put together:
|
||||
|
||||
- [mjstealey/ohif-orthanc-dimse-docker](https://github.com/mjstealey/ohif-orthanc-dimse-docker)
|
||||
|
||||
<!--
|
||||
Links
|
||||
-->
|
||||
|
||||
<!-- prettier-ignore-start -->
|
||||
<!-- DOCS -->
|
||||
[nginx]: https://www.nginx.com/resources/glossary/nginx/
|
||||
[understanding-cors]: https://medium.com/@baphemot/understanding-cors-18ad6b478e2b
|
||||
[orthanc-docs]: http://book.orthanc-server.com/users/configuration.html#configuration
|
||||
[lua-resty-openidc-docs]: https://github.com/zmartzone/lua-resty-openidc
|
||||
<!-- SRC -->
|
||||
[config]: #
|
||||
[dockerfile]: #
|
||||
[config-nginx]: #
|
||||
[config-orthanc]: #
|
||||
<!-- prettier-ignore-end -->
|
||||
|
||||
@ -1 +1,66 @@
|
||||
# Scope of Project
|
||||
|
||||
The OHIF Viewer is a web based medical imaging viewer. This allows it to be used
|
||||
on almost any device, anywhere. The OHIF Viewer is what is commonly reffered to
|
||||
as a ["Dumb Client"][simplicable]
|
||||
|
||||
> A dumb client is software that fully depends on a connection to a server or
|
||||
> cloud service for its functionality. Without a network connection, the
|
||||
> software offers nothing useful. - [simplicable.com][simplicable]
|
||||
|
||||
While the Viewer persists some data, it's scope is limited to caching things
|
||||
like user preferences and previous query paramaters. Because of this, the Viewer
|
||||
has been built to be highly configurable to work with almost any web accessible
|
||||
data source.
|
||||
|
||||

|
||||
|
||||
To be more specific, the OHIF Viewer is a collection of HTML, JS, and CSS files.
|
||||
These can be delivered to your end users however you would like:
|
||||
|
||||
- From the local networok
|
||||
- From a remote web server
|
||||
- From a CDN (content delivery network)
|
||||
- From a service-worker's cache
|
||||
- etc.
|
||||
|
||||
These "static asset" files are referred to collectively as a "Progressive Web
|
||||
Application" (PWA), and have the same capabilities and limitations that all PWAs
|
||||
have.
|
||||
|
||||
All studies, series, images, imageframes, metadata, and the images themselves
|
||||
must come from an external source. There are many, many ways to provide this
|
||||
information, the OHIF Viewer's scope **DOES NOT** encompass providing _any_
|
||||
data; only the configuration necessary to interface with one or more of these
|
||||
many data sources. The OHIF Viewer's scope **DOES** include configuration and
|
||||
support for services that are protected with OpenID-Connect.
|
||||
|
||||
In an effort to aide our users and contributors, we attempt to provide several
|
||||
[deployment and hosting recipes](./../deployment/index.md) as potential starting
|
||||
points. These are not meant to be rock solid, production ready, solutions; like
|
||||
most recipes, they should be augmented to best fit you and your organization's
|
||||
taste, preferences, etc.
|
||||
|
||||
## FAQ
|
||||
|
||||
_Am I able to cache studies for offline viewing?_
|
||||
|
||||
Not currently. A web page's offline cache capabilities are limited and somewhat
|
||||
volatile (mostly imposed at the browser vendor level). For more robust offline
|
||||
caching, you may want to consider a server on the local network, or packaging
|
||||
the OHIF Viewer as a desktop application.
|
||||
|
||||
_Does the OHIF Viewer work with the local filesystem?_
|
||||
|
||||
It is possible to accomplish this through extensions; however, for an user
|
||||
experience that accomodates a large number of studies, you would likely need to
|
||||
package the OHIF Viewer as an [Electron app][electron].
|
||||
|
||||
<!--
|
||||
Links
|
||||
-->
|
||||
|
||||
<!-- prettier-ignore-start -->
|
||||
[simplicable]: https://simplicable.com/new/dumb-client
|
||||
[electron]: https://electronjs.org/
|
||||
<!-- prettier-ignore-end -->
|
||||
|
||||
@ -4,16 +4,14 @@
|
||||
|
||||
We accept and triage bug reports through Github primarily.
|
||||
|
||||
1. [Create a Github account](https://github.com/join)
|
||||
2. Search the current [Issue List](https://github.com/OHIF/Viewers/issues) to
|
||||
ensure you are not creating a duplicate issue.
|
||||
|
||||
If your issue already exists, post a comment to show us that this issue also
|
||||
affects you.
|
||||
|
||||
3. If no prior issue exists,
|
||||
[Create a New Issue](https://github.com/OHIF/Viewers/issues/new) on the
|
||||
repository.
|
||||
- [Create a Github account](https://github.com/join)
|
||||
- Search the current [Issue List](https://github.com/OHIF/Viewers/issues) to
|
||||
ensure you are not creating a duplicate issue.
|
||||
- If your issue already exists, post a comment to show us that this issue also
|
||||
affects you.
|
||||
- If no prior issue exists,
|
||||
[Create a New Issue](https://github.com/OHIF/Viewers/issues/new) on the
|
||||
repository.
|
||||
|
||||
Some tips for filing a new issue:
|
||||
|
||||
|
||||
26
public/config/docker_openresty-orthanc.js
Normal file
26
public/config/docker_openresty-orthanc.js
Normal file
@ -0,0 +1,26 @@
|
||||
window.config = {
|
||||
routerBasename: '/',
|
||||
relativeWebWorkerScriptsPath: '',
|
||||
servers: {
|
||||
// This is an array, but we'll only use the first entry for now
|
||||
dicomWeb: [
|
||||
{
|
||||
name: 'Orthanc',
|
||||
wadoUriRoot: 'http://127.0.0.1/pacs/wado',
|
||||
qidoRoot: 'http://127.0.0.1/pacs/dicom-web',
|
||||
wadoRoot: 'http://127.0.0.1/pacs/dicom-web',
|
||||
qidoSupportsIncludeField: false,
|
||||
imageRendering: 'wadors',
|
||||
thumbnailRendering: 'wadors',
|
||||
// REQUIRED TAG:
|
||||
// https://github.com/OHIF/ohif-core/blob/59e1e04b92be24aee5d4402445cb3dcedb746995/src/studies/retrieveStudyMetadata.js#L54
|
||||
// TODO: Remove tag after https://github.com/OHIF/ohif-core/pull/19 is merged and we bump version
|
||||
requestOptions: {
|
||||
// undefined to use JWT + Bearer auth
|
||||
// auth: 'orthanc:orthanc',
|
||||
requestFromBrowser: true,
|
||||
},
|
||||
},
|
||||
],
|
||||
},
|
||||
}
|
||||
Loading…
Reference in New Issue
Block a user