Sunday, November 25, 2018

Part 11 - Server Side Setup of a Service for your Mobile App

We are on one of the last part of our server side setup.  After this, much of the app production will be repeating a build process in which we can identify specific steps to add onto the mobile application.
The goal of this step is to create a home for our business logic and keep it separate from the API.  This will allow us to use the same business logic in other areas.  For example, say in the future we setup a separate client-side login in which clients can login to pay their invoices.  Or maybe we are working towards a suite of apps in which we want to leverage the same invoicing functionality, but don’t want to muddy up the API for our mobile app.

Open up Visual Studio 2017 to the Invoicing solution.  We will start by adding a base Service class under the Invoicing.Core project's Services folder.  Right-click on the Services folder and add a new class.  Name the class ServiceBase.cs.

Make the class public and add a protected field for the IUnitOfWork interface.  We'll need this in the majority of our services, so we’ll have this in here by default.

image

We need an AccountService now such that we can move our 'login' logic we had defined in the controller into this service and have the controller use this service to test the login credentials.  Since we will be using dependency injection to create this service, we'll need to create an interface for it as we had for the IUnitOfWork class.  Right-click on the Services folder and add a new interface named IAccountService.  Make sure we make the interface public such that it can be found from other classes.

image

Now we can create our AccountService and implement this interface and inherit from the ServiceBase class.

image

Add a controller that has a parameter for the IUnitOfWork interface such that dependency injection can create or pass in our singleton instance of the UnitOfWork class.

image

Now, we need to add the IAccountService to the Startup.cs class in the Invoicing.API project.  This will give the application a heads-up that this class will need dependency injection performed when it is encountered and providing instruction how it should be instantiated.

We'll add this as a scoped instance since we only want a maximum of one instance of this to be created per request.  If our app usage becomes higher or we have multiple users per "company" then we may want to change the IUnitOfWork to Scoped as well, but for now it is OK as a singleton.

image

Last, but not least, we'll move over the business logic we had placed in our AccountController.  I have identified our current business logic as the following highlighted section.

image

We'll first create a method stub in the IAccountService interface, and then we can implement the interface to add the method to the service with the above logic.

image

image

Now, we need to inject the AccountService via the controller's constructor and save it to a field in the class so we can use it in our Login method.

image

And… there it is!

This pretty much wraps up our server side setup.  Now that people can login… it seems we had forgotten a way for people to actually signup!  In the next post, we will go through from start to finish using everything we have learned to create a new component and actually use the database we worked so hard to setup.

Thursday, November 22, 2018

Part 10 - Server Side Setup of a Controller for your Mobile App

Now that we have our database setup and our repositories defined, we can create the first controller that will accept and respond to requests from our mobile application.  As part of building the controller, we will also define a standard response type for the mobile application such that we can provide some extra context with any data that is returned.

Open Visual Studio 2017 and expand the Controllers folder in the Invoicing.API project.  The Invoicing.API project is the project that will be directly accessed via our mobile application, and the controllers are where these requests will be accepted and from which responses will be made.

You should see the ValuesController already in there.  This can be deleted.

Right-click on the Controllers folder and Add a new controller.

image

Select the API Controller – Empty template and click the Add button.

image

The first Controller we will create will be our API controller base class from which our other controllers will inherit.  This will provide us with some flexibility down the road, but for now, we will leave this empty.

image

image

Next, add another controller and name it AccountController.  Have it inherit from the ApiBaseController.  This controller will be used to handle requests from our login page.

image

Since we will be handling the login in the AccountController, the first end point (i.e. method) we need is the Login method.  We will specify this as an HttpPost via an attribute and additionally specify the end point path to this method as Login.  These methods will always return a string which will eventually be a JSON object.

Quick snapshot of where we are with this method so far.

image

We will add a parameter to this method for the LoginViewModel, we created in a previous post, which we will be sending from the mobile app with the user's login credentials.  We will specify that it will be in the body of the HttpPost as well.

image

And now let's add a simple username and password logic such that we can verify a single user and password.

image

Now that we have a basic outline for this end point, we will define our standard response types.

Create a new class in the Inventory.Core project's Base folder.  We need to add "State", "Message", and "Data" properties that we will return for each response to a request.  We will also add a shortcut to the JsonConvert.SerializeObject method in here such that we don’t have to import this into all of our controllers.  If you haven't added package yet, you can add it via NuGet Package Manager under Newtonsoft.Json namespace.

image

Now, let's head over to our AccountController and use this response object to return the success of failure of the login request.

image

That should be all we need for our first crack at the Login method and a standardized response.

One thing that we will clean up in our next post is moving this business logic out of the controller and into a service in our Invoicing.Core project.  We will create our first business logic service in the next part.

Sunday, November 18, 2018

Part 9 - Server Side Setup of Unit of Work for your Mobile App

Now that we have setup our repositories, we need something to manage the repositories and expose them easily to our various services.  To do this, we will implement the Unit of Work pattern.

Start by opening Visual Studio 2017 to our Invoicing solution.  In the Invoicing.Core project, right click on the project and add a new class.  When the pop-up comes up, click the Interface option and name the interface IUnitOfWork.cs.  We’ll use this interface to allow us to implement dependency injection with this class.

image

Make the interface public and add a property for each of our repositories.  Next, add a requirement for a SaveChanges method that we'll define in the class that implements this interface.  Notice we only specified the "get" accessor such that we don't inadvertently overwrite an existing repository.  We want to make sure we leave all of the management of these repositories up to the Unit of Work class and not allow interference.

image

Next let's add a new class to the project called UnitOfWork.cs.  Make the class public and add the implementation of the IUnitOfWork class to the class declaration line.  Then select the Implement Interface option from the suggested fixes.

image

So far, we should be looking at the following:

image

If you recall, each of our repositories expects to receive an ApplicationDbContext as a parameter in their constructor and the Save Changes needs access to the database context to actually save any changes.  So, before defining each of these properties and the SaveChanges method, we need to create a constructor for this class and an instance of the ApplicationDbContext that we can save to a private field in the UnitOfWork class.  Something that should help us here is the ApplicationDbContextFactory, which we had already created in our ApplicationDbContext.cs file.

image

Now we have to implement the properties for each of the repositories the UnitOfWork will manage.  This should be as simple as creating a private field, checking if it is null, if so creating one and saving it to the field, then returning the field.  If it was previously created, then it will return the existing one.

image

And then follow through with the others.

image

Now we have the chore of implementing the method that will save all of the changes back to our database.

image

And, we are done with that, for now anyway.

I mentioned earlier in this post that we will need need to use this in dependency injection.  As such, we need to give the web application a heads-up that this will need created on the fly when it finds it in the constructor of our services.  We'll get into making services soon enough.  This "heads-up" is done in the Invoicing.API project's Startup.cs class.

Open up this class and look for the ConfigureServices method and add a reference to the the UnitOfWork class as a "singleton" to the list of available services for your application as shown below.  Adding the class as a singleton will ensure that each of the services we inject the UnitOfWork class into will receive the same instance of this class.  A little heavy duty on the terminology, but it will make much more sense once we create our first couple service.

image

And there we have it.  The UnitOfWork should be all setup for our first service.  In the next post we will work on setting up our first Controller.  Controllers represent the endpoints for our mobile application to connect and request data.

Tuesday, November 13, 2018

Part 8 - Server Side Repository Setup for your Mobile App

If you have been following along we have just finished up creating our database using the code-first method and found how easy it is to create and publish database objects that are tied to your server side code.  Now that we have the database objects setup, we need to create a little bit of abstraction from them such that we can consolidate functionality, handle ad-hoc changes to the database, and implement further caching as needed for any necessary speed improvements.  This isn't necessarily required, but will prove invaluable as we develop our application.

To do this, we'll implement data repositories that will handle all interactions with our data.  We should keep these repositories geared toward the main ideas of our database.  This will help us classify the data access methods and keep us from creating repository objects we don't need to manage for a particular request from the application further helping us improve our application response times.  At this point, our application only has three main areas and not many details.

As such, we'll create three repositories for our invoicing application: one for Invoices, one for Clients, and one for Users.  Before we get into the specifics, let's create a generic repository base class to help share functionality between our repositories.

Open Visual Studio 2017 to our Invoicing solution.  Right-click on the Repositories folder in the Invoicing.Core project that we created in our first post and add a new class named Repository.

I made the class public and since this is meant to be a generic base class, I added the generic TEntity attribute and specified it must be derived from EntityBase, which all of our database objects will be derived from in some fashion.  I added the constructor with the ApplicationDbContext as the only parameter and save it to a protected field such that it is accessible in our sub-classes.  I also instantiated an empty DbSet to store temporary/cached results.

image

We'll add to the base class later in this post.  At this point, we can save this and continue to the creation of the specific repositories we are interested in creating.  We'll start with the ClientRepository.  Right-click on Repositories folder and add this class inheriting from the Repository base class and specify the Client model as the entity to be used as the targeted data object.  Create the default constructor as required by the parent class and pass along the context to that class.

image

Create your InvoiceRepository next.  It should look very similar to the one you just created.

image

Lastly, we'll create an ApplicationUserRepository.  You shouldn't be overly surprised at this point on what this one looks like.

image

Next, we'll implement a couple base class methods such that these repositories are somewhat usable with little or no extra effort.

Open the Repository base class again and add a new method to obtain the total count of TEntity records and return them for the user.  The method should look as it does below.  You will need to add a using statement for System.Linq to resolve the red squiggly.

image

Now let's add some basic CRUD (Create, Read, Update, Delete) methods to expose to classes that may be using this repository.

image

Your Repository base class should now resemble the below screen shot.  We'll add more to this class as we go to help with other common requests from our database.

image

That's it for the repository creation for now.  In the next post, we will take a look at the "Unit of Work" pattern that will manage our various repositories to ensure we maintain consistent creation of our repositories and communication to the database.


Monday, November 5, 2018

Part 7 - Server Side Database Setup for your Mobile App

Now that the client side app is in fairly decent shape, we should start preparing the back-end to accept requests from the client side mobile app.  In this post, we’ll replicate our client side view models on the server and create database objects using the code-first method.

Open Visual Studio 2017 to the invoicing solution we setup in Part 2 of this mini-series.  We’ll first get the easy part out of the way by duplicating our client side View Models.

Let’s recall what our LoginViewModel.ts from the client side looks like.

LoginViewModel

Now, to replicate on the server side.  Right-click on the ViewModels folder in the Invoicing.Core project and click Add -> Class.  Name the class LoginViewModel.cs to match our client side class name.

image

Next, add the two properties from the client side ViewModel into the server side ViewModel and add "public" in front of your class so it is accessible from other classes.

image

Save your changes, and continue through the rest of your ViewModels until all are replicated.

InvoiceViewModel

image

ClientViewModel

image

image

Piece of cake.  Now, let’s get the database setup.  First let’s add the necessary dependencies for the Entity Framework using the NuGet Package Manager.  You can start the NuGet Package Manager from the Tools menu.  Select NuGet Package Manager, then Manage NuGet Packages for Solution.

image

Under the Browse tab of the "NuGet – Solution" tab, search for "Microsoft.EntityFrameworkCore" and click the first package that shows (also shown below in case your results vary).

image

Select both projects on the right and click Install and accept any user agreements or dependency requirements that pop up.

image

image

Next, search and install the following in the same manner.

Microsoft.EntityFrameworkCore.Design
Microsoft.EntityFrameworkCore.Tools
Microsoft.EntityFrameworkCore.Sqlite
Microsoft.VisualStudio.Web.CodeGeneration.Tools
Newtonsoft.Json

You should now be able to expand the Dependencies folder and then the NuGet folder in your solution to check if everything is installed properly.  As you may have guessed, if we were to be connecting to SQL Server, you would instead add Microsoft.EntityFrameworkCore.SqlServer.  If you start with Sqlite now to follow along, you can easily deploy to SQL Server by changing a (yes, just one) line of code later on.

image

Now that we have the dependencies added to your projects, right click on the Data folder in your Invoicing.Core project and add a new class.  Name the class ApplicationDbContext.cs.  We’ll then inherit from DbContext in the Microsoft.EntityFrameworkCore namespace. This class will serve as your "Database".

image

Next, we’ll create a base class for our entity objects.  These objects will serve as your tables in your database.  The purpose of creating a base class is to provide consistency among your database tables.  We’ll want all of our tables to have an Id column, Created date/time, and Modified date/time.  This will also help prevent duplication among all of our entity classes.

Right-click on the Models folder and add a new class called EntityBase.cs.  Add the above mentioned properties and refer to the below image for additional annotations (brackets above the properties) that need added.  Resolve the using statements as we did with the DbContext above.

image

Next add a new class for ApplicationUser in the Models folder to represent the table to hold the users for your application.  We’ll need a field for Email and a field for Password.  Be sure to make the class public and inherit from the EntityBase object to get our default columns.  We’ll also specify any additional database constraints here using annotations.

image

Do similar for a Client entity and Invoice entity.  One twist to this is that we need to add a reference for ApplicationUser such that we know which user the clients belong to.  We'll skip adding an ApplicationUser reference to the Invoice since we can simply reference the attached client, but this can be done as well to provide simplicity down the road.

image

image

Now that we have defined our entities, we need to make sure they are added to our database (ApplicationDbContext).  So let’s open that back up and get them added.

image

There are a couple last things to wrap this up prior to creating our database.  We need to create a factory to build our ApplicationDbContext object.  This can be done right inside the ApplicationDbContext.cs file to keep everything together.  The gist of this extra class is to provide an access point to build the database with the included connection string.  The connection string in this case points to a file.

image
Note: The optionsBuilder.UseSqlite line is the line that can be changed to publish to SQL Server instead.  You'd specify UseSqlServer and provide the corresponding connection string.
Now that we have a way to create the ApplicationDbContext, we use it to create a migration file.  The migration file contains the code needed to create or upgrade your database to the latest version.  Each time we make changes to the entities, we’ll create a new migration file and then use it to publish to the database.  If you publish your project in multiple locations, the migrations will be tracked for each database and missing migrations will be applied in sequence to ensure your database is updated properly.

To create a migration file and update the database, we’ll run a few commands from the Package Manager Console.  You can access this similar to how we accessed the Package Manager earlier, via the Tools menu.  Select NuGet Package Manager and Package Manager Console.

image

When the Console opens up, ensure you select the correct project in the “Default project:” drop down at the top of the console window.  Since we’ll be running commands to setup our database that we added to the Invoicing.Core project, we need to ensure that is the project we have selected in the Default project box.

image

Run the following command to create your first migration file.

Add-Migration FirstMigration

image

Next publish all unpublished migrations to the database by running the following command (we only have one at this point).

Update-Database

image

Since we didn’t specify a direct path in our connection string, the database was created in the default project directory.  At this point you should have the following file.

C:\Users\Micha\Source\Repos\Invoicing\Invoicing.API\invoices.db

You can browse this file with the “DB Browser for SQLite” application by clicking Open Database and locating the file.

DB Browser for SQLite: https://sqlitebrowser.org/

We can now see that our database appears to be in good order.

image

Next we’ll start working towards building up our services, repositories, and UnitOfWork pattern to manage our application's back-end.