@rocali/expo-ts-rest-template v1.0.6
Expo Rest Template
Check demo gif
Expo project template with the following features:
- Full TypeScript integration
- Prettier and Eslint configured
- Light and Dark theme support with styled-components
- React Navigation with initial structure to get started
- Storybook integrated with components and screens
- Hygen for generating new components and screens
- @testing-library/react-native with testing examples
- i18n integration
- React Query with initial data structure and examples integrated with Rick and Morty API
- Initial components structure integrated with storybook
- Initial screens structure integrated with storybook and tests
Install
npx create-expo-app --template @rocali/expo-ts-rest-template my-appUsage
- start yarn start
- run on web yarn web
- run on ios yarn ios
- run on android yarn android
- compile typescript yarn ts
- lint yarn lf
- run tests yarn t
- ci (lint, typescript and tests) yarn ci
- create new component yarn new-comp NAME
- create new screen yarn new-screen NAME
- add screen or component to storybook yarn sbl
Structure
src/components
Create a component
Run yarn new-comp NAME to create component files
Run yarn sbl to add the new componente to Storybook
Creating a new component generates
src/components/NAME/index.stories.tsx
src/components/NAME/index.tsxThe component structure is based on src/components/Base component We're using Hygen for generating the files and you can modify as you want on _templates/components/new
src/context
src/context folder is used mostly exporting all Providers you need in the app
The exported AppProviders is linked on src/index.tsx
src/data
src/data is used to centralize all data related structure
The template comes with examples integrated with Rick and Morty API
For integrating the API data with Typescript we need to defined API all data types, so we devide the data info on:
src/data/models
Define all data model types
For example on /api/character request it returns a list of Character and we define the Character types on src/data/models/character.ts
export interface Character {
  id: number;
  name: string;
  ...
}src/data/operations
Define the requests functions
For example on /api/character request we define the typed function request on src/data/operations/characters.ts integrating with the axiosInstance exported on src/data/api.ts and defining the request variables CharactersVars and the request response CharactersData integrated with the Character data model from src/data/models/character
import { axiosInstance, PaginatedResponse } from '../api';
import { Character } from '../models/character';
//getCharacters
export interface CharactersVars {
  page: number;
}
export type CharactersData = PaginatedResponse<Character>;
export async function getCharacters({
  page,
}: CharactersVars): Promise<CharactersData> {
  const { data } = await axiosInstance.get<CharactersData>(
    `/character/?page=${page}`,
  );
  return data;
}src/data/hooks
We're using React Query for data fecthing
React Query is often described as the missing data-fetching library for React, but in more technical terms, it makes fetching, caching, synchronizing and updating server state in your React applications a breeze.
React query exports useQuery and useMutaion hooks, and we define those typed hooks on src/data/hooks
For /api/character request example we export a useCharactersQuery on src/data/hooks/character so when data response from useCharactersQuery already defines as CharactersData type
import { AxiosError } from 'axios';
import {
  useQuery,
  UseQueryOptions,
} from 'react-query';
import {
  getCharacters,
  CharactersData
} from '../operations/characters';
//useCharactersQuery
type CharactersQueryOptions = {
  options?: Omit<
    UseQueryOptions<CharactersData, AxiosError>,
    'queryKey' | 'queryFn'
  >;
};
export function useCharactersQuery({
  options
}: CharactersQueryOptions) {
  return useQuery(
    ['characters'],
    getCharacters
    options,
  );
}