Is there an automated mechanism where I can detect if any email field is missing? - asp.net-core

Let's assume this class:
public class AccountInfo
{
public string Email;
public string Username;
public string Password;
}
and this ASP api:
[HttpPost, Route("create")]
public IActionResult CreateUser([FromBody]AccountInfo Info)
{
...
}
If a user passes something like this:
{
"eail" : "ndienw", <--- notice the mispelling
"username" : "djiw",
"password" : "dow"
}
The email field will be null, so I need in each call to check for every fields.
Is there an automated mechanism where I can detect if any field is missing? I'm looking for something generic that can be applied through all calls.
Being able to opt out and mark some parameters optional would be great, but in our case, everything is always needed so far.
In this scenario, the ModelState is still valid; is that the expected behavior?

You can use data annotations on your Email property. RegularExpression attribute will check the field that located on, whether the value which provided is matching with this pattern. Required attribute checks whether this field is empty or not.
[RegularExpression(#"\w+([-+.']\w+)*#\w+([-.]\w+)*\.\w+([-.]\w+)*", ErrorMessage = "Email was invalid.")]
[Required]
public string Email;

Related

Validate existing entity in CQRS + EventSourcing. Microservice ASP.NET Core 5.0

I am currently building an app, and I would like to use micro services.
I use Mediatr for implementing a CQRS pattern and EventStore for event sourcing.
I have a problem with checking that an entity exists before creating an event of aggregate and appending it to the EventStore.
For example: I have LanguageAggregateRoot
public class LanguageAggregateRoot
{
public Guid Id {get;set}
public string Code { get; private set; }
public string Name { get; private set; }
public bool Enable { get; private set; }
public string Icon { get; private set; }
}
Field Code is unique and user can change code for language.
When I use Code field for stream id of eventstore, if the user sends a CreateLanguageCommand and ChangeCodeCommand, I need to check that the new code exists.
So I use Id field for stream id. But I don't understand how I can validate whether code field is unique?
As far as I've found out should not use query handling in command handling.
If i use client to check existed then send command to server. I think it doesn't look good. Because something/someone can request only command with out my client.
How can I do that?
Thanks for your support.
It should be fine to validate your request in your command itself.
you can use the below link for more details.
CQRS - is it allowed to call the read side from the write side?

asp.net core api - how to distinguish between `api/cars` and `api/cars?color=red` calls with [FromQuery] object

I am using [FromQuery] atribute in controller's Get method:
//CarsController, etc..
[HttpGet]
public async Task<ActionResult<IEnumerable<CarsDto>>> Get([FromQuery] CarsParameter? carsParam = null)
{
//param is always not null here
}
Inside the method I need to distinguish between api/cars and api/cars?color=red calls. Problem is, that carsParam object is never null, so I cannot say if the Color="" (defailt value) is intended to be empty string or it's because of the call was api/cars
CarsParameter is a simple class:
public class CarsParameter
{
public string Color {get; set;} = "";
//more params here
}
Yes, I can use different path, like api/cars/withParams?color=red, but i am looking for more subtle solution.
I need to distinguish between api/cars and api/cars?color=red calls. Problem is, that carsParam object is never null
Please note that default model binding starts by looking through the sources for the key carsParam.Color. If that isn't found, it looks for Color without a prefix, which cause the issue.
To achieve your requirement, you can try to specify prefix explicitly, like below.
public async Task<ActionResult<IEnumerable<CarsDto>>> Get([FromQuery][Bind(Prefix = "carsParam")] CarsParameter? carsParam = null)
{
Request to api/cars?color=red&carsParam.color=yellow&carsParam.brand=test and following is test result

how to hide field during serialization (but not deserialization)

In our project (springMVC) Rest API project I wish to only use ONE model for both request and response (to avoid having to add tons of code to copy field from object to object)
I'd like to use Swagger to handle all the doc, but I'm running into a little problem. For example let say I have a model User
public class User {
private Long id;
private String username;
private String password;
}
And a simple controller
public void createUser(#RequestBody User user)...
public User getUser(Long id) ..
Now I would like swagger to hide the property password on deserialization but not serialization (so having it display for the Input but the output)
and the opposite for the Id field.
I have tried using #JsonIgnore coupled with #JsonProperty but on the swagager-ui it either displays everything or hides everything. I cannot manage to it work.
Could someone indicate me what is the best way of archiving my goal ? Is it possible to use a single model for request and response while using swagger? In case it is not possible to use #JsonIgnore, is there a way to archive this differently ?
Swagger doesn't want you to have different input/output models with the same name. You should simply create an interface and attach that to the input, and for the output extend that interface or add an implementation with the additional field. For example, please see here for modeling tips:
https://swaggerhub.com/api/swagger-tutorials/modeling-samples/1.0.0
Your exact use case is one of them. The solution posted in the above link is here:
definitions:
User:
description: this is a user that would be passed into the system
properties:
username:
type: string
UserResponse:
allOf:
- $ref: '#/definitions/User'
- type: object
required:
- id
properties:
id:
type: string
format: uuid
readOnly: true
where User is the input object, and UserResponse is the output object, with the additional id field.
Add #JsonIgnore with getter of the field and #JsonProperty with the setter or with the field . As Due to use of immutable code or final fields sometime setter doesn't work.
example :
public class Student {
private Float name;
private String rollnum;
private String section;
#JsonProperty
private Boolean passOrFailed;
#JsonIgnore
public Boolean getpassOrFailed {
return active;
}
}
Remember to use both else else it will lead to removing element in deserialization

What is the recommended way to do partial updates with PATCH in ServiceStack?

I am building a RESTful API using the ServiceStack framework. A lot of the resources that I need to update are quite big, with up to 40 attributes per class, so I would like to do partial updates instead of replacing the entire resource. Often the client will only need to update one or two attributes out of the 40, so I would like to just send a JSON body consisting of the few attributes.
Since all combinations of attributes are possible, it is not feasible to make an "Update" class per class as suggested here: https://github.com/ServiceStack/ServiceStack/wiki/New-Api#patch-request-example
In the Microsoft ASP.NET WebAPI OData package there is a Delta class that takes a subset of a class and updates the resource based on this subset (http://www.strathweb.com/2013/01/easy-asp-net-web-api-resource-updates-with-delta/). This is the functionality I would like to have, as I will be having quite a few classes so a generic method would be best.
Basically, if I have a class
public class MyClass {
public int a { get; set; }
public int b { get; set; }
...
public int z { get; set; }
}
I would like to update a resource of MyClass with a PATCH request with body
{"a":42,"c":42}
Is there a standard or recommended way to accomplish this with ServiceStack?
Declare any scalar values in your DTO as nullable. This will allow you to determine which fields were actually sent in the request:
public class MyClass {
public int? a { get; set; }
public int? b { get; set; }
public int? c { get; set; }
// etc.
// object-type properties are already nullable of course
public string MyString { get; set; }
}
Now if a client sends a partial request, like so:
{ "a": 1, "b": 0 }
You'll be able to determine which properties were actually sent when inspecting your DTO:
myClass.a == 1
myClass.b == 0
myClass.c == null
myClass.MyString == null
etc.
Set up a PATCH route for your DTO and implement a Patch method in your service:
public object Patch(MyClass request)
{
var existing = GetMyClassObjectFromDatabase();
existing.PopulateWithNonDefaultValues(request);
SaveToDatabase(existing);
...
}
PopulateWithNonDefaultValues is key here. It will copy values from your request object onto the database entity, but will only copy properties that are not the default values. Thus, if a value is null, it won't copy it, because the client didn't send a value for it. Notice that it will copy an integer value of zero though, because we made it a nullable int, and the default value for a nullable int is considered by this method to be null, not zero. Declaring your DTO properties as nullable shouldn't cause much of a hassle in the rest of your code.
Note that this approach works easily with JSON. If you need to support XML requests/responses, you may need need to do some additional work with DataContract/DataMember attributes to insure that nulls are handled correctly.
While esker's response is fine I would like to add that it might not be enough for nullable fields - since you don't know if the deserializer or the user have created that null field.
One approach would be to peek at the raw request.
A different approach is to ask the user to provide additional request (querystring) parameter to clearly specify which fields to patch.
Something like: patch_fields=name,description,field3
The bonus of that approach is that the end user has more control over the patching and is not overriding a value by mistake (because he used the original entity and forgot to clear some fields)

help me understand the method Validator.TryValidateObject()

this is the method definition:
public static bool TryValidateObject(
Object instance,
ValidationContext validationContext,
ICollection<ValidationResult> validationResults,
bool validateAllProperties
)
what i am confused is the validateAllProperties parameter, I understand when it is true-validate all properties.
What about when it is false, not validate all properties, but which property will be validated?
See here for a good answer:
http://connect.microsoft.com/VisualStudio/feedback/details/605635/missleading-parametername-validateallproperties-in-validator-try-validate-componentemodel-dataannotations
It seems that when validateAllProperties is set to false that only the RequiredAttribute is validated.
When the property is false the Validator should validate each of the properties on the object that have a ValidationAttribute applied to them. This can include any of these attributes: CustomValidationAttribute, DataTypeAttribute, RangeAttribute, RegularExpressionAttribute, RequiredAttribute, and StringLengthAttribute, along with any other attributes that derive from ValidationAttribute.
See the MSDN library on the TryValidateObject method for more information.
In the following example, Foo should be validated, while Bar should not.
public class Example
{
[Required(ErrorMessage = "Foo is a required property.")]
public object Foo { get; set; }
public object Bar { get; set; }
}
I also don't fully understand it but after struggling with Unit Testing custom validators written by me I noticed one interresting thing.
When I launched my tests without this parameter (so by default it was false), my custom validators were omitted! if I set it to true, they were taken into account in my tests and now I can happily continue TDD. Hope this helps you a bit.
Arjen is right, only the Required attribute is validated when the validateAllProperties parameter is false.
I wrote a post about OData validation using DataAnnotations and I found the same issue.
http://blog.jorgef.net/2011/01/odata-dataannotations.html