# Knowledge Base
## Ngrok
``` shell
ngrok http 52922 -host-header="localhost:52922"
ngrok http https://localhost:44301 -host-header="localhost:44301"
```
## C#
### Enable Split Query for EF
``` csharp
sqlServerOptions =>
{
sqlServerOptions.UseQuerySplittingBehavior(QuerySplittingBehavior.SplitQuery);
}));
```
go through a model by its property names
``` csharp
foreach (var i in infos)
{
if (string.IsNullOrWhiteSpace(i.Zusatzkonfiguration.Fieldname))
{
continue;
}
// get model property by name
PropertyInfo p = objectModel
.GetType()
.GetProperties()
.SingleOrDefault(p => p.Name == i.Zusatzkonfiguration.Fieldname);
if (p == null)
{
continue;
}
...
}
```
set empty properties of an object to NULL
```csharp
public async Task SetEmptyPropertiesNullAsync(object obj)
{
foreach (var p in obj.GetType().GetProperties())
{
// todo: check if p is a nested object itself and then call this method recursively
var value = p.GetValue(obj, null)?.ToString();
if (value == null)
{
continue;
}
if (string.IsNullOrWhiteSpace(value))
{
p.SetValue(obj, null);
}
}
}
```
### parallel foreach
```csharp
Parallel.ForEach(numbers, number =>
{
if (IsPrime(number))
{
primeNumbers.Add(number);
}
});
```
## JS
filtering array
``` js
$scope.filteredEndgeraete = $scope.endgeraete.filter(device => {
if (!device.Id) {
return false;
}
if (device.DienstleisterEndgeraete) {
return deviceHasTeam(device.DienstleisterEndgeraete, teamId)
}
})
```
## MongoDB filter
```
db.getCollection('Test_Instances').find({'_id':'CHECKLISTID'})
```
## Xamarin Forms Fontawesome implementation...
To use Fontawesome within the app:
1. Make a "Fonts" folder in the shared project
2. Add the font to the folder and set the Build Action to Embedded Resource within the properties
3. add an assembly reference in assemblyinfo.cs like
``` c#
[assembly: ExportFont("fontawesome4.ttf", Alias = "FontAwesome4")]
[assembly: ExportFont("fa5brands.ttf", Alias = "FontAwesome5Brands")]
[assembly: ExportFont("fa5regular.ttf", Alias = "FontAwesome5Regular")]
[assembly: ExportFont("fa5solid.ttf", Alias = "FontAwesome5Solid")]
```
4. Use the font by setting the font family as usual
``` html
<Label Text="{Binding IconProperty}" FontFamily="FontAwesome5Solid">
```
Use Fontawesome inside code/xaml without setting a font family
```
"\uUNICODE" => code (e.g. "\uf123)
"&#xUNICODE;" => xaml (e.g. ")
```
App.xaml
``` xml
<Application.Resources>
<!-- font awesome icons -->
<!-- naming rule: fa + TYPE + NAME -->
<x:String x:Key="faSolidSave"></x:String>
<x:String x:Key="faSolidEdit"></x:String>
<x:String x:Key="faSolidSearch"></x:String>
<x:String x:Key="faSolidCaretUp"></x:String>
<x:String x:Key="faSolidCaretDown"></x:String>
<!-- converters -->
<local:NegateBooleanConverter x:Key="BoolInverter"></local:NegateBooleanConverter>
<local:AmountConverter x:Key="AmountConverter"></local:AmountConverter>
<!-- colors -->
<Color x:Key="TelekomMagenta">#e10075</Color>
</Application.Resources>
```
## Regex
Mail regex
``` shell
^([a-zA-Z0-9ßöäüÖÄÜ]+[\.\_\+\-]{0,1}[a-zA-Z0-9ßöäüÖÄÜ]{1,})+@([a-zA-Z0-9ßöäüÖÄÜ]+[\.\_\+\-]{0,1}[a-zA-Z0-9ßöäüÖÄÜ]{1,})+\.[a-zA-Z0-9]{2,}$
```
Filename regex
``` shell
FileNameRegex: /^([a-zA-Z0-9\_\-]+[\.][a-zA-Z0-9]+)$/;
```
``` shell
Regex rgx = new Regex("[^a-zA-Z0-9 -]");
str = rgx.Replace(str, "");
```
## Datatrigger
``` xml
<Button Content="Enable">
<Button.Style>
<Style TargetType="{x:Type Button}">
<Setter Property="Visibility" Value="Visible"/>
<Style.Triggers>
<DataTrigger Binding="{Binding IsEnabled}" Value="True">
<Setter Property="Visibility" Value="Hidden"/>
</DataTrigger>
</Style.Triggers>
</Style>
</Button.Style>
</Button>
```
## MIGRATION
Get-DbContext
1. change the database model (e.g. add a property)
2. open the Package Manager Console (View -> Other Windows -> Package Manager Console)
3. set the default project in the top-center to the project containing the db models
4. input "add-migration 'NameOfTheMigration' -Context ContextName" and wait for the migration model to show up
5. input "update-database" to run the migration against the database
6. commit everything and merge it into the main development branch
### Migration Wizardry
Add data in migration automatically
``` csharp=
migrationBuilder.InsertData(
table: "TableName",
columns: new[] { "ColumnName" },
values: new object[,]
{
{ "Value1" },
{ "Value2" },
{ "Value3" }
});
```
### EntityFramework Migration Default Value
```csharp
AddColumn("dbo.Datei", "StorageId", c => c.Guid(nullable: false, defaultValueSql: "NEWID()"));
```
## SQL
### transaction
``` sql
BEGIN Transaction
ROLLBACK Transaction
COMMIT Transaction
```
### joins
``` sql
select Checklist.MongoId, Antwortliste.Text
from Checklist
inner join Antwortliste on Antwortliste.Id = Checklist.Id
order by MongoId asc
```
``` sql
select Auftrag.Id as AuftragId, Auftrag.Bezeichnung as AuftragsBezeichnung,
Auftrag.CompletionDate as AbschlussDatum, Auftrag.Erstellungsdatum as Erstelldatum, Datei.Id as DateiId
from Datei
inner join AuftragDatei on Datei.Id = AuftragDatei.DateiId
inner join Auftrag on AuftragDatei.AuftragId = Auftrag.Id
where Auftrag.Erstellungsdatum <= '2020-10-01 12:00:00.7871205 +02:00'
```
``` sql
delete t
from [dbo].[Text] as t
inner join [dbo].[Zusatzinfo] as i on i.Id = t.Id
where i.AuftragspositionId is not null
```
get all jobs and its positions where the position does not have infos
``` sql
SELECT a.Id, a.Bezeichnung, ap.Id, ap.Beschreibung, zi.Id
FROM [dbo].[Auftrag] as a
inner join [Auftragsposition] as ap on ap.AuftragId = a.Id
left outer join [Zusatzinfo] as zi on zi.AuftragspositionId = ap.Id
where a.Status = 9 and a.AuftragstypId = 1 and zi.AuftragspositionId is null
GO
```
get all elements where the child has a parent id, but the parent is missing
``` sql
SELECT parent.ArchObjId, child.ParentArchObjId
FROM [smartus].[DT_ArchObjHierarchy] as child
left outer join [smartus].[DT_ArchObjHierarchy] as parent on child.ParentArchObjId = parent.ArchObjId
where child.ParentArchObjId is not null and parent.ArchObjId is null
GO
```
### check protocols for job
``` sql
SELECT a.[Id] as JobId,
a.[Bezeichnung] as JobName,
a.MandantId as JobMandant,
a.Termin as JobAppointment,
a.Status as JobStatus,
at.Name as JobTypeName,
p.Id as ProtocolId,
p.Bezeichnung as ProtocolName
FROM [dbo].[Auftrag] as a
inner join [dbo].[Auftragstyp] as at on at.Id = a.AuftragstypId
inner join [dbo].[Protokoll] as p on p.AuftragsTypId = at.Id
WHERE a.Bezeichnung like '%JOBNAME%'
```
### counting
``` sql
SELECT COUNT(*) as ENTITYCOUNT
FROM [dbo].[Table]
```
### check duplications
``` sql
SELECT OrderID, ProductID, COUNT(*)
FROM OrderDetails
GROUP BY OrderID, ProductID
HAVING COUNT(*)>1
```
### update
``` sql
UPDATE tablename
SET column = value,
WHERE column = value;
```
## API call response handling
When you decide you want to handle failure cases in a specific way, do not do the following.
``` csharp
var response = await httpClient.GetAsync(...);
try
{
response.EnsureSuccessStatusCode();
// Handle success
}
catch (HttpRequestException)
{
// Handle failure
}
```
This throws an exception just to immediately catch it, which doesn't make any sense. The IsSuccessStatusCode property of HttpResponseMessage is there for this purpose. Do the following instead.
``` csharp
var response = await client.GetAsync(...);
if (response.IsSuccessStatusCode)
{
// Handle success
}
else
{
// Handle failure
}
```
## Backup and Restore DB in Azure
Server Studio
* rclick on DB => Tasks => Export Data-Tier Application
* Modal => Introduciton/Next => Export Settings => Save to Microsoft Azure => * Connect => Put in credentials => Summary => Export
* IF Database still exists => Delete it and copy the name of the database for later
* Azure Portal => SQL Server => Import Database => Select Backup => Select storage * container => Select .bacpac file => Input credentials and copied database name => * Ok => Wait until its done!
## Link Resources
* [My Visual Studio Product Keys](https://my.visualstudio.com/ProductKeys?mkt=en-us)
* [GIT Merging vs Rebasing](https://www.atlassian.com/git/tutorials/merging-vs-rebasing)
* [Extern-Alias](https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/keywords/extern-alias?redirectedfrom=MSDN)
* [.NET Action Results Explained](https://hamidmosalla.com/2017/03/29/asp-net-core-action-results-explained/)
* [JsonSerializer 400mb](https://stackoverflow.com/a/33489745/12017899)
* [Cron Jobs every 5, 10 and 15 minutes](https://linuxize.com/post/cron-jobs-every-5-10-15-minutes/)
* [Agile Software Development Overview](https://www.smartsheet.com/agile-vs-scrum-vs-waterfall-vs-kanban)
* [Understanding Epics, Features and User Stories](https://www.scrumdistrict.com/understanding-epics-features-and-user-stories/)
* [EF Core - Modifying Data](https://www.learnentityframeworkcore.com/dbcontext/modifying-data)
* [EF Core - Update many to many](https://stackoverflow.com/questions/59695717/how-to-add-update-many-to-many-relations-with-one-end-of-entity-in-ef-core)
* [Set up Automapper in .Net Core](https://stackoverflow.com/questions/40275195/how-to-set-up-automapper-in-asp-net-core)
* [EF Core: How to create a composite primary key](https://makolyte.com/ef-core-how-to-create-a-composite-primary-key/)
* [REST Put vs Post](https://restfulapi.net/rest-put-vs-post/)
* [Xamarin Essentials - Secure Storage](https://docs.microsoft.com/en-us/xamarin/essentials/secure-storage?tabs=android)
* [Simplifying MVVM INotifyPropertyChanged](https://www.c-sharpcorner.com/article/simplifying-mvvm-inotifypropertychanged-on-xamarin-forms/)
* [ASP.NET Core Localization Deep Dive](https://joonasw.net/view/aspnet-core-localization-deep-dive)
* [Async Await Task Best Practices](https://web.archive.org/web/20210515054313/https://luismts.com/async-await-task-best-practices/)
* [Xamarin Forms Bindable Layout](https://www.c-sharpcorner.com/article/xamarin-forms-bindable-layout/)
* [Xamarin Forms Memory Usage](https://debruyn.dev/2017/optimize-memory-usage-in-xamarin-apps/)
* [Collections](https://medium.com/developers-arena/ienumerable-vs-icollection-vs-ilist-vs-iqueryable-in-c-2101351453db)
* [Xamarin Forms IFormFile App to API](https://ilclubdellesei.blog/2018/02/14/how-to-upload-images-to-an-asp-net-core-rest-service-with-xamarin-forms/)
* [API Responses](https://www.c-sharpcorner.com/article/3-ways-to-return-the-data-from-controller-action-method-in-asp-net-core/)
* [Realm relations](https://docs.mongodb.com/realm/sdk/dotnet/fundamentals/relationships/#std-label-dotnet-inverse-relationship)
* [AspNetCore.ReCaptcha](https://github.com/michaelvs97/AspNetCore.ReCaptcha)
* [Using Newtonsoft.Json In .NET Core 3+ Projects - .NET Core Tutorials](https://dotnetcoretutorials.com/2019/12/19/using-newtonsoft-json-in-net-core-3-projects/)
* [Fixing JSON Self Referencing Loop Exceptions - .NET Core Tutorials](https://dotnetcoretutorials.com/2020/03/15/fixing-json-self-referencing-loop-exceptions/)
* [Fix Azure DevOps pipeline nuget restore for assets.json](https://github.com/actions/virtual-environments/issues/3501)
* [JWT Authentication Tutorial With Example API](https://medium.com/c-sharp-progarmming/asp-net-core-5-jwt-authentication-tutorial-with-example-api-aa59e80d02da)
* [XAML Spacing](https://stackoverflow.com/questions/1768293/what-does-the-wpf-star-do-width-100/2318082#2318082)
* [Xamarin Forms Localization via App Resource File](https://docs.microsoft.com/en-us/xamarin/xamarin-forms/app-fundamentals/localization/text?pivots=windows)
* [Package Manager Migration Commands](https://www.entityframeworktutorial.net/efcore/pmc-commands-for-ef-core-migration.aspx)
* [EF Core Code First Migrations With DataAnnotations Attributes](https://geeksarray.com/blog/efcore-code-first-migrations-with-dataannotations-attributes)
* [Abstract vs. Interface in C#](https://www.c-sharpcorner.com/article/abstract-class-vs-interface-c-sharp/)
* [Azure Maps - Best Practices for Search](https://docs.microsoft.com/en-us/azure/azure-maps/how-to-use-best-practices-for-search)
* [Software Documentation](https://www.indeed.com/career-advice/career-development/documentation-for-software-development)
## Azure
### Web app
* To use certificates in Azure you must add "WEBSITE_LOAD_CERTIFICATES" with value "0" to the environment variables!
## XAML
### Binding Context
### Onplatform/OnIdiom
```xml
<Image
Source="{Binding Thumbnail}"
WidthRequest="{OnIdiom
Phone={OnPlatform Android=100, iOS=100, UWP=100},
Tablet={OnPlatform Android=200, iOS=200, UWP=200},
Desktop=200}"
HeightRequest="{OnIdiom
Phone={OnPlatform Android=100, iOS=100, UWP=100},
Tablet={OnPlatform Android=200, iOS=200, UWP=200},
Desktop=200}"/>
<StackLayout
Orientation="Vertical"
VerticalOptions="Center"
HorizontalOptions="Start"
Padding="{OnPlatform Android='5,0,0,0', iOS='10,0,0,0', UWP='5,0,0,0'}">
```
## MVVM
### Commands
So just to elaborate on Commands and how they work. Take a simple login button example. Your ViewModel will have a Command to handle the login button click like so:
```csharp
public Command LoginCommand = new Command<T>(async () => DoSomething();)
```
The command needs an action to call when the command is fired. So in your constructor, you could initialize the command with the following:
```csharp
LoginCommand = new Command(Login);
```
The Login Action corresponds to a method you have in your ViewModel like so:
```csharp
private void Login()
{
// do login stuff
}
```
Finally, in your View you Bind the command to your control in this case the login button:
```xml
<Button
x:Name="loginButton"
Command="{Binding LoginCommand}"
Text="Login" />
```
```xml
<Button
Content="Edit"
Command="{Binding EditCommand}"
CommandParameter="{Binding ViewModelItem}" >
```
### INotifyPropertyChanged in ViewModel
``` csharp
/// <summary>
/// property changed event for MVVM bindings
/// </summary>
public event PropertyChangedEventHandler PropertyChanged;
/// <summary>
/// method to update the properties of this view model via MVVM
/// </summary>
/// <param name="propertyName"> name of the property to be updated </param>
public virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
this.PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
```
## Resx Translates
In XAML
``` xml
<Binding Source="{x:Static resources:AppResources.TranslateId}" />
```
In code behind
``` c#
string labelString = AppResources.TranslateId;
```
## Emotes
༼ つ ◕_◕ ༽つ GIV PLX PLX