# Customize

By default, `GraphQL(source)` derives typed [filter](../reference/Dataset.md#graphique.Dataset.filter), [columns](../reference/Dataset.md#graphique.Dataset.columns), and [row](../reference/Dataset.md#graphique.Dataset.row) from the schema. This can be done explicitly by calling [implement](../reference/implement.md#graphique.implement) on the ibis schema.


``` python
import ibis
import strawberry

from graphique import Dataset, GraphQL, implement

source = ibis.read_parquet("../../tests/fixtures/zipcodes.parquet")
Table = implement(source.schema())
issubclass(Table, Dataset)
```


    True


Subclass [Dataset](../reference/Dataset.md#graphique.Dataset) - or `Table` to include the typed fields - and register additional fields.

Protected fields such as [sql](../reference/Dataset.md#graphique.Dataset.sql) are denied by default; opt in with `strawberry.field(Dataset.sql, ...)`.


``` python
@strawberry.type
class Zipcodes(Table):
    sql = strawberry.field(Dataset.sql, permission_classes=[])  # enable permissions

    @strawberry.field  # add schema-aware fields manually
    def states(self) -> list[str]:
        return self.table["state"].value_counts()[0].to_list()
```


Call [GraphQL](../reference/GraphQL.md#graphique.GraphQL) on a `Query` type with attributes, so that the root value is stored. The types are inferred.


``` python
class Query:
    zipcodes = Zipcodes(source=source)

app = GraphQL(Query)
```


## Usage


``` python
def execute(query):
    result = app.schema.execute_sync(query, root_value=app.root_value)
    for error in result.errors or []:
        raise ValueError(error)
    return result.data

execute("""{ zipcodes {
    count
    filter(state: {eq: "CA"}) { count }
    sql(query: "select * from t where state = 'CA'", alias: "t") { count }
    states
} }""")
```


    {'zipcodes': {'count': 41700,
      'filter': {'count': 2647},
      'sql': {'count': 2647},
      'states': ['PR',
       'ME',
       'VT',
       'CT',
       'DC',
       'VA',
       'WV',
       'FL',
       'MS',
       'IN',
       'IL',
       'NE',
       'LA',
       'AR',
       'ID',
       'RI',
       'NJ',
       'DE',
       'SC',
       'AL',
       'TN',
       'KY',
       'OH',
       'MI',
       'IA',
       'SD',
       'ND',
       'MT',
       'MO',
       'OK',
       'TX',
       'AZ',
       'NV',
       'CA',
       'OR',
       'AK',
       'NC',
       'GA',
       'WI',
       'MN',
       'KS',
       'UT',
       'NM',
       'HI',
       'NY',
       'MA',
       'NH',
       'PA',
       'MD',
       'CO',
       'WY',
       'WA']}}


## Advanced

GraphQL implementations commonly treat top-level fields as [static methods](https://coady.github.io/posts/graphql-root-fields.html#static-methods). Whereas `graphique` requires root values to function as expected. The above example is syntactic sugar for:


``` python
@strawberry.type
class Query:
    zipcodes: Zipcodes

app = GraphQL(Query(zipcodes=Zipcodes(source=source)))
```
