343 lines
8.1 KiB
JavaScript
343 lines
8.1 KiB
JavaScript
import config from '../config';
|
|
import * as Errors from './Errors';
|
|
|
|
class Api {
|
|
constructor() {
|
|
}
|
|
|
|
baseUrl() { return config.baseApiUrl; }
|
|
|
|
url(path) {
|
|
return this.baseUrl() + path;
|
|
}
|
|
|
|
checkStatus(response) {
|
|
if (response.status == 204) {
|
|
return null;
|
|
} else if (response.ok) {
|
|
return response.json();
|
|
} else if (response.status === 404) {
|
|
throw new Errors.ApiNotFoundError(response.statusText, response);
|
|
} else if (response.status === 422) {
|
|
return response.json().then(json => { throw new Errors.ApiValidationError(null, response, json) }, jsonErr => { throw new Errors.ApiValidationError(null, response, null) });
|
|
} else {
|
|
throw new Errors.ApiServerError(response.statusText || "Unknown Server Error", response);
|
|
}
|
|
}
|
|
|
|
parseJSON(response) {
|
|
return response.json();
|
|
}
|
|
|
|
performRequest(url, method, params = {}) {
|
|
const hasBody = Object.keys(params || {}).length !== 0;
|
|
|
|
const headers = new Headers();
|
|
headers.append('Accept', 'application/json');
|
|
headers.append('Content-Type', 'application/json');
|
|
|
|
const opts = {
|
|
headers,
|
|
method: method,
|
|
credentials: "same-origin"
|
|
};
|
|
|
|
if (hasBody) {
|
|
opts.body = JSON.stringify(params);
|
|
}
|
|
|
|
return fetch(url, opts).then(this.checkStatus);
|
|
}
|
|
|
|
objectToUrlParams(obj, queryParams = [], prefixes = []) {
|
|
for (let key in obj) {
|
|
const val = obj[key];
|
|
const paramName = prefixes.join("[") + "[".repeat(Math.min(prefixes.length, 1)) + encodeURIComponent(key) + "]".repeat(prefixes.length);
|
|
if (Array.isArray(val)) {
|
|
for (let x of val) {
|
|
queryParams.push(paramName + "[]=" + (x === null ? '' : encodeURIComponent(x)));
|
|
}
|
|
} else if (typeof(val) === "object") {
|
|
this.objectToUrlParams(val, queryParams, prefixes.concat([key]));
|
|
} else {
|
|
queryParams.push(paramName + "=" + (val === null ? '' : encodeURIComponent(val)));
|
|
}
|
|
}
|
|
|
|
return queryParams;
|
|
}
|
|
|
|
get(url, params = {}) {
|
|
|
|
const queryParams = this.objectToUrlParams(params);
|
|
|
|
if (queryParams.length) {
|
|
url = url + "?" + queryParams.join("&");
|
|
}
|
|
|
|
return this.performRequest(url, "GET");
|
|
}
|
|
|
|
post(url, params = {}) {
|
|
return this.performRequest(url, "POST", params);
|
|
}
|
|
|
|
patch(url, params = {}) {
|
|
return this.performRequest(url, "PATCH", params);
|
|
}
|
|
|
|
del(url, params = {}) {
|
|
return this.performRequest(url, "DELETE", params);
|
|
}
|
|
|
|
getRecipeList(page, per, sortColumn, sortDirection, name, tags) {
|
|
const params = {
|
|
criteria: {
|
|
page: page || null,
|
|
per: per || null,
|
|
sort_column: sortColumn || null,
|
|
sort_direction: sortDirection || null,
|
|
name: name || null,
|
|
tags: tags || null
|
|
}
|
|
};
|
|
|
|
return this.get("/recipes", params);
|
|
}
|
|
|
|
getRecipe(id, scale = null, system = null, unit = null) {
|
|
const params = {
|
|
scale,
|
|
system,
|
|
unit
|
|
};
|
|
|
|
return this.get("/recipes/" + id, params);
|
|
}
|
|
|
|
buildRecipeParams(recipe) {
|
|
const params = {
|
|
recipe: {
|
|
name: recipe.name,
|
|
description: recipe.description,
|
|
source: recipe.source,
|
|
yields: recipe.yields,
|
|
total_time: recipe.total_time,
|
|
active_time: recipe.active_time,
|
|
step_text: recipe.step_text,
|
|
tag_names: recipe.tag_names,
|
|
recipe_ingredients_attributes: recipe.ingredients.map(i => {
|
|
if (i._destroy) {
|
|
return {
|
|
id: i.id,
|
|
_destroy: true
|
|
};
|
|
} else {
|
|
return {
|
|
id: i.id,
|
|
name: i.name,
|
|
ingredient_id: i.ingredient_id,
|
|
quantity: i.quantity,
|
|
units: i.units,
|
|
preparation: i.preparation,
|
|
sort_order: i.sort_order
|
|
};
|
|
}
|
|
})
|
|
}
|
|
};
|
|
return params;
|
|
}
|
|
|
|
patchRecipe(recipe) {
|
|
return this.patch("/recipes/" + recipe.id, this.buildRecipeParams(recipe));
|
|
}
|
|
|
|
postRecipe(recipe) {
|
|
return this.post("/recipes/", this.buildRecipeParams(recipe));
|
|
}
|
|
|
|
postPreviewSteps(step_text) {
|
|
const params = {
|
|
step_text: step_text
|
|
};
|
|
|
|
return this.post("/recipes/preview_steps", params);
|
|
}
|
|
|
|
getSearchIngredients(query) {
|
|
const params = { query: query };
|
|
return this.get("/ingredients/search", params);
|
|
}
|
|
|
|
getCalculate(input, output_unit, density) {
|
|
const params = {
|
|
input,
|
|
output_unit,
|
|
density
|
|
};
|
|
return this.get("/calculator/calculate", params);
|
|
}
|
|
|
|
getIngredientList(page, per, name) {
|
|
const params = {
|
|
page,
|
|
per,
|
|
name
|
|
};
|
|
|
|
return this.get("/ingredients/", params);
|
|
}
|
|
|
|
getIngredient(id) {
|
|
return this.get("/ingredients/" + id);
|
|
}
|
|
|
|
buildIngredientParams(ingredient) {
|
|
return {
|
|
ingredient: {
|
|
name: ingredient.name,
|
|
notes: ingredient.notes,
|
|
ndbn: ingredient.ndbn,
|
|
density: ingredient.density,
|
|
|
|
water: ingredient.water,
|
|
ash: ingredient.ash,
|
|
protein: ingredient.protein,
|
|
kcal: ingredient.kcal,
|
|
fiber: ingredient.fiber,
|
|
sugar: ingredient.sugar,
|
|
carbohydrates: ingredient.carbohydrates,
|
|
calcium: ingredient.calcium,
|
|
iron: ingredient.iron,
|
|
magnesium: ingredient.magnesium,
|
|
phosphorus: ingredient.phosphorus,
|
|
potassium: ingredient.potassium,
|
|
sodium: ingredient.sodium,
|
|
zinc: ingredient.zinc,
|
|
copper: ingredient.copper,
|
|
manganese: ingredient.manganese,
|
|
vit_c: ingredient.vit_c,
|
|
vit_b6: ingredient.vit_b6,
|
|
vit_b12: ingredient.vit_b12,
|
|
vit_a: ingredient.vit_a,
|
|
vit_e: ingredient.vit_e,
|
|
vit_d: ingredient.vit_d,
|
|
vit_k: ingredient.vit_k,
|
|
cholesterol: ingredient.cholesterol,
|
|
lipids: ingredient.lipids,
|
|
|
|
|
|
ingredient_units_attributes: ingredient.ingredient_units.map(iu => {
|
|
if (iu._destroy) {
|
|
return {
|
|
id: iu.id,
|
|
_destroy: true
|
|
};
|
|
} else {
|
|
return {
|
|
id: iu.id,
|
|
name: iu.name,
|
|
gram_weight: iu.gram_weight
|
|
};
|
|
}
|
|
})
|
|
}
|
|
}
|
|
}
|
|
|
|
postIngredient(ingredient) {
|
|
return this.post("/ingredients/", this.buildIngredientParams(ingredient));
|
|
}
|
|
|
|
patchIngredient(ingredient) {
|
|
return this.patch("/ingredients/" + ingredient.id, this.buildIngredientParams(ingredient));
|
|
}
|
|
|
|
postIngredientSelectNdbn(ingredient) {
|
|
const url = ingredient.id ? "/ingredients/" + ingredient.id + "/select_ndbn" : "/ingredients/select_ndbn";
|
|
return this.post(url, this.buildIngredientParams(ingredient));
|
|
}
|
|
|
|
getUsdaFoodSearch(query) {
|
|
return this.get("/ingredients/usda_food_search", {query: query});
|
|
}
|
|
|
|
getNoteList() {
|
|
return this.get("/notes/");
|
|
}
|
|
|
|
postNote(note) {
|
|
const params = {
|
|
content: note.content
|
|
};
|
|
|
|
return this.post("/notes/", params);
|
|
}
|
|
|
|
deleteNote(note) {
|
|
return this.del("/notes/" + note.id);
|
|
}
|
|
|
|
getLogList(page, per) {
|
|
const params = {
|
|
page,
|
|
per
|
|
};
|
|
|
|
return this.get("/logs", params);
|
|
}
|
|
|
|
getLog(id) {
|
|
return this.get("/logs/" + id);
|
|
}
|
|
|
|
buildLogParams(log) {
|
|
const recParams = this.buildRecipeParams(log.recipe);
|
|
|
|
return {
|
|
log: {
|
|
date: log.date,
|
|
rating: log.rating,
|
|
notes: log.notes,
|
|
source_recipe_id: log.source_recipe_id,
|
|
recipe_attributes: recParams.recipe
|
|
}
|
|
};
|
|
}
|
|
|
|
postLog(log) {
|
|
const params = this.buildLogParams(log);
|
|
const rec = params.log.recipe_attributes;
|
|
if (rec && rec.recipe_ingredients_attributes) {
|
|
rec.recipe_ingredients_attributes.forEach(ri => ri.id = null);
|
|
}
|
|
return this.post("/recipes/" + log.original_recipe_id + "/logs/", params);
|
|
}
|
|
|
|
patchLog(log) {
|
|
return this.patch("/logs/" + log.id, this.buildLogParams(log));
|
|
}
|
|
|
|
postLogin(username, password) {
|
|
const params = {
|
|
username: username,
|
|
password: password
|
|
};
|
|
|
|
return this.post("/login", params);
|
|
}
|
|
|
|
getLogout() {
|
|
return this.get("/logout");
|
|
}
|
|
|
|
getCurrentUser() {
|
|
return this.get("/user")
|
|
}
|
|
}
|
|
|
|
const api = new Api();
|
|
|
|
export default api;
|