2026-09-01
- CDK
- redo dry run
- 6055:
- see if the AI has a plan
2026-08-28
- PDM
- currently only silver service, working on getting platinum (this FY)
- Jane ? going to mat leave soon, Michael Sinclair taking over
- CPSU problem flagged by Kayal
- likely due to eRD test data, disable feature flag (manually)
- initally thought, can’t do that as only CDK param, not SSM param
- but of course it’s an env var on the lambdaπ€¦
- likely due to eRD test data, disable feature flag (manually)
- 6908: retries
- add evidence and close
- 6857: eRD
- release revised build to Kayal in qa initially
- then to
int
Panic attack on eRDs not showing
- Enable ERD is true in release.yml for int: https://github.com/NHSDigital/prescriptionsforpatients/blob/bc1cc0e7f649181aeee4ddd5d095a81b826d5b1a/.github/workflows/release.yml#L243
- Also true when passed to CDK in cdk_release_code.yml: https://github.com/NHSDigital/prescriptionsforpatients/blob/bc1cc0e7f649181aeee4ddd5d095a81b826d5b1a/.github/workflows/cdk_release_code.yml#L178
- read into CDK from env (checked var name): https://github.com/NHSDigital/prescriptionsforpatients/blob/bc1cc0e7f649181aeee4ddd5d095a81b826d5b1a/packages/cdk/bin/PfPApiApp.ts#L32
- passed to Functions cdk constructor: https://github.com/NHSDigital/prescriptionsforpatients/blob/bc1cc0e7f649181aeee4ddd5d095a81b826d5b1a/packages/cdk/stacks/PfPApiStack.ts#L50
- passed to getMyPrescriptions function: https://github.com/NHSDigital/prescriptionsforpatients/blob/bc1cc0e7f649181aeee4ddd5d095a81b826d5b1a/packages/cdk/resources/Functions.ts#L74
- Splunk shows we do respond as expected: https://nhsdigital.splunkcloud.com/en-GB/app/nhse_eps_all_sh_all_viz/search?earliest=-4h%40m&latest=now&q=search%20index%3Dapp_prescriptions_int%20source%3D%22AWS%3ALogGroup%3A%2Faws%2Flambda%2Fpfp-*-GetMyPrescriptions%22%2037ECA4-B81077-000A3X&display.page.search.mode=verbose&dispatch.sample_ratio=1&display.page.search.tab=events&display.general.type=events&sid=1787930533.1097476_A4B52FC8-BD0B-412C-926E-13800280D44B
CPSU has With Pharmacy as well as RTC
- find PSU dynamo db transactions: 2 but both RTC
index=app_prescriptions_qa source="aws:loggroup:/aws/lambda/psu-*UpdatePrescriptionStatus" F98A42-A83008-775565
| spath path=message.command.input.TransactItems{0}.Put.Item.PrescriptionID.S output=PrescriptionId
| spath path=message.command.input.TransactItems{0}.Put.Item.PatientNHSNumber.S output=PatientNhsNumber
| spath path=message.command.input.TransactItems{0}.Put.Item.Status.S output=Status
| spath path=message.command.input.TransactItems{0}.Put.Item.ApplicationName.S output=ApplicationName
| spath path=message.timestamp output=rawTime
| spath path="message.x-request-id" output=x_request_id
| eval time_iso=strftime(strptime(rawTime,"%Y-%m-%dT%H:%M:%S.%3NZ"),"%Y-%m-%dT%H:%M:%S.%3NZ")
| table PrescriptionId PatientNhsNumber time_iso Status ApplicationName x_request_id
- New release made for the change to the eRD works :-/
2026-08-27
- 6857
- AC 3: I do have to do something says Matt, change something to ‘continuous’ https://github.com/NHSDigital/prescriptionsforpatients/blob/e544f305dd1ad0d181d225903e69834be4d51ff2/packages/getMyPrescriptions/src/eRD_example_response.ts#L71
- AC 4: send to Pete for confirmation β
- self-service read dynamo and s3
- 6908: CDK incident
- simplify query to get NHS number as well as request id and prescription id -> read dynamo table (needs TEAMS PR)
- OR try to do it logs
- gonna have to go this way, can’t wait for account resources PR to roll out
Problem: find all prescriptions not sent updates, determine if have been retried
- Affected request ids (775)
Between 25 Aug 26 10:17 and 11:08 BST
index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-3-beta-UpdatePrescriptionStatus" "message.level"=ERROR
| search message.message="Failed to push prescriptions to the notifications SQS"
| rename "message.nhsd-request-id" as request_id
| table request_id
- Request ids for successful notify requests
index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-5-beta-UpdatePrescriptionStatus"
| search message.message="Successfully sent a batch of prescriptions to the SQS"
| rename "message.nhsd-request-id" as request_id
| table request_id
- All prescription updates received
Problem with this is that it can only be run for very short periods (like 15 mins) before hitting 100Mb disk limit.
index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-*-beta-UpdatePrescriptionStatus"
| search message.message="Transitioning item status."
| eval iso_dt=strftime(_time, "%Y-%m-%dT%H:%M:%S.%3N%z")
| table iso_dt message.x-request-id message.prescriptionID message.nhsNumber message.newStatus message.newTerminalStatus message.previousStatus message.previousTerminalStatus
- successful notify requests (variation on 2 above) showing prescription id
Promising, gives > 20K records from 25th Aug 11:08 to 27th 18:00
index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-5-beta-UpdatePrescriptionStatus"
| search message.message="Transitioning item status."
| rename "message.x-request-id" as request_id
| rename "message.prescriptionID" as prescription_id
| search [
search index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-5-beta-UpdatePrescriptionStatus"
| search message.message="Successfully sent a batch of prescriptions to the SQS"
| rename "message.nhsd-request-id" as request_id
| fields request_id
]
| table request_id prescription_id message.nhsNumber message.newStatus message.newTerminalStatus message.previousStatus message.previousTerminalStatus
- correlate succssful notifications with problematic prescription ids
This gives 0 records having scanned over 100 million events between 25 Aug 11:08 to 27 18:00 as well as the warning:
[subsearch]: Subsearch produced 10000 results, truncating to maxout [subsearch_maxout] 10000.
I doubt we’re going to get any sense out of this route.
index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-*-beta-UpdatePrescriptionStatus"
| search message.message="Transitioning item status."
| rename "message.x-request-id" as request_id
| rename "message.prescriptionID" as prescription_id
| search prescription_id IN ("PRESCRIPTION_ID")
| search request_id [
search index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-5-beta-UpdatePrescriptionStatus"
| search message.message="Successfully sent a batch of prescriptions to the SQS"
| rename "message.nhsd-request-id" as request_id
| fields request_id
]
| table request_id prescription_id message.nhsNumber message.newStatus message.newTerminalStatus message.previousStatus message.previousTerminalStatus
- find requests with retries
Finds 2,094 from the point we started the release on 25th to 27 Aug 18:00
index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-*-beta-UpdatePrescriptionStatus"
| search message.message="Transitioning item status."
| eval iso_dt=strftime(_time, "%Y-%m-%dT%H:%M:%S.%3N%z")
| eventstats count as request_count by message.x-request-id
| where request_count > 1
| table iso_dt message.x-request-id message.prescriptionID message.nhsNumber message.newStatus message.newTerminalStatus message.previousStatus message.previousTerminalStatus request_count
restrict to prescriptions that are of interest gives 2,117 retries across all suppliers in the range of 2-4 retries.
index=app_prescriptions_prod source="AWS:LogGroup:/aws/lambda/psu-api-stateless-v1-18-*-beta-UpdatePrescriptionStatus"
| search message.message="Transitioning item status."
| search message.prescriptionID IN ("PRESCRIPTION_ID")
| eval iso_dt=strftime(_time, "%Y-%m-%dT%H:%M:%S.%3N%z")
| eventstats count as request_count by message.x-request-id
| where request_count > 1
| table iso_dt message.x-request-id message.prescriptionID message.nhsNumber message.newStatus message.newTerminalStatus message.previousStatus message.previousTerminalStatus request_count
2026-07-26
- show and tell
- PARS replacing SARS
- eps library approach, not yet in place
- test tooling discussion prompted thoughts of how it is hard to interact with PSU
- PARS replacing SARS
PSU tooling use case
- TUI app that accepts params
- aws profile
- period(default to last five minutes),
- max count: defaults to 5
- Sample prescription updates during period limit number to max count but include total count
- Where updates are RTC / RTC Partial, report the update status
- Present a table of results inc. result index number
- Await user input: options to include: q (quit), r (resample), (n) resend notification (additionally requires result index)
Seems promising, but can’t decrypt prod without Teams.
Need way to create test prescription and send update.
spr - eps store
- 3 mnths prescription data already terabytse
- suggests eps data store will only be summary (model on FHIR vsn of app reqts?)
- PDM is basically a FHIR document store
carries but does not validate our profiles
Matt: do we just hold the references to prescribe, dispenser, patient in pdm fhir docs
- existing sources ODS for prescribers, dispensers etc, pds for patient, healthcare ??? api too
- ODS (but not DOHS) keeps obsolete records (pharmacy that closed)
Ant
- If hold reference only, will we see patient as is not as was in the moment
- PDS should be able to store history (name changes etc)
Being data driven about this: trading larger redundant records vs compute to look up / rehydrate each time
2 prescription line items of 20 pills and 10 pills, could be fullfilled as 10, 10, 10
- need to record prescribed line items and dispense items
- could prescribe cocodamol as separate codeine and paracetamol both tracked back to same prescription line item.
- need longitudinal view not only of what was prescribed by what patient received.
- justification? could
- need to record prescribed line items and dispense items
Rob: initially ignore claims, but understand how easy it would be to do.
Matt: could update the medication request with tracking status (rather than storing separately)
- benefit: making PfP requests is faster / simpler
- What is service level of PDM? and eventual consistency or instant? if eventual, how long?
is it useful to store EPS status? (cancelled, expiry, others?)
- we need something as not all dispensers are onboarded to NPPTS (and may never be?)
spr data model
- medication request info
- extensions
- number of prescriptions issued: for erds
- authorisation expiry date (for erd)
- responsible practitioner :
- currently can have multiple (locum, registrar etc)
- (Oracle want to do this for 2ndary care). Could we use prescribing org?
- nhsbs prescription type (nonsense!!)
- take first half only?
- map to category?
- controlledDrug
- schedule
- dispensingInformation
- dispenseStatus: needed?
- prescriptionStatusHistory:
- NPPTS status (embedded?)
- full prescription status
- identifier
- may need new extension that holds presciption and issue number for erds
- status: this is where we put cancelled
- statusReason
- intent
- category: leave (NHS specific), outpatient, community, discharge … not mapped to HL7
- medication
- could we replace Snowmed with DM+D (they are already DM+D codes)
- could replace separate to this work (certainly on the way out, should be ok on the way in)
- subject: only nhs number
- requester: the person (or org?) signing; suggest practitioner role and practicioner org
- performer: ~~?~~inc. (used for pfp, should really be dispenseRequest performer)
- intention is admin
- pfp uses as the actual dispenser rather than nominated one (stored in dispense request performer)
- basedOn (used for erd)
- groupIdentifier (holds precription id)
- courseOfTherapyType
- note
- doseageInstruction
- dispenseRequest
- extension
- performerSiteType - exclude
- initialFill - not supported - exclude
- dispenseInterval - exc. not currently supported (fhir expects fixed interval hence can’t use for eRD) - ex
- validityPeriod - inc. - use for post dated scripts (diff to post dated notifications) - filtered out > 28 in future in PfP (spine?), Rob would like to see how many post dated scripts actually used (Rob says should be discouraged)
- numberOfRepeatsAllowed - include - PfP max 6 in API is wrong!
- quantity - inc.
- expectedSupplyDuration - inc. eRD, currently in days, FAME could be smaller
- performer - inc. ODS of nominated pharmacy
- substitution - inc. - policy says currently always false - (few exceptions like sugar free, cfc free), US allows substitution of anything deemed professionally appropriate
- priorPrescription - exc. - could use once have single item prescribing - could use for previous eRD issue (compound prescription id and issue) as part of SPR
- detectedIssue - exc.
- eventHistory - exc.
- extension
- extensions
2026-07-25
- 6857
- Kayal reporting no data
- confirmed it is passing thru the merge test+real data code: https://nhsdigital.splunkcloud.com/en-GB/app/nhse_eps_all_sh_all_viz/search?q=search%20index%3Dapp_prescriptions_qa%20source%3Daws%3Aloggroup%3A%2Faws%2Flambda%2Fpfp-api-*-GetMyPrescriptions%7C%20spath%20%22message.message%22%20%7C%20search%20%22message.message%22%3D%22eRD%20test%20enabled.%20Merging%20eRD%20test%20data%20with%20Spine%20prescription%20data.%22&display.page.search.mode=verbose&dispatch.sample_ratio=1&earliest=%40d&latest=now&display.events.type=list&sid=1787568689.948502_B0CE89C3-9041-4AF1-AFF9-6AFCE78E12FE
- need to investigate further, unable to curl as used to in SAM days, getting 104…
- Kayal reporting no data
- PSU CDK
- regression tests failing
- KMS perms issue found by Ant: https://nhsdigital.splunkcloud.com/en-GB/app/nhse_eps_all_sh_all_viz/search?q=search%20index%3Dapp_prescriptions_dev%20source%3Daws%3Aloggroup%3A%2Faws%2Flambda%2Fpsu*3346*%20%22message.level%22%3DERROR&display.page.search.mode=verbose&dispatch.sample_ratio=1&earliest=%40d&latest=now&sid=1787581549.998403_BB61ADB1-3A73-48B5-BC03-E240FB6BBA1F
- both now passing regression tests
- Clean PR with the updated CDK: https://github.com/NHSDigital/eps-prescription-status-update-api/actions/runs/32824158023/job/97735864800?pr=3452
- anually added new policy on the already migrated branch: https://github.com/NHSDigital/eps-prescription-status-update-api/actions/runs/32752297024/job/97732300094?pr=3346
- regression tests failing
- 6901: requested notify update link (CS1611306)
2026-08-24
- 6857
- try to get PfP v1.11.3-beta deployed
- confirmation of changed link by App team
- need to raise change request with Notify
- confirmation of changed link by App team
- is PfP v1.12.0-beta unblocked from FHIR facade issues? Release to
int.- released to int but issue in qa that Kayal is not seeing the test data
$ curl --header "nhsd-nhslogin-user: P9:9436300034" --header "x-request-id: $(cat /proc/sys/kernel/random/uuid)" https://${stack_name}.qa.eps.national.nhs.uk/Bundle curl: (56) OpenSSL SSL_read: Connection reset by peer, errno 104 vscode β /workspaces/prescriptionsforpatients (main) $ echo $stack_name pfp-api-v1-12-0-beta
- released to int but issue in qa that Kayal is not seeing the test data
- try to get PfP v1.11.3-beta deployed
- PSU CDK
- migrate in dev, inc merge of 3346
2026-08-21
- 6857
- get approval to accelerate releases
- after some thought and discussion: testing ok’d by Kayal blocked by App
- discussion with App team
- PSU CDK
- return to the Table migration issue
- couple more tweaks and migration completed ok
- run the ‘clean’ cdk deploy over the migrated
- again, a small fix needed to avoid destructive change, this time to kms key alias
- rerun… looks promising
- CDK fine, but the same reg test failure as ever: https://ubiquitous-adventure-p8885yq.pages.github.io/PSU/PULL-REQUEST/pr-3346/18855/index.html#3f5295924a5e8bfcdf8e3002d1fe4d31
- need to investigate this, happens too consistently
- SPR
- review Pete’s doc
- EPS datastore (new apparently)
- how diff to eps-spine-datastore?
- longer TTL (currently 2year ?)
- more attributes? what do we currently throw away?
- how diff to eps-spine-datastore?
- NPPTS = updates within PSU IIRC
- updates to both trigger PDM API (wip?)
- EPS datastore (new apparently)
- review Pete’s doc
- Unattended downloads test
- now blocked by CDK cross stack references (presumably Adam’s ongoing fight) https://github.com/NHSDigital/electronic-prescription-service-api/actions/runs/32501514397/job/96835442902?pr=5077
2026-08-20
- PSU CDK
- agreed to defer tightening permissions will after CDK migration complete
- dry run
- ran into validation error after [accidentally] triggering unmigrated builds by pushing doc changes
- start clean migration on new branch
- SQS went fine
- issues with tables
- some refining of rename and move scripts
- start clean migration on new branch
- ran into validation error after [accidentally] triggering unmigrated builds by pushing doc changes
2026-08-19
- 6857
- merged PR
- release needs to wait for this week’s release to clear int
- PSU CDK
- completed SQS test migration on PR branch
- prep similar steps for tables
- identified that permissions are still looser than ideal (eg kms:* in Messaing.ts)
2026-08-18
- 6857
- spine setup
- had to kill iBoss (start > services > idsa > click stop)
- actually hard-coded data will work
- prepped PR
- spine setup
- 6822
- review with Jono
- PSU CDK: parked temporarily
2026-08-17
- PSU CDK migration
- PSU deploy to env reg test fail: https://github.com/NHSDigital/eps-prescription-status-update-api/actions/runs/31796461572/job/94835421842
- dependent on VPC fix for FHIR facade
- PfP PR to feature flag the eRD needs merging: https://github.com/NHSDigital/prescriptionsforpatients/pull/2909
- before and separate from 6857 to unblock testing
- stateful branch: merge main and retest
- CDK and SAM retention policies are opposite:
- CDK β aws-cdk-lib.aws_dynamodb.Table docs:
removalPolicy? β default: RemovalPolicy.RETAINCDK deliberately overrides CloudFormation’s default to protect against accidental data loss. - SAM’s AWS::Serverless::SimpleTable has no DeletionPolicy property and transforms directly to AWS::DynamoDB::Table.
The CloudFormation DeletionPolicy docs state:
If you don't specify a DeletionPolicy, CloudFormation deletes the resource by default.
- CDK β aws-cdk-lib.aws_dynamodb.Table docs:
- CDK and SAM retention policies are opposite:
- migrate queues practice
- parked for now because of 6857
- PSU deploy to env reg test fail: https://github.com/NHSDigital/eps-prescription-status-update-api/actions/runs/31796461572/job/94835421842
- 6857
- requires spine change as data filtered there
- Pete to go back to Jen to propose enhanced hard-coded test data as quicker
- Kayal is expecting spine change :sigh:
- GH had a pretty wide ranging outage (copilot, actions etc)
2026-08-14
- PSU CDK migration
- adoption of params merged
- release cut to replace Jack’s taken on Tuesday
- testing will be blocked by eRD experiment
- regression tests failing!
- retry failed
- test locally?
- PfP
- disable eRD hack to re-enable testing
- 6857
- top priority, discuss in planning on Monday
2026-08-13
- Find
sso_role_namefor~/.aws/configTOKEN="$(jq -r '.accessToken' ~/.aws/sso/cache/*.json | head -n1)" aws sso list-account-roles \ --account-id 434629240718 \ --access-token "$TOKEN" \ --query 'roleList[].roleName' \ --output text | tr '\t' '\n'
2026-08-10,11,12: Vacation
2026-08-07
- PSU CDK migration
- no one to test new release containing new CDK managed params
- prep PR to follow on that uses params
- PfP release to
intfor eRD testing- force-merged to avoid SQ complaints: https://github.com/NHSDigital/prescriptionsforpatients/commit/d174d1900eb7dc9ad062f0c3fd3a2197ee35b2a9
- Tom reports issues (too few prescriptions returned): https://nhsdigital-platforms.slack.com/archives/C08MBDLCU0P/p1786118683580849
2026-08-06
- Cegedim incident
- prod rollout completed
- Splunk reports update
- Ant made the proposed change, Pete confirms arrival of reports today
- I caught up the missing 4th and 5th data (20 separate queries) manually
- PSU CDK migration
- new cut (1.18.3-beta) to add the new parameters and secrets
- fix grype!
- script to copy params and secrets
- new cut (1.18.3-beta) to add the new parameters and secrets
2026-08-06
Cegedim incident
- APIM unblocked by 13:15
- Tom confirmed test now passing
- deploying to
int - prod rollout blocked by GitHub actions outage
PSU CDK migration
- proposed to
- deploy additional parameters and secrets
- adopt the new parameters and secrets
- do migration for messaging and then separately for tables
- agreed at rubber duck
- could do resource renames
2026-08-05
Cegedim incident
errors in CPSU lambda
- not St Andrews Med Practive and appear to be legit eg https://nhsdigital.splunkcloud.com/en-GB/app/nhse_eps_all_sh_all_viz/search?earliest=-24h%40h&latest=now&q=search%20index%3Dapp_prescriptions_prod%0Asource%3D%22aws%3Aloggroup%3A%2Faws%2Flambda%2Fpsu-api-*-ConvertRequestToFhirFormat%22%20014cdafd-4a62-46a3-aec5-0cc321434120&display.page.search.mode=verbose&dispatch.sample_ratio=1&sid=1785925882.438140_BB61ADB1-3A73-48B5-BC03-E240FB6BBA1F
found line in CPSU path on API Gateway that deletes apostrophes from body before passing on to the state machine
PSU CDK migration
Error for “StackRefactorId”: “2e380eae-ed04-4c7b-8df8-80ff562615e0”
The resource PrescriptionStatusUpdatesTable defined in the resources mapping did not move from its original stack psu-pr-3374-Tables-KFOVFV9B9W3U. Review your stack template desired state.\nThe resource PrescriptionNotificationStatesTableV1 defined in the resources mapping did not move from its original stack psu-pr-3374-Tables-KFOVFV9B9W3U. Review your stack template desired state.\nThe resource PrescriptionStatusUpdatesKMSKey defined in the resources mapping did not move from its original stack psu-pr-3374-Tables-KFOVFV9B9W3U. Review your stack template desired state.\nThe resource PrescriptionNotificationStatesKMSKey defined in the resources mapping did not move from its original stack psu-pr-3374-Tables-KFOVFV9B9W3U. Review your stack template desired state.\nThe resource PrescriptionStatusUpdatesKMSKeyAlias defined in the resources mapping did not move from its original stack psu-pr-3374-Tables-KFOVFV9B9W3U. Review your stack template desired state.\nThe resource PrescriptionNotificationStatesKMSKeyAlias defined in the resources mapping did not move from its original stack psu-pr-3374-Tables-KFOVFV9B9W3U. Review your stack template desired state.\nThe resource BlockedSiteODSCodesParameter defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource EnabledSiteODSCodesParameter defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource EnabledSupplierApplicationIDsParameter defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource EnableNotificationsExternal defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource EnableNotificationsInternal defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource NotifyAPIBaseURLParameter defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource NotifyRoutingPlanIDParameter defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource TestPrescriptionsParameter1 defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource TestPrescriptionsParameter2 defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource TestPrescriptionsParameter3 defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource TestPrescriptionsParameter4 defined in the resources mapping did not move from its original stack psu-pr-3374-Parameters-1QO5KXDIKZ3SW. Review your stack template desired state.\nThe resource SQSSaltSecret defined in the resources mapping did not move from its original stack psu-pr-3374-Secrets-1ENBPHCVRNDJ. Review your stack template desired state.\nThe resource PSUNotifyAPIKeySecret defined in the resources mapping did not move from its original stack psu-pr-3374-Secrets-1ENBPHCVRNDJ. Review your stack template desired state.\nThe resource PSUNotifyApplicationIDSecret defined in the resources mapping did not move from its original stack psu-pr-3374-Secrets-1ENBPHCVRNDJ. Review your stack template desired state.\nThe resource PSUNotifyKIDSecret defined in the resources mapping did not move from its original stack psu-pr-3374-Secrets-1ENBPHCVRNDJ. Review your stack template desired state.\nThe resource PSUNotifyPrivateKeySecret defined in the resources mapping did not move from its original stack psu-pr-3374-Secrets-1ENBPHCVRNDJ. Review your stack template desired state.\nThe resource PSUSecretsKMSKey defined in the resources mapping did not move from its original stack psu-pr-3374-Secrets-1ENBPHCVRNDJ. Review your stack template desired state.\nThe resource PSUSecretsKMSKeyAlias defined in the resources mapping did not move from its original stack psu-pr-3374-Secrets-1ENBPHCVRNDJ. Review your stack template desired state.\nThe resource NHSNotifyPrescriptionsSQSQueue defined in the resources mapping did not move from its original stack psu-pr-3374-Messaging-4GAS9IGUR5AE. Review your stack template desired state.\nThe resource NHSNotifyPrescriptionsDeadLetterQueue defined in the resources mapping did not move from its original stack psu-pr-3374-Messaging-4GAS9IGUR5AE. Review your stack template desired state.\nThe resource PostDatedNotificationsSQSQueue defined in the resources mapping did not move from its original stack psu-pr-3374-Messaging-4GAS9IGUR5AE. Review your stack template desired state.\nThe resource PostDatedNotificationsDeadLetterQueue defined in the resources mapping did not move from its original stack psu-pr-3374-Messaging-4GAS9IGUR5AE. Review your stack template desired state.\nThe resource NotificationSQSQueueKMSKey defined in the resources mapping did not move from its original stack psu-pr-3374-Messaging-4GAS9IGUR5AE. Review your stack template desired state.\nThe resource NotificationSQSQueueKMSKeyAlias defined in the resources mapping did not move from its original stack psu-pr-3374-Messaging-4GAS9IGUR5AE. Review your stack template desired state."
Root cause: CloudFormation refactor validates nested stack templates at their S3 URLs
When create-stack-refactor sees a resource mapping where Source.StackName = psu-pr-3374-Tables-KFOVFV9B9W3U, it downloads the template for that nested stack from its original S3 URL and checks whether the moved resources are absent from the revised source. They aren’t absent β we never provided a revised template for that nested stack β so it fails with “did not move from its original stack”.
The StackDefinitions we provided only covered:
psu-pr-3374 (parent SAM) β source-revised.template.yaml psu-api-pr-3374-stateful (CDK) β destination-revised.template.json CloudFormation also requires revised templates for the four nested stacks that are the actual sources: psu-pr-3374-Tables-, psu-pr-3374-Parameters-, psu-pr-3374-Secrets-, psu-pr-3374-Messaging-.
But the nested stack templates are not straightforward to revise, because β as the Tables stack shows β they contain resources that depend on what we’re moving:
So providing a revised nested template that removes the moved resources leaves broken Ref/Fn::GetAtt references in the resources that stay.
The additional information is all in the describe output β Status: CREATE_FAILED with that long StatusReason list is the full extent of what CF reports. There is no deeper log.
The path forward has two realistic options:
Option 1 β Include revised nested stack templates in StackDefinitions Download each of the 4 nested stacks via get-template, strip the moved resources, upload revised versions to S3, and add them to StackDefinitions. The broken intra-template references would need to be tolerated or worked around (e.g. by also moving the dependent AutoScaling/IAM resources into CDK). This is significantly more complex.
Option 2 β Use CloudFormation resource import instead of stack refactor Rather than moving ownership via refactor:
Remove the SAM nested stacks (Tables, Parameters, Secrets, Messaging) from the SAM parent template β CloudFormation will retain the physical resources because of DeletionPolicy: Retain (or add it first) Import the retained physical resources directly into the CDK stack using aws cloudformation create-change-set –change-set-type IMPORT This avoids the nested stack template problem entirely. The cost is it’s a two-step process (SAM update to drop nested stacks β CDK import) rather than atomic.
2026-08-04
Cegedim incident
500 from CPSU endpoint
name of state machine handler has to be ‘handler’
no regression tests :-/
most of the day spent making release
2026-08-03
- not on spine triage
- PSU CDK
- release to prod done!
- new cut for Apotec rollout
- APIM failure to qa and ref -> retry
- stateful migration rehearsal
2026-07-31
- PSU CDK
- release signed off by Kayal in int, but too late to release to prod
- TODO: Unable to get pharmacy details => non-existent prescription seems like an interesting definition of resilience: https://github.com/NHSDigital/spineii/blob/fcfed2311cb49c8aaebd9be2f3a2979c58ca5abc/dev/spinecore/src/spinecore/prescriptions/patientfacingprescriptions/interactionworker.py#L424
- stateful migration rehearsal
- partial run crashed because of ‘drift’ in stateful stack
- one theory is around the resourcePrefix. stateful is set to psu-api (=> stack name psu-api-pr-3346) but migration is set to psu-pr-3346
- might be easier to use Ant’s script now I understand what needs to be in the mapping file and how to create it https://github.com/NHSDigital/electronic-prescription-service-account-resources/blob/main/packages/cdk/scripts/move_stack_resources.py
- think I need to use the PR for migration (3178) whilst referencing the cdk code branch on a different PR (3346).
- maybe can rename resources from psu- to psu-api- after? https://github.com/NHSDigital/electronic-prescription-service-account-resources/blob/main/packages/cdk/scripts/rename_stack_resources.py
- release signed off by Kayal in int, but too late to release to prod