S
SolidJS2mo ago
najati

Idiomatic way to async update a signal through api call

I'm trying to async'ly update a value that's displayed in a couple places on the page. I'm looking for the most idiomatic/straightforward way to have a signal (or something that looks like one and is reactive) that I can use to display the value, update the value, and get the current state of the async update request. I've looked at createResource, query, and createAsync and none of them seem like natural fits, primarily because they are oriented around looking up an object from some key or other object, not providing a notion of having an object that can be updated. Maybe I'm totally wrong there, but I've tried a couple implementations and they didn't feel right. So I wrote my own little wrapper around a couple signals to show what I'm trying to do in case there's a more natural way. It's small, about 15 lines of actual code, and results in an interface that feels natural. This is the wrapper: https://gist.github.com/najati/7fc22ace9b8b48646f182b6bdff41db1 Example usage:
// initialization
const updateName = (value) => axios.post(`/budgets/${budgetId}/rename`, {name: value});
const budgetName = createUpdatable(getBudgetName(state), updateName);

// display
function BudgetName(props: { budgetName: Updatable.Updatable<string> }) {
const budgetName = props.budgetName;
const className = Updatable.State[budgetName.state()].toLowerCase();

return <span className={"budget-name " + className}>
<Switch>
<Match when={budgetName.error}>
<span>Error: {budgetName.error}</span>
</Match>
<Match when={budgetName.value()}>
<div>{budgetName.value()}</div>
</Match>
</Switch>
</span>;
}

// update
function UpdateBudgetName(props: UpdateBudgetNameProps) {
const budgetName = props.budgetName;

const submitUpdate = () => {
budgetName.setValue(inputElement.value);
return true;
};

// call submitUpdate somewhere in some input hander
// initialization
const updateName = (value) => axios.post(`/budgets/${budgetId}/rename`, {name: value});
const budgetName = createUpdatable(getBudgetName(state), updateName);

// display
function BudgetName(props: { budgetName: Updatable.Updatable<string> }) {
const budgetName = props.budgetName;
const className = Updatable.State[budgetName.state()].toLowerCase();

return <span className={"budget-name " + className}>
<Switch>
<Match when={budgetName.error}>
<span>Error: {budgetName.error}</span>
</Match>
<Match when={budgetName.value()}>
<div>{budgetName.value()}</div>
</Match>
</Switch>
</span>;
}

// update
function UpdateBudgetName(props: UpdateBudgetNameProps) {
const budgetName = props.budgetName;

const submitUpdate = () => {
budgetName.setValue(inputElement.value);
return true;
};

// call submitUpdate somewhere in some input hander
Is there a more idiomatic way to do this?
1 Reply
Madaxen86
Madaxen862mo ago
One way : wrap your getBudgetName in query wrap your updateName in action (helper to update) and in there optionally add one of the response helpers (json,reload,redirect) and provide revalidate with then query key. Call the query with createAsync

Did you find this page helpful?