8000 feat(ehr): contribution workflow piece by thomasyopes · Pull Request #3891 · metriport/metriport · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

feat(ehr): contribution workflow piece #3891

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 73 commits into from
Jun 24, 2025

Conversation

thomasyopes
Copy link
Contributor
@thomasyopes thomasyopes commented May 23, 2025

Ref: ENG-72

Issues:

Dependencies

Description

  • adding data contribution step to the workflow
  • adding resource ID level fetching from the EHRs
  • adding missing reference logic for generating the contribution bundles
  • allow non-uuid resources
  • map resource to metriport patient ID

Testing

  • Local
    • contribution flow runs successfully for Canvas and Athena
  • Staging
    • contribution flow runs successfully for Canvas and Athena
  • Sandbox
    • N/A
  • Production
    • contribution flow runs successfully for Canvas and Athena

Release Plan

  • Upstream dependencies are met/released
  • Merge this

Summary by CodeRabbit

  • New Features

    • Introduced contribution of EHR resource diff bundles with new API endpoints and Lambda handlers.
    • Added capability to fetch FHIR resource bundles by resource ID from Canvas and Athena EHR systems.
    • Added new FHIR extensions for predecessor and data source metadata.
  • Improvements

    • Expanded supported resource types and validation for Canvas and Athena integrations.
    • Enhanced resource bundle management with new bundle types and optional mixed resource type support.
    • Reduced parallel patient processing limit from 200 to 100 for appointments.
    • Added environment variable validation in multiple Lambda handlers for robust configuration.
    • Simplified constructors for cloud client classes by consolidating AWS region and client initialization.
    • Centralized and standardized SQS message body parsing and validation across Lambdas.
    • Improved partitioning and caching of EHR bundles, separating target and reference resources for better management.
  • Infrastructure

    • Added new Lambda function and SQS queue for processing resource diff bundle contributions with proper permissions and environment setup.
  • Bug Fixes

    • Fixed parameter handling and logging inconsistencies in bundle fetch and creation commands.
  • Refactor

    • Renamed and standardized direct and cloud-based EHR processing handlers.
    • Improved error handling and job status updates in EHR data workflows.

Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Copy link
linear bot commented May 23, 2025

Copy link
coderabbitai bot commented May 23, 2025
## Walkthrough

This change introduces a new multi-stage workflow for contributing EHR resource diff bundles, including new API endpoints, Lambda handlers, SQS queues, and supporting infrastructure. It implements logic for hydrating, preparing, and contributing resource diffs, updates job status handling, and extends bundle management to support resource-level operations. The update also refactors development and production code paths for better modularity.

## Changes

| Files / Paths                                                                                  | Change Summary                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
|-----------------------------------------------------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| `packages/api/src/external/ehr/shared/command/bundle/contribute-resource-diff-bundle.ts`<br>`packages/api/src/external/ehr/shared/utils/bundle/types.ts`<br>`packages/api/src/routes/internal/ehr/patient.ts` | Adds a new function and API endpoint for contributing resource diff bundles, introduces a new params type, and updates route documentation and logic to use the new contribution workflow instead of setting entry status.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| `packages/core/src/external/ehr/api/bundle/contribute-resource-diff-bundle.ts`                | Adds a new API client function and parameter type for contributing resource diff bundles via HTTP, with error handling and retry logic.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| `packages/core/src/external/ehr/api/job/create-resource-diff-bundles/set-entry-status.ts`     | Removes the function and type for setting resource diff job entry status, as this is now handled differently.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             |
| `packages/core/src/external/ehr/athenahealth/command/get-resource-bundle-by-resource-id.ts`<br>`packages/core/src/external/ehr/canvas/command/get-resource-bundle-by-resource-id.ts`<br>`packages/core/src/external/ehr/command/get-resource-bundle-by-resource-id.ts` | Adds new functions and unified interface for retrieving FHIR resource bundles by resource ID from AthenaHealth and Canvas EHRs.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| `packages/core/src/external/ehr/athenahealth/index.ts`<br>`packages/core/src/external/ehr/canvas/index.ts` | Adds support for resource-level bundle fetching, new supported resource types, and type guards for reference resources. Adds new methods to EHR API classes for retrieving bundles by resource ID.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        |
| `packages/core/src/external/ehr/bundle/bundle-shared.ts`<br>`packages/core/src/external/ehr/bundle/command/create-or-replace-bundle.ts`<br>`packages/core/src/external/ehr/bundle/command/fetch-bundle.ts` | Adds support for resource-level bundle keys with optional `resourceId`, new bundle type for resource diff data contributions, and updates bundle creation and fetching logic to handle resource IDs and mixed resource types.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| `packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/compute/ehr-compute-resource-diff-bundles-direct.ts`<br>`packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/compute/ehr-compute-resource-diff-bundles-factory.ts`<br>`packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/contribute/ehr-contribute-resource-diff-bundles-cloud.ts`<br>`packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/contribute/ehr-contribute-resource-diff-bundles-direct.ts`<br>`packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/contribute/ehr-contribute-resource-diff-bundles-factory.ts`<br>`packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/contribute/ehr-contribute-resource-diff-bundles.ts` | Refactors resource diff bundle computation and contribution steps, introducing direct and cloud handlers, a factory for handler instantiation, and an interface for contribution. Adds logic for hydrating, preparing, and contributing bundles, with error handling and SQS integration.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     
8000
          |
| `packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/refresh/ehr-refresh-ehr-bundles-direct.ts`<br>`packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/refresh/ehr-refresh-ehr-bundles-factory.ts` | Renames and refactors refresh bundle handler for direct execution, updates factory to use new class.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| `packages/core/src/util/config.ts`                                                            | Adds a new configuration method for retrieving the contribute diff bundles queue URL from environment variables.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| `packages/infra/lib/api-stack.ts`<br>`packages/infra/lib/ehr-nested-stack.ts`                 | Adds Lambda and SQS resources for resource diff bundle contribution to the infrastructure stack, wires up permissions, environment, and event sources.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| `packages/lambdas/src/ehr/contribute-resource-diff-bundles.ts`                                | Introduces a new Lambda handler for processing SQS events and contributing resource diff bundles, with error/event capturing, environment config, and schema validation.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| `packages/lambdas/src/ehr/compute-resource-diff-bundles.ts`<br>`packages/lambdas/src/ehr/refresh-ehr-bundles.ts` | Updates Lambda handlers to use new direct handler classes and removes Sentry serverless integration in favor of a new error/event capture utility.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                |
| `packages/core/src/external/fhir/shared/extensions/derived-from.ts`<br>`packages/core/src/external/fhir/shared/extensions/extension.ts` | Adds new FHIR extension helpers for predecessor and data source metadata on resources.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| `packages/api/src/external/ehr/shared/utils/appointment.ts`                                   | Reduces the `parallelPatients` constant from 200 to 100.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| `packages/lambdas/src/shared/parse-body.ts`<br>`packages/lambdas/src/shared/sqs.ts`            | Moves `parseBody` function from shared SQS module to a new shared parse-body module to centralize JSON parsing and schema validation with consistent error handling. Updates imports accordingly in Lambda handlers and other files.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| `packages/lambdas/src/job/patient/run-job.ts`<br>`packages/lambdas/src/surescripts/receive-response.ts`<br>`packages/lambdas/src/surescripts/receive-verification.ts`<br>`packages/lambdas/src/surescripts/send-batch-request.ts`<br>`packages/lambdas/src/surescripts/send-patient-request.ts`<br>`packages/lambdas/src/surescripts/verify-request-in-history.ts` | Updates imports to use the new centralized `parseBody` function from the shared parse-body module instead of the shared SQS module.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| `packages/lambdas/src/ehr/elation/link-patient.ts`<br>`packages/lambdas/src/ehr/healthie/link-patient.ts`<br>`packages/lambdas/src/ehr/sync-patient.ts` | Adds validation in Lambda handlers to ensure `WAIT_TIME_IN_MILLIS` environment variable parses to a valid number, throwing a `MetriportError` if invalid.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| `packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/compute/ehr-compute-resource-diff-bundles-cloud.ts`<br>`packages/core/src/external/ehr/job/create-resource-diff-bundles/steps/refresh/ehr-refresh-ehr-bundles-cloud.ts`<br>`packages/core/src/external/ehr/command/get-appointments/ehr-get-appointments-cloud.ts`<br>`packages/core/src/external/ehr/command/sync-patient/ehr-sync-patient-cloud.ts`<br>`packages/core/src/external/ehr/elation/command/link-patient/elation-link-patient-cloud.ts`<br>`packages/core/src/external/ehr/healthie/command/link-patient/healthie-link-patient-cloud.ts` | Simplifies constructors by removing optional region parameters and requiring clients (SQS or Lambda) with default instantiation using configured AWS region, eliminating conditional client creation inside constructors.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |

## Sequence Diagram(s)

### Resource Diff Bundle Contribution Workflow

```mermaid
sequenceDiagram
    participant Client
    participant API
    participant Lambda_Compute
    participant SQS_Contribute
    participant Lambda_Contribute
    participant S3
    participant EHR
    participant DB

    Client->>API: POST /internal/ehr/:ehrId/patient/:id/resource/diff/:jobId/contribute?resourceType=...
    API->>Lambda_Compute: Trigger compute resource diff bundles
    Lambda_Compute->>S3: Fetch RESOURCE_DIFF_EHR_ONLY bundle
    Lambda_Compute->>EHR: Hydrate missing referenced resources
    Lambda_Compute->>S3: Store hydrated resource diff data contribution bundle
    Lambda_Compute->>SQS_Contribute: Send message with contribution payload
    SQS_Contribute->>Lambda_Contribute: Triggered with payload
    Lambda_Contribute->>S3: Fetch resource diff data contribution bundle
    Lambda_Contribute->>API: Call contributeResourceDiffBundle endpoint
    API->>DB: Store contributed resources and update job status

Old vs New Control Flow for Job Entry Status

sequenceDiagram
    participant API
    participant Lambda_Compute
    participant Lambda_Contribute
    participant DB

    rect rgb(240,240,240)
    note left of API: Old Flow
    API->>DB: Set job entry status directly
    end

    rect rgb(220,255,220)
    note left of API: New Flow
    API->>Lambda_Compute: Trigger compute/contribute
    Lambda_Compute->>Lambda_Contribute: (via SQS) Contribute resource diff bundle
    Lambda_Contribute->>DB: Update job entry status (success/failure)
    end
Loading

Possibly related PRs



<!-- walkthrough_end -->
<!-- This is an auto-generated comment: all tool run failures by coderabbit.ai -->

> [!WARNING]
> There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.
> 
> <details>
> <summary>🔧 ESLint</summary>
> 
> > If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.
> 
> npm error code ERR_SSL_WRONG_VERSION_NUMBER
> npm error errno ERR_SSL_WRONG_VERSION_NUMBER
> npm error request to https://10.0.0.28:4873/punycode/-/punycode-2.3.1.tgz failed, reason: C07C0607687F0000:error:0A00010B:SSL routines:ssl3_get_record:wrong version number:../deps/openssl/openssl/ssl/record/ssl3_record.c:354:
> npm error
> npm error A complete log of this run can be found in: /.npm/_logs/2025-06-24T16_26_57_999Z-debug-0.log
> 
> 
> 
> </details>

<!-- end of auto
8000
-generated comment: all tool run failures by coderabbit.ai -->
<!-- internal state start -->


<!-- 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= -->

<!-- internal state end -->
<!-- finishing_touch_checkbox_start -->

<details open="true">
<summary>✨ Finishing Touches</summary>

- [ ] <!-- {"checkboxId": "7962f53c-55bc-4827-bfbf-6a18da830691"} --> 📝 Generate Docstrings

</details>

<!-- finishing_touch_checkbox_end -->
<!-- tips_start -->

---



<details>
<summary>🪧 Tips</summary>

### Chat

There are 3 ways to chat with [CodeRabbit](https://coderabbit.ai?utm_source=oss&utm_medium=github&utm_campaign=metriport/metriport&utm_content=3891):

- Review comments: Directly reply to a review comment made by CodeRabbit. Example:
  - `I pushed a fix in commit <commit_id>, please review it.`
  - `Explain this complex logic.`
  - `Open a follow-up GitHub issue for this discussion.`
- Files and specific lines of code (under the "Files changed" tab): Tag `@coderabbitai` in a new review comment at the desired location with your query. Examples:
  - `@coderabbitai explain this code block.`
  -	`@coderabbitai modularize this function.`
- PR comments: Tag `@coderabbitai` in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
  - `@coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.`
  - `@coderabbitai read src/utils.ts and explain its main purpose.`
  - `@coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.`
  - `@coderabbitai help me debug CodeRabbit configuration file.`

### Support

Need help? Create a ticket on our [support page](https://www.coderabbit.ai/contact-us/support) for assistance with any issues or questions.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

### CodeRabbit Commands (Invoked using PR comments)

- `@coderabbitai pause` to pause the reviews on a PR.
- `@coderabbitai resume` to resume the paused reviews.
- `@coderabbitai review` to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
- `@coderabbitai full review` to do a full review from scratch and review all the files again.
- `@coderabbitai summary` to regenerate the summary of the PR.
- `@coderabbitai generate docstrings` to [generate docstrings](https://docs.coderabbit.ai/finishing-touches/docstrings) for this PR.
- `@coderabbitai generate sequence diagram` to generate a sequence diagram of the changes in this PR.
- `@coderabbitai resolve` resolve all the CodeRabbit review comments.
- `@coderabbitai configuration` to show the current CodeRabbit configuration for the repository.
- `@coderabbitai help` to get help.

### Other keywords and placeholders

- Add `@coderabbitai ignore` anywhere in the PR description to prevent this PR from being reviewed.
- Add `@coderabbitai summary` to generate the high-level summary at a specific location in the PR description.
- Add `@coderabbitai` anywhere in the PR title to generate the title automatically.

### CodeRabbit Configuration File (`.coderabbit.yaml`)

- You can programmatically configure CodeRabbit by adding a `.coderabbit.yaml` file to the root of your repository.
- Please see the [configuration documentation](https://docs.coderabbit.ai/guides/configure-coderabbit) for more information.
- If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: `# yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json`

### Documentation and Community

- Visit our [Documentation](https://docs.coderabbit.ai) for detailed information on how to use CodeRabbit.
- Join our [Discord Community](http://discord.gg/coderabbit) to get help, request features, and share feedback.
- Follow us on [X/Twitter](https://twitter.com/coderabbitai) for updates and announcements.

</details>

<!-- tips_end -->

Thomas Yopes added 3 commits May 23, 2025 13:30
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Thomas Yopes added 10 commits May 28, 2025 12:52
…port/metriport into eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
…port/metriport into eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Thomas Yopes added 12 commits May 29, 2025 06:15
…port/metriport into eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
…port/metriport into eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-199

Ref: #1040
Signed-off-by: Thomas Yope
A3E2
s <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-199

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
…port/metriport into eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
…port/metriport into eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
…port/metriport into eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-199

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-199

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-199

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-199

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
… eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
},
{
numberOfParallelExecutions: parallelRequests,
delay: delayBetweenRequestBatches.asMilliseconds(),
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wouldn't be better to use min/max jitter? It adds some delay and spreads the load over time

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thomas Yopes added 2 commits June 22, 2025 05:26
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
… eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Copy link
@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

🧹 Nitpick comments (1)
packages/shared/src/common/env-var.ts (1)

20-27: Specify radix parameter for parseInt to ensure consistent parsing.

The implementation looks good and follows the established patterns in the file. However, consider specifying the radix parameter for parseInt to ensure consistent decimal parsing regardless of input format.

Apply this diff to improve parsing reliability:

-  const int = parseInt(value);
+  const int = parseInt(value, 10);

This ensures that values like "08" are always parsed as decimal 8 rather than potentially being interpreted as octal in some environments.

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between cbc2d89 and b1b6238.

📒 Files selected for processing (7)
  • packages/lambdas/src/ehr/compute-resource-diff-bundles.ts (2 hunks)
  • packages/lambdas/src/ehr/contribute-resource-diff-bundles.ts (1 hunks)
  • packages/lambdas/src/ehr/elation/link-patient.ts (2 hunks)
  • packages/lambdas/src/ehr/healthie/link-patient.ts (2 hunks)
  • packages/lambdas/src/ehr/refresh-ehr-bundles.ts (2 hunks)
  • packages/lambdas/src/ehr/sync-patient.ts (2 hunks)
  • packages/shared/src/common/env-var.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (6)
  • packages/lambdas/src/ehr/healthie/link-patient.ts
  • packages/lambdas/src/ehr/elation/link-patient.ts
  • packages/lambdas/src/ehr/sync-patient.ts
  • packages/lambdas/src/ehr/refresh-ehr-bundles.ts
  • packages/lambdas/src/ehr/compute-resource-diff-bundles.ts
  • packages/lambdas/src/ehr/contribute-resource-diff-bundles.ts
🧰 Additional context used
📓 Path-based instructions (1)
`**/*.ts`: - Use the Onion Pattern to organize a package's code in layers - Try to use immutable code and avoid sharing state across different functions, objects, and systems - Try...

**/*.ts: - Use the Onion Pattern to organize a package's code in layers

  • Try to use immutable code and avoid sharing state across different functions, objects, and systems
  • Try to build code that's idempotent whenever possible
  • Prefer functional programming style functions: small, deterministic, 1 input, 1 output
  • Minimize coupling / dependencies
  • Avoid modifying objects received as parameter
  • Only add comments to code to explain why something was done, not how it works
  • Naming
    • classes, enums: PascalCase
    • constants, variables, functions: camelCase
    • file names: kebab-case
    • table and column names: snake_case
    • Use meaningful names, so whoever is reading the code understands what it means
    • Don’t use negative names, like notEnabled, prefer isDisabled
    • For numeric values, if the type doesn’t convey the unit, add the unit to the name
  • Typescript
    • Use types
    • Prefer const instead of let
    • Avoid any and casting from any to other types
    • Type predicates: only applicable to narrow down the type, not to force a complete type conversion
    • Prefer deconstructing parameters for functions instead of multiple parameters that might be of
      the same type
    • Don’t use null inside the app, only on code interacting with external interfaces/services,
      like DB and HTTP; convert to undefined before sending inwards into the code
    • Use async/await instead of .then()
    • Use the strict equality operator ===, don’t use abstract equality operator ==
    • When calling a Promise-returning function asynchronously (i.e., not awaiting), use .catch() to
      handle errors (see processAsyncError and emptyFunction depending on the case)
    • Date and Time
      • Always use buildDayjs() to create dayjs instances
      • Prefer dayjs.duration(...) to create duration consts and keep them as duration
  • Prefer Nullish Coalesce (??) than the OR operator (||) to provide a default value
  • Avoid creating arrow functions
  • Use truthy syntax instead of in - i.e., if (data.link) not if ('link' in data)
  • Error handling
    • Pass the original error as the new one’s cause so the stack trace is persisted
    • Error messages should have a static message - add dynamic data to MetriportError's additionalInfo prop
    • Avoid sending multiple events to Sentry for a single error
  • Global constants and variables
    • Move literals to constants declared after imports when possible (avoid magic numbers)
    • Avoid shared, global objects
  • Avoid using console.log and console.error in packages other than utils, infra and shared,
    and try to use out().log instead
  • Avoid multi-line logs
    • don't send objects as a second parameter to console.log() or out().log()
    • don't create multi-line strings when using JSON.stringify()
  • Use eslint to enforce code style
  • Use prettier to format code
  • max column length is 100 chars
  • multi-line comments use /** */
  • scripts: top-level comments go after the import
  • packages/shared/src/common/env-var.ts
⏰ Context from checks skipped due to timeout of 90000ms (1)
  • GitHub Check: Analyze (javascript)

Thomas Yopes added 2 commits June 22, 2025 05:35
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
< 10000 a href="/metriport/metriport/pull/3891/commits/1cedab94edd213001468b6daa61c7515444f173d" class="Link--secondary">1cedab9
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
@thomasyopes thomasyopes mentioned this pull request Jun 23, 2025
6 tasks
Thomas Yopes added 8 commits June 23, 2025 15:28
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
… eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
Ref: ENG-72

Ref: #1040
Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
… eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
… eng-72-athena-data-contribution

Signed-off-by: Thomas Yopes <thomasyopes@Thomass-MBP.attlocal.net>
@thomasyopes thomasyopes added this pull request to the merge queue Jun 24, 2025
Merged via the queue into develop with commit 6ce9905 Jun 24, 2025
21 checks passed
@thomasyopes thomasyopes deleted the eng-72-athena-data-contribution branch June 24, 2025 16:50
@coderabbitai coderabbitai bot mentioned this pull request Jun 25, 2025
2 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants
0