Skip to content

Conversation

@genu
Copy link
Contributor

@genu genu commented Sep 9, 2025

Fixes #240

@ymc9 I believe this is just a type change. Should there be a test associated with this?

Summary by CodeRabbit

  • Bug Fixes

    • Corrected TypeScript typing when combining array and optional flags, ensuring arrays stay arrays and become nullable only when marked optional (e.g., T[] | null), improving IntelliSense and reducing type mismatches.
  • Refactor

    • Reordered internal typing logic for more predictable outcomes across all flag combinations. No runtime behavior changes.

Copilot AI review requested due to automatic review settings September 9, 2025 13:23
@coderabbitai
Copy link

coderabbitai bot commented Sep 9, 2025

Walkthrough

The WrapType<T, Optional = false, Array = false> type alias in packages/runtime/src/utils/type-utils.ts was redefined to evaluate the Array flag before Optional, altering the resulting type combinations accordingly.

Changes

Cohort / File(s) Summary
Type utility refactor
packages/runtime/src/utils/type-utils.ts
Reordered conditional logic in WrapType to prioritize Array over Optional, yielding: (Array=true, Optional=true) → T[] | null; (Array=true, Optional=false) → T[]; (Array=false, Optional=true) → T | null; else T. Updated exported type alias definition accordingly.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~10 minutes

Pre-merge checks (5 passed)

✅ Passed checks (5 passed)
Check name Status Explanation
Title Check ✅ Passed The pull request title "fix: Correctly infer optional enum arrays" directly summarizes the primary change of adjusting type inference for optional enum arrays and is both concise and specific.
Linked Issues Check ✅ Passed The modification of the WrapType<T, Optional, Array> alias now applies array wrapping before optional wrapping, ensuring optional enum arrays resolve to T[]
Out of Scope Changes Check ✅ Passed All changes are confined to the WrapType alias in type-utils.ts, which directly addresses the enum array inference problem without adding unrelated code.
Description Check ✅ Passed The description refers to issue #240 and notes that this is purely a type change, which aligns with the change to the WrapType alias in the code.
Docstring Coverage ✅ Passed No functions found in the changes. Docstring coverage check skipped.

Poem

I twitch my whiskers at types so neat,
Arrays first, then options—what a treat!
A hop, a bop, null snugly fits,
Enum colors bundled in tidy bits.
With carrot-codes and curly braces,
I bound through strongly-typed places. 🥕✨

Tip

👮 Agentic pre-merge checks are now available in preview!

Pro plan users can now enable pre-merge checks in their settings to enforce checklists before merging PRs.

  • Built-in checks – Quickly apply ready-made checks to enforce title conventions, require pull request descriptions that follow templates, validate linked issues for compliance, and more.
  • Custom agentic checks – Define your own rules using CodeRabbit’s advanced agentic capabilities to enforce organization-specific policies and workflows. For example, you can instruct CodeRabbit’s agent to verify that API documentation is updated whenever API schema files are modified in a PR. Note: Upto 5 custom checks are currently allowed during the preview period. Pricing for this feature will be announced in a few weeks.

Example:

reviews:
  pre_merge_checks:
    custom_checks:
      - name: "Undocumented Breaking Changes"
        mode: "warning"
        instructions: |
          Pass/fail criteria: All breaking changes to public APIs, CLI flags, environment variables, configuration keys, database schemas, or HTTP/GraphQL endpoints must be documented in the "Breaking Change" section of the PR description and in CHANGELOG.md. Exclude purely internal or private changes (e.g., code not exported from package entry points or explicitly marked as internal).

Please share your feedback with us on this Discord post.

✨ Finishing Touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull Request Overview

This pull request fixes the WrapType TypeScript utility to correctly handle optional enum arrays. The change ensures that when both Optional and Array flags are true, the type properly returns T[] | null instead of the previous incorrect behavior.

  • Restructured the conditional logic in WrapType to prioritize array handling before optional handling
  • Fixed the type inference for optional arrays to correctly produce T[] | null

Tip: Customize your code reviews with copilot-instructions.md. Create the file or learn how to get started.

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 (2)
packages/runtime/src/utils/type-utils.ts (2)

19-25: Prefer composition with NullableIf; constrain and rename type params.

Cuts duplication, tightens the contract to booleans, and avoids shadowing exported Optional and global Array names.

Apply:

- export type WrapType<T, Optional = false, Array = false> = Array extends true
-     ? Optional extends true
-         ? T[] | null
-         : T[]
-     : Optional extends true
-       ? T | null
-       : T;
+/** Wraps T into an array and/or makes it nullable.
+ * - IsArray true  => T[]
+ * - IsOptional true => ... | null
+ * Combine both => T[] | null
+ * Note: property optionality (| undefined) is handled separately via `?` or `OrUndefinedIf`.
+ */
+export type WrapType<
+    T,
+    IsOptional extends boolean = false,
+    IsArray extends boolean = false
+> = NullableIf<IsArray extends true ? T[] : T, IsOptional>;

19-25: Add a minimal type-level test to lock this behavior.

Prevents regressions for enum arrays and optional arrays.

Example (place under tests/types, compiled-only):

// tests/types/wraptype.test-d.ts
import type { WrapType } from '../../packages/runtime/src/utils/type-utils';

type Equal<A, B> =
  (<T>() => T extends A ? 1 : 2) extends (<T>() => T extends B ? 1 : 2) ? true : false;
type Assert<T extends true> = T;

// Array + Optional => T[] | null
type A1 = WrapType<'X', true, true>;
type E1 = 'X'[] | null;
type _t1 = Assert<Equal<A1, E1>>;

// Array only => T[]
type A2 = WrapType<'X', false, true>;
type E2 = 'X'[];
type _t2 = Assert<Equal<A2, E2>>;

// Optional only => T | null
type A3 = WrapType<'X', true, false>;
type E3 = 'X' | null;
type _t3 = Assert<Equal<A3, E3>>;
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 67d35d5 and 9e51596.

📒 Files selected for processing (1)
  • packages/runtime/src/utils/type-utils.ts (1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
{packages,samples,tests}/**

📄 CodeRabbit inference engine (CLAUDE.md)

Place packages only under packages/, samples/, or tests/

Files:

  • packages/runtime/src/utils/type-utils.ts
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: build-test (20.x)
🔇 Additional comments (1)
packages/runtime/src/utils/type-utils.ts (1)

19-25: Verify codegen Optional+Array behavior and impact

  • Ensure optional enum arrays still generate | undefined (e.g. ShirtColor[] | null | undefined).
  • Confirm no existing call sites rely on the old T | null collapse for arrays.

Copy link
Member

@ymc9 ymc9 left a comment

Choose a reason for hiding this comment

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

LGTM! Thanks for making the fix. I'll add a test for it.

@ymc9 ymc9 merged commit 71935e0 into zenstackhq:dev Sep 12, 2025
5 of 6 checks passed
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.

2 participants