From 59e6f7ebe87c516752275d11673557cc58ed9d09 Mon Sep 17 00:00:00 2001 From: Tucker Evans Date: Mon, 9 Dec 2019 17:29:18 -0500 Subject: Fix ingredient unit type to be same across frontend & backend --- backend/readme.adoc | 1 - backend/recipe.go | 3 +-- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/backend/readme.adoc b/backend/readme.adoc index b10ea07..2a00ba5 100644 --- a/backend/readme.adoc +++ b/backend/readme.adoc @@ -37,7 +37,6 @@ The current implementation expects (and returns) recipes in the form: "name": "Ingredient 1 Name", "amount": 1.0, "unit": "Ingredient Units" - "type_": "" }, ], "steps": [ diff --git a/backend/recipe.go b/backend/recipe.go index a3191c3..3511fd6 100644 --- a/backend/recipe.go +++ b/backend/recipe.go @@ -6,8 +6,7 @@ import "strings" type Ingredient struct { Name string `json:"name"` Amount float64 `json:"amount"` - Unit string `json:"units"` - Type string `json:"type"` + Unit string `json:"unit"` } type Step struct { -- cgit v1.1 From 24e9e8530fe5b7ee4a6da37b5da7a1b66eb5b467 Mon Sep 17 00:00:00 2001 From: Tucker Evans Date: Mon, 9 Dec 2019 18:03:41 -0500 Subject: Add routing to main page after sumbitting --- recipeBuddy/src/app/add-recipe/add-recipe.component.ts | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/recipeBuddy/src/app/add-recipe/add-recipe.component.ts b/recipeBuddy/src/app/add-recipe/add-recipe.component.ts index 407997c..8f00146 100644 --- a/recipeBuddy/src/app/add-recipe/add-recipe.component.ts +++ b/recipeBuddy/src/app/add-recipe/add-recipe.component.ts @@ -7,6 +7,8 @@ import { FormArray } from '@angular/forms'; import { Validators } from '@angular/forms'; +import { Router } from '@angular/router'; + import { Recipe } from '../DataModels/recipe'; import { Ingredient } from '../DataModels/ingredient' import { Step } from '../DataModels/step'; @@ -43,7 +45,8 @@ export class AddRecipeComponent { }); constructor(private fb: FormBuilder, - private restService: BackendService + private restService: BackendService, + private router: Router, ) { } ngOnInit() { @@ -121,6 +124,7 @@ export class AddRecipeComponent { formData.tags.split(','), //tags formData.photos.split(',') //photos ); - this.restService.createRecipe(recipe).subscribe() + this.restService.createRecipe(recipe).subscribe(); + this.router.navigate(['/']); } } -- cgit v1.1 From e8d327e3783831107400456de84ecd79241b5773 Mon Sep 17 00:00:00 2001 From: Tucker Evans Date: Mon, 9 Dec 2019 18:03:59 -0500 Subject: Fix array indexing of formData.steps --- recipeBuddy/src/app/add-recipe/add-recipe.component.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/recipeBuddy/src/app/add-recipe/add-recipe.component.ts b/recipeBuddy/src/app/add-recipe/add-recipe.component.ts index 8f00146..e6555d4 100644 --- a/recipeBuddy/src/app/add-recipe/add-recipe.component.ts +++ b/recipeBuddy/src/app/add-recipe/add-recipe.component.ts @@ -102,9 +102,9 @@ export class AddRecipeComponent { } var steps = [] - for (i = 0; i < formData.ingredients.length; i++) { - var tmp_timer = parseInt(formData.steps[0].timer) - steps.push(new Step(formData.steps[0].instruct, + for (i = 0; i < formData.steps.length; i++) { + var tmp_timer = parseInt(formData.steps[i].timer) + steps.push(new Step(formData.steps[i].instruct, (isNaN(tmp_timer) ? 0 : tmp_timer) )); } -- cgit v1.1 From 58043492cf8a12d3b73dbb8760e26ffce0e2dc41 Mon Sep 17 00:00:00 2001 From: Tucker Evans Date: Fri, 6 Dec 2019 15:32:20 -0500 Subject: Add toolbar to main app template --- recipeBuddy/src/app/app.component.html | 18 +++++++++++++++++- recipeBuddy/src/app/app.module.ts | 4 +++- 2 files changed, 20 insertions(+), 2 deletions(-) diff --git a/recipeBuddy/src/app/app.component.html b/recipeBuddy/src/app/app.component.html index 014c6b0..830c5cb 100644 --- a/recipeBuddy/src/app/app.component.html +++ b/recipeBuddy/src/app/app.component.html @@ -1,2 +1,18 @@ -

{{title}}

+ + + + + +
+ + + +
+
diff --git a/recipeBuddy/src/app/app.module.ts b/recipeBuddy/src/app/app.module.ts index 359254e..e6c3a27 100644 --- a/recipeBuddy/src/app/app.module.ts +++ b/recipeBuddy/src/app/app.module.ts @@ -19,6 +19,7 @@ import { MatInputModule } from '@angular/material/input'; import { MatFormFieldModule } from '@angular/material'; import { MatIconModule } from '@angular/material/icon'; import { MatButtonModule } from '@angular/material/button'; +import { MatToolbarModule } from '@angular/material/toolbar'; @NgModule({ declarations: [ @@ -37,7 +38,8 @@ import { MatButtonModule } from '@angular/material/button'; MatInputModule, MatFormFieldModule, MatIconModule, - MatButtonModule + MatButtonModule, + MatToolbarModule ], providers: [], bootstrap: [AppComponent] -- cgit v1.1 From c85f7519729d5ad4120f60d742e5f5e6f62d136e Mon Sep 17 00:00:00 2001 From: Tucker Evans Date: Tue, 10 Dec 2019 14:50:28 -0500 Subject: Fix intructions -> intruction for backend json Now the same as frontend data models. --- backend/readme.adoc | 12 ++++++------ backend/recipe.go | 2 +- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/backend/readme.adoc b/backend/readme.adoc index 2a00ba5..bc3c50f 100644 --- a/backend/readme.adoc +++ b/backend/readme.adoc @@ -41,7 +41,7 @@ The current implementation expects (and returns) recipes in the form: ], "steps": [ { - "instructions": "Step Instructions/Description", + "instruction": "Step Instructions/Description", "timer": 0 } ] @@ -121,11 +121,11 @@ $ curl -X POST api.recipebuddy.xyz:8888/recipes -d ' {"name":"INGR 2","amount":1,"unit":"oz"} ], "steps":[ - {"instructions":"Step 1: Do this first","timer":10} + {"instruction":"Step 1: Do this first","timer":10} ] }' -{"Status":{"Code":201,"Msg":"Recipe added successfully"},"Data":{"id":2,"name":"Test Recipe 2","description":"This is a descripiton for the test recipe","photos":["photo_url_1","photo_url_2"],"servingSize":0,"cookTime":60,"rating":5,"timesCooked":0,"tags":["keyword_1","keyword_2","keyword_3"],"ingredients":[{"name":"INGR 1","amount":2.5,"unit":"cups"},{"name":"INGR 2","amount":1,"unit":"oz"}],"steps":[{"instructions":"Step 1: Do this first","timer":10}]}} +{"Status":{"Code":201,"Msg":"Recipe added successfully"},"Data":{"id":2,"name":"Test Recipe 2","description":"This is a descripiton for the test recipe","photos":["photo_url_1","photo_url_2"],"servingSize":0,"cookTime":60,"rating":5,"timesCooked":0,"tags":["keyword_1","keyword_2","keyword_3"],"ingredients":[{"name":"INGR 1","amount":2.5,"unit":"cups"},{"name":"INGR 2","amount":1,"unit":"oz"}],"steps":[{"instruction":"Step 1: Do this first","timer":10}]}} ---- Read @@ -137,7 +137,7 @@ http://api.recipebuddy.xyz:8888/recipes/0[`/recipes/{id}`], the HTTP body is ign ---- $ curl -X GET api.recipebuddy.xyz:8888/recipes/1 -{"Status":{"Code":200,"Msg":"Successful"},"Data":{"id":1,"name":"Test Recipe","description":"This is a descripiton for the test recipe","photos":["photo_url_1","photo_url_2",""],"servingSize":0,"cookTime":60,"rating":5,"timesCooked":0,"tags":["keyword_1","keyword_2","keyword_3",""],"ingredients":[{"name":"INGR 1","amount":2.5,"unit":"cups"},{"name":"INGR 2","amount":1,"unit":"oz"}],"steps":[{"instructions":"Step 1: Do this first","timer":10}]}} +{"Status":{"Code":200,"Msg":"Successful"},"Data":{"id":1,"name":"Test Recipe","description":"This is a descripiton for the test recipe","photos":["photo_url_1","photo_url_2",""],"servingSize":0,"cookTime":60,"rating":5,"timesCooked":0,"tags":["keyword_1","keyword_2","keyword_3",""],"ingredients":[{"name":"INGR 1","amount":2.5,"unit":"cups"},{"name":"INGR 2","amount":1,"unit":"oz"}],"steps":[{"instruction":"Step 1: Do this first","timer":10}]}} ---- To access a list of all recipe ids in the database send a `GET` request to @@ -170,11 +170,11 @@ $ curl -X PUT localhost:8888/recipes/1 -d ' { "name":"INGR 2", "amount":1, "unit":"oz" } ], "steps":[ - { "instructions":"Step 1: Do this first", "timer":10 } + { "instruction":"Step 1: Do this first", "timer":10 } ] }' -{"Status":{"Code":201,"Msg":"Recipe added successfully"},"Data":{"id":1,"name":"Test Recipe 1","description":"This is a descripiton for the test recipe","photos":["photo_url_1","photo_url_2"],"servingSize":0,"cookTime":60,"rating":5,"timesCooked":0,"tags":["keyword_1","keyword_2","keyword_3"],"ingredients":[{"name":"INGR 1","amount":2.5,"unit":"cups"},{"name":"INGR 2","amount":1,"unit":"oz"}],"steps":[{"instructions":"Step 1: Do this first","timer":10}]}} +{"Status":{"Code":201,"Msg":"Recipe added successfully"},"Data":{"id":1,"name":"Test Recipe 1","description":"This is a descripiton for the test recipe","photos":["photo_url_1","photo_url_2"],"servingSize":0,"cookTime":60,"rating":5,"timesCooked":0,"tags":["keyword_1","keyword_2","keyword_3"],"ingredients":[{"name":"INGR 1","amount":2.5,"unit":"cups"},{"name":"INGR 2","amount":1,"unit":"oz"}],"steps":[{"instruction":"Step 1: Do this first","timer":10}]}} ---- [WARNING] diff --git a/backend/recipe.go b/backend/recipe.go index 3511fd6..59b7366 100644 --- a/backend/recipe.go +++ b/backend/recipe.go @@ -10,7 +10,7 @@ type Ingredient struct { } type Step struct { - Desc string `json:"instructions"` + Desc string `json:"instruction"` Time int `json:"timer"` } -- cgit v1.1 From e249709c792bb7e819be661a134e3a965d2a0919 Mon Sep 17 00:00:00 2001 From: Tucker Evans Date: Tue, 10 Dec 2019 15:04:51 -0500 Subject: Fix blank tags/photos not added to Recipe --- recipeBuddy/src/app/add-recipe/add-recipe.component.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/recipeBuddy/src/app/add-recipe/add-recipe.component.ts b/recipeBuddy/src/app/add-recipe/add-recipe.component.ts index e6555d4..5109c34 100644 --- a/recipeBuddy/src/app/add-recipe/add-recipe.component.ts +++ b/recipeBuddy/src/app/add-recipe/add-recipe.component.ts @@ -121,8 +121,8 @@ export class AddRecipeComponent { (isNaN(cookTimeTmp) ? 0 :cookTimeTmp), //cookTime 0, //timesCooked 0, //rating - formData.tags.split(','), //tags - formData.photos.split(',') //photos + formData.tags.split(',').filter(word=> !(word==="")), //tags + formData.photos.split(',').filter(word=> !(word==="")) //photos ); this.restService.createRecipe(recipe).subscribe(); this.router.navigate(['/']); -- cgit v1.1 From d8e99623986708c7b64984f8bf638a9fbec4a3d2 Mon Sep 17 00:00:00 2001 From: Tucker Evans Date: Tue, 10 Dec 2019 12:27:46 -0500 Subject: Add edit-recipe form/page Mostly copied from add recipe page. Updates recipe successfully, but doesn't pull ingredients/steps into form, and doesn't use pass service to get recipe. --- recipeBuddy/src/app/app-routing.module.ts | 4 +- recipeBuddy/src/app/app.module.ts | 6 +- .../src/app/edit-recipe/edit-recipe.component.css | 43 +++++ .../src/app/edit-recipe/edit-recipe.component.html | 110 ++++++++++++ .../app/edit-recipe/edit-recipe.component.spec.ts | 25 +++ .../src/app/edit-recipe/edit-recipe.component.ts | 188 +++++++++++++++++++++ 6 files changed, 372 insertions(+), 4 deletions(-) create mode 100644 recipeBuddy/src/app/edit-recipe/edit-recipe.component.css create mode 100644 recipeBuddy/src/app/edit-recipe/edit-recipe.component.html create mode 100644 recipeBuddy/src/app/edit-recipe/edit-recipe.component.spec.ts create mode 100644 recipeBuddy/src/app/edit-recipe/edit-recipe.component.ts diff --git a/recipeBuddy/src/app/app-routing.module.ts b/recipeBuddy/src/app/app-routing.module.ts index bb7c96e..9620f04 100644 --- a/recipeBuddy/src/app/app-routing.module.ts +++ b/recipeBuddy/src/app/app-routing.module.ts @@ -3,11 +3,13 @@ import { RouterModule, Routes } from '@angular/router'; import { CookPageComponent } from './cook-page/cook-page.component'; import { AddRecipeComponent } from './add-recipe/add-recipe.component'; +import { EditRecipeComponent } from './edit-recipe/edit-recipe.component'; const routes: Routes = [ { path: '', redirectTo: '/cook', pathMatch: 'full' }, { path: 'cook', component: CookPageComponent }, - { path: 'add', component: AddRecipeComponent } + { path: 'add', component: AddRecipeComponent }, + { path: 'edit', component: EditRecipeComponent }, ]; @NgModule({ diff --git a/recipeBuddy/src/app/app.module.ts b/recipeBuddy/src/app/app.module.ts index 359254e..4acbaa6 100644 --- a/recipeBuddy/src/app/app.module.ts +++ b/recipeBuddy/src/app/app.module.ts @@ -5,7 +5,6 @@ import { MatCardModule } from '@angular/material'; import { AppComponent } from './app.component'; import { CookPageComponent} from './cook-page/cook-page.component'; -import { StepCardComponent } from './cook-page/step-card/step-card.component'; import { AppRoutingModule } from './app-routing.module'; @@ -19,13 +18,14 @@ import { MatInputModule } from '@angular/material/input'; import { MatFormFieldModule } from '@angular/material'; import { MatIconModule } from '@angular/material/icon'; import { MatButtonModule } from '@angular/material/button'; +import { EditRecipeComponent } from './edit-recipe/edit-recipe.component'; @NgModule({ declarations: [ AppComponent, CookPageComponent, - StepCardComponent, - AddRecipeComponent + AddRecipeComponent, + EditRecipeComponent ], imports: [ BrowserModule, diff --git a/recipeBuddy/src/app/edit-recipe/edit-recipe.component.css b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.css new file mode 100644 index 0000000..9d74c53 --- /dev/null +++ b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.css @@ -0,0 +1,43 @@ +.form { + min-width: 150px; + max-width: 750px; + width: 95%; + margin-left: auto; + margin-right: auto; + padding-left: 5px; + padding-right: 5px; +} + +.full-width { + width: 100%; +} + +.half-width { + width: 50%; + padding: 1%; + margin-left:auto; + margin-right:auto; +} + +.quarter-width { + width: 25%; + padding: 1%; + margin-left:auto; + margin-right:auto; +} + +.third-width { + width: 33%; + padding: 1%; + margin-left:auto; + margin-right:auto; +} + +td { + padding-right: 8px; +} + +.center { + margin-left:auto; + margin-right:auto; +} diff --git a/recipeBuddy/src/app/edit-recipe/edit-recipe.component.html b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.html new file mode 100644 index 0000000..a8f2e97 --- /dev/null +++ b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.html @@ -0,0 +1,110 @@ +
+

Add Recipe

+ + + + Name is required + + + Name is required + + + + + + + + + Servings must be a number. + + + + + Minutes + + Must be in the form hh:mm + + + + Keywords/Tags + + + + Photos (URLS) + + + +
+

Ingredients

+
+
+

Ingredient {{ i + 1 }}

+
+ + + + + + + Amount must be a number. + + + + + + +
+
+
+
+ +
+
+ +
+

Steps

+
+
+

Step {{ i + 1 }}

+
+ + + + + + Minutes + + +
+
+
+
+ +
+
+ + +
diff --git a/recipeBuddy/src/app/edit-recipe/edit-recipe.component.spec.ts b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.spec.ts new file mode 100644 index 0000000..e92d28b --- /dev/null +++ b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.spec.ts @@ -0,0 +1,25 @@ +import { async, ComponentFixture, TestBed } from '@angular/core/testing'; + +import { EditRecipeComponent } from './edit-recipe.component'; + +describe('EditRecipeComponent', () => { + let component: EditRecipeComponent; + let fixture: ComponentFixture; + + beforeEach(async(() => { + TestBed.configureTestingModule({ + declarations: [ EditRecipeComponent ] + }) + .compileComponents(); + })); + + beforeEach(() => { + fixture = TestBed.createComponent(EditRecipeComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/recipeBuddy/src/app/edit-recipe/edit-recipe.component.ts b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.ts new file mode 100644 index 0000000..203f733 --- /dev/null +++ b/recipeBuddy/src/app/edit-recipe/edit-recipe.component.ts @@ -0,0 +1,188 @@ +import { Component, OnInit } from '@angular/core'; + +import { FormControl } from '@angular/forms'; + +import { FormBuilder } from '@angular/forms'; +import { FormArray } from '@angular/forms'; + +import { Validators } from '@angular/forms'; + +import { Router } from '@angular/router'; + +import { Recipe } from '../DataModels/recipe'; +import { Ingredient } from '../DataModels/ingredient' +import { Step } from '../DataModels/step'; +import { BackendService } from '../REST_service/backend.service'; + +@Component({ + selector: 'app-edit-recipe', + templateUrl: './edit-recipe.component.html', + styleUrls: ['./edit-recipe.component.css'] +}) +export class EditRecipeComponent implements OnInit { + + baseRecipe: Recipe = new Recipe (15, //id + '', //name + '', //description + [], //ingredients + [], //steps + 0, //servingSize + 0, //cookTime + 0, //timesCooked + 0, //rating + [], //tags + [] //photos + ); + + recipeForm = this.fb.group({ + recipeName: ['', Validators.required], + desc: [''], + ingredients: this.fb.array([ + this.fb.group({ + name: [''], + amount: ['', Validators.pattern('^[0-9]*(\.[0-9]*)?$')], + unit: [''] + }) + ]), + steps: this.fb.array([ + this.fb.group({ + instruction: [''], + timer: [''] + }) + ]), + servingSize: ['', Validators.pattern('^[0-9]*(\.[0-9]*)?$')], + cookTime: ['', Validators.pattern('^[0-9]*$')], + tags: [''], + photos: [''] + }); + + constructor(private fb: FormBuilder, + private restService: BackendService, + private router: Router, + /*private passService: PassService,*/ + ) + { + restService.getRecipe(this.baseRecipe.id).subscribe( + res=> this.updateRecipe(res), + err=> console.log('EditRecipeComponent:restService:getRecipes: id='+ this.baseRecipe.id + 'err=' + err), + () => console.log('EditRecipe:restService:getRecipes: completed') + ) + + this.rmIngredient(0); + this.rmStep(0); + } + + updateRecipe(r: Recipe) + { + var i: number; + + this.recipeForm.patchValue( + { + recipeName: r.name, + desc: r.description, + servingSize: r.servingSize, + cookTime: r.cookTime, + tags: r.tags.join(','), + photos: r.photos.join(','), + } + ) + + console.log(r.tags.join(',')); + + for(i = 0; i < r.ingredients.length; i++) { + this.addIngredient(); + this.ingredients.controls[0].setValue(r.ingredients[i]); + } + for(i = 0; i < r.steps.length; i++) { + this.addStep(); + console.log(r.steps[i]) + this.steps.controls[0].setValue(r.steps[i]); + } + } + + ngOnInit() { + } + + get ingredients() { + return this.recipeForm.get('ingredients') as FormArray; + } + + addIngredient() { + this.ingredients.push( + this.fb.group({ + name: [''], + amount: ['', Validators.pattern('^[0-9]*(\.[0-9]*)?$')], + unit: [''] + }) + ); + } + + rmIngredient(i) { + this.ingredients.removeAt(i); + } + + get steps() { + return this.recipeForm.get('steps') as FormArray; + } + + addStep() { + this.steps.push( + this.fb.group({ + instruction: [''], + timer: ['', Validators.pattern('^[0-9]*$')] + }) + ); + } + + rmStep(i) { + this.steps.removeAt(i); + } + + onSubmit() { + var formData = this.recipeForm.value; + + var ingredients = [] + var i; + for (i = 0; i < formData.ingredients.length; i++) { + var tmp_amount = parseFloat(formData.ingredients[0].amount) + ingredients.push(new Ingredient(formData.ingredients[0].name, + (isNaN(tmp_amount) ? 0 : tmp_amount), + formData.ingredients[0].unit, + "" + )); + } + + var steps = [] + for (i = 0; i < formData.steps.length; i++) { + var tmp_timer = parseInt(formData.steps[0].timer) + steps.push(new Step(formData.steps[0].instruction, + (isNaN(tmp_timer) ? 0 : tmp_timer) + )); + } + + console.log(steps); + + var servingsTmp = parseFloat(formData.servingSize) + var cookTimeTmp = parseInt(formData.cookTime) + + var recipe = new Recipe (this.baseRecipe.id, //id + formData.recipeName, //name + formData.desc, //description + ingredients, //ingredients + steps, //steps + (isNaN(servingsTmp) ? 0 :servingsTmp), //servingSize + (isNaN(cookTimeTmp) ? 0 :cookTimeTmp), //cookTime + 0, //timesCooked + 0, //rating + formData.tags.split(',').filter(word => !(word==="")), //tags + formData.photos.split(',').filter(word => !(word==="")) //photos + ); + console.log(recipe) + this.restService.updateRecipe(recipe).subscribe() + this.router.navigate(['/']); + } + + onCancel() { + this.router.navigate(['/']); + } +} -- cgit v1.1