Skip to content
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

v10 missing mechanism to reference resolved types when typecasting #1921

Open
jacksonopp opened this issue May 23, 2023 · 2 comments
Open

v10 missing mechanism to reference resolved types when typecasting #1921

jacksonopp opened this issue May 23, 2023 · 2 comments
Assignees

Comments

@jacksonopp
Copy link

jacksonopp commented May 23, 2023

Expected Behavior

When typecasting data, I should be able to have correct type definitions when accessing resolved links. This is frequently required if you are rendering a RichText content type.

In this example, let's have a BlogPost containing a Hero content type which has some references to a CallToAction content type.

// These types were generated via the cf-content-types-generator library as recommended in the docs

export interface TypeBlogPost {
  content: EntryFieldTypes.RichText
}

export interface TypeHeroFields {
  title: EntryFieldTypes.Symbol;
  primaryCta?: EntryFieldTypes.EntryLink<TypeCtaSkeleton>;
  /** TypeImageSkeleton is a wrapper around an asset */
  heroImage?: EntryFieldTypes.EntryLink<TypeImageSkeleton>;
}
// ... with the correct skeleton type

export interface TypeCta {
  linkText: EntryFieldTypes.Symbol;
  url: EntryFieldTypes.Symbol;
}
// ... with the correct skeleton type

Using a rich text renderer, we need to switch through the result of a query and build components based on the content types. Since the RichText entry field type has no mechanism for explaining what the underlying data is in the resolved rich text links, we have to resort to typecasting that data.

The following code snippet is pseudocode which is similar to most of the rendering patterns across frameworks.

// 1. Get the data using the cdaClient.getEntries

// 2. Set up a renderer
// -- function to render the resolved component
const renderers = {
  [BLOCKS.EMBEDDED_ENTRY] = (node) => {
    switch (nodeType /* extract the nodeType from the node param */) {
      case 'hero':
        return HeroComponent
    }
  }
}

// 3. Create the component
// -- a psueudocode component representing a 'Hero component'
function HeroComponent = () => ({
  data: TypeHeroFields // renderers will provide the data somewhere

  /*
    The type of `data.primaryCta` contains `entry and type`
    But the actual data in the log contains `metadata, sys, and fields`
  */
  console.log(data.primaryCta)
})

Actual Behavior

I need to cast the types manually, which can be brittle if there are multiple layers linked

function HeroComponent = () => ({
  data: TypeHeroFields
  
  primaryCtaUrl = (data.primaryCta as unknown as TypeCtaFields).url

 // etc
})

Possible Solution

Create a recursive type which allows you to specify resolved types

Context

I have fairly deeply nested references in my blog post components, and we are frequently updating the content model. Using the recommended auto-generation tools, or following the typescrip tutorial (which is pretty short and doesn't explain in too much detail) plus the type casting on multiple layers inside my rendered components is super brittle and prone to breakage.

Environment

  • Language Version: v16.15.1
  • Package Manager Version: 8.11.0
  • Operating System: Darwin My-MacBook-Pro.local 22.2.0 Darwin Kernel Version 22.2.0: Fri Nov 11 02:03:51 PST 2022; root:xnu-8792.61.2~4/RELEASE_ARM64_T6000 arm64
  • Package Version: ^10.0.0
  • Which API are you using?: Preview
@VDinets
Copy link

VDinets commented Oct 2, 2023

Any updates?

@sdornan
Copy link

sdornan commented Oct 25, 2023

Running into this as well trying to upgrade Contentful.js to v10.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants