Skip to content
This repository was archived by the owner on Oct 27, 2023. It is now read-only.

Technical Documentation

Peter Steele edited this page Dec 6, 2020 · 1 revision

Welcome to the Technical Documentation

This document was created to aid in new developers that want to come on board to help build the application out. This will describe what needs to be done in order to get up and running with the project and how to develop in it.

Pre-Requisites

In order to be successful, you will need to have a strong understanding of Object Oriented Programming, the C# language, and MVVM and N-Tier design patterns. You must also be comfortable with Git and using GitHub. This project uses .NET Core 3.1.x along with Entity Framework Core 3.x. You will need to be familiar with LINQ, lambda functions, delegates, factory patterns, dependency injection, and utilizing repositories. XAML and databinding are a must as well. TweetInvi is used to communicate with Twitter and you should be comfortable looking up the documentation on how to use this package as it is used throughout the application and then converted over into custom models.

Project Structure

The project uses the N-Tier design pattern and is currently split between 3 different projects under 1 solution. There is the Domain layer, the Data Access Layer (DAL), and the Presentation layer.

Domain Layer

The domain layer houses the models that are used in this project along with the interfaces for various domain logic services.

DAL Layer

The DAL layer has the Entity Framework Core implementation along with some factory patterns in place for the DbContext. This is only needed for the MySQL implementation and uses a Code First approach to creating the database from the models. There are services here as well that are implementations of the interfaces defined in the domain layer.

Presentation Layer

This layer is the MVVM layer that houses the views, viewmodels, and other necessary components like the navigator, commands, and user controls. It also has the dependency injection container in this project as well, which is where you will inject the dependencies needed for various components from one location.

Creating a new View

To create a new view for a page in this application, you will need to do several things first. First you will need to create the view as a user control. Then you will need to create the view model that this view will rely on to data bind too. For the actual view content, you are going to create another user control or several user controls in the controls section. These will be brought in via name spaces to the main view user control so that you can input them into the view. This allows us to swap out user controls anytime we need without having to create new views all together and makes updating and modularity very simple.

After you have created all of that, you will need to go into the State folder, and under INavigator, add in the appropriate name in the enum of ViewType. This will allow us to dynamically generate the view with the view model later on to the main window so that we can easily switch between views. Once you have created all of that, you will need to go into the ViewModelFactory folder and open the ViewModelFactory.cs file. In here you will see a switch statement that allows you to specify which view model to create when you set the INavigator ViewType enum to the selection that you have added. Don't forget to create a private field for the view model delegate and pass it through the constructor.

Once that is done, you can head to the App.xaml.cs file where the DI container is located. Here you can register the new view model to be created. Make sure you include any services that you need injected to the view model here. You can view the existing implementations to get an idea of how this works. After that has been registered, we need to head into the App.xaml file and you will notice under the Application Resources section the DataTemplates that we are using to swap views in an out. Create a new data template of the datatype that matches your new view model. Underneath that, set the view to the new view that you have created. This will swap views out based on the current view model that is being created so that we can dynamically change the window at anytime.

The last thing that needs to be done, is to create a button somewhere on the application that will trigger this navigation to the new view and view model. You will use the UpdateCurrentViewModelCommand command and pass in the command parameter of the ViewType enum you are targeting. To see this in action, please take a look at the PinVerificationControl in the Controls folder. Look for the Verify Pin button and study the implementation of the command and command parameter. Don't forget to import the navigator namespace so you have access to the ViewType enum to pass as a command parameter.

That is it! You have created a new view, view model, and got everything registered with the DI container. Navigation has been setup and now you can start developing whatever view you would like to add onto the application.

Adding New Components to the Main Application Page

To add new components to the main application page, you will want to most likely utilize commands and command parameters. The HomeViewModel is the base view model for this view and houses the logic and commands needed to make the application run in its current state. To add additional features, please study this view model to get an understanding of how it works and what it is doing. You should be able to utilize the various fields and properties needed to add any additional features as well as working with the databases.

Working with the Databases

The databases that are used in this application are both remote. They need the App.config file in order to pass in the information you will need to connect. To use your own credentials, study the App.xaml.cs DI container to see what I have named the credentials I use. Then create an App.config file and create new keys and values inside to coincide with my naming conventions. You are free to change the names of course, but make sure you follow the dependency injection path and change them elsewhere as needed. For this application, you will need a Twitter Dev account and your own app credentials. This is typically called the consumerKey and consumerSecret. The way the application is setup, you can get the accessKey and accessSecret for any user once they have authorized the application. These values are stored to the database as they do not change and allow you to continue calls to Twitters API moving forward.

MySQL

I have implemented two databases, one MySQL, and one MongoDB. For the MySQL database, you will need to provide the proper credentials for your database and make sure you have whitelisted remote connections based off your IP address. Simply changing out the connection string credentials and running the migrations against your new database should be enough to get the tables and everything created and up and running for the application. Be aware that MySQL will not work with EF Core 5.0+ at this time, and I have downgraded the EF Core installation to 3.x for this reason. You will also need to manually create a table called _EFMigrationHistory as well in your MySQL database as for some reason EF Core has an issue with this and errors out. You do not need to generate any fields, just create and name the table and EF Core will take care of the rest.

MongoDB

For MongoDB, you will want to create a free Atlas account and get your DB name and Collection created. This is a simple process, and their website has great tutorials for how to do this. Once you have that created, pass in the credentials I have outlined in the DI container to your App.config file and you should be good to do. MonogDB is much faster at indexing and grabbing the data from the collection, and is the default method that I use for the Feed Section of this application. I have also taken the liberty of creating the appropriate repositories as well for both databases and you can see those in action in the HomeViewModel. They are injected in from the DI container and allow you to create, update, delete, get, and getall from the DB. I have also added in some additional methods like GetAllByUser.

Conclusion

That is about it. This project is fairly straight forward once you understand how it all works under the hood. I am using TweetInvi for communicating with the Twitter API in real-time, because why reinvent the wheel?, and then convert that information over into my own models that has only the data that I need. I hope you found this document helpful and if you have any questions, please don't hesitate to contact me at info@pbsteele.com