61 Commits

Author SHA1 Message Date
4813f63da5 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m55s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-08 13:12:35 +06:00
04ef3b0b55 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m43s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-08 05:03:04 +06:00
25f0017595 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m5s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-08 04:48:06 +06:00
a5e39b94d3 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m43s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 10s
2026-03-08 00:08:16 +06:00
9968c28e5c #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m37s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 10s
2026-03-07 23:51:13 +06:00
7125b57aa2 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m34s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 10s
2026-03-07 23:31:52 +06:00
958eba6c44 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m42s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 10s
2026-03-07 22:44:54 +06:00
fcb5002641 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 10m21s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 10s
2026-03-07 22:20:07 +06:00
b7c824b34a #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m52s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 22:08:18 +06:00
e8cf5ab9be #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m59s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-07 21:54:05 +06:00
c35bc8e8a4 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 6m33s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 21:42:57 +06:00
c2e7119335 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 3m49s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 21:32:34 +06:00
c6903044aa #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 1m44s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 21:05:46 +06:00
aca893377c #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 3m22s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 20:56:36 +06:00
ccf6fef643 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 1m24s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 20:53:06 +06:00
c80f2f3a40 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 46s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 20:48:42 +06:00
804a7ff3d6 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 2m7s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 20:40:50 +06:00
db2f074cbe #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 3m52s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 20:22:12 +06:00
7731328402 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 10m54s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 20:02:55 +06:00
a5d41e88de #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 9m5s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 19:36:05 +06:00
5ca0ffdd86 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m14s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 19:28:52 +06:00
d82e428e24 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m8s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 18:57:46 +06:00
dc43651043 # 2026-03-07 18:45:16 +06:00
2fc782a082 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m46s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 18:30:22 +06:00
2db03cd2cc #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 9s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 18:29:27 +06:00
323abf04dc #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 5s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 18:28:13 +06:00
e3de38a794 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m47s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 18:04:46 +06:00
9ed33227d3 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m47s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 17:47:51 +06:00
8ddb62ab26 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m50s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 17:30:52 +06:00
c2be28e714 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m13s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 17:16:58 +06:00
dee47229d7 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m54s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 17:01:01 +06:00
a60c2c6c21 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m51s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 16:42:54 +06:00
b759890259 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m49s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 16:28:14 +06:00
c9cf4c5157 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m48s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 15:41:05 +06:00
45505bd4b8 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m47s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 15:20:14 +06:00
3e1f6979b5 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m44s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 13:57:53 +06:00
c39615ff85 #
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m55s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 13:49:26 +06:00
06d3a6ef13 #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m50s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 13:41:30 +06:00
8c8b8f032c #
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m53s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 13:32:02 +06:00
4d24e3f30c modified history template
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m38s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 05:40:28 +06:00
57aba6ddc6 modified history template and workflow
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m36s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 05:32:12 +06:00
665ba07e37 modified history template
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m41s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 05:20:59 +06:00
18f71a6a04 updated history template
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 5m40s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 8s
2026-03-07 04:58:21 +06:00
83ad838fc4 removed js from template
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m40s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-07 04:42:27 +06:00
63ca3fa44f updated template javascript
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m45s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 04:25:27 +06:00
fdca2f9c3b fixed template javascript
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 4m42s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 04:08:55 +06:00
3b48bd79e2 updated template
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m30s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-07 03:49:23 +06:00
b620db17d5 updated workflow
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m35s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-07 03:30:16 +06:00
f2201f4da8 updated history template
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m36s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-07 03:09:35 +06:00
b3cf356b32 modified history template
All checks were successful
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Successful in 6m49s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Successful in 9s
2026-03-07 02:53:09 +06:00
7cb360b1d2 added history template
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 5m38s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 02:40:13 +06:00
6beb9318fe fixed workflow
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 5m34s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 02:20:58 +06:00
423d1c271f modified workflow
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Has been cancelled
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been cancelled
2026-03-07 02:12:12 +06:00
53190dddd6 removed cleanup workflow
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 29s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:58:35 +06:00
5205c06bab modified cleanup workflow
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 28s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:46:27 +06:00
b89620b4ed Added cleanup workflow
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 29s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:40:48 +06:00
c195390fe7 fixed ci/cd workflow to save disk space
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 29s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:33:29 +06:00
e6cb213212 fixed ci workflow to save disk space
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 40s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:30:57 +06:00
0bce070ae2 fixed workflow to save disk space
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 29s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:28:06 +06:00
9bf4b2d457 modified workflow to save disk space
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 5s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:23:26 +06:00
68c748b06e Add debugging to workflow and bump to 0.2.5
Some checks failed
FHIR IG CI/CD Pipeline with Version Persistence / build-ig (push) Failing after 29s
FHIR IG CI/CD Pipeline with Version Persistence / deploy (push) Has been skipped
2026-03-07 01:06:10 +06:00
5 changed files with 628 additions and 349 deletions

View File

@@ -2,9 +2,8 @@ name: FHIR IG CI/CD Pipeline with Version Persistence
on: on:
push: push:
branches: [ main, develop ]
tags: tags:
- 'v*.*.*' # Trigger on version tags like v0.3.0 - 'v*.*.*'
pull_request: pull_request:
branches: [ main ] branches: [ main ]
@@ -14,357 +13,616 @@ env:
jobs: jobs:
build-ig: build-ig:
runs-on: ubuntu-latest runs-on: fhir-runner
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@v3 uses: actions/checkout@v3
with: with:
fetch-depth: 0 fetch-depth: 0
- name: Extract version from IG - name: Extract version from IG
id: version id: version
run: | run: |
# Extract version from ImplementationGuide resource VERSION=$(grep -oP '<version value="\K[^"]+' input/bd.fhir.core.xml | head -1)
VERSION=$(grep -oP '<version value="\K[^"]+' input/bd.fhir.core.xml | head -1)
if [ -z "$VERSION" ]; then if [ -z "$VERSION" ]; then
echo "ERROR: Could not extract version from ImplementationGuide XML" echo "ERROR: Could not extract version from ImplementationGuide XML"
exit 1
fi
echo "Extracted version: $VERSION"
echo "version=$VERSION" >> $GITHUB_OUTPUT
# Determine if this is a release build (git tag) or dev build
if [[ "$GITHUB_REF" == refs/tags/v* ]]; then
BUILD_TYPE="release"
TAG_VERSION="${GITHUB_REF#refs/tags/v}"
# Verify tag matches IG version
if [ "$TAG_VERSION" != "$VERSION" ]; then
echo "ERROR: Git tag version ($TAG_VERSION) doesn't match IG version ($VERSION)"
exit 1 exit 1
fi fi
else
BUILD_TYPE="dev"
fi
echo "build_type=$BUILD_TYPE" >> $GITHUB_OUTPUT echo "Extracted version: $VERSION"
echo "Build type: $BUILD_TYPE" echo "version=$VERSION" >> $GITHUB_OUTPUT
- name: Install Docker CLI if [[ "$GITHUB_REF" == refs/tags/v* ]]; then
run: | BUILD_TYPE="release"
apt-get update TAG_VERSION="${GITHUB_REF#refs/tags/v}"
apt-get install -y docker.io
docker --version
- name: Build FHIR IG if [ "$TAG_VERSION" != "$VERSION" ]; then
run: | echo "ERROR: Git tag version ($TAG_VERSION) doesn't match IG version ($VERSION)"
echo "Building FHIR IG version ${{ steps.version.outputs.version }}..." exit 1
fi
else
BUILD_TYPE="dev"
fi
CONTAINER_ID=$(docker create \ echo "build_type=$BUILD_TYPE" >> $GITHUB_OUTPUT
hl7fhir/ig-publisher-base:latest \ echo "Build type: $BUILD_TYPE"
/bin/bash -c "cp -r /home/publisher/ig /tmp/build && cd /tmp/build && _updatePublisher.sh -y && _genonce.sh")
echo "Container ID: $CONTAINER_ID" - name: Prepare package-list.json and history.xml for IG Publisher
run: |
VERSION="${{ steps.version.outputs.version }}"
BUILD_TYPE="${{ steps.version.outputs.build_type }}"
DATE=$(date +%Y-%m-%d)
docker cp $(pwd)/. $CONTAINER_ID:/home/publisher/ig/ export VERSION DATE BUILD_TYPE
docker start -a $CONTAINER_ID
EXIT_CODE=$?
# Copy outputs echo "📋 Preparing package-list.json and history.xml for IG Publisher..."
echo "Copying outputs from container..."
docker cp $CONTAINER_ID:/tmp/build/output ./output || echo "Warning: No output directory"
docker cp $CONTAINER_ID:/tmp/build/fsh-generated ./fsh-generated || echo "No FSH generated"
docker cp $CONTAINER_ID:/tmp/build/input-cache ./input-cache || echo "No input-cache"
docker cp $CONTAINER_ID:/tmp/build/temp ./temp || echo "No temp directory"
if [ $EXIT_CODE -ne 0 ]; then if [ ! -f "package-list.json" ]; then
echo "Build failed, showing logs:" echo "⚠️ package-list.json not found in repo root"
docker logs $CONTAINER_ID echo "Creating initial package-list.json..."
docker rm $CONTAINER_ID cat > package-list.json << 'PKGEOF'
exit 1 {
fi "package-id": "bd.fhir.core",
"title": "Bangladesh Core FHIR Implementation Guide",
"canonical": "https://fhir.dghs.gov.bd/core",
"introduction": "The Bangladesh Core FHIR IG defines national base profiles, value sets, and extensions for health data interoperability.",
"list": [
{
"version": "current",
"desc": "Continuous Integration Build (latest in version control)",
"path": "https://fhir.dghs.gov.bd/core/",
"status": "ci-build",
"current": true
}
]
}
PKGEOF
fi
docker rm $CONTAINER_ID python3 << 'PYEOF'
import json
import os
import sys
if [ ! -f "output/index.html" ]; then version = os.environ.get('VERSION', '')
echo "ERROR: Build failed - no index.html" date = os.environ.get('DATE', '')
exit 1 build_type = os.environ.get('BUILD_TYPE', '')
fi
echo "✅ Build successful!" with open('package-list.json', 'r', encoding='utf-8') as f:
pkg_list = json.load(f)
- name: Update package-list.json and package-feed.xml for releases if 'list' not in pkg_list or not isinstance(pkg_list['list'], list):
if: steps.version.outputs.build_type == 'release' print("ERROR: package-list.json does not contain a valid 'list' array")
run: | sys.exit(1)
VERSION="${{ steps.version.outputs.version }}"
DATE=$(date +%Y-%m-%d)
DATETIME=$(date -u +%Y-%m-%dT%H:%M:%SZ)
# Update package-list.json and package-feed.xml current_entries = [e for e in pkg_list['list'] if e.get('version') == 'current']
cat > update-registry-files.py << 'EOF' if not current_entries:
import json pkg_list['list'].insert(0, {
import sys "version": "current",
import xml.etree.ElementTree as ET "desc": "Continuous Integration Build (latest in version control)",
from datetime import datetime "path": "https://fhir.dghs.gov.bd/core/",
"status": "ci-build",
"current": True
})
version = sys.argv[1] if build_type == 'release':
date = sys.argv[2] version_entry = None
datetime_iso = sys.argv[3] for e in pkg_list['list']:
if e.get('version') == version:
version_entry = e
break
if version_entry is None:
new_entry = {
"version": version,
"date": date,
"desc": f"Release {version}",
"path": f"https://fhir.dghs.gov.bd/core/{version}/",
"status": "trial-use",
"sequence": "STU 1"
}
# ========== Update package-list.json ========== insert_index = 1
with open('package-list.json', 'r') as f: for i, entry in enumerate(pkg_list['list']):
pkg_list = json.load(f) if entry.get('version') == 'current':
insert_index = i + 1
break
# Update current build path pkg_list['list'].insert(insert_index, new_entry)
for entry in pkg_list['list']: print(f"✅ Added version {version} to package-list.json")
if entry['version'] == 'current': else:
entry['path'] = 'https://fhir.dghs.gov.bd/core/' print(f" Version {version} already exists in package-list.json")
break else:
print(" Dev build - using existing package-list.json without release modification")
# Check if this version already exists with open('package-list.json', 'w', encoding='utf-8') as f:
version_exists = any(e['version'] == version for e in pkg_list['list']) json.dump(pkg_list, f, indent=2, ensure_ascii=False)
PYEOF
if not version_exists: echo "🔍 Validating package-list.json..."
# Add new version entry python3 -m json.tool package-list.json > /dev/null && echo "✅ Valid JSON" || (echo "❌ Invalid JSON!" && exit 1)
new_entry = {
"version": version,
"date": date,
"desc": f"Release {version}",
"path": f"https://fhir.dghs.gov.bd/core/{version}/",
"status": "trial-use",
"sequence": "STU 1"
}
# Insert after 'current' entry
pkg_list['list'].insert(1, new_entry)
else:
# Update existing entry
for entry in pkg_list['list']:
if entry['version'] == version:
entry['date'] = date
entry['path'] = f"https://fhir.dghs.gov.bd/core/{version}/"
break
with open('output/package-list.json', 'w') as f: echo "📂 Ensuring package-list.json is in required locations..."
json.dump(pkg_list, f, indent=2) mkdir -p input
cp package-list.json input/package-list.json
print(f"✅ Updated package-list.json with version {version}") echo "📝 Generating static history.xml from package-list.json..."
mkdir -p input/pagecontent
# ========== Update package-feed.xml ========== python3 << 'PYEOF'
# Register namespaces import json
ET.register_namespace('', 'http://www.w3.org/2005/Atom') import os
from html import escape
# Parse existing feed os.makedirs('input/pagecontent', exist_ok=True)
tree = ET.parse('package-feed.xml')
root = tree.getroot()
ns = {'atom': 'http://www.w3.org/2005/Atom'}
# Update feed updated timestamp with open('package-list.json', 'r', encoding='utf-8') as f:
updated_elem = root.find('atom:updated', ns) pkg_list = json.load(f)
if updated_elem is not None:
updated_elem.text = datetime_iso
# Check if entry for this version already exists xml = '''<?xml version="1.0" encoding="UTF-8"?>
entry_exists = False <div xmlns="http://www.w3.org/1999/xhtml">
for entry in root.findall('atom:entry', ns):
title = entry.find('atom:title', ns)
if title is not None and version in title.text:
entry_exists = True
# Update existing entry timestamp
entry_updated = entry.find('atom:updated', ns)
if entry_updated is not None:
entry_updated.text = datetime_iso
break
# If entry doesn't exist, create new one <p>This page provides the version history for the Bangladesh Core FHIR Implementation Guide.</p>
if not entry_exists:
new_entry = ET.Element('{http://www.w3.org/2005/Atom}entry')
title = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}title') <p>For a machine-readable version history see <a href="package-list.json">package-list.json</a>.</p>
title.text = f"bd.fhir.core version {version}"
link = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}link') <p><b>Published Versions</b></p>
link.set('rel', 'alternate')
link.set('href', f"https://fhir.dghs.gov.bd/core/{version}/")
entry_id = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}id') <table class="grid table table-striped table-bordered table-hover">
entry_id.text = f"https://fhir.dghs.gov.bd/core/{version}/" <thead>
<tr>
<th>Version</th>
<th>Date</th>
<th>Status</th>
<th>Description</th>
</tr>
</thead>
<tbody>
'''
entry_updated = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}updated') def version_key(v):
entry_updated.text = datetime_iso try:
return tuple(int(x) for x in v.split('.'))
except:
return (0,)
summary = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}summary') published = [
summary.text = f"Release {version} of Bangladesh Core FHIR Implementation Guide" e for e in pkg_list['list']
if e.get('version') and e.get('version') != "current"
]
# Insert new entry at the beginning (after feed metadata) # Sort newest version first
# Find the position after the last feed-level element published.sort(
insert_pos = 0 key=lambda e: version_key(e.get("version", "0.0.0")),
for i, child in enumerate(root): reverse=True
if child.tag.endswith('entry'): )
insert_pos = i
break
insert_pos = i + 1
root.insert(insert_pos, new_entry) published_found = False
first_row = True
# Write updated feed for entry in published:
tree.write('output/package-feed.xml', encoding='utf-8', xml_declaration=True) published_found = True
print(f"✅ Updated package-feed.xml with version {version}")
EOF version = escape(entry.get('version', 'Unknown'))
date = escape(entry.get('date', 'N/A'))
desc = escape(entry.get('desc', ''))
path = escape(entry.get('path', '#'))
python3 update-registry-files.py "$VERSION" "$DATE" "$DATETIME" status_val = entry.get('status', 'unknown')
# Copy updated files if status_val == "trial-use":
cp output/package-list.json package-list.json status = '<span class="badge bg-info">Trial Use</span>'
cp output/package-feed.xml package-feed.xml elif status_val == "normative":
status = '<span class="badge bg-success">Normative</span>'
else:
status = f'<span class="badge bg-secondary">{escape(status_val)}</span>'
echo "📋 Updated registry files (package-list.json and package-feed.xml)" badge = '<span class="badge bg-success">Latest</span> ' if first_row else ''
- name: Prepare deployment artifact xml += f'''
run: | <tr>
VERSION="${{ steps.version.outputs.version }}" <td><a href="{path}">{badge}{version}</a></td>
BUILD_TYPE="${{ steps.version.outputs.build_type }}" <td>{date}</td>
<td>{status}</td>
<td>{desc}</td>
</tr>
'''
first_row = False
if not published_found:
xml += '''
<tr>
<td colspan="4">No published versions available yet.</td>
</tr>
'''
xml += '''
</tbody>
</table>
<p class="lead"><b>Continuous Integration Build</b></p>
'''
current_entry = None
for entry in pkg_list['list']:
if entry.get('version') == 'current':
current_entry = entry
break
if current_entry:
path = escape(current_entry.get('path', pkg_list.get('canonical', '') + '/'))
xml += f'''
<p>The latest development build is available at:
<a href="{path}">{path}</a></p>
'''
else:
xml += '''
<p><i>No CI build entry found in package-list.json.</i></p>
'''
xml += '''
</div>
'''
with open('input/pagecontent/history.xml', 'w', encoding='utf-8') as f:
f.write(xml)
print("✅ Generated static history.xml")
print(f" File location: {os.path.abspath('input/pagecontent/history.xml')}")
print(f" File size: {os.path.getsize('input/pagecontent/history.xml')} bytes")
PYEOF
if [ -f "input/pagecontent/history.xml" ]; then
echo "✅ Verified: history.xml exists"
echo " First 20 lines:"
head -20 input/pagecontent/history.xml
else
echo "❌ ERROR: history.xml was not created!"
exit 1
fi
echo "✅ Pre-build preparation complete:"
echo " - Root: $(pwd)/package-list.json"
echo " - Input: $(pwd)/input/package-list.json"
echo " - History: $(pwd)/input/pagecontent/history.xml"
echo "==============================="
echo "PACKAGE LIST USED FOR BUILD:"
cat package-list.json
echo "-------------------------------"
echo "INPUT COPY:"
cat input/package-list.json
echo "==============================="
- name: Emergency Disk Cleanup
run: |
echo "Disk usage before:"
df -h
echo "Clearing tool cache..."
rm -rf /opt/hostedtoolcache/* || true
rm -rf /usr/share/dotnet || true
rm -rf /usr/local/lib/android || true
rm -rf /opt/ghc || true
rm -rf ~/.fhir/packages || true
echo "Disk usage after:"
df -h
- name: Install Docker CLI
run: |
apt-get update
apt-get install -y docker.io
docker --version
- name: Preload previous IG package for comparison
run: |
echo "Detecting previous version..."
PREV_VERSION=$(python3 <<'PY'
import json
with open("package-list.json") as f:
data = json.load(f)
versions = [v["version"] for v in data["list"] if v["version"] != "current"]
print(versions[0] if versions else "")
PY
)
if [ -z "$PREV_VERSION" ]; then
echo "No previous version found. Skipping preload."
exit 0
fi
echo "Previous version detected: $PREV_VERSION"
mkdir -p previous-packages
TMPDIR=$(mktemp -d)
URL="https://fhir.dghs.gov.bd/core/$PREV_VERSION/package.tgz"
echo "Downloading $URL"
curl -L "$URL" -o "$TMPDIR/package.tgz"
mkdir -p "previous-packages/bd.fhir.core#$PREV_VERSION"
tar -xzf "$TMPDIR/package.tgz" -C "previous-packages/bd.fhir.core#$PREV_VERSION"
echo "Previous package cached:"
ls previous-packages
- name: Build FHIR IG
run: |
echo "Building FHIR IG version ${{ steps.version.outputs.version }}..."
CONTAINER_ID=$(docker create \
-v $(pwd)/previous-packages:/previous-packages \
hl7fhir/ig-publisher-base:latest \
/bin/bash -c "
mkdir -p /tmp/build
cp -r /home/publisher/ig /tmp/build/ig
cd /tmp/build/ig
rm -f package-list.json
_updatePublisher.sh -y
_genonce.sh
")
echo "Container ID: $CONTAINER_ID"
docker cp "$(pwd)/." "$CONTAINER_ID:/home/publisher/ig/"
echo "Mounted FHIR packages:"
ls -R previous-packages || echo "No previous packages directory"
docker start -a "$CONTAINER_ID"
EXIT_CODE=$?
echo "Copying outputs from container..."
docker cp "$CONTAINER_ID:/tmp/build/ig/output" ./output || echo "Warning: No output directory"
docker cp "$CONTAINER_ID:/tmp/build/ig/fsh-generated" ./fsh-generated || echo "No FSH generated"
docker cp "$CONTAINER_ID:/tmp/build/ig/input-cache" ./input-cache || echo "No input-cache"
docker cp "$CONTAINER_ID:/tmp/build/ig/temp" ./temp || echo "No temp directory"
if [ $EXIT_CODE -ne 0 ]; then
echo "Build failed, showing logs:"
docker logs "$CONTAINER_ID"
docker rm "$CONTAINER_ID"
exit 1
fi
docker rm "$CONTAINER_ID"
if [ ! -f "output/index.html" ]; then
echo "ERROR: Build failed - no index.html"
exit 1
fi
echo ""
echo "🔍 Checking for history.html..."
if [ -f "output/history.html" ]; then
echo "✅ history.html generated successfully!"
echo "📄 history.html size: $(ls -lh output/history.html | awk '{print $5}')"
else
echo "⚠️ WARNING: history.html was NOT generated"
echo "This might indicate an issue with the template or history.xml/package-list.json"
fi
echo "================================"
echo "IG Publisher comparison log:"
cat output/qa.compare.txt || echo "qa.compare.txt not found"
echo "================================"
echo "✅ Build successful!"
- name: Update package-feed.xml for releases
if: steps.version.outputs.build_type == 'release'
run: |
VERSION="${{ steps.version.outputs.version }}"
DATETIME=$(date -u +%Y-%m-%dT%H:%M:%SZ)
cat > update-feed.py << 'EOF'
import sys
import xml.etree.ElementTree as ET
version = sys.argv[1]
datetime_iso = sys.argv[2]
ET.register_namespace('', 'http://www.w3.org/2005/Atom')
tree = ET.parse('package-feed.xml')
root = tree.getroot()
ns = {'atom': 'http://www.w3.org/2005/Atom'}
updated_elem = root.find('atom:updated', ns)
if updated_elem is not None:
updated_elem.text = datetime_iso
entry_exists = False
for entry in root.findall('atom:entry', ns):
title = entry.find('atom:title', ns)
if title is not None and version in (title.text or ''):
entry_exists = True
entry_updated = entry.find('atom:updated', ns)
if entry_updated is not None:
entry_updated.text = datetime_iso
break
if not entry_exists:
new_entry = ET.Element('{http://www.w3.org/2005/Atom}entry')
title = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}title')
title.text = f"bd.fhir.core version {version}"
link = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}link')
link.set('rel', 'alternate')
link.set('href', f"https://fhir.dghs.gov.bd/core/{version}/")
entry_id = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}id')
entry_id.text = f"https://fhir.dghs.gov.bd/core/{version}/"
entry_updated = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}updated')
entry_updated.text = datetime_iso
summary = ET.SubElement(new_entry, '{http://www.w3.org/2005/Atom}summary')
summary.text = f"Release {version} of Bangladesh Core FHIR Implementation Guide"
insert_pos = 0
for i, child in enumerate(root):
if child.tag.endswith('entry'):
insert_pos = i
break
insert_pos = i + 1
root.insert(insert_pos, new_entry)
tree.write('output/package-feed.xml', encoding='utf-8', xml_declaration=True)
print("✅ Updated package-feed.xml")
EOF
python3 update-feed.py "$VERSION" "$DATETIME"
cp package-list.json output/package-list.json
echo "📋 Updated registry files"
- name: Prepare deployment artifact
run: |
VERSION="${{ steps.version.outputs.version }}"
BUILD_TYPE="${{ steps.version.outputs.build_type }}"
# Create a tarball of the output
if [ "$BUILD_TYPE" == "release" ]; then
tar -czf ig-output.tar.gz -C output . tar -czf ig-output.tar.gz -C output .
else
tar -czf ig-output.tar.gz -C output .
fi
echo "version=$VERSION" > deployment.env echo "version=$VERSION" > deployment.env
echo "build_type=$BUILD_TYPE" >> deployment.env echo "build_type=$BUILD_TYPE" >> deployment.env
echo "build_date=$(date -u +%Y-%m-%dT%H:%M:%SZ)" >> deployment.env echo "build_date=$(date -u +%Y-%m-%dT%H:%M:%SZ)" >> deployment.env
ls -lh ig-output.tar.gz echo "📦 Output contents:"
ls -lh output/ | grep -E "(history\.html|package-list\.json|package-feed\.xml|index\.html)" || echo "Some files may be missing"
- name: Upload artifact ls -lh ig-output.tar.gz
uses: actions/upload-artifact@v3
with: - name: Upload artifact
name: ig-output uses: actions/upload-artifact@v3
path: | with:
ig-output.tar.gz name: ig-output
deployment.env path: |
package-list.json ig-output.tar.gz
package-feed.xml deployment.env
retention-days: 30 package-list.json
package-feed.xml
retention-days: 30
deploy: deploy:
needs: build-ig needs: build-ig
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: (github.ref == 'refs/heads/main' || startsWith(github.ref, 'refs/tags/v')) if: github.ref == 'refs/heads/main' || startsWith(github.ref, 'refs/tags/v')
steps: steps:
- name: Download artifact - name: Download artifact
uses: actions/download-artifact@v3 uses: actions/download-artifact@v3
with: with:
name: ig-output name: ig-output
- name: Load deployment env - name: Load deployment env
id: deploy_info id: deploy_info
run: | run: |
source deployment.env source deployment.env
echo "version=$version" >> $GITHUB_OUTPUT echo "version=$version" >> $GITHUB_OUTPUT
echo "build_type=$build_type" >> $GITHUB_OUTPUT echo "build_type=$build_type" >> $GITHUB_OUTPUT
echo "build_date=$build_date" >> $GITHUB_OUTPUT echo "build_date=$build_date" >> $GITHUB_OUTPUT
echo "Deploying version: $version" echo "Deploying version: $version"
echo "Build type: $build_type" echo "Build type: $build_type"
- name: Deploy to server - name: Deploy to server
uses: appleboy/scp-action@v0.1.7 uses: appleboy/scp-action@v0.1.7
with: with:
host: ${{ secrets.DEPLOY_HOST }} host: ${{ secrets.DEPLOY_HOST }}
username: ${{ secrets.DEPLOY_USER }} username: ${{ secrets.DEPLOY_USER }}
password: ${{ secrets.DEPLOY_PASSWORD }} password: ${{ secrets.DEPLOY_PASSWORD }}
port: ${{ secrets.DEPLOY_PORT || 22 }} port: ${{ secrets.DEPLOY_PORT || 22 }}
source: "ig-output.tar.gz,deployment.env,package-list.json,package-feed.xml" source: "ig-output.tar.gz,deployment.env,package-list.json,package-feed.xml"
target: "/tmp/fhir-ig-deploy/" target: "/tmp/fhir-ig-deploy/"
- name: Execute deployment on server - name: Execute deployment on server
uses: appleboy/ssh-action@v1.0.3 uses: appleboy/ssh-action@v1.0.3
with: with:
host: ${{ secrets.DEPLOY_HOST }} host: ${{ secrets.DEPLOY_HOST }}
username: ${{ secrets.DEPLOY_USER }} username: ${{ secrets.DEPLOY_USER }}
password: ${{ secrets.DEPLOY_PASSWORD }} password: ${{ secrets.DEPLOY_PASSWORD }}
port: ${{ secrets.DEPLOY_PORT || 22 }} port: ${{ secrets.DEPLOY_PORT || 22 }}
script: | script: |
set -e set -e
# Load deployment info source /tmp/fhir-ig-deploy/deployment.env
source /tmp/fhir-ig-deploy/deployment.env
echo "==========================================" echo "=========================================="
echo "Deploying FHIR IG" echo "Deploying FHIR IG"
echo "Version: $version" echo "Version: $version"
echo "Build Type: $build_type" echo "Build Type: $build_type"
echo "Build Date: $build_date" echo "Build Date: $build_date"
echo "==========================================" echo "=========================================="
# Create version directory structure VERSIONS_DIR="/opt/fhir-ig/versions"
VERSIONS_DIR="/opt/fhir-ig/versions" mkdir -p "$VERSIONS_DIR"
mkdir -p "$VERSIONS_DIR"
# Determine target directory if [ "$build_type" = "release" ]; then
if [ "$build_type" == "release" ]; then TARGET_DIR="$VERSIONS_DIR/$version"
TARGET_DIR="$VERSIONS_DIR/$version" echo "📦 Deploying release version to: $TARGET_DIR"
echo "📦 Deploying release version to: $TARGET_DIR" else
else TARGET_DIR="$VERSIONS_DIR/dev"
TARGET_DIR="$VERSIONS_DIR/dev" echo "🔧 Deploying dev build to: $TARGET_DIR"
echo "🔧 Deploying dev build to: $TARGET_DIR" mkdir -p "$TARGET_DIR"
fi echo "Cleaning old dev files..."
rm -rf "$TARGET_DIR"/*
fi
# Create target directory mkdir -p "$TARGET_DIR"
mkdir -p "$TARGET_DIR"
# Extract IG output echo "Extracting IG output..."
echo "Extracting IG output..." tar -xzf /tmp/fhir-ig-deploy/ig-output.tar.gz -C "$TARGET_DIR"
tar -xzf /tmp/fhir-ig-deploy/ig-output.tar.gz -C "$TARGET_DIR"
# Copy package-list.json to root if [ -f "$TARGET_DIR/history.html" ]; then
cp /tmp/fhir-ig-deploy/package-list.json "$VERSIONS_DIR/package-list.json" echo "✅ history.html deployed successfully"
else
echo "⚠️ WARNING: history.html not found in deployment"
fi
# Copy package-feed.xml to root cp "$TARGET_DIR/package-list.json" "$VERSIONS_DIR/package-list.json"
cp /tmp/fhir-ig-deploy/package-feed.xml "$VERSIONS_DIR/package-feed.xml" cp "$TARGET_DIR/package-feed.xml" "$VERSIONS_DIR/package-feed.xml"
# Update 'current' symlink for releases cp "$TARGET_DIR/package-list.json" "/opt/fhir-ig/package-list.json"
if [ "$build_type" == "release" ]; then cp "$TARGET_DIR/package-feed.xml" "/opt/fhir-ig/package-feed.xml"
echo "Updating 'current' symlink to point to $version"
rm -f "$VERSIONS_DIR/current"
ln -sf "$version" "$VERSIONS_DIR/current"
fi
# Ensure nginx container is running with correct config if [ "$build_type" = "release" ]; then
cd /opt/fhir-ig echo "Updating 'current' symlink to point to $version"
rm -f "$VERSIONS_DIR/current"
ln -sf "$version" "$VERSIONS_DIR/current"
fi
# Download deployment files if they don't exist cd /opt/fhir-ig
if [ ! -f "docker-compose.prod.yml" ]; then
echo "ERROR: docker-compose.prod.yml not found!"
echo "Please deploy the updated docker-compose.prod.yml and nginx.conf first"
exit 1
fi
# Restart nginx to pick up new content if [ ! -f "docker-compose.prod.yml" ]; then
docker compose -f docker-compose.prod.yml restart fhir-ig || \ echo "ERROR: docker-compose.prod.yml not found!"
docker compose -f docker-compose.prod.yml up -d echo "Please deploy the updated docker-compose.prod.yml and nginx.conf first"
exit 1
fi
# Cleanup docker compose -f docker-compose.prod.yml up -d --force-recreate fhir-ig
rm -rf /tmp/fhir-ig-deploy
echo "==========================================" rm -rf /tmp/fhir-ig-deploy
echo "✅ Deployment completed successfully!"
echo "Version $version is now available at:"
if [ "$build_type" == "release" ]; then
echo " - https://fhir.dghs.gov.bd/core/$version/"
echo " - https://fhir.dghs.gov.bd/core/ (current)"
else
echo " - https://fhir.dghs.gov.bd/core/dev/"
fi
echo "=========================================="
# List all versions echo "=========================================="
echo "Available versions:" echo "✅ Deployment completed successfully!"
ls -lh "$VERSIONS_DIR" | grep -v total echo "Version $version is now available at:"
if [ "$build_type" = "release" ]; then
echo " - https://fhir.dghs.gov.bd/core/$version/"
echo " - https://fhir.dghs.gov.bd/core/$version/history.html"
echo " - https://fhir.dghs.gov.bd/core/ (current)"
else
echo " - https://fhir.dghs.gov.bd/core/dev/"
fi
echo "=========================================="
echo "Available versions:"
ls -lh "$VERSIONS_DIR" | grep -v total

View File

@@ -13,7 +13,7 @@
</extension>--> </extension>-->
<url value="https://fhir.dghs.gov.bd/core/ImplementationGuide/bd.fhir.core"/> <url value="https://fhir.dghs.gov.bd/core/ImplementationGuide/bd.fhir.core"/>
<!-- This version will propagate to all artifacts unless the "propagate-version" extension is overridden --> <!-- This version will propagate to all artifacts unless the "propagate-version" extension is overridden -->
<version value="0.2.4"/> <version value="0.2.5"/>
<name value="BangladeshCoreFHIRIG"/> <name value="BangladeshCoreFHIRIG"/>
<title value="Bangladesh Core FHIR Implementation Guide"/> <title value="Bangladesh Core FHIR Implementation Guide"/>
<status value="active"/> <status value="active"/>
@@ -102,6 +102,11 @@
<title value="IG Change History"/> <title value="IG Change History"/>
<generation value="html"/> <generation value="html"/>
</page> </page>
<page>
<nameUrl value="history.html"/>
<title value="Version History"/>
<generation value="html"/>
</page>
</page> </page>
<!-- copyright year is a mandatory parameter --> <!-- copyright year is a mandatory parameter -->
<parameter> <parameter>

View File

@@ -11,6 +11,14 @@
"status": "ci-build", "status": "ci-build",
"current": true "current": true
}, },
{
"version": "0.2.4",
"date": "2025-10-06",
"desc": "Second draft release of the Bangladesh Core FHIR IG",
"path": "https://fhir.dghs.gov.bd/core/0.2.4/",
"status": "trial-use",
"sequence": "STU 1"
},
{ {
"version": "0.2.3", "version": "0.2.3",
"date": "2025-10-06", "date": "2025-10-06",

View File

@@ -11,6 +11,14 @@
"status": "ci-build", "status": "ci-build",
"current": true "current": true
}, },
{
"version": "0.2.4",
"date": "2025-10-06",
"desc": "Second draft release of the Bangladesh Core FHIR IG",
"path": "https://fhir.dghs.gov.bd/core/0.2.4/",
"status": "trial-use",
"sequence": "STU 1"
},
{ {
"version": "0.2.3", "version": "0.2.3",
"date": "2025-10-06", "date": "2025-10-06",

View File

@@ -6,7 +6,7 @@ description: >
This Implementation Guide defines the Bangladesh Core FHIR profiles, This Implementation Guide defines the Bangladesh Core FHIR profiles,
value sets, code systems, and implementation rules for national digital health systems. value sets, code systems, and implementation rules for national digital health systems.
status: draft status: draft
version: 0.2.4 version: 0.2.5
fhirVersion: 4.0.1 fhirVersion: 4.0.1
copyrightYear: 2025+ copyrightYear: 2025+
releaseLabel: CI Build releaseLabel: CI Build