Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
209 changes: 209 additions & 0 deletions api_reference.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,209 @@
# FetchQL API Reference

FetchQL is a GraphQL client built on top of the Fetch API. It provides an easy-to-use interface for making GraphQL queries and managing request interceptors.

## Table of Contents

1. [Constructor](#constructor)
2. [Methods](#methods)
- [query](#query)
- [getEnumTypes](#getenumtypes)
- [getUrl](#geturl)
- [setUrl](#seturl)
- [addInterceptors](#addinterceptors)
- [removeInterceptors](#removeinterceptors)
- [clearInterceptors](#clearinterceptors)

## Constructor

### `new FetchQL(options)`

Creates a new FetchQL instance.

#### Parameters

- `options` (Object):
- `url` (String): The server address of GraphQL.
- `interceptors` (Object | Object[]): Optional. Request interceptors.
- `headers` (Object): Optional. Request headers.
- `onStart` (Function): Optional. Callback function when a new request queue starts.
- `onEnd` (Function): Optional. Callback function when a request queue finishes.
- `omitEmptyVariables` (Boolean): Optional. Remove null props (null or '') from the variables. Default is `false`.
- `requestOptions` (Object): Optional. Additional options for fetch requests.

#### Example

```javascript
const client = new FetchQL({
url: 'https://api.example.com/graphql',
headers: {
'Authorization': 'Bearer token123'
},
omitEmptyVariables: true
});
```

## Methods

### query

`query(options): Promise<FetchQLQueryResult>`

Executes a GraphQL query.

#### Parameters

- `options` (Object):
- `operationName` (String): Name of the GraphQL operation.
- `query` (String): GraphQL query string.
- `variables` (Object): Optional. Variables for the query.
- `opts` (Object): Optional. Additional options.
- `omitEmptyVariables` (Boolean): Remove null props from variables.
- `requestOptions` (Object): Optional. Additional options for fetch request.

#### Returns

A Promise that resolves to a `FetchQLQueryResult` object containing `data` and optional `errors`.

#### Example

```javascript
client.query({
operationName: 'GetUser',
query: `
query GetUser($id: ID!) {
user(id: $id) {
id
name
email
}
}
`,
variables: { id: '123' }
}).then(result => {
console.log(result.data);
}).catch(error => {
console.error(error);
});
```

### getEnumTypes

`getEnumTypes(EnumNameList): Promise<FetchQLEnumResult>`

Retrieves information about enum types.

#### Parameters

- `EnumNameList` (String[]): Array of enum names to fetch.

#### Returns

A Promise that resolves to a `FetchQLEnumResult` object containing enum information.

#### Example

```javascript
client.getEnumTypes(['UserRole', 'OrderStatus']).then(result => {
console.log(result.data);
}).catch(error => {
console.error(error);
});
```

### getUrl

`getUrl(): string`

Gets the current server address.

#### Returns

The current GraphQL server URL.

#### Example

```javascript
const currentUrl = client.getUrl();
console.log(currentUrl);
```

### setUrl

`setUrl(url: string): void`

Sets a new server address.

#### Parameters

- `url` (String): The new GraphQL server URL.

#### Example

```javascript
client.setUrl('https://new-api.example.com/graphql');
```

### addInterceptors

`addInterceptors(interceptors: FetchQLInterceptor | FetchQLInterceptor[]): () => void`

Adds new interceptors to the FetchQL instance.

#### Parameters

- `interceptors` (Object | Object[]): Interceptor object(s) with optional methods:
- `request`: Function called before a request is sent.
- `requestError`: Function called when a request encounters an error.
- `response`: Function called after a response is received.
- `responseError`: Function called when a response encounters an error.

#### Returns

A function that, when called, removes the added interceptors.

#### Example

```javascript
const removeInterceptors = client.addInterceptors({
request: (url, config) => {
console.log('Request intercepted:', url);
return [url, config];
},
response: (response) => {
console.log('Response intercepted:', response);
return response;
}
});

// Later, to remove the interceptors:
removeInterceptors();
```

### removeInterceptors

`removeInterceptors(indexes: number[]): void`

Removes interceptors by their indexes.

#### Parameters

- `indexes` (number[]): Array of interceptor indexes to remove.

#### Example

```javascript
client.removeInterceptors([0, 2]); // Removes the first and third interceptors
```

### clearInterceptors

`clearInterceptors(): void`

Removes all interceptors.

#### Example

```javascript
client.clearInterceptors();
```
148 changes: 148 additions & 0 deletions best_practices.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,148 @@
# Best Practices for Using FetchQL in Production

This guide provides a comprehensive list of best practices for using FetchQL in production applications. By following these recommendations, you can optimize performance, enhance security, and improve the overall organization of your GraphQL queries.

## Performance Optimization

1. **Use Query Batching**: Combine multiple queries into a single request when possible to reduce network overhead.

```javascript
const fetchQL = new FetchQL({ url: 'https://api.example.com/graphql' });

fetchQL.query({
operationName: 'BatchedQueries',
query: `
query BatchedQueries {
users { id name }
posts { id title }
}
`
});
```

2. **Implement Caching**: Utilize client-side caching to store frequently accessed data and reduce server load.

3. **Optimize Query Complexity**: Avoid overfetching by requesting only the necessary fields in your queries.

4. **Use Pagination**: For large datasets, implement pagination to limit the amount of data transferred in a single request.

```javascript
fetchQL.query({
operationName: 'PaginatedPosts',
query: `
query PaginatedPosts($page: Int, $pageSize: Int) {
posts(page: $page, pageSize: $pageSize) {
id
title
}
}
`,
variables: { page: 1, pageSize: 10 }
});
```

5. **Leverage Enum Caching**: FetchQL provides built-in caching for enum types. Use `getEnumTypes()` to fetch and cache enum information.

```javascript
fetchQL.getEnumTypes(['PostStatus', 'UserRole'])
.then(({ data }) => {
console.log('Cached enum types:', data);
});
```

## Security Considerations

1. **Use HTTPS**: Always use HTTPS for your GraphQL endpoint to encrypt data in transit.

2. **Implement Authentication**: Secure your GraphQL API with proper authentication mechanisms.

```javascript
const fetchQL = new FetchQL({
url: 'https://api.example.com/graphql',
headers: {
Authorization: 'Bearer YOUR_AUTH_TOKEN'
}
});
```

3. **Sanitize User Input**: Validate and sanitize all user-provided input before including it in queries.

4. **Set Request Timeouts**: Implement timeouts to prevent long-running queries from overwhelming your server.

```javascript
const fetchQL = new FetchQL({
url: 'https://api.example.com/graphql',
requestOptions: {
timeout: 5000 // 5 seconds timeout
}
});
```

5. **Use Query Whitelisting**: Implement a query whitelist on the server to prevent arbitrary queries from being executed.

## Query Organization

1. **Modularize Queries**: Organize your queries into separate files or modules for better maintainability.

2. **Use Fragment Composition**: Utilize fragments to compose reusable query parts and reduce duplication.

```javascript
const userFragment = `
fragment UserDetails on User {
id
name
email
}
`;

fetchQL.query({
operationName: 'GetUser',
query: `
${userFragment}
query GetUser($id: ID!) {
user(id: $id) {
...UserDetails
}
}
`,
variables: { id: 'user123' }
});
```

3. **Implement Error Handling**: Use FetchQL's error handling capabilities to gracefully manage query errors.

```javascript
fetchQL.query({
operationName: 'GetUser',
query: '...',
variables: { id: 'user123' }
}).then(({ data, errors }) => {
if (errors) {
console.error('GraphQL Errors:', errors);
} else {
console.log('User data:', data);
}
}).catch(error => {
console.error('Network Error:', error);
});
```

4. **Use Named Operations**: Always provide operation names for better debugging and logging.

5. **Implement Request Queue Management**: Utilize FetchQL's `onStart` and `onEnd` callbacks to manage request queues and implement loading indicators.

```javascript
const fetchQL = new FetchQL({
url: 'https://api.example.com/graphql',
onStart: (queueLength) => {
console.log(`Request queue started. Length: ${queueLength}`);
showLoadingIndicator();
},
onEnd: (queueLength) => {
console.log(`Request queue finished. Length: ${queueLength}`);
hideLoadingIndicator();
}
});
```

By following these best practices, you can ensure that your FetchQL implementation is efficient, secure, and well-organized in production environments. Remember to regularly review and update your practices as your application scales and new features are introduced.
Loading
Loading