All files / src/context SertoUiProvider.tsx

80% Statements 8/10
100% Branches 4/4
50% Functions 2/4
80% Lines 8/10

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57                                                      1x   1x 1x       1x 1x       1x               1x       2x          
import * as React from "react";
import { ToastMessage } from "rimble-ui";
import { IdentityThemeProvider } from "../themes/IdentityTheme";
import { SertoUiContext, SertoUiContextInterface, defaultSertoUiContext, ToastInterface } from "./SertoUiContext";
import { SertoSearchService } from "../services/SertoSearchService";
import { SertoSchemasService } from "../services/SertoSchemasService";
import { JwtUserData } from "../types";
 
declare global {
  interface Window {
    toastProvider: ToastInterface;
  }
}
 
type DeepPartial<T> = {
  [P in keyof T]?: DeepPartial<T[P]>;
};
 
export interface SertoUiContextProviderProps {
  schemasApiUrl?: string;
  schemasApiJwt?: string;
  schemasApiUserData?: JwtUserData;
  searchApiUrl?: string;
  theme?: any;
  context?: DeepPartial<SertoUiContextInterface>;
}
 
export const SertoUiProvider: React.FunctionComponent<SertoUiContextProviderProps> = (props) => {
  // We want to merge props.context.schemasService into the default SertoSchemasService, but can't use the spread operator cause it will ignore the prototype properties of SertoSchemasService. So instead instantiate the class and then apply any overrides from props:
  const schemasService = new SertoSchemasService(props.schemasApiUrl, props.schemasApiJwt, props.schemasApiUserData);
  Object.keys(props.context?.schemasService || {}).forEach((key) => {
    // "as any" cause TypeScript doesn't like indexing a class instance with an arbitrary string, and `Object.keys` doesn't seem to preserve types.
    (schemasService as any)[key] = (props.context?.schemasService as any)[key];
  });
  const searchService = new SertoSearchService(props.searchApiUrl);
  Object.keys(props.context?.searchService || {}).forEach((key) => {
    (searchService as any)[key] = (props.context?.searchService as any)[key];
  });
 
  const context = {
    ...defaultSertoUiContext,
    ...props.context,
    schemasService,
    searchService,
    toastProvider: window.toastProvider,
  } as SertoUiContextInterface;
 
  return (
    <SertoUiContext.Provider value={context}>
      <IdentityThemeProvider theme={props.theme}>
        {props.children}
        <ToastMessage.Provider ref={(node: any) => (window.toastProvider = node)} />
      </IdentityThemeProvider>
    </SertoUiContext.Provider>
  );
};