YourPHR lets you create a secure, private personal health record that never leaves your hands — self-hosted, open source, and yours. Project home: yourphr.org
Mission: Your medical records, immediately and in your hands — for free. Fulfilling the 21st Century Cures Act (2016).
Note
YourPHR is a standalone, community-maintained continuation of Fasten OnPrem, carried forward by @jwilleke to keep a fully open-source, self-hostable PHR going after upstream's hosted sync relay (Lighthouse) moved into the commercial Fasten Connect product — which broke provider sync in the open-source build.
The original work is by Jason Kulatunga (@AnalogJ) and Alex Szilagyi (@alexszilagyi) under the GNU GPL v3 license. YourPHR remains GPL v3 and retains full attribution.
Focus: a free, self-hosted Personal Health Record anyone can run — including improved display support for non-US-Core FHIR R4 exports (e.g. Veradigm/FollowMyHealth). See docs/Roadmap.md.
Important
YourPHR is an open-source, self-hosted Personal Health Record app for managing and viewing your own medical data. It does not integrate with EHRs directly — you import FHIR R4 bundles exported from patient portals, or enter data manually.
YourPHR is not affiliated with Fasten Health, Inc. or its commercial Fasten Connect product.
Like many of you, I've worked for many companies over my career. In that time, I've had multiple health, vision and dental insurance providers, and visited many different clinics, hospitals and labs to get procedures & tests done.
Recently I had a semi-serious medical issue, and I realized that my medical history (and the medical history of my family members) is a lot more complicated than I realized and distributed across the many healthcare providers I've used over the years. I wanted a single (private) location to store our medical records, and I just couldn't find any software that worked as I'd like:
- self-hosted/offline - this is my medical history, I'm not willing to give it to some random multi-national corporation to data-mine and sell
- It should aggregate my data from multiple healthcare providers (insurance companies, hospital networks, clinics, labs) across multiple industries (vision, dental, medical) -- all in one dashboard
- open source - the code should be available for contributions & auditing
So, I built it.
YourPHR is an open-source, self-hosted, personal/family electronic medical record viewer. It continues the original project's vision (described above by its original author) as a community-maintained, standalone app.
It's pretty basic right now, but it's designed with a easily extensible core around a solid foundation:
- Self-hosted
- Designed for families, not Clinics (unlike OpenEMR and other popular EMR systems)
- Supports the Medical industry's (semi-standard) FHIR protocol
- (Future) Multi-user support for household/family use
- Condition specific user Dashboards & tracking for diagnostic tests
- (Future) Vaccination & condition specific recommendations using NIH/WHO clinical care guidelines (HEDIS/CQL)
- (Future) ChatGPT-style interface to query your own medical history (offline)
- (Future) Integration with smart-devices & wearables
First, if you don't have Docker installed on your computer, get Docker by following this install guide.
Next, run the following commands from the Windows command line or Mac/Linux terminal in order to download and start the YourPHR docker container.
One command. One image holding the server and the app, and one volume holding everything the instance owns.
docker run -d --name yourphr --restart unless-stopped \
-p 9090:8080 \
-v ./data:/opt/yourphr/data \
ghcr.io/jwilleke/yourphr:3.2.0./data is the directory to back up: the database, the config store and the generated signing key
all live there. Pin a version rather than a floating tag — :latest moves only when a release is
cut, but it does move.
Optional, before first start — database encryption. The key is read from a .env on that same
volume, and a database written unencrypted cannot be encrypted later by restarting with a key set.
So if you want it, decide now:
mkdir -p ./data
printf 'YOURPHR_DATABASE_ENCRYPTION_KEY=%s\nYOURPHR_BACKUP_ENCRYPTION_KEY=%s\n' \
"$(openssl rand -hex 32)" "$(openssl rand -hex 32)" > ./data/.env
chmod 600 ./data/.envRecord those keys somewhere that is not this machine. If the volume is lost and the keys with it, the database and every backup are permanently unreadable. The app warns about this on every start, and it means it.
A compose file is not shipped yet (#641), along with example Kubernetes manifests and a bare-metal path. The
docker runabove is the equivalent in the meantime.
If you prefer not to run the set_env.sh script, you can configure the .env file manually. You will need to create a .env file and add the following variables:
-
Find your hostname:
hostname
-
Find your local IP address:
- macOS:
ifconfig | grep "inet " | grep -v 127.0.0.1 | cut -d' ' -f2 - Linux:
hostname -I | awk '{print $1}' - Windows (Command Prompt):
ipconfig | findstr /i "ipv4"
- macOS:
-
Create and edit the
.envfile: Create a file named.envin the same directory as yourdocker-compose.ymland add the following lines, replacing<your_hostname>and<your_ip_address>with the values you found:HOSTNAME=<your_hostname> IP=<your_ip_address> PORT=9090
Next, open a browser to http://localhost:9090
The docker-compose flow above is the easy path, but YourPHR is deployment-agnostic — it is a single Go binary with an embedded SQLite database and no required external services, so it does not depend on any particular orchestrator. You can also run it via plain docker run, on bare metal, or in Kubernetes, and configure it via .env/.env_custom, YOURPHR_* environment variables, or the Admin → Configuration screen (layered, lowest → highest: shipped defaults < instance overrides in <data>/config/app-custom-config.json < YOURPHR_* env). See docs/configuration-system.md.
➡️ See docs/deployment/README.md for every deployment option (docker-compose / docker run / bare metal / Kubernetes), the configuration model + precedence, the full config-key reference, and how secrets are handled (the DB encryption key, the auto-generated JWT key, and per-source OAuth client_secrets stored in the DB).
The application speaks plain HTTP. It does not terminate TLS and does not generate a
certificate authority — put a reverse proxy in front of it and let that hold the certificate. That
is how the maintainer's own instance runs (Traefik, with the app behind it on :8080).
Earlier versions of YourPHR — the Go stack, through v2.10.3 — generated their own "YourPHR CA" at
startup and wrote certs/rootCA.pem, which you then imported into your browser's trust store. v3
does none of that. If you are following older notes: there is no certs/ directory to find, and
https://localhost:9090 will not answer.
For a LAN-only instance, the simplest options are Caddy (which obtains and renews certificates on its own), or any reverse proxy you already run. Example manifests and a worked compose file are #641.
Requires a local clone, Node 24 and the frontend's toolchain.
cp .env.dev.example .env
make serve-server # the API on :8080
make serve-frontend # the Angular dev server, proxying to itmake test runs both suites; make test-e2e builds the app and drives a real browser over it.
One image holds the TypeScript server and the Angular app, built from the same commit.
docker run -d --name yourphr --restart unless-stopped \
-p 9090:8080 \
-v ./data:/opt/yourphr/data \
ghcr.io/jwilleke/yourphr:3.2.0Everything the instance owns lives in that one volume — the database, the config store, the
generated signing key. It is the directory to back up. Use a version tag rather than a floating
one; :latest moves only when a release is cut.
The image takes a command, so it can also do the jobs that are not "serve":
docker run --rm ghcr.io/jwilleke/yourphr:3.2.0 help # every command and its flags
docker run --rm ghcr.io/jwilleke/yourphr:3.2.0 version # which build this actually isAt this point you'll be redirected to the login page.
You do not create an account — the first start already made one for you.
# docker
docker exec yourphr cat /opt/yourphr/data/.admin_bootstrap_password
# or read it from the mounted volume
cat ./data/.admin_bootstrap_passwordSign in as admin with that password, then change it. The file is deleted once that account has
signed in, so read it before you do.
Important
The first start creates your admin account for you. It generates a password and writes it to
<data>/.admin_bootstrap_password (mode 0600); the startup log names the file, never the value.
Sign in with it once and change it. That account controls configuration, the database (backup,
restore, download), users, the provider catalog and the logs.
Self-service signup is closed by default (signup.enabled). Nobody can register themselves
until you turn it on at Admin → Configuration, and an instance reachable from the internet is
safe to leave running while you get to it. Until then, add household members at Admin →
Users. Anyone who does sign up gets an ordinary user account, never an admin.
If you lose the password, the image can issue a new one without touching the database:
docker run --rm -v "$PWD/data:/opt/yourphr/data" ghcr.io/jwilleke/yourphr:3.2.0 reset-password --user <account> --data /opt/yourphr/data.
It writes the new password to <data>/.recovery_password and ends that account's sessions.
See docs/deployment/README.md.
Note
NOTE: Multi-user features are a work in progress. This section describes the eventual goals.
YourPHR is designed to work well for an individual or a family. Since it is self-hosted, by nature the person running the service will have full root access to all user records. For most families, this is perfect! If you need stronger security, YourPHR might not be for you.
YourPHR assumes that all records connected from a single user account (from one or more sources) belong to a single individual, and thus will show aggregations that will only make sense for a single person. Be careful to not connect sources for different people to the same YourPHR user account.
Tracking health data for multiple family members works by creating new user accounts for each person. Any user with the admin role can manage users and permissions. Any user can be granted access (by an admin) to view another user's records. Through this mechanism, it's easy to setup any family configuration needed. For example: a family of four can have two parents that can each see the records of the two children.
It is also possible to create users with the viewer role that only have access to view records of other users. This can be used to share records with a caregiver.
This allows for a more complex example:
- a family consisting of 2 parents, and 2 children and a caregiver (nurse, babysitter, grandparent).
- both parents need to be able to access both children's records, and maybe each-others
- the caregiver should have view-only access to 1 or both children, but not the parents.
Have a question? Search existing issues or open a new one. (A project FAQ will live at yourphr.org as YourPHR grows.)
Have questions? Need help? Found a bug? Create an issue and we'll do our best to help you out.
Please see the CONTRIBUTING.md for instructions for how to develop and contribute to the YourPHR codebase.
Work your magic and then submit a pull request. We love pull requests!
If you find the documentation lacking, help us out and update this README.md. If you don't have the time to work on YourPHR, but found something we should know about, please submit an issue.
We use SemVer for versioning. For the versions available, see the tags on this repository.
- Jason Kulatunga - Initial Development - @AnalogJ
- Alex Szilagyi - Co-Author - @alexszilagyi
