Skip to content

Commit

Permalink
feat: Add functionality to AsyncBlock, PollBlock, LazyBlock and LoadB…
Browse files Browse the repository at this point in the history
…lock controllers to allow them to retry fetching content a set number of times when network errors occur.
  • Loading branch information
Sub-Xaero committed Nov 19, 2021
1 parent fe9d185 commit 3368392
Show file tree
Hide file tree
Showing 8 changed files with 42 additions and 7 deletions.
1 change: 1 addition & 0 deletions docs/docs/controllers/async_block_controller.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ AJAX load heavy content after the initial page load, while showing a placeholder
| `endpoint` | String | The URL to fetch content from | - |
| `errorMessage` (Optional) | String | The error message to display when the remote content fails to load | `This content failed to load` |
| `selector` (Optional) | String | The CSS selector to use to extract the desired element(s) from the returned HTML response | Empty. The entire HTML response will be loaded |
| `maxRetries` (Optional) | Number | How many times the controller should retry fetching the content in the event of network errors or bad responses | 1 |

## Events

Expand Down
1 change: 1 addition & 0 deletions docs/docs/controllers/lazy_block_controller.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ AJAX load content, only when it comes into view, while showing a placeholder.
| `endpoint` | String | The URL to fetch content from | - |
| `errorMessage` (Optional) | String | The error message to display when the remote content fails to load | `This content failed to load` |
| `selector` (Optional) | String | The CSS selector to use to extract the desired element(s) from the returned HTML response | Empty. The entire HTML response will be loaded |
| `maxRetries` (Optional) | Number | How many times the controller should retry fetching the content in the event of network errors or bad responses | 1 |

## Events

Expand Down
1 change: 1 addition & 0 deletions docs/docs/controllers/load_block_controller.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ AJAX load heavy content after the initial page load, while showing a placeholder
| `endpoint` | String | The URL to fetch content from | - |
| `errorMessage` (Optional) | String | The error message to display when the remote content fails to load | `This content failed to load` |
| `selector` (Optional) | String | The CSS selector to use to extract the desired element(s) from the returned HTML response | Empty. The entire HTML response will be loaded |
| `maxRetries` (Optional) | Number | How many times the controller should retry fetching the content in the event of network errors or bad responses | 1 |

## Events

Expand Down
1 change: 1 addition & 0 deletions docs/docs/controllers/poll_block_controller.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ AJAX load/refresh content periodically, at a configurable interval.
| `endpoint` | String | The URL to fetch content from | - |
| `errorMessage` (Optional) | String | The error message to display when the remote content fails to load | `This content failed to load` |
| `selector` (Optional) | String | The CSS selector to use to extract the desired element(s) from the returned HTML response | Empty. The entire HTML response will be loaded |
| `maxRetries` (Optional) | Number | How many times the controller should retry fetching the content in the event of network errors or bad responses | 1 |

## Events

Expand Down
11 changes: 7 additions & 4 deletions src/controllers/ajax/async_block_controller.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,19 @@
import {LoadBlockController} from "./load_block_controller";

export class AsyncBlockController extends LoadBlockController {

static targets = ["replace"];
static values = {endpoint: String, errorMessage: String, selector: String};
static values = {
endpoint: String,
errorMessage: String,
selector: String,
maxRetries: Number,
};

declare readonly replaceTarget: HTMLElement;
declare readonly hasReplaceTarget: boolean;
declare readonly endpointValue: string;

declare readonly hasSelectorValue: boolean;
declare readonly selectorValue: string;

declare readonly hasErrorMessageValue: boolean;
declare readonly errorMessageValue: string;

Expand Down
17 changes: 15 additions & 2 deletions src/controllers/ajax/load_block_controller.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,18 @@
import {BaseController} from "../../utilities/base_controller";
import {fetchRetry} from "../../utilities/fetchRetry";

export class LoadBlockController extends BaseController {

static targets = ["replace"];
static values = {endpoint: String, errorMessage: String, selector: String};
static values = {
endpoint: String,
errorMessage: String,
selector: String,
maxRetries: Number,
};

declare maxRetriesValue: number;
declare readonly hasMaxRetriesValue: boolean;

declare readonly replaceTarget: HTMLElement;
declare readonly hasReplaceTarget: boolean;
Expand All @@ -19,6 +28,10 @@ export class LoadBlockController extends BaseController {
return this.hasErrorMessageValue ? this.errorMessageValue : "This content failed to load";
}

get _maxRetries(): number {
return this.hasMaxRetriesValue ? this.maxRetriesValue : 1;
}

connect() {
}

Expand All @@ -34,7 +47,7 @@ export class LoadBlockController extends BaseController {
};

try {
let response = await fetch(this.endpointValue);
let response = await fetchRetry(this._maxRetries, this.endpointValue);
if (!response.ok) {
failure();
}
Expand Down
7 changes: 6 additions & 1 deletion src/controllers/ajax/poll_block_controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,12 @@ import {useInterval} from "../../mixins/use_interval";
export class PollBlockController extends LoadBlockController {

static targets = ["replace"];
static values = {endpoint: String, errorMessage: String, selector: String, seconds: Number};
static values = {
endpoint: String,
errorMessage: String,
selector: String,
maxRetries: Number,
};

declare readonly hasSecondsValue: boolean;
declare readonly secondsValue: number;
Expand Down
10 changes: 10 additions & 0 deletions src/utilities/fetchRetry.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
export async function fetchRetry(n: number, input: RequestInfo, init?: RequestInit): Promise<Response> {
try {
return await fetch(input, init);
} catch (err) {
if (n === 1) {
throw err;
}
return await fetchRetry(n - 1, input, init);
}
}

0 comments on commit 3368392

Please sign in to comment.