[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/resolvers/source.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
interface Args {
  id: string
}

export const source = (
  _: any,
  { id }: Args,
  { clients: { markdown } }: Context
) => markdown.get(id)

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/resolvers/book.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export const book = async (
  _: any,
  { id }: { id: string },
  { clients: { book: bookClient } }: Context
) => bookClient.book(id)

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/resolvers/total.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export const total = (
  _: any,
  __: any,
  { clients: { book: booksClient } }: Context
) => booksClient.total()

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/resolvers/books.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
interface Args {
  from: number
  to: number
}

export const books = (
  _: any,
  args: Args,
  { clients: { book: booksClient } }: Context
) => booksClient.books(args)

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/resolvers/newBook.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import type { BookInput } from '../typings/custom'

interface Args {
  book: BookInput
}

export const newBook = (
  _: any,
  { book }: Args,
  { clients: { book: booksClient } }: Context
) => booksClient.newBook(book)

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/resolvers/editBook.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import { BookInput } from '../typings/custom'

interface EditBookArg {
  id: string
  book: BookInput
}

export const editBook = (
  _: any,
  { id, book }: EditBookArg,
  { clients: { book: booksClient } }: Context
) => booksClient.editBook(id, book)

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/resolvers/delete.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
interface Args {
  id: string
}

export const deleteBook = (
  _: any,
  { id }: Args,
  { clients: { book: booksClient } }: Context
) => booksClient.delete(id)

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/mock.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import automaticCacheUpdates from './docs/automaticCacheUpdates'
import dynamicPagination from './docs/dynamicPagination'
import home from './docs/home'
import previewWithCachedData from './docs/previewWithCachedData'
import staticPagination from './docs/staticPagination'
import styleguide from './docs/styleguide'

interface MarkdownData {
  [key: string]: string
}

const mock: MarkdownData = {
  'automatic-cache-updates/after': automaticCacheUpdates.after,
  'automatic-cache-updates/before': automaticCacheUpdates.before,
  'dynamic-pagination/after': dynamicPagination.after,
  'dynamic-pagination/before': dynamicPagination.before,
  'home/main': home.main,
  'preview-with-cached-data/after': previewWithCachedData.after,
  'preview-with-cached-data/before': previewWithCachedData.before,
  'static-pagination/after': staticPagination.after,
  'static-pagination/before': staticPagination.before,
  'styleguide/after': styleguide.after,
  'styleguide/before': styleguide.before,
}

export default mock

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import type { InstanceOptions, IOContext } from '@vtex/api'
import { ExternalClient } from '@vtex/api'

import mock from './mock'

export class MarkdownClient extends ExternalClient {
  private db = mock

  constructor(context: IOContext, options?: InstanceOptions) {
    super('http://example.com', context, options)
  }

  public get = (id: string) => this.db[id]
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/book/mock.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import type { Book } from '../../typings/custom'

const mock: Book[] = [
  {
    authors: ['Default Author 1'],
    id: '0',
    name: 'Default Book 1',
  },
  {
    authors: ['Default Author 2'],
    id: '1',
    name: 'Default Book 2',
  },
  {
    authors: ['Default Author 3'],
    id: '2',
    name: 'Default Book 3',
  },
  {
    authors: ['Default Author 4'],
    id: '3',
    name: 'Default Book 4',
  },
  {
    authors: ['Default Author 5'],
    id: '4',
    name: 'Default Book 5',
  },
  {
    authors: ['Default Author 11'],
    id: '10',
    name: 'Default Book 11',
  },
  {
    authors: ['Default Author 12'],
    id: '11',
    name: 'Default Book 12',
  },
  {
    authors: ['Default Author 13'],
    id: '12',
    name: 'Default Book 13',
  },
  {
    authors: ['Default Author 14'],
    id: '13',
    name: 'Default Book 14',
  },
  {
    authors: ['Default Author 15'],
    id: '14',
    name: 'Default Book 15',
  },
  {
    authors: ['Default Author 21'],
    id: '20',
    name: 'Default Book 21',
  },
  {
    authors: ['Default Author 22'],
    id: '21',
    name: 'Default Book 22',
  },
  {
    authors: ['Default Author 23'],
    id: '22',
    name: 'Default Book 23',
  },
  {
    authors: ['Default Author 24'],
    id: '23',
    name: 'Default Book 24',
  },
  {
    authors: ['Default Author 25'],
    id: '24',
    name: 'Default Book 25',
  },
]

export default mock

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/book/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import type { InstanceOptions, IOContext } from '@vtex/api'
import { ExternalClient } from '@vtex/api'
import { find, findIndex, propEq } from 'ramda'

import type { Book, BookInput, Maybe } from '../../typings/custom'
import mock from './mock'

export class BookClient extends ExternalClient {
  private db = mock

  constructor(context: IOContext, options?: InstanceOptions) {
    super('http://example.com', context, options)
  }

  public book = (id: string) => find(propEq('id', id), this.db)

  public books = ({ from, to }: { from: number; to: number }) =>
    this.db.slice(Math.max(from, 0), Math.min(to, this.db.length))

  public delete = (id: string) => {
    const foundIndex = findIndex(propEq('id', id), this.db)

    if (foundIndex >= 0 && foundIndex < this.db.length) {
      const newDb = [
        ...this.db.slice(0, foundIndex),
        ...this.db.slice(foundIndex + 1),
      ]

      this.db = newDb

      return true
    }

    return false
  }

  public editBook = (id: string, book: BookInput): Maybe<Book> => {
    const foundIndex = findIndex(propEq('id', id), this.db)

    if (foundIndex >= 0 && foundIndex < this.db.length) {
      const foundBook = this.db[foundIndex]

      this.db[foundIndex] = { ...foundBook, ...book }

      return this.db[foundIndex]
    }
  }

  public newBook = (book: BookInput): Book => {
    const newBook = {
      ...book,
      id: this.db.length.toString(),
    }

    const newDb = [newBook, ...this.db]

    this.db = newDb

    return newBook
  }

  public total = () => this.db.length
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/home/main.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  # VTEX IO Web Framework Best-Practices

  ## Welcome
  While coding apps, developers face common problems and patterns that are not strictly related to their business logic, like pagination and editing entities. To help you focuss more on your business logic, and less on reinventing the wheel, this repo was created aimming to contain all common patterns, all while respecting **VTEX IO Web Framework's** best practices and performance.

  ## What can I learn in this code base ?
  In this repo you will learn how to:

  - Use [VTEX Styleguide](https://styleguide.vtex.com/)
  - Internationalize your app
  - GraphQL (Back-End):
    - Architecture a GraphQL Schema
    - Create resolvers
    - Use Datasources
  - Front-End
    - Use extension points
    - Automatic cache updates
    - Preview with GraphQL cache
    - Pagination

  ## Can I use this repo in my projects ?
  Sure! this repository was designed with this goal in mind. If you are not able to easily port this code into your app, feel free to make a PR and start [contributing](https://github.com/vtex-apps/awesome-io#contributing).

  ## Getting Started
  This repo is an IO app like any other, so getting started is easy, just clone it, open your terminal, and type:

  \`\`\`sh
  vtex link
  \`\`\`

  just enter the \`/guide\` route and play a little

  ## How to read this repo
  An antipattern present in this repo is that the front and back-end code are in the same app. Usually they are split into different apps, given their differences in development cycle. Also, if your project is big enought, it's suggested you split your front-end app into a components app and a **Pages** app (app that places and instanciates these components). For the sake of simplicity and example efficiency, all these apps are joined into this one

  ### Basic architecture
  Since *web-framework-guide* is a VTEX IO app like any other, its folder structure is well known. In the root folder you can find a \`manifest.json\`, containing all of the app's metadata, like name, vendor, version etc. Also, you will find the following folders, each one matching it's corresponding builder

  - node - *where you actually implement your back-end app*
  - graphql - *where you define your graphql schema*
  - react - *where you write your react components*
  - pages - *where you place and instanciate the components*

  ### What if I didn't understand something ?
  If you didn't understand something or if you think this doc is incomplete, please open an issue in GitHub!
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/home/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import main from './main'

export default {
  main,
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/staticPagination/after.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  The most important part of the pagination implementation is coded in the \`PaginationController\` component.

  The pagination starts by querying the total number of items and the first 5 items of the list.

  When the \`next page\` button is clicked, the same query used for listing the first 5 elements is reused with the [fetchMore](https://www.apollographql.com/docs/react/features/pagination.html#fetch-more) function. The \`fetchMore\` function will then make a new query, bringing 5 more elements.

  After the loading state is finished, the \`updateQuery\` function is run, updating the Apollo Client's InMemory cache and concatenating the result into a single list.
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/staticPagination/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import after from './after'
import before from './before'

export default {
  after,
  before,
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/staticPagination/before.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  # Static Pagination

  In this example you will learn how to create a static, offset-based, pagination, i.e. how to paginate a list of items that DO NOT support adding or removing an element from the list. If you want to know how to handle a list that do support adding and removing elements, please check the \`Dynamic Pagination\` topic

  This example is a classical list-detail problem, where there is a list rendered in rows. Each row, when clicked, takes the user to a details page where more info can be seen about the element.

  In this topic, we use the detail component of the prior topic and focus on the list pagination.
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/dynamicPagination/after.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  The most important components in this example are the \`DeleteButton\` and \`NewElement\`, that handle deletion and creation of a list element respectively.

  Their code is really similar and takes advantage of the React Apollo Mutation's \`update\` method for updating the list in Apollo Client's InMemory cache.

  Basically, the these components make the deletion/creation mutation. In case of the mutation completing successfully, the book list is updated in the cache, removing or adding the altered element.

  When going back to the list view. The pagination component will render the list with the correct mutation applied and the element will be created/deleted.
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/dynamicPagination/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import after from './after'
import before from './before'

export default {
  after,
  before,
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/dynamicPagination/before.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  # Dynamic Pagination

  In this example you will learn how to create a dinamic, offset-based, pagination, i.e. how to paginate a list of items that DO support adding and removing an elements from the list.

  This example is a continuation of the *Static Pagination* topic and understanding the \`PaginationController\` component is a pre-requisite.

  As in the *Static Pagination* topic, we won't focuss on the detail, but rather on adding and removing and element from the list.
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/previewWithCachedData/after.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  Cool! But how is it coded?

  The implementation can be seen in \`PreviewWithCachedData\` component.

  The main ideia is to use the book query's loading state as a switcher between using the cached data or reading from the incoming query data.

  If the query is in loading state, the function \`readFromApolloCache\` is executed. It reads a Fragment from the Apollo Client's InMemory cache and the renderization occurs as usual.

  One important hint is using the \`buildCacheLocator\` function exported by \`render\`. This function takes as input the app id, the type and id of the fragment,and generates the Apollo Client's InMemory cache ID of the object we want to read the fragment from.

  When the book's query finishes loading, its data is used for rendering the final component.
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/previewWithCachedData/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import after from './after'
import before from './before'

export default {
  after,
  before,
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/previewWithCachedData/before.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  # Preview with Cached Data

  In this example you will learn how to
  [Reuse Cached Data](https://www.apollographql.com/docs/react/advanced/caching.html#readfragment).

  This technique uses [Apollo Client's InMemory cache](https://www.apollographql.com/docs/react/advanced/caching.html#smooth-scroll-top) and enables a greater user experience by reusing the data already present in the browser's local cache for making content preview.

  This example shows how this feature can improve the user's experience. It starts by querying a book list, which is shown below.

  Clicking in a row will take you to the detail page. The detail page needs more data than the available in the list, like the author's name.

  We can deliver a better user experience by previewing the edition component with the already present book's name in the browser's cache.

  To make our code more simple, we do not allow the edition of any of the book's properties before the query bringing the whole book info is completed, so the preview info is shown with the input disabled.
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/styleguide/after.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  To know more about the available components, visit the [**Styleguide** page](styleguide.vtex.com).
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/styleguide/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import after from './after'
import before from './before'

export default {
  after,
  before,
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/styleguide/before.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  # Using VTEX Styleguide

  To use **VTEX Styleguide**, you first need to add it as a dependency in your app's \`manifest.json\`

  \`\`\`json
  {
    "dependencies": {
      "vtex.styleguide": "8.x"
    }
  }
  \`\`\`

  after adding it as a dependency, you can import components from **Styleguide** in React components like so:

  \`\`\`tsx
  import React from 'react'
  import { Button } from 'vtex.styleguide'

  const MyAwesomeComponent: React.SFC = () => (
    <Button>Click me</Button>
  )
  \`\`\`

  The code above is shown running below:
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/automaticCacheUpdates/after.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  It's a kind of magic!

  The whole magic is made by using the cacheId option available in type Book and supported by InMemoryCache.

  Since InMemoryCache is a normalized data store, each element in the list has a unique key in the cache. This key is given by the cacheId field returned from the books.graphql query.

  The result of the mutation updates the book object under the key given by the returned cacheId. Since the object under the cacheId key was changed, when clicking in the back button and rerendering the book list, the list will be reconstructed with the new data, thus changing the rendered book info.

  Note that this feature can replace the use of Redux in most applications. Also, the name of the field cacheId is a convention and has to be respected
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/automaticCacheUpdates/index.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
import after from './after'
import before from './before'

export default {
  after,
  before,
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of graphql-example/node/clients/markdown/docs/automaticCacheUpdates/before.ts from the graphql-example VTEX app.

[Assistant]
Here's the implementation:

```typescript
export default `
  # Automatic Cache Updates

  In this example you will learn how to use
    [Automatic Cache Updates](https://www.apollographql.com/docs/react/advanced/caching.html#automatic-updates)

  Automatic Cache Updates let you update the Apollo Client's cache without any code!

  This example shows how this feature can be handy. It starts by querying a book list, which is shown by clicking in a row will take you to the detail page. The detail page allows you to edit the name and authors of a book. By clicking in save, a mutation will be made to the GraphQL API, mutating one SINGLE Book object. By click in the back button, the mutated book in the list will also be changed, all in ONE SINGLE MUTATION!
`

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/messages/pt.json from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.challenge-permission.title": "Desafio de permissão",
  "admin/editor.challenge-permission.permissions.title": "Permissões",
  "admin/editor.challenge-permission.permissions.items.title": "Permissões",
  "admin/editor.challenge-permission.permissions.items.name": "Nome",
  "admin/test": "teste",
  "store/test": "teste"
}
```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/messages/en.json from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.challenge-permission.title": "Permission Challenge",
  "admin/editor.challenge-permission.permissions.title": "Permissions",
  "admin/editor.challenge-permission.permissions.items.title": "Permissions",
  "admin/editor.challenge-permission.permissions.items.name": "Name",
  "admin/test": "test",
  "store/test": "test"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/messages/context.json from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.challenge-permission.title": "Permission Challenge",
  "admin/editor.challenge-permission.permissions.title": "Permissions",
  "admin/editor.challenge-permission.permissions.items.title": "Permissions",
  "admin/editor.challenge-permission.permissions.items.name": "Name",
  "admin/test": "test",
  "store/test": "test"
}
```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/messages/es.json from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.challenge-permission.title": "Desafío de permisos",
  "admin/editor.challenge-permission.permissions.title": "Permisos",
  "admin/editor.challenge-permission.permissions.items.title": "Permisos",
  "admin/editor.challenge-permission.permissions.items.name": "Nombre",
  "admin/test": "teste",
  "store/test": "teste"
}
```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/docs/README.md from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```markdown
# Organizations Challenge

Organizations Challenge is an app that checks if users are allowed to view content, based on their roles and permissions within [Organizations](https://github.com/vtex-apps/organizations).

## Prerequisites

Before using the Organizations Challenge app, please make sure you meet the following prerequisites.

### Set up your development environment

Before starting with the B2B Store Theme setup itself, you must:

1. [Set up a workspace to develop in VTEX IO](https://developers.vtex.com/vtex-developer-docs/docs/vtex-io-documentation-2-basicsetuptodevelopinvtexio) on your machine.
2. Follow [these instructions](https://developers.vtex.com/vtex-developer-docs/docs/vtex-io-documentation-2-prerequesites) to make sure you meet all the prerequisites to develop using Store Framework.
3. Make sure your store’s catalog is integrated with VTEX Intelligent Search, as described in [this article](https://help.vtex.com/en/tracks/vtex-intelligent-search--19wrbB7nEQcmwzDPl1l4Cb/6wKQgKmu2FT6084BJT7z5V).

### Install required Organizations apps

Now you must install the required apps listed below. They are mandatory for the Organizations Challenge app to work properly.

#### Admin Organizations

In brief, the [Admin Organizations](https://github.com/vtex-apps/admin-organizations) app is responsible for managing the Roles and Permissions modules on your store’s Admin.

Run the command  `vtex install vtex.admin-organizations@1.x` on the CLI to install it in your store.

#### Organizations

The [Organizations](https://github.com/vtex-apps/organizations) app allows you to create an organization — a business store — and manage users under that organization with different roles.

Run the command `vtex install vtex.organizations@1.x` on the CLI to install it on your store.

### Create Master Data schemas

You must have the following Master Data schemas configured:

* [`BusinessPermission schema`](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme#businesspermission-schema)
* [`BusinessRole schema`](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme#businessrole-schema)
* [`BusinessOrganization schema`](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme#businessorganization-schema)
* [`UserOrganization schema`](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme#userorganization-schema)

Learn more about how to create these schemas in the [Create Master Data schemas](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme#create-master-data-schemas) section of our guide on [Installing the B2B Store Theme](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme).

### Create Master Data fields

You need to have the `isOrgAdmin` and `organizationId` fields configured in Master Data. Learn more about how to create this field in the [Create fields in Master Data](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme#create-fields-in-master-data) section of our guide on [Installing the B2B Store Theme](https://developers.vtex.com/vtex-developer-docs/docs/installing-the-b2b-store-theme).

## Installation

First, add the app as a dependency in your theme’s `manifest.json` file, as follows:

```json
  "dependencies": {
    "vtex.organizations-challenge": "1.x"
  }
```

Then, follow the instructions below to set your theme’s blocks, manage roles and permissions and add permissions using the **Site Editor**.

### Set theme blocks

In your theme’s files, wrap the blocks you want to be visible only to the allowed logged-in users with `challenge-permission`.

This component will check if the user has permission to see the `allowed-content`, otherwise they will see the `disallowed-content`.

In the example below, taken from the B2B Store Theme’s `product-summary-prices.jsonc` file, the product prices are only visible to logged-in users with the `view_prices` permission. Otherwise, the store will show the `"Log in or sign up to view prices"` message instead.

Example:

```json
{
  "challenge-permission#product-summary-price": {
    "blocks": [
      "allowed-content#product-summary-price",
      "disallowed-content#product-summary-price"
    ],
    "props": {
      "permissions": [{ "name": "view_prices" }]
    }
  },
  "allowed-content#product-summary-price": {
    "children": ["product-summary-price"]
  },
  "disallowed-content#product-summary-price": {
    "children": ["rich-text#product-summary-price"]
  },
  "rich-text#product-summary-price": {
    "props": {
      "blockClass": ["product-summary-price-message"],
      "text": "Log in or sign up to view prices"
    }
  }
}
```

### Manage roles and permissions

To manage users’ permissions to view prices, you must follow the steps below to associate them with the `view_prices` permission.

1. In the **Account Settings** module on VTEX’s Admin panel, click on **Authorizations** and then on **All Permissions**.

2. Check if the `view_prices` permission exists, as shown in the image below.

    ![Permissions](https://raw.githubusercontent.com/vtex-apps/organizations-challenge/master/docs/images/1-permissions.png "Permissions")

    If it already exists, proceed to step 3.

    If it does not exist yet, click on `New` and fill in the fields as follows:

      * **Name:** view_prices
      * **Label:** View Prices

    Click on `Save`.

3. In the **Account Settings** module, click on **Authorizations** and then on **All Roles**.
4. Check if the **sales_manager** role exists and is associated with the **View Prices** permission, as shown below.

    ![Roles](https://raw.githubusercontent.com/vtex-apps/organizations-challenge/master/docs/images/2-roles.png "Roles")

    If it already exists, proceed to step 5.

    If it does not exist yet, click on `New` and fill in the fields as follows:

      * **Name:** sales_manager
      * **Label:** Sales Manager
      * **Add Permissions:** click on `˅` and then on **View Prices**.

    Click on `Save`.

5. Go to the store’s website and log in as the desired user.

6. Click on `Hello, {name}` and then on `My Account`, as shown below.

    ![My Account](https://raw.githubusercontent.com/vtex-apps/organizations-challenge/master/docs/images/3-myaccount.png "My Account")

7. Click on the **My Organization** tab.

8. Fill the data below and click on `Save`.

    * **Name:** organization name.
    * **Phone number:** organization phone number.
    * **Address:** address of the organization.
    * **Email:** email address of the organization.

The user will then be saved automatically with the **Sales Manager** role and the **View Prices** permission. If you refresh this page, you will be able to add other users as members of the organization and give them roles.

### Edit blocks’ permissions using Site Editor [OPTIONAL]

After the steps above, if you must edit the permissions allowed to see the defined blocks, you can do that either directly in the code – as explained in the [Set theme blocks](#set-theme-blocks) section – or using the **Site Editor**, on the VTEX Admin. This section will explain how to use the **Site Editor** with this purpose.

You should give a list of permissions to `challenge-permission` block from the **Site Editor** to allow or disallow relevant blocks.

1. In the **Store Setup** module on VTEX’s admin panel, click on **CMS** and then on **Site Editor**.

2. In the list of blocks, illustrated below, find the **Permission Challenge** block whose permissions you want to edit and click on it.

    ![Site Editor](https://raw.githubusercontent.com/vtex-apps/organizations-challenge/master/docs/images/4-siteeditor.png "Site Editor")

3. You will see the options below on the sidebar.

    ![Permission Challenge block](https://raw.githubusercontent.com/vtex-apps/organizations-challenge/master/docs/images/5-permissionchallengeblock.png "Permission Challenge block")

By clicking on the **Untitled content** field, you have the option to name this Permission Challenge block as you wish.

Under **Permissions**, you can click on `+ Add` to inform the **Name** of a permission allowed to see this block and click on `Apply` to save your changes.

![Allowed Permissions](https://raw.githubusercontent.com/vtex-apps/organizations-challenge/master/docs/images/6-allowedpermissions.png "Allowed Permissions")

The **view_prices** permission is already saved as an **Item** – if you click it you will have the option to change it, the same way you would create a new one.

If you perform any changes, make sure you click on `Apply`.

> ℹ The permission **Name** used on **Site Editor** must be valid on the **Permissions** page, as described in step 2 of the [Manage roles and permissions](#manage-roles-and-permissions) section.

## Customization

In order to apply CSS customizations in this and other blocks, follow the instructions given in the recipe on [Using CSS Handles for store customization](https://developers.vtex.com/vtex-developer-docs/docs/vtex-io-documentation-using-css-handles-for-store-customization).

You can create a file called `vtex.challenge-permission.css` inside the `styles/css` folder to add your custom styles.

| CSS Handle |
| ---------  |
| `challengeContentWrapper` |

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/PermissionChallenge.tsx from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```tsx
import React from 'react'
import type { ElementType } from 'react'
import { ExtensionPoint } from 'vtex.render-runtime'
import { defineMessages } from 'react-intl'

import { useProfileData } from './hooks/useProfileData'
import { useOrgAssignment } from './hooks/useOrgAssignment'
import { usePermissionIds } from './hooks/usePermissionIds'
import { useUserPermissionNames } from './hooks/useUserPermissionNames'

interface Permission {
  name: string
}

export interface MDField {
  key: string
  value: string
}

export interface MDSearchData {
  documents?: MDSearchDocument[]
}

export interface MDSearchDocument {
  id: string
  fields?: MDField[]
}

interface Props {
  permissions: Permission[]
  AllowedContent?: ElementType
  DisallowedContent?: ElementType
}

function PermissionChallenge({
  permissions = [],
  AllowedContent,
  DisallowedContent,
}: Props) {
  const profileData = useProfileData()
  const orgAssignment = useOrgAssignment(profileData)
  const permissionIds = usePermissionIds(orgAssignment)
  const { userPermissionNames } = useUserPermissionNames(permissionIds)

  let hasPermission = false

  if (userPermissionNames) {
    hasPermission = permissions.some(permission =>
      userPermissionNames.includes(permission.name)
    )
  }

  if (hasPermission) {
    return AllowedContent ? (
      <AllowedContent />
    ) : (
      <ExtensionPoint id="allowed-content" />
    )
  }

  return DisallowedContent ? (
    <DisallowedContent />
  ) : (
    <ExtensionPoint id="disallowed-content" />
  )
}

const messages = defineMessages({
  permissionChallengeTitle: {
    defaultMessage: '',
    id: 'admin/editor.challenge-permission.title',
  },
})

PermissionChallenge.schema = {
  // tslint:disable: object-literal-sort-keys
  title: messages.permissionChallengeTitle.id,
  type: 'object',
  properties: {
    permissions: {
      minItems: 0,
      type: 'array',
      title: 'admin/editor.challenge-permission.permissions.title',
      items: {
        title: 'admin/editor.challenge-permission.permissions.items.title',
        type: 'object',
        properties: {
          name: {
            title: 'admin/editor.challenge-permission.permissions.items.name',
            type: 'string',
          },
        },
      },
    },
  },
}

export default PermissionChallenge

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/BlockContent.tsx from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```tsx
import React from 'react'
import type { PropsWithChildren } from 'react'
import { useCssHandles } from 'vtex.css-handles'
import type { CssHandlesTypes } from 'vtex.css-handles'

const CSS_HANDLES = ['challengeContentWrapper'] as const

interface Props {
  classes?: CssHandlesTypes.CustomClasses<typeof CSS_HANDLES>
}

function BlockContent({ children, classes }: PropsWithChildren<Props>) {
  const { handles } = useCssHandles(CSS_HANDLES, { classes })

  return (
    <div className={`mw9 center ${handles.challengeContentWrapper}`}>
      {children}
    </div>
  )
}

export default BlockContent

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/package.json from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "scripts": {
    "test": "vtex-test-tools test"
  },
  "dependencies": {
    "apollo-client": "^2.6.3",
    "graphql": "^14.5.8",
    "react": "^16.8.6",
    "react-apollo": "^3.1.3",
    "react-dom": "^16.8.6",
    "react-intl": "3.9.1"
  },
  "devDependencies": {
    "@types/graphql": "^14.5.0",
    "@types/jest": "^24.0.21",
    "@types/node": "^12.12.3",
    "@vtex/test-tools": "^0.3.2",
    "@vtex/tsconfig": "^0.2.0",
    "vtex.css-handles": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.css-handles@1.0.0/public/@types/vtex.css-handles",
    "vtex.render-runtime": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.render-runtime@8.126.11/public/@types/vtex.render-runtime",
    "vtex.store": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.store@2.111.1/public/@types/vtex.store",
    "vtex.store-graphql": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.store-graphql@2.138.0/public/@types/vtex.store-graphql"
  },
  "version": "1.2.2"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/store/interfaces.json from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "challenge-permission": {
    "component": "PermissionChallenge",
    "allowed": ["allowed-content", "disallowed-content"]
  },
  "allowed-content": {
    "component": "BlockContent",
    "composition": "children",
    "allowed": "*"
  },
  "disallowed-content": {
    "component": "BlockContent",
    "composition": "children",
    "allowed": "*"
  }
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/typings/graphql.d.ts from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```typescript
declare module '*.graphql' {
  import type { DocumentNode } from 'graphql'

  const value: DocumentNode
  export default value
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/utils/const.ts from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```typescript
export const PROFILE_FIELDS = 'organizationId'

export const BUSINESS_ROLE = 'BusinessRole'
export const BUSINESS_ROLE_FIELDS = ['permissions']
export const BUSINESS_ROLE_SCHEMA = 'business-role-schema-v1'

export const BUSINESS_PERMISSION = 'BusinessPermission'
export const BUSINESS_PERMISSION_FIELDS = ['id', 'name']
export const BUSINESS_PERMISSION_SCHEMA = 'business-permission-schema-v1'

export const ORG_ASSIGNMENT = 'UserOrganization'
export const ORG_ASSIGNMENT_FIELDS = ['roleId']
export const ORG_ASSIGNMENT_SCHEMA = 'user-organization-schema-v1'

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/__tests__/index.test.tsx from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```tsx
describe('Product description scenario', () => {
  it('should work', () => {
    expect(1).toBe(1)
  })
})

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/graphql/getProfile.graphql from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```graphql
query Profile($customFields: String) @context(scope: "private") {
  profile(customFields: $customFields) {
    email
    customFields {
      key
      value
    }
  }
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/graphql/documents.graphql from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```graphql
query getDocuments(
  $acronym: String
  $fields: [String]
  $schema: String
  $where: String
  $page: Int
  $pageSize: Int
) {
  documents(
    acronym: $acronym
    fields: $fields
    schema: $schema
    where: $where
    page: $page
    pageSize: $pageSize
  ) {
    id
    fields {
      key
      value
    }
  }
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/hooks/useProfileData.ts from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```typescript
import { useQuery } from 'react-apollo'

import profileQuery from '../graphql/getProfile.graphql'
import { PROFILE_FIELDS } from '../utils/const'
import type { MDField } from '../PermissionChallenge'

interface ProfileData {
  profile?: {
    email?: string
    customFields?: MDField[]
  }
}

export interface UseProfileDataReturn {
  email?: string
  organizationId?: string
}

export function useProfileData(): UseProfileDataReturn {
  const { data: profileData } = useQuery<ProfileData>(profileQuery, {
    variables: { customFields: PROFILE_FIELDS },
    ssr: false,
  })

  const email = profileData?.profile?.email
  const customFields = profileData?.profile?.customFields

  const organizationId = customFields?.find(
    customField => customField.key === 'organizationId'
  )?.value

  return { email, organizationId }
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/hooks/useUserPermissionNames.ts from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```typescript
import { useQuery } from 'react-apollo'

import documentQuery from '../graphql/documents.graphql'
import {
  BUSINESS_PERMISSION,
  BUSINESS_PERMISSION_FIELDS,
  BUSINESS_PERMISSION_SCHEMA,
} from '../utils/const'
import type { MDSearchData } from '../PermissionChallenge'
import type { UsePermissionIdsReturn } from './usePermissionIds'

export interface UseUserPermissionNames {
  userPermissionNames?: string[] | null
}

export function useUserPermissionNames({
  permissionIds,
}: UsePermissionIdsReturn): UseUserPermissionNames {
  const { data: permissionData } = useQuery<MDSearchData>(documentQuery, {
    skip: !(permissionIds?.length > 0),
    variables: {
      acronym: BUSINESS_PERMISSION,
      fields: BUSINESS_PERMISSION_FIELDS,
      schema: BUSINESS_PERMISSION_SCHEMA,
    },
  })

  if (!permissionData || !permissionData.documents) {
    return { userPermissionNames: null }
  }

  const userPermissionNames: string[] = permissionData.documents
    .filter(document => permissionIds.includes(document.id))
    .map(
      document =>
        document.fields?.find(field => field.key === 'name')?.value ?? ''
    )
    .filter(Boolean)

  return { userPermissionNames }
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/hooks/useProfileAllowed.ts from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```typescript
import { useQuery } from 'react-apollo'

import checkProfileAllowedQuery from '../graphql/documents.graphql'

export const useProfileAllowed = (skip: boolean) => {
  const { loading, data, error } = useQuery(checkProfileAllowedQuery, {
    ssr: false,
    skip,
  })

  return !loading && data && !error ? !!data.checkProfileAllowed.allowed : null
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/hooks/useOrgAssignment.ts from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```typescript
import { useQuery } from 'react-apollo'

import documentQuery from '../graphql/documents.graphql'
import {
  ORG_ASSIGNMENT_FIELDS,
  ORG_ASSIGNMENT_SCHEMA,
  ORG_ASSIGNMENT,
} from '../utils/const'
import type { MDSearchData } from '../PermissionChallenge'
import type { UseProfileDataReturn } from './useProfileData'

export interface UseOrgAssignmentReturn {
  roleId?: string | null
}

export function useOrgAssignment({
  email,
  organizationId,
}: UseProfileDataReturn): UseOrgAssignmentReturn {
  const { data: orgAssignmentData } = useQuery<MDSearchData>(documentQuery, {
    skip: !email || !organizationId,
    variables: {
      acronym: ORG_ASSIGNMENT,
      schema: ORG_ASSIGNMENT_SCHEMA,
      fields: ORG_ASSIGNMENT_FIELDS,
      where: `(email=${email} AND businessOrganizationId=${organizationId})`,
    },
  })

  if (!orgAssignmentData || !orgAssignmentData.documents) {
    return { roleId: null }
  }

  const lastDocumentIndex = orgAssignmentData?.documents?.length - 1
  const rolePermissionFields =
    orgAssignmentData.documents[lastDocumentIndex]?.fields

  const roleId = rolePermissionFields?.find(field => field.key === 'roleId')
    ?.value

  return { roleId }
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of organizations-challenge/react/hooks/usePermissionIds.ts from the organizations-challenge VTEX app.

[Assistant]
Here's the implementation:

```typescript
import { useQuery } from 'react-apollo'

import documentQuery from '../graphql/documents.graphql'
import {
  BUSINESS_ROLE,
  BUSINESS_ROLE_FIELDS,
  BUSINESS_ROLE_SCHEMA,
} from '../utils/const'
import type { MDSearchData } from '../PermissionChallenge'
import type { UseOrgAssignmentReturn } from './useOrgAssignment'

const ARRAY_AS_STRING = '[]'

export interface UsePermissionIdsReturn {
  permissionIds: string[]
}

export function usePermissionIds({
  roleId,
}: UseOrgAssignmentReturn): UsePermissionIdsReturn {
  const { data: rolePermissionData } = useQuery<MDSearchData>(documentQuery, {
    skip: !roleId,
    variables: {
      acronym: BUSINESS_ROLE,
      fields: BUSINESS_ROLE_FIELDS,
      where: `(id=${roleId})`,
      schema: BUSINESS_ROLE_SCHEMA,
    },
  })

  if (!rolePermissionData || !rolePermissionData.documents) {
    return { permissionIds: [] }
  }

  const lastDocumentIndex = rolePermissionData.documents.length - 1
  const rolePermissionFields =
    rolePermissionData.documents[lastDocumentIndex]?.fields

  const unparsedPermissionIds = rolePermissionFields?.find(
    field => field.key === 'permissions'
  )?.value

  const permissionIds: string[] = JSON.parse(
    unparsedPermissionIds ?? ARRAY_AS_STRING
  )

  return { permissionIds }
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/it-IT.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Rich Text",
  "admin/editor.rich-text.text.title": "Testo",
  "admin/editor.rich-text.text.description": "Testi da visualizzare in linguaggio markdown",
  "admin/editor.rich-text.textPosition.title": "Posizione testo",
  "admin/editor.rich-text.textPosition.description": "Scegli in quale posizione verrà visualizzato il testo del componente: sinistra, centro o destra",
  "admin/editor.rich-text.textAlignment.title": "Allineamento testo",
  "admin/editor.rich-text.textAlignment.description": "Controlla l'allineamento del testo all'interno del componente",
  "admin/editor.rich-text.textPosition.left": "Sinistra",
  "admin/editor.rich-text.textPosition.center": "Centro",
  "admin/editor.rich-text.textPosition.right": "Destra",
  "admin/editor.rich-text.textAlignment.left": "Sinistra",
  "admin/editor.rich-text.textAlignment.center": "Centro",
  "admin/editor.rich-text.textAlignment.right": "Destra",
  "admin/editor.rich-text.font.title": "Token font",
  "admin/editor.rich-text.font.description": "Specifica il token del font da utilizzare come predefinito",
  "admin/editor.rich-text.textColor.title": "Token colore del testo",
  "admin/editor.rich-text.textColor.description": "Specifica il token del colore del testo da utilizzare",
  "admin/editor.rich-text.blockClass.title": "Classe di blocco",
  "admin/editor.rich-text.blockClass.description": "Nome di classe univoco da aggiungere alle classi di blocco"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/bs-BA.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "crwdns130176:0crwdne130176:0",
  "admin/editor.rich-text.text.title": "crwdns130178:0crwdne130178:0",
  "admin/editor.rich-text.text.description": "crwdns130180:0crwdne130180:0",
  "admin/editor.rich-text.textPosition.title": "crwdns130182:0crwdne130182:0",
  "admin/editor.rich-text.textPosition.description": "crwdns130184:0crwdne130184:0",
  "admin/editor.rich-text.textAlignment.title": "crwdns130186:0crwdne130186:0",
  "admin/editor.rich-text.textAlignment.description": "crwdns130188:0crwdne130188:0",
  "admin/editor.rich-text.textPosition.left": "crwdns130190:0crwdne130190:0",
  "admin/editor.rich-text.textPosition.center": "crwdns130192:0crwdne130192:0",
  "admin/editor.rich-text.textPosition.right": "crwdns130194:0crwdne130194:0",
  "admin/editor.rich-text.textAlignment.left": "crwdns130196:0crwdne130196:0",
  "admin/editor.rich-text.textAlignment.center": "crwdns130198:0crwdne130198:0",
  "admin/editor.rich-text.textAlignment.right": "crwdns130200:0crwdne130200:0",
  "admin/editor.rich-text.font.title": "crwdns130202:0crwdne130202:0",
  "admin/editor.rich-text.font.description": "crwdns130204:0crwdne130204:0",
  "admin/editor.rich-text.textColor.title": "crwdns130206:0crwdne130206:0",
  "admin/editor.rich-text.textColor.description": "crwdns130208:0crwdne130208:0",
  "admin/editor.rich-text.blockClass.title": "crwdns130210:0crwdne130210:0",
  "admin/editor.rich-text.blockClass.description": "crwdns130212:0crwdne130212:0"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/ko-KR.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "리치 텍스트",
  "admin/editor.rich-text.text.title": "텍스트",
  "admin/editor.rich-text.text.description": "표시할 마크다운 언어로 된 텍스트",
  "admin/editor.rich-text.textPosition.title": "텍스트 위치",
  "admin/editor.rich-text.textPosition.description": "왼쪽, 가운데 또는 오른쪽에 표시될 구성요소 텍스트의 위치 선택",
  "admin/editor.rich-text.textAlignment.title": "텍스트 정렬",
  "admin/editor.rich-text.textAlignment.description": "구성 요소 내부의 텍스트 정렬 제어",
  "admin/editor.rich-text.textPosition.left": "왼쪽",
  "admin/editor.rich-text.textPosition.center": "가운데",
  "admin/editor.rich-text.textPosition.right": "오른쪽",
  "admin/editor.rich-text.textAlignment.left": "왼쪽",
  "admin/editor.rich-text.textAlignment.center": "가운데",
  "admin/editor.rich-text.textAlignment.right": "오른쪽",
  "admin/editor.rich-text.font.title": "폰트 토큰",
  "admin/editor.rich-text.font.description": "기본값으로 사용할 폰트 토큰 지정",
  "admin/editor.rich-text.textColor.title": "텍스트 색 토큰",
  "admin/editor.rich-text.textColor.description": "사용할 텍스트 색 토큰 지정",
  "admin/editor.rich-text.blockClass.title": "블록 클래스",
  "admin/editor.rich-text.blockClass.description": "블록 클래스에 추가할 고유 클래스 이름"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/ja-JP.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "リッチテキスト",
  "admin/editor.rich-text.text.title": "テキスト",
  "admin/editor.rich-text.text.description": "表示するマークダウン言語のテキスト",
  "admin/editor.rich-text.textPosition.title": "テキストの位置",
  "admin/editor.rich-text.textPosition.description": "コンポーネントテキストが表示される位置を左、中央、右から選びます。",
  "admin/editor.rich-text.textAlignment.title": "文字揃え",
  "admin/editor.rich-text.textAlignment.description": "コンポーネント内の文字揃えをコントロールします",
  "admin/editor.rich-text.textPosition.left": "左",
  "admin/editor.rich-text.textPosition.center": "中央",
  "admin/editor.rich-text.textPosition.right": "右",
  "admin/editor.rich-text.textAlignment.left": "左",
  "admin/editor.rich-text.textAlignment.center": "中央",
  "admin/editor.rich-text.textAlignment.right": "右",
  "admin/editor.rich-text.font.title": "フォントトークン",
  "admin/editor.rich-text.font.description": "デフォルトで使うフォントトークンを指定する",
  "admin/editor.rich-text.textColor.title": "テキストカラートークン",
  "admin/editor.rich-text.textColor.description": "使用するテキストカラートークンを指定する",
  "admin/editor.rich-text.blockClass.title": "ブロッククラス",
  "admin/editor.rich-text.blockClass.description": "ブロッククラスに添付する独自のクラス名"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/bg-BG.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "RTF текст",
  "admin/editor.rich-text.text.title": "Текст",
  "admin/editor.rich-text.text.description": "Текст в маркдаун език, който ще се показва",
  "admin/editor.rich-text.textPosition.title": "Разположение на текста",
  "admin/editor.rich-text.textPosition.description": "Изберете в коя позиция на компонента ще се показва текстът – ляво, центрирано или дясно",
  "admin/editor.rich-text.textAlignment.title": "Подравняване на текста",
  "admin/editor.rich-text.textAlignment.description": "Контролира подравняването на текста в компонента",
  "admin/editor.rich-text.textPosition.left": "Ляво",
  "admin/editor.rich-text.textPosition.center": "Центрирано",
  "admin/editor.rich-text.textPosition.right": "Дясно",
  "admin/editor.rich-text.textAlignment.left": "Ляво",
  "admin/editor.rich-text.textAlignment.center": "Центрирано",
  "admin/editor.rich-text.textAlignment.right": "Дясно",
  "admin/editor.rich-text.font.title": "Маркер за шрифт",
  "admin/editor.rich-text.font.description": "Посочете маркера за шрифт, който да се използва по подразбиране",
  "admin/editor.rich-text.textColor.title": "Маркер за цвят на текст",
  "admin/editor.rich-text.textColor.description": "Посочете маркера за цвят на текст, който ще се използва",
  "admin/editor.rich-text.blockClass.title": "Блок клас",
  "admin/editor.rich-text.blockClass.description": "Уникално име на клас, което да се добавя към блок класовете"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/pt.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Rich Text",
  "admin/editor.rich-text.text.title": "Texto",
  "admin/editor.rich-text.text.description": "Texto em linguagem markdown a ser mostrado",
  "admin/editor.rich-text.textPosition.title": "Posição do texto",
  "admin/editor.rich-text.textPosition.description": "Escolha em qual posição o texto deve ser apresentado (esquerda, centro ou direita)",
  "admin/editor.rich-text.textAlignment.title": "Alinhamento do texto",
  "admin/editor.rich-text.textAlignment.description": "Controla o alinhamento dos textos dentro do componente",
  "admin/editor.rich-text.textPosition.left": "Esquerda",
  "admin/editor.rich-text.textPosition.center": "Centro",
  "admin/editor.rich-text.textPosition.right": "Direita",
  "admin/editor.rich-text.textAlignment.left": "Esquerda",
  "admin/editor.rich-text.textAlignment.center": "Centro",
  "admin/editor.rich-text.textAlignment.right": "Direita",
  "admin/editor.rich-text.font.title": "Token de fonte",
  "admin/editor.rich-text.font.description": "Especifique o token de fonte para ser usado como padrão",
  "admin/editor.rich-text.textColor.title": "Token de cor",
  "admin/editor.rich-text.textColor.description": "Especifique o token de cor do texto para ser usado como padrão",
  "admin/editor.rich-text.blockClass.title": "Classe do bloco",
  "admin/editor.rich-text.blockClass.description": "Nome da classe do bloco para ser anexado as classes padrão do bloco"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/en.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Rich Text",
  "admin/editor.rich-text.text.title": "Text",
  "admin/editor.rich-text.text.description": "Text in markdown language to be displayed",
  "admin/editor.rich-text.textPosition.title": "Text Position",
  "admin/editor.rich-text.textPosition.description": "Choose in which position of the component text will be displayed, left, center or right",
  "admin/editor.rich-text.textAlignment.title": "Text Alignment",
  "admin/editor.rich-text.textAlignment.description": "Control the text alignment inside component",
  "admin/editor.rich-text.textPosition.left": "Left",
  "admin/editor.rich-text.textPosition.center": "Center",
  "admin/editor.rich-text.textPosition.right": "Right",
  "admin/editor.rich-text.textAlignment.left": "Left",
  "admin/editor.rich-text.textAlignment.center": "Center",
  "admin/editor.rich-text.textAlignment.right": "Right",
  "admin/editor.rich-text.font.title": "Font token",
  "admin/editor.rich-text.font.description": "Specify the font token to be used as default",
  "admin/editor.rich-text.textColor.title": "Text Color token",
  "admin/editor.rich-text.textColor.description": "Specify the text color token to be used",
  "admin/editor.rich-text.blockClass.title": "Block class",
  "admin/editor.rich-text.blockClass.description": "Unique class name to be appended to block classes"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/ro-RO.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Text îmbogățit",
  "admin/editor.rich-text.text.title": "Text",
  "admin/editor.rich-text.text.description": "De afișat text în limbajul markdown",
  "admin/editor.rich-text.textPosition.title": "Poziție text",
  "admin/editor.rich-text.textPosition.description": "Alege în care poziție a componentei va fi textul afișat, stânga, centru sau dreapta",
  "admin/editor.rich-text.textAlignment.title": "Alinierea textului",
  "admin/editor.rich-text.textAlignment.description": "Controlează alinierea textului în interiorul componentei",
  "admin/editor.rich-text.textPosition.left": "Stânga",
  "admin/editor.rich-text.textPosition.center": "Centru",
  "admin/editor.rich-text.textPosition.right": "Dreapta",
  "admin/editor.rich-text.textAlignment.left": "Stânga",
  "admin/editor.rich-text.textAlignment.center": "Centru",
  "admin/editor.rich-text.textAlignment.right": "Dreapta",
  "admin/editor.rich-text.font.title": "Token font",
  "admin/editor.rich-text.font.description": "Specifică token-ul fontului care să fie folosit în calitate de cel prestabilit",
  "admin/editor.rich-text.textColor.title": "Token culoare text",
  "admin/editor.rich-text.textColor.description": "Specifică token-ul culorii textului care să fie folosit",
  "admin/editor.rich-text.blockClass.title": "Clasa de blocuri",
  "admin/editor.rich-text.blockClass.description": "Denumire unică a clasei care se anexează claselor de blocuri"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/context.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Title of Rich Text component",
  "admin/editor.rich-text.text.title": "Title of text property",
  "admin/editor.rich-text.text.description": "Description of text property",
  "admin/editor.rich-text.textPosition.title": "Title of textPosition property",
  "admin/editor.rich-text.textPosition.description": "Description of textPosition property",
  "admin/editor.rich-text.textAlignment.title": "Title of textAlignment property",
  "admin/editor.rich-text.textAlignment.description": "Description of textAlignment property",
  "admin/editor.rich-text.textPosition.left": "Name of enum value to make text at left position",
  "admin/editor.rich-text.textPosition.center": "Name of enum value to make text at center position",
  "admin/editor.rich-text.textPosition.right": "Name of enum value to make text at right position",
  "admin/editor.rich-text.textAlignment.left": "Name of enum value to align text to the left",
  "admin/editor.rich-text.textAlignment.center": "Name of enum value to align text to the center",
  "admin/editor.rich-text.textAlignment.right": "Name of enum value to align text to the right",
  "admin/editor.rich-text.font.title": "Title of font property",
  "admin/editor.rich-text.font.description": "Description of font property",
  "admin/editor.rich-text.textColor.title": "Title of textColor property",
  "admin/editor.rich-text.textColor.description": "Description of textColor property",
  "admin/editor.rich-text.blockClass.title": "Title of blockClass prop on Storefront",
  "admin/editor.rich-text.blockClass.description": "Description of blockClass prop on Storefront"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/de-DE.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Rich-Text",
  "admin/editor.rich-text.text.title": "Text",
  "admin/editor.rich-text.text.description": "Text in Markdown Sprache angezeigt werden",
  "admin/editor.rich-text.textPosition.title": "Textposition",
  "admin/editor.rich-text.textPosition.description": "Wählen Sie, an welcher Position der Text der Komponente angezeigt werden soll: links, mittig oder rechts",
  "admin/editor.rich-text.textAlignment.title": "Textausrichtung",
  "admin/editor.rich-text.textAlignment.description": "Steuern Sie die Textausrichtung innerhalb der Komponente",
  "admin/editor.rich-text.textPosition.left": "Links",
  "admin/editor.rich-text.textPosition.center": "Mittig",
  "admin/editor.rich-text.textPosition.right": "Rechts",
  "admin/editor.rich-text.textAlignment.left": "Links",
  "admin/editor.rich-text.textAlignment.center": "Mittig",
  "admin/editor.rich-text.textAlignment.right": "Rechts",
  "admin/editor.rich-text.font.title": "Font-Token",
  "admin/editor.rich-text.font.description": "Geben Sie den Font-Token an, der als Standard verwendet werden soll",
  "admin/editor.rich-text.textColor.title": "Textfarbe Token",
  "admin/editor.rich-text.textColor.description": "Geben Sie das Textfarbe Token an, das verwendet werden soll",
  "admin/editor.rich-text.blockClass.title": "Blockklasse",
  "admin/editor.rich-text.blockClass.description": "Eindeutiger Klassenname, der an Blockklassen angehängt werden soll"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/fr-FR.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Texte enrichi",
  "admin/editor.rich-text.text.title": "TextE",
  "admin/editor.rich-text.text.description": "Texte à afficher dans la langue de démarque",
  "admin/editor.rich-text.textPosition.title": "Position du texte",
  "admin/editor.rich-text.textPosition.description": "Choisir la position dans laquelle le texte composant sera affiché, à gauche, au centre ou à droite",
  "admin/editor.rich-text.textAlignment.title": "Alignement du texte",
  "admin/editor.rich-text.textAlignment.description": "Contrôler l’alignement du texte à l’intérieur du composant",
  "admin/editor.rich-text.textPosition.left": "Gauche",
  "admin/editor.rich-text.textPosition.center": "Centre",
  "admin/editor.rich-text.textPosition.right": "Droite",
  "admin/editor.rich-text.textAlignment.left": "Gauche",
  "admin/editor.rich-text.textAlignment.center": "Centre",
  "admin/editor.rich-text.textAlignment.right": "Droite",
  "admin/editor.rich-text.font.title": "Police d’écriture",
  "admin/editor.rich-text.font.description": "Préciser la police à utiliser par défaut",
  "admin/editor.rich-text.textColor.title": "Couleur du texte",
  "admin/editor.rich-text.textColor.description": "Préciser la couleur du texte à utiliser",
  "admin/editor.rich-text.blockClass.title": "Classe de bloc",
  "admin/editor.rich-text.blockClass.description": "Nom de classe unique à ajouter aux classes de bloc"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/nl-NL.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Rich tekst",
  "admin/editor.rich-text.text.title": "Tekst",
  "admin/editor.rich-text.text.description": "Tekst in markdown-taal die moet worden weergegeven",
  "admin/editor.rich-text.textPosition.title": "Tekstpositie",
  "admin/editor.rich-text.textPosition.description": "Kies in welke positie de componenttekst wordt weergegeven, links, in het midden of rechts",
  "admin/editor.rich-text.textAlignment.title": "Tekstuitlijning",
  "admin/editor.rich-text.textAlignment.description": "Regel de tekstuitlijning binnen het onderdeel",
  "admin/editor.rich-text.textPosition.left": "Links",
  "admin/editor.rich-text.textPosition.center": "Midden",
  "admin/editor.rich-text.textPosition.right": "Rechts",
  "admin/editor.rich-text.textAlignment.left": "Links",
  "admin/editor.rich-text.textAlignment.center": "Midden",
  "admin/editor.rich-text.textAlignment.right": "Rechts",
  "admin/editor.rich-text.font.title": "Lettertype token",
  "admin/editor.rich-text.font.description": "Specificeer het lettertype-token dat als standaard moet worden gebruikt",
  "admin/editor.rich-text.textColor.title": "Tekstkleurtoken",
  "admin/editor.rich-text.textColor.description": "Geef het tekstkleurtoken op dat moet worden gebruikt",
  "admin/editor.rich-text.blockClass.title": "Klasse blokkeren",
  "admin/editor.rich-text.blockClass.description": "Unieke klassenaam die moet worden toegevoegd om klassen te blokkeren"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/messages/es.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "admin/editor.rich-text.title": "Texto RTF",
  "admin/editor.rich-text.text.title": "Texto",
  "admin/editor.rich-text.text.description": "Texto en lenguaje de markdown que se mostrará",
  "admin/editor.rich-text.textPosition.title": "Posición del texto",
  "admin/editor.rich-text.textPosition.description": "Elija en que posición del componente se mostrará el texto: izquierda, centro o derecha",
  "admin/editor.rich-text.textAlignment.title": "Alineación del texto",
  "admin/editor.rich-text.textAlignment.description": "Controle la alineación del texto dentro del componente",
  "admin/editor.rich-text.textPosition.left": "Izquierda",
  "admin/editor.rich-text.textPosition.center": "Centro",
  "admin/editor.rich-text.textPosition.right": "Derecha",
  "admin/editor.rich-text.textAlignment.left": "Izquierda",
  "admin/editor.rich-text.textAlignment.center": "Centro",
  "admin/editor.rich-text.textAlignment.right": "Derecha",
  "admin/editor.rich-text.font.title": "Token de fuente",
  "admin/editor.rich-text.font.description": "Especifique el token de fuente que se utilizará como estándar",
  "admin/editor.rich-text.textColor.title": "Token de color del texto",
  "admin/editor.rich-text.textColor.description": "Especifique el token de color de texto que se utilizará",
  "admin/editor.rich-text.blockClass.title": "Clase del bloque",
  "admin/editor.rich-text.blockClass.description": "Nombre de clase único que se adjuntará a las clases de los bloques"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/docs/README.md from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```markdown
<!-- ALL-CONTRIBUTORS-BADGE:START - Do not remove or modify this section -->
[![All Contributors](https://img.shields.io/badge/all_contributors-0-orange.svg?style=flat-square)](#contributors-)
<!-- ALL-CONTRIBUTORS-BADGE:END -->
> 📢 Don't fork this project. Use, [contribute](https://github.com/vtex-apps/awesome-io#contributing), or open issues through [Store Discussion](https://github.com/vtex-apps/store-discussion).

# Rich Text

The Rich Text block converts text written in Markdown to HTML and displays it on your storefront.

![image](https://cdn.jsdelivr.net/gh/vtexdocs/dev-portal-content@main/images/vtex-rich-text-0.png)

For example, the following Markdown content

```txt
[Help](https://developers.vtex.com/vtex-developer-docs/docs/welcome).\n**Be Bold!**\n*This is italic*
```

would be rendered as

```html

        Help

        Be Bold!

        This is italic

```

Learn more in [Markdown documentation](https://www.markdownguide.org/cheat-sheet/).

## Configuration

1. Add the `rich-text` app to your theme’s dependencies in the `manifest.json` file:

```json
  "dependencies": {
    "vtex.rich-text": "0.x"
  }
```

2. Add the `rich-text` block to your block files in the desired template position. Example:

```json
"rich-text": {
  "props": {
    "textAlignment": "CENTER",
    "textPosition": "CENTER",
    "text": "Visit our [help](https://developers.vtex.com/) section.\n**Be Bold!**\n*This is italic*",
    "textColor": "c-on-emphasis",
    "font": "t-heading-5",
    "blockClass": "help-message"
  }
}
```

## Props

| Prop name       | Type                | Description                                                                                |
| --------------- | ------------------- | ------------------------------------------------------------------------------------------------------------ |
| `blockClass`    | `string`            | Unique class name appended to block classes. Default: ''                                               |
| `font`          | `string`            | Tachyon token used as font. Default: `t-body`. |
| `htmlId`     | `String` | HTML ID of the element.                                          |
| `textColor`     | `string`            | Tachyon token used as text color. Default: `c-on-base`.                                                |
| `text`          | `string`            | Text written in Markdown.                                                           |
| `textAlignment` | `TextAlignmentEnum` | Text alignment inside the component. Default: `"LEFT"`.                                                      |
| `textPosition`  | `TextPostionEnum`   | Text position relative to the component. Default: `"LEFT"`.                                               |

* **`TextAlignmentEnum` possible values**

| Enum name | Enum value | Description                           |
| --------- | ---------- | ------------------------------------- |
| Left      | 'LEFT'     | Aligns text to the left.   |
| Center    | 'CENTER'   | Aligns text to the center. |
| Right     | 'RIGHT'    | Aligns text to the right.  |

* **`TextPostionEnum` possible values**

| Enum name | Enum value | Description                           |
| --------- | ---------- | ------------------------------------- |
| Left      | 'LEFT'     | Positions content at the left of the component.   |
| Center    | 'CENTER'   | Positions content at the horizontal center of the component. |
| Right     | 'RIGHT'    | Positions content at the right of the component. |

## Customization

To apply CSS customizations to this and other blocks, follow the guide [Using CSS handles for store customization](https://developers.vtex.com/docs/guides/vtex-io-documentation-using-css-handles-for-store-customization).

| CSS Handle      |
| --------------- |
| `container`     |
| `heading`       |
| `headingLevel1` |
| `headingLevel2` |
| `headingLevel3` |
| `headingLevel4` |
| `headingLevel5` |
| `headingLevel6` |
| `image`         |
| `italic`        |
| `link`          |
| `list`          |
| `listItem`      |
| `listOrdered`   |
| `paragraph`     |
| `strong`        |
| `table`         |
| `tableBody`     |
| `tableHead`     |
| `tableTd`       |
| `tableTh`       |
| `tableTr`       |
| `wrapper`       |

<!-- DOCS-IGNORE:start -->

## Contributors ✨

Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/docs/en/emoji-key)):

<!-- ALL-CONTRIBUTORS-LIST:START - Do not remove or modify this section -->
<!-- prettier-ignore-start -->
<!-- markdownlint-disable -->
<!-- markdownlint-enable -->
<!-- prettier-ignore-end -->
<!-- ALL-CONTRIBUTORS-LIST:END -->

This project follows the [all-contributors](https://github.com/all-contributors/all-contributors) specification. Contributions of any kind welcome!
<!-- DOCS-IGNORE:end -->

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/react/index.tsx from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```tsx
import React, { memo, useEffect, useState, useRef, useMemo } from 'react'
import { useIntl } from 'react-intl'
import marked, { Renderer } from 'marked'
import escapeHtml from 'escape-html'
import insane from '@vtex/insane'
import { useCssHandles } from 'vtex.css-handles'
import { useResponsiveValue } from 'vtex.responsive-values'
import { formatIOMessage } from 'vtex.native-types'
import type { CssHandlesTypes } from 'vtex.css-handles'

import {
  textPositionTypes,
  textAlignmentTypes,
  TextPositionValues,
  TextAlignmentValues,
} from './typings/SchemaTypes'
import styles from './styles/index.css'

const CSS_HANDLES = [
  'container',
  'heading',
  'headingLevel1',
  'headingLevel2',
  'headingLevel3',
  'headingLevel4',
  'headingLevel5',
  'headingLevel6',
  'image',
  'italic',
  'link',
  'list',
  'listItem',
  'listOrdered',
  'paragraph',
  'strong',
  'table',
  'tableBody',
  'tableHead',
  'tableTd',
  'tableTh',
  'tableTr',
  'wrapper',
] as const

const JUSTIFY_TOKENS = {
  [TextPositionValues.LEFT]: 'justify-start',
  [TextPositionValues.CENTER]: 'justify-center',
  [TextPositionValues.RIGHT]: 'justify-end',
} as const

const ALIGN_TOKENS = {
  [TextAlignmentValues.LEFT]: 'tl',
  [TextAlignmentValues.CENTER]: 'tc',
  [TextAlignmentValues.RIGHT]: 'tr',
} as const

const ITEMS_TOKENS = {
  [TextAlignmentValues.LEFT]: 'items-start',
  [TextAlignmentValues.CENTER]: 'items-center',
  [TextAlignmentValues.RIGHT]: 'items-end',
} as const

const TYPOGRAPHY = [
  't-heading-1',
  't-heading-2',
  't-heading-3',
  't-heading-4',
  't-heading-5',
  't-heading-6',
  't-body',
  't-small',
  't-mini',
  't-code',
] as const

type PropTokensNames = 'textPosition' | 'textAlignment'

const DEFAULT_VALUES = {
  textPosition: textPositionTypes.TEXT_POSITION_LEFT.value,
  textAlignment: textAlignmentTypes.TEXT_ALIGNMENT_LEFT.value,
}

const safelyGetToken = (
  tokenMap: Record<string, string>,
  valueWanted: string,
  propName: PropTokensNames
) => tokenMap[valueWanted] || DEFAULT_VALUES[propName]

const sanitizerConfig = {
  allowedTags: [
    'a',
    'br',
    'div',
    'h1',
    'h2',
    'h3',
    'h4',
    'h5',
    'h6',
    'iframe',
    'img',
    'li',
    'ol',
    'p',
    'span',
    'sup',
    'table',
    'tbody',
    'td',
    'th',
    'thead',
    'tr',
    'ul',
  ],
  allowedAttributes: {
    '*': ['class', 'title'],
    a: ['href', 'target'],
    img: ['src', 'alt'],
    iframe: ['frameborder', 'height', 'src', 'width', 'style'],
  },
  allowedSchemes: ['http', 'https', 'mailto', 'tel'],
}

const getLevel = (level: number) => (level > 0 && level <= 6 ? level : 6)

const getTargetFromUrl = (url: string) => {
  const urlSplit = url.split('?')

  if (urlSplit.length < 2) {
    return ''
  }

  const [, qs] = urlSplit
  const hastTargetBlank = qs.includes('target=_blank')

  return hastTargetBlank ? 'target=_blank' : ''
}

const sanitizeFont = (font: string) => {
  if (!font) {
    return 't-body'
  }

  const [first] = font.split(' ')

  if (TYPOGRAPHY.indexOf(first as typeof TYPOGRAPHY[number]) === -1) {
    return 't-body'
  }

  return first
}

const sanitizeColor = (color: string) => {
  if (!color) {
    return 'c-on-base'
  }

  const [first] = color.split(' ')

  if (first.indexOf('c-') === 0) {
    return first
  }

  return 'c-on-base'
}

type RichTextCssHandles = CssHandlesTypes.CssHandles<typeof CSS_HANDLES>

const getHeadingLevelClass = (handles: RichTextCssHandles, level: number) => {
  if (level === 1) return handles.headingLevel1
  if (level === 2) return handles.headingLevel2
  if (level === 3) return handles.headingLevel3
  if (level === 4) return handles.headingLevel4
  if (level === 5) return handles.headingLevel5
  if (level === 6) return handles.headingLevel6

  return ''
}

const renderHeading = (handles: RichTextCssHandles) => (
  text: string,
  level: number
) => {
  const levelNumber = getLevel(level)
  const classes = `${
    handles.heading
  } t-heading-${levelNumber} ${getHeadingLevelClass(handles, levelNumber)} ${
    styles[`heading-level-${levelNumber}`]
  }`

  return `<h${levelNumber} class="${classes}">${text}</h${levelNumber}>`
}

type Props = {
  font?: string
  text?: string
  textAlignment?: TextAlignmentValues
  textColor?: string
  textPosition?: TextPositionValues
  htmlId?: string
  classes?: CssHandlesTypes.CustomClasses<typeof CSS_HANDLES>
}

function RichText({
  font = 't-body',
  text = '',
  textPosition = DEFAULT_VALUES.textPosition,
  textAlignment = DEFAULT_VALUES.textAlignment,
  textColor = 'c-on-base',
  htmlId,
  classes,
}: Props) {
  const intl = useIntl()
  const { handles } = useCssHandles(CSS_HANDLES, {
    classes,
  })

  const [isMounted, setMounted] = useState(false)
  const renderer = useRef<Renderer>()
  const responsiveFont = useResponsiveValue(font)

  useEffect(() => {
    setMounted(true)
  }, [])

  if (!isMounted) {
    renderer.current = new Renderer()
    renderer.current.paragraph = (content: string) =>
      `<p class="lh-copy ${handles.paragraph}">${content}</p>`
    renderer.current.strong = (content: string) =>
      `<span class="b ${handles.strong}">${content}</span>`
    renderer.current.em = (content: string) =>
      `<span class="i ${handles.italic}">${content}</span>`
    renderer.current.heading = renderHeading(handles)
    renderer.current.link = (href: string, title: string, content: string) => {
      const targetAtr = getTargetFromUrl(href)
      const targetRemoved = targetAtr
        ? href.replace(/target=_blank/, '').replace(/\?&/, '?')
        : href

      // clean trailing ? or &
      const cleanHref = targetRemoved.replace(/(\?|&)$/, '')
      const titleAtr = title ? `title="${title}"` : ''

      let finalLink = `<a class="${handles.link}" href="${cleanHref}"`

      if (titleAtr) {
        finalLink += ` ${titleAtr}`
      }

      if (targetAtr) {
        finalLink += ` ${targetAtr}`
      }

      finalLink += `>${content}</a>`

      return finalLink
    }

    renderer.current.html = (html) => escapeHtml(html)
    renderer.current.table = (header, body) => `
    <table class="${handles.table}">
      <thead class="${handles.tableHead}">
        ${header}
      </thead>
      <tbody class="${handles.tableBody}">
        ${body}
      </tbody>
    </table>`
    renderer.current.tablerow = (content) => {
      return `<tr class=${handles.tableTr}>\n${content}</tr>\n`
    }

    renderer.current.tablecell = (content, flags) => {
      const type = flags.header ? 'th' : 'td'
      const tag = `<${type} class="${
        type === 'th' ? handles.tableTh : handles.tableTd
      }"
        ${flags.align ? ` align="${flags.align}"` : ''}>`

      return `${tag + content}</${type}>\n`
    }

    renderer.current.image = (href: string, title: string, content: string) =>
      `<img class="${handles.image}" src="${href}" alt="${content}" ${
        title ? `title="${title}"` : ''
      } />`
    renderer.current.list = (body: string, ordered: boolean) => {
      const tag = ordered ? 'ol' : 'ul'

      return `<${tag} class="${handles.list} ${
        ordered ? handles.listOrdered : ''
      }">${body}</${tag}>`
    }

    renderer.current.listitem = (content: string) =>
      `<li class="${handles.listItem}">${content}</li>`
  }

  const alignToken = safelyGetToken(
    ALIGN_TOKENS,
    textAlignment,
    'textAlignment'
  )

  const itemsToken = safelyGetToken(ITEMS_TOKENS, textPosition, 'textPosition')
  const justifyToken = safelyGetToken(
    JUSTIFY_TOKENS,
    textPosition,
    'textPosition'
  )

  const html = useMemo(() => {
    marked.setOptions({
      gfm: true,
      breaks: true,
      sanitize: false, // Use insane lib for sanitizing
      smartLists: true,
      renderer: renderer.current,
    })

    return insane(
      // TODO: While markdown component isn't released, it needs to be done this way.
      marked(formatIOMessage({ id: text, intl })),
      sanitizerConfig
    )
  }, [text, intl])

  return (
    <div
      id={htmlId}
      className={`${
        handles.container
      } flex ${alignToken} ${itemsToken} ${justifyToken} ${sanitizeFont(
        responsiveFont
      )} ${sanitizeColor(textColor)}`}
    >
      <div
        className={handles.wrapper}
        dangerouslySetInnerHTML={{ __html: html }}
      />
    </div>
  )
}

const MemoizedRichText = memo(RichText)

// eslint-disable-next-line @typescript-eslint/no-explicit-any
;(MemoizedRichText as any).schema = {
  title: 'admin/editor.rich-text.title',
}

export default MemoizedRichText

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/react/package.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "name": "vtex.rich-text",
  "scripts": {
    "lint": "eslint . --ext .ts --ext .tsx",
    "lint:fix": "eslint --fix . --ext .ts --ext .tsx",
    "pretest": "yarn",
    "test": "vtex-test-tools test"
  },
  "dependencies": {
    "@vtex/insane": "^2.8.0",
    "escape-html": "^1.0.3",
    "marked": "^0.6.1",
    "react-intl": "^3.0.0"
  },
  "devDependencies": {
    "@apollo/react-testing": "^4.0.0",
    "@babel/core": "^7.3.4",
    "@babel/preset-env": "^7.3.4",
    "@types/escape-html": "^0.0.20",
    "@types/jest": "^24.0.9",
    "@types/marked": "^0.6.4",
    "@types/node": "^11.10.0",
    "@types/react": "^16.8.6",
    "@vtex/test-tools": "^3.3.2",
    "react-dom": "^16.8.4",
    "typescript": "3.9.7",
    "vtex.native-types": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.native-types@0.7.4/public/@types/vtex.native-types",
    "vtex.css-handles": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.css-handles@1.0.0/public/@types/vtex.css-handles",
    "vtex.render-runtime": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.render-runtime@8.126.4/public/@types/vtex.render-runtime",
    "vtex.responsive-values": "http://vtex.vtexassets.com/_v/public/typings/v1/vtex.responsive-values@0.4.0/public/@types/vtex.responsive-values"
  },
  "version": "0.16.1"
}

```


[System] You are an expert VTEX IO developer. You specialize in building VTEX Store Framework apps, React components, GraphQL APIs, and Node.js services for e-commerce platforms.

[User] Show me the implementation of rich-text/store/interfaces.json from the rich-text VTEX app.

[Assistant]
Here's the implementation:

```json
{
  "rich-text": {
    "component": "index",
    "content": {
      "title": "admin/editor.rich-text.title",
      "properties": {
        "text": {
          "title": "admin/editor.rich-text.text.title",
          "$ref": "app:vtex.native-types#/definitions/richText",
          "default": ""
        }
      }
    }
  }
}

```