apollo-client: Typescript error when compiling a module using apollo-client and apollo-cache-inmemory

Intended outcome:

Successful compilation of the project.

Actual outcome:

ERROR in [at-loader] ./node_modules/apollo-cache-inmemory/lib/inMemoryCache.d.ts:5:22
    TS2415: Class 'InMemoryCache' incorrectly extends base class 'ApolloCache<NormalizedCacheObject>'.
  Types of property 'read' are incompatible.
    Type '<T>(query: ReadOptions) => T | null' is not assignable to type '<T>(query: ReadOptions) => T'.
      Type 'T | null' is not assignable to type 'T'.
        Type 'null' is not assignable to type 'T'.

How to reproduce the issue: tsconfig.json

{
  "compilerOptions": {
    "sourceMap": true,
    "jsx": "preserve",
    "target": "es2015",
    "lib": ["es2017", "dom", "esnext.asynciterable"],
    "module": "es2015",
    "moduleResolution": "node",
    "noImplicitAny": true,
    "noImplicitThis": true,
    "noUnusedLocals": true,
    "noUnusedParameters": true,
    "strictNullChecks": true,
    "allowSyntheticDefaultImports": false,
    "baseUrl": ".",
    "paths": {
    }
  },
  "include": [
    "src/**/*.ts",
    "src/**/*.tsx"
  ],
  "exclude": [
    "node_modules"
  ]
}

Sample module:

import { InMemoryCache } from "apollo-cache-inmemory";
import { ApolloClient, ApolloQueryResult } from "apollo-client";
import { HttpLink } from "apollo-link-http";
import gql from "graphql-tag";

const client = new ApolloClient({
  cache: new InMemoryCache() as any,
  link: new HttpLink({ uri: process.env.GRAPHQL_ENDPOINT })
});

Version

  • apollo-client@2.0.2
  • apollo-cache-inmemory@^1.1.0
  • apollo-cache@^1.0.0

** Possible cause **

apollo-cache defines ApolloCache base class with read method which cannot miss:

abstract read<T>(query: Cache.ReadOptions): T

apollo-cache-inmemory actually has more realistic definition of the return value as T | null

About this issue

  • Original URL
  • State: closed
  • Created 7 years ago
  • Reactions: 14
  • Comments: 22 (2 by maintainers)

Commits related to this issue

Most upvoted comments

Am I right to assume that this is still not fixed? I have this code:

    const client = new ApolloClient({
      cache: new InMemoryCache(),
      link: batchHttpLink,
      queryDeduplication: true,
      ssrMode: true,
    })

and am getting this TS error:

Type 'InMemoryCache' is not assignable to type 'ApolloCache<NormalizedCacheObject>'.
  Property 'data' is protected in type 'InMemoryCache' but public in type 'ApolloCache<NormalizedCacheObject>'. [2322]

Temporary, and unfortunate, workaround is to set "strictNullChecks": false 😞

@mbrochh The trick (?) is to use the interface NormalizedCacheObject as the generic type for TCacheShape:

new ApolloClient<NormalizedCacheObject>({
    ssrMode: typeof window === 'undefined',
    link: auth.concat(http),
    cache: new InMemoryCache(),
});

For now you can also set skipLibCheck to true. Might be better for this issue.

This seems to work together with skipLibCheck: true.

import { ApolloCache } from 'apollo-cache';
import { InMemoryCache, NormalizedCacheObject } from 'apollo-cache-inmemory';
import { ApolloClient } from 'apollo-client';
import { HttpLink } from 'apollo-link-http';

const client = new ApolloClient({
  cache: new InMemoryCache() as ApolloCache<NormalizedCacheObject>,
  link: new HttpLink({ uri: '/graphql' }),
});

// ... later ...

<ApolloProvider client={client as ApolloClient<any>}>
  {/* ... */}
</ApolloProvider>

@jbaxleyiii It seems like you merged what may be a fix just after the most recent release - assuming that’s correct, can we get a patch release, or at least a beta/rc with the fix?

This compiles in TypeScript for me

import { ApolloClient } from 'apollo-client';
import { InMemoryCache, NormalizedCacheObject } from 'apollo-cache-inmemory';
import { HttpLink } from 'apollo-link-http';

export function createApolloClient(): ApolloClient<NormalizedCacheObject> {
  return new ApolloClient({
    link: new HttpLink({
      uri: "...",
    }),
    cache: new InMemoryCache(),
  });
}

This still happens: https://gist.github.com/prencher/ad626ca0ec21ce8bfc41e4bfcfc54a81

Turning strictNullChecks off is not an answer to this problem. What can we do to get this actually resolved?

@jbaxleyiii please re-open, just installed everything in a new project (apolo-client@2.0.3). I’m still getting this error.

@jbaxleyiii I’m afraid this did not fix the issue.

If you clone my repository and then run yarn upgrade followed by ./node_modules/.bin/tsc the issue persists. The fix is to modify the base class to allow null being returned from the read query. The client expects a type conforming to the base class which the InMemoryCache class does not.

For those looking for a great example of next with apollo and typescript, here’s the repo that saved me: https://github.com/borisowsky/next-advanced-starter

This is still an issue.

"apollo-boost": "^0.4.7",
    "react-apollo": "^3.1.3",

My code

import React from 'react'
import ReactDOM from 'react-dom'
import { withApollo, ApolloProvider } from 'react-apollo'
import { ApolloClient, ApolloLink, InMemoryCache, HttpLink, NormalizedCacheObject } from 'apollo-boost'

const httpLink = new HttpLink({ uri: url })

const authLink = new ApolloLink((operation, forward) => {
  // Call the next link in the middleware chain.
  return forward(operation)
})

const client = new ApolloClient<NormalizedCacheObject>({
  link: authLink.concat(httpLink), // Chain it with the HttpLink
  cache: new InMemoryCache() as any
})

const AppWithApollo = withApollo(App)

const Index = () => (
  <ApolloProvider client={client as ApolloClient<any>}>
    <AppWithApollo />
  </ApolloProvider>
)

ERROR in /Users/Peter/Workspace/petenelson.dev/src/index.tsx ./src/index.tsx [tsl] ERROR in /Users/Peter/Workspace/petenelson.dev/src/index.tsx(23,46) TS2769: No overload matches this call. The last overload gave the following error. Argument of type ‘{ client: ApolloClient<NormalizedCacheObject>; }’ is not assignable to parameter of type ‘Attributes & ApolloProviderProps<any>’. Property ‘children’ is missing in type ‘{ client: ApolloClient<NormalizedCacheObject>; }’ but required in type ‘ApolloProviderProps<any>’.

@donaldpipowitch still seeing the error. Webpack emits

TS2322: Type '{ client: ApolloClient<NormalizedCacheObject>; children: Element; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<ApolloProvider> & Readonly<{ children?: ReactNode;...'.
  Type '{ client: ApolloClient<NormalizedCacheObject>; children: Element; }' is not assignable to type 'Readonly<ProviderProps<Cache>>'.
    Types of property 'client' are incompatible.
      Type 'ApolloClient<NormalizedCacheObject>' is not assignable to type 'ApolloClient<Cache>'.
        Type 'NormalizedCacheObject' is not assignable to type 'Cache'.
          Property 'add' is missing in type 'NormalizedCacheObject'.

@tackley thank you for the suggestion.

After following the suggestion to set strictNullChecks to false. I experience another TypeError:

'Type 'ApolloClient<NormalizedCacheObject>' is not assignable to type 'ApolloClient<Cache>'

Below is the client/server code for rendering resulting in the error. The ApolloClient is created as stated in the docs.

// server.js
export const rootRoute = (req: express.Request, res: express.Response) => {
  const location = req.url
  const context: AppContext = {}
  const client = createApolloServer() // Create ApolloClient
  const store: Redux.Store<Store> = configureStore()

  const rawHTML = (
    <ApolloProvider client={client}> <----ERROR FROM ABOVE HERE
      <Provider store={store}> <---- Redux store
        <StaticRouter location={location} context={context}>
          <Main />
        </StaticRouter>
      </Provider>
    </ApolloProvider>
  )
}
// client.js
  const client = createApolloBrowser()
  const history = createHistory()
  const store: Redux.Store<Store> = configureStore()

  hydrate(
    <ApolloProvider client={client}> <----ERROR FROM ABOVE HERE
      <Provider store={store}> <---- Redux store
        <ConnectedRouter history={history}>
          <Main />
        </ConnectedRouter>
      </Provider>
    </ApolloProvider>,
    rootNode
  )

Below are the current set of dependencies:

    "apollo-cache-inmemory": "^1.1.0",
    "apollo-client-preset": "^1.0.2",
    "apollo-client": "^2.0.2",
    "apollo-link-context": "^1.0.0",
    "apollo-link-http": "^1.1.0",
    "react-apollo": "^2.0.0"

Thank you team Apollo for all your effort!