Why I the method don't have an acsess to the controller? Blazor Webassembly - c#

#page "/choosedata"
<div class="choose-form">
<input type="text" #bind="p1" /> <span>:מחוז</span>
<br /><br />
<input type="text" #bind="p2" /> <span>:תאריך</span>
<div class="choose-btn">
<a class="btn btn-primary" href="/routeddata/#p1/#p2">Select</a>
</div>
</div>
#code {
string p1 = string.Empty;
string p2 = string.Empty;
}
That page, by clicking Select that page routing to another page by url. that called RoutedData
#page "/routeddata"
#page "/routeddata/{p1}/{p2}"
#using Microsoft.AspNetCore.Components.Forms
#inject HttpClient Http
#inject IJSRuntime JS
#using MyApp.Shared;
<h1>Routed Data Page</h1>
<!--There will be a table that that fetched from SQL server after Post requset-->
<p>#ObjectForShowing</p>
#code {
//What will happens when the blazor page will start?
protected override async Task OnInitializedAsync()
{
ObjectForShowing= await ShowTable();
}
[Parameter]
public string P1 { get; set; }
[Parameter]
public string P2 { get; set; }
private District district = new();
private District ObjectForShowing = new();
public async Task<District> ShowTable()
{
district.DistrictName = P1;
district.PresentationDate = P2;
using var result = await Http.PostAsJsonAsync("RoutedData/ShowData",district);
var content = await result.Content.ReadFromJsonAsync<District>();
return content;
}
}
JsonAsync Mehod doest have any access to controlle URI.
using Microsoft.AspNetCore.Mvc;
using Microsoft.Data.SqlClient;
using MyApp.Shared;
namespace MyApp.Server.Controllers;
[ApiController]
[Route("[controller]/[action]")]
public class RoutedDataController : ControllerBase
{
private readonly ILogger<RoutedDataController> _logger;
public RoutedDataController(ILogger<RoutedDataController> logger) => _logger = logger;
[HttpPost]
public District ShowData(District d)
{
return d;
}
}
...............................................................................................
I tried to check the routing and the routing is fine between post method and controller
....................................................................................................

Related

Razor page <input asp-for> only submits as null value for my class' int value, despite entering a value

I cannot seem to use integers with <input asp-for="" /> when creating a new Department instance, the value reverts to null when reaching OnPost(). I have no idea as to what the issue is,
<input asp-for="" /> works fine for the other value types within Department.
Department.cs
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using System.Diagnostics.CodeAnalysis;
namespace Scratch.Data
{
public class Department
{
[Key]
public int Id { get; set; }
[Required]
public string departmentName { get; set; }
[Required]
[ForeignKey("AspNetUsers")]
public string departmentManagerId { get; set; }
[AllowNull]
[ForeignKey("AspNetUserRoles")]
public string? managerRoleId;
[AllowNull]
[ForeignKey("AspNetUserRoles")]
public string? userRoleId;
[AllowNull]
public int? defaultDisplayOrder;
}
}
I simplified the code below down to testing for the one input I want to get from the page:
CreateDepartmentIntTestModel
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Identity;
using Microsoft.AspNetCore.Identity.EntityFrameworkCore;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.RazorPages;
using Microsoft.Build.Evaluation;
using Microsoft.CodeAnalysis;
using Microsoft.EntityFrameworkCore;
using Scratch.Data;
using System.Text.RegularExpressions;
using Microsoft.AspNetCore.Mvc.TagHelpers;
namespace Scratch.Pages.Admin_Tools
{
[BindProperties]
[Authorize(Roles = "Administrators,ProjectManager")]
public class CreateDepartmentIntTestModel : PageModel
{
private readonly ApplicationDbContext _db;
private readonly UserManager<IdentityUser> _userManager;
private readonly IUserStore<IdentityUser> _userStore;
private readonly RoleManager<IdentityRole> _roleManager;
private readonly IRoleStore<IdentityRole> _roleStore;
public Department Department { get; set; }
public CreateDepartmentIntTestModel(ApplicationDbContext db, UserManager<IdentityUser> userManager,
IUserStore<IdentityUser> userStore,
RoleManager<IdentityRole> roleManager,
IRoleStore<IdentityRole> roleStore)
{
_db = db;
_userManager = userManager;
_userStore = userStore;
_roleManager = roleManager;
_roleStore = roleStore;
}
public async Task<IActionResult> OnGet()
{
return Page();
}
public async Task<IActionResult> OnPost()
{
//this is always null despite inputs
if (Department.defaultDisplayOrder == null)
{
//add breakpoint here:
ModelState.AddModelError("Department.defaultDisplayOrder", "display order is null");
}
return Page();
}
}
}
Html
#page
#model Scratch.Pages.Admin_Tools.CreateDepartmentIntTestModel
#{
}
<form method="post">
<input hidden asp-for="Department.managerRoleId" />
<input hidden asp-for="Department.userRoleId" />
<div class="border p-3 mt-4">
<div asp-validation-summary="All" class="text-danger"></div>
<div class="row pb-2">
<h2 class="text-primary pl-3">
Test to enter a numeric value to department:
</h2>
</div>
<div class="mb-3">
Department Display Order Value:
<input asp-for="Department.defaultDisplayOrder" class="form-control" />
<span asp-validation-for="Department.defaultDisplayOrder" class="text-danger"></span>
<hr/>
</div>
<button type="submit" class="btn btn-primary" style="width:150px;">Create</button>
</div>
</form>
Your defaultDisplayOrder member is a field, not a property (ref: What is the difference between a field and a property?). Model binding only works with public properties. Add { get; set; } to the declaration to make it a property:
public int? defaultDisplayOrder { get; set; }

Selected item in ASP.NET Core razor not being passed

I'm using ASP.NET Core Razor for the first time. I'm trying to simply set a bound property with the selected value of a dropdown but the property is always null when the form is posted. Also, how does one get the form posted when a selection is made? TIA
Razor page:
<td>
<form method="post">
<select asp-for="#Model.selectedReport" asp-items="#Model.Reports" class="form-control">
</select>
</form>
</td>
Code behind:
public class SubscribedReportsModel : PageModel
{
[BindProperty]
public List<SelectListItem> Workspaces { get; private set; }
[BindProperty]
public List<SelectListItem> Reports { get; private set; }
[BindProperty]
public string selectedReport { get; set; }
public async Task OnGetAsync()
{
await GetWorkspaces();
}
public async Task<IActionResult> OnPostAsync()
{
if (!ModelState.IsValid)
{
return Page();
}
if (selectedReport != null)
{
return Page();
}
return RedirectToPage("./Index");
}
}
I'm a bit rusty it appears. All I had to do was add onchange="this.form.submit()" to the control:
<td>
<form method="post">
<select asp-for="#Model.selectedReport" asp-items="#Model.Reports" class="form-control" onchange="this.form.submit()">
</select>
#*#Html.DropDownList("ddl_Reports", Model.Reports, new {#class="form-control"})*#
#*#Html.DropDownListFor(m => m.selectedReport, Model.Reports, "--Select Report--", new{#class="form-control"})*#
</form>
</td>

Re-render Blazor Component

I have a catalogue page that renders a Blazor component which displays a list of products with the following code:
#(await Html.RenderComponentAsync<ProductList>(RenderMode.ServerPrerendered, new { MinimumPrice = Model.MinimumPrice, MaximumPrice = Model.MaximumPrice }))
Now, I want to change the values of MinimumPrice and MaximumPrice from the catalogue page and have the blazor component re-rendered after the values have changed.
How can I do that from the catalogue page?
Thanks.
You want to change the razor view and then update the blazor component?
You can submit a form to change the Model.MinimumPrice, because you can't change the Model
in view, it's from server side, so you should change it in server side too.
This is the demo:
blazor component:
<p>Min:#MinimumPrice</p>
#code {
[Parameter]
public int MinimumPrice { get; set; }
[Parameter]
public int MaximumPrice { get; set; }
}
Razor view:
<form method="post">
Change min to<input type="text" name="value"/>
<input type="submit" value="ok" class="btn btn-primary" />
</form>
<component type="typeof(S42111.Components.ProductList)" render-mode="Static" param-MinimumPrice="Model.MinimumPrice" param-MaximumPrice="10" />
server side:
[BindProperty]
public int MinimumPrice { get; set; }
public void OnGet()
{
MinimumPrice = 1;
}
public async Task<IActionResult> OnPostAsync(int value)
{
this.MinimumPrice = value;
return Page();
}
Result:

Using forms in partial views in asp.net core razor pages

I have the following structure:
SelectLoc.cshtml:
#model SelectLocModel
<div class="dropdown">
<form method="get">
<select asp-for="Location" asp-items="Model.Locations"
class="btn btn-secondary" formaction="Partials/SelectLoc" onchange="this.form.submit()">
</select>
</form>
</div>
SelectLoc.cshtml.cs:
using Microsoft.AspNetCore.Mvc.RazorPages;
using Microsoft.AspNetCore.Mvc.Rendering;
using System.Collections.Generic;
using System.Net.Http;
using System.Net.Http.Json;
namespace AdminPortal.Web.Pages.Partials
{
public class SelectLocModel : PageModel
{
private readonly HttpClient httpClient;
private readonly string key = "FAKE TOKEN";
public string Location { get; set; }
public List<SelectListItem> Locations { get; } = new List<SelectListItem>
{
new SelectListItem { Value = null, Text = "Select Location" },
new SelectListItem { Value = "Kothrud", Text = "Kothrud" },
new SelectListItem { Value = "Dhanakawdi", Text = "Dhanakawdi" },
new SelectListItem { Value = "Karvenagar", Text = "Karvenagar" },
new SelectListItem { Value = "Wakad", Text = "Wakad" },
};
public SelectLocModel(HttpClient httpClient)
{
this.httpClient = httpClient;
}
public void OnSubmit()
{
}
public void OnGet()
{
}
public void OnGetSubmit()
{
}
public async void OnGetLocation()
{
string geocodeRequest = $"https://maps.googleapis.com/maps/api/geocode/json?address={Location}&key={key}";
Location jsonResponse = await httpClient.GetFromJsonAsync<Location>(geocodeRequest);
}
}
}
I know, that there isn't any useful code in any of the methods, but I want the form to use the OnGet handlers in the code-behind file. It somehow keeps calling the ctor. What am I doing wrong?
If you want to go to https://localhost:xxx/Partials/SelectLoc?Location=xxx when submit form,you can add action="/Partials/SelectLoc" in form.
SelectLoc.cshtml:
#model SelectLocModel
<div class="dropdown">
<form method="get" action="/Partials/SelectLoc">
<select asp-for="Location" asp-items="Model.Locations"
class="btn btn-secondary" formaction="Partials/SelectLoc" onchange="this.form.submit()">
</select>
</form>
result:

using a javascript variable in asp-route (parameter)?

I'm extremely new to C# and .Net Core and Razor Pages.
I'm trying to create a super simple application where you can submit your first name and last name to a form and it will redirect you to a template which accepts the parameters firstname and surname and will print them out.
So what I'm doing is that I'm currently trying to store the value of the input (only trying with the first name right now) within script tags and then adding the variable within the asp-route-firstname when you submit the form. But it doesn't seem to work. Is this even the right way to try to approach this or am I somehow supposed to do this in the #{} field at the top?
In this case it just prints out {foo} as a string and the hardcoded surname Browder.
#page
#model IndexModel
#{
ViewData["Title"] = "Home page";
}
<div class="text-center">
<h1 class="display-4">Welcome #Model.FirstName</h1>
<p>Learn about building Web apps with ASP.NET Core.</p>
<form method="post" asp-page="/nametemplate" asp-route-firstname="{foo}" asp-route-surname="Browder">
<label for="fname">First name:</label><br>
<input type="text" id="fname" name="fname" value="John"><br>
<label for="lname">Last name:</label><br>
<input type="text" id="lname" name="lname" value="Doe"><br><br>
<input type="submit" value="Submit">
</form>
</div>
<script>
let foo = document.querySelector("#fname").value;
</script>
Thank you a million times in advance!
This is a very basic example to get you started but I highly recommend reading the docs.
Essentially you want to look at model binding. You don't need to use JS as per your example.
Razor Pages Docs
Index.cshtml
#page
#model IndexModel
#{
ViewData["Title"] = "Home page";
}
<div class="text-center">
<h1 class="display-4">Welcome</h1>
<p>Learn about building Web apps with ASP.NET Core.</p>
</div>
<form method="post">
<input asp-for="Firstname" />
<input asp-for="Lastname" />
<input type="submit" value="Submit" />
</form>
Index.cshtml.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Policy;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.RazorPages;
using Microsoft.Extensions.Logging;
namespace RazorPageTest.Pages
{
public class IndexModel : PageModel
{
public string Firstname { get; set; }
public string Lastname { get; set; }
private readonly ILogger<IndexModel> _logger;
public IndexModel(ILogger<IndexModel> logger)
{
_logger = logger;
}
public void OnGet()
{
}
public IActionResult OnPost(string firstname, string lastname)
{
return RedirectToPage("Display", new { firstname, lastname });
}
}
}
Display.cshtml.cs (new page)
using Microsoft.AspNetCore.Mvc.RazorPages;
namespace RazorPageTest.Pages
{
public class DisplayModel : PageModel
{
public string Firstname { get; set; }
public string Lastname { get; set; }
public void OnGet(string firstname, string lastname)
{
Firstname = firstname;
Lastname = lastname;
}
}
}
Display.cshtml
#page
#model RazorPageTest.Pages.DisplayModel
#{
ViewData["Title"] = "Display";
}
<h1>#Model.Firstname #Model.Lastname</h1>

Categories