Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions CodingTracker.Solomonlol/CodingTracker.Solomonlol.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net10.0</TargetFramework>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Dapper" Version="2.1.79" />
<PackageReference Include="Microsoft.Data.Sqlite.Core" Version="10.0.10" />
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="10.0.10" />
<PackageReference Include="Spectre.Console" Version="0.57.2" />
<PackageReference Include="SQLitePCLRaw.bundle_e_sqlite3" Version="2.1.12" />
</ItemGroup>

<ItemGroup>
<None Update="appsetings.json">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
</ItemGroup>

</Project>
3 changes: 3 additions & 0 deletions CodingTracker.Solomonlol/CodingTracker.Solomonlol.slnx
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<Solution>
<Project Path="CodingTracker.Solomonlol.csproj" />
</Solution>
216 changes: 216 additions & 0 deletions CodingTracker.Solomonlol/Controllers/CodingController.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,216 @@
using CodingTracker.Solomonlol.Model;
using Dapper;
using Microsoft.Data.Sqlite;
using Microsoft.Extensions.Configuration;
using Spectre.Console;
using System.Data;
using System.Diagnostics;
using System.Globalization;
using static CodingTracker.Solomonlol.Model.MenuValues;

namespace CodingTracker.Solomonlol.Controllers
{
internal class CodingController : ICodingController
{
public void CreateTableIfNotExists()
{
using IDbConnection db = new SqliteConnection(GetConString());
db.Open();
var sqlQuery = "CREATE TABLE IF NOT EXISTS CodingSessions" +
"(Id INTEGER PRIMARY KEY AUTOINCREMENT," +
"Date TEXT NOT NULL," +
"StartTime TEXT NOT NULL," +
"EndTime TEXT NOT NULL," +
"Duration TEXT NOT NULL)";
db.Execute(sqlQuery);
db.Close();
}

public List<CodingSession> GetData(string? s = null)
{
if (s == null) s = "SELECT * FROM CodingSessions";
using IDbConnection db = new SqliteConnection(GetConString());
return [.. db.Query<CodingSession>(s)];
}

public void CreateData(CodingSession? codingSession=null)
{
PrintData();
CodingSession session = new();
if (codingSession == null)
{
session = NewRecord();
}
else session = codingSession;

using IDbConnection db = new SqliteConnection(GetConString());
var sqlQuery = "INSERT INTO CodingSessions (Date, StartTime, EndTime, Duration)" +
"VALUES (@Date, @StartTime, @EndTime, @Duration)";
db.Execute(sqlQuery, session);
PrintData();
}

public void DeleteData()
{
PrintData();
NumberInput("Write record Id to delete:", out int id);
using IDbConnection db = new SqliteConnection(GetConString());
var sqlQuery = "DELETE FROM CodingSessions WHERE Id=@id";
var check = db.Execute(sqlQuery, new { id });
if (check == 0)
{
AnsiConsole.MarkupLine($"[red]Record whith Id={id} does not exists.[/]");

}
else
{
PrintData();
AnsiConsole.MarkupLine($"[green]Record whith Id={id} was deleted.[/]");
}

}

public void UpdateData()
{
PrintData();
NumberInput("Write record Id to update:", out int id);
string sql = "SELECT COUNT(1) FROM CodingSessions WHERE Id = @Id";


using IDbConnection db = new SqliteConnection(GetConString());
var checkIfExist = db.ExecuteScalar<bool>(sql, new { Id = id });
if (checkIfExist)
{
var session = NewRecord(id);

var sqlQuery = "UPDATE CodingSessions SET Date=@Date," +
"StartTime=@StartTime," +
"EndTime=@EndTime," +
"Duration=@Duration " +
"WHERE Id=@Id";
db.Execute(sqlQuery, session);
PrintData();
AnsiConsole.MarkupLine($"[green]Record whith Id={id} was upadted.[/]");
}
else
{
PrintData();
AnsiConsole.MarkupLine($"[red]Record whith Id={id} does not exists.[/]");
}

}

public void PrintData(string? s = null)
{
AnsiConsole.Clear();
List<CodingSession> toPrint = new List<CodingSession>();
if (s != null)
{
toPrint = GetData(s);
}
else toPrint = GetData();
if (toPrint.Count>0)
{
var table = new Table();
table.AddColumns("ID", "Date", "Start time", "End time", "Duration");

foreach (var c in toPrint)
{
table.AddRow($"{c.Id}",
$"{c.Date}",
$"{c.StartTime}",
$"{c.EndTime}",
$"{c.Duration}");
}
AnsiConsole.Write(table);
}
else AnsiConsole.MarkupLine("[red]Database is empty.[/]");
}

private static string GetConString()
{
IConfiguration config = new ConfigurationBuilder()
.AddJsonFile("appsetings.json")
.Build();

var connectionString = config.GetConnectionString("SQLiteConnection");
return connectionString;
}

private CodingSession NewRecord(int? id = null)
{
DateTime startTime, endTime;
do
{
PrintData();
DateInput("Write start time in 'dd.MM.yyyy H:m' format:", out startTime);
DateInput("Write end time in 'dd.MM.yyyy H:m' format:", out endTime);
if (!(endTime > startTime))
{
AnsiConsole.MarkupLine("[red]The end time cannot be earlier than or the same as the start time.[/]" +
"\nPress any key to continue");
AnsiConsole.Console.Input.ReadKey(true);
}
} while (!(endTime > startTime));
CodingSession session = new(startTime, endTime, id);
return session;

}
private static void DateInput(string s, out DateTime date)
{
Console.WriteLine(s);
while (!DateTime.TryParseExact(Console.ReadLine(), "dd.MM.yyyy H:m", CultureInfo.InvariantCulture, DateTimeStyles.None, out date))
{
AnsiConsole.MarkupLine("[red]Wrong data format. Write it like 'dd.MM.yyyy H:m' and try again.[/]");
}
}
private static void NumberInput(string s, out int id)
{
Console.WriteLine(s);
while (!int.TryParse(Console.ReadLine(), out id) || id <= 0)
{
AnsiConsole.MarkupLine("[red]Wrong data format. The string must contain only digits above zero. Try again.[/]");
}
}
public void StartTimer()
{
Stopwatch stopwatch = new Stopwatch();
DateTime start = DateTime.Now;
DateTime end = new();
stopwatch.Start();
while(true)
{
if(Console.KeyAvailable)
{
var key = Console.ReadKey(true).Key;
if(key==ConsoleKey.Enter)
{
stopwatch.Stop();
end = start+stopwatch.Elapsed;
CreateData(new CodingSession(start, end));
break;
}
}

Console.Clear();
AnsiConsole.MarkupLine("[green]IT'S CODING TIME![/]\nPress Enter key to stop this session...");
AnsiConsole.MarkupLine($"Current session: {stopwatch.Elapsed.ToString(@"mm\:ss")}");
Thread.Sleep(1000);
}
}
public void PrintOrderby()
{
var choice = AnsiConsole.Prompt(new SelectionPrompt<string>()
.Title("Select an [green]option[/]:")
.AddChoices(printValues.Keys));

printValues[choice]("");

}

public void Exit()
{
Environment.Exit(0);
}
}
}
17 changes: 17 additions & 0 deletions CodingTracker.Solomonlol/Controllers/ICodingController.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
using CodingTracker.Solomonlol.Model;
using System;
using System.Collections.Generic;
using System.Text;

namespace CodingTracker.Solomonlol.Controllers
{
internal interface ICodingController
{
public void CreateTableIfNotExists();
public void UpdateData();
public void DeleteData();
public void PrintData(string? s=null);
public void CreateData(CodingSession? codingSession=null);
public void Exit();
}
}
29 changes: 29 additions & 0 deletions CodingTracker.Solomonlol/Menu.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
using CodingTracker.Solomonlol.Controllers;
using CodingTracker.Solomonlol.Model;
using Dapper;
using Spectre.Console;
using System;
using System.Collections.Generic;
using System.Text;
using static CodingTracker.Solomonlol.Model.MenuValues;


namespace CodingTracker.Solomonlol
{
internal class Menu
{

public static void MainMenu()
{
cod.CreateTableIfNotExists();
while (true)
{
var choice = AnsiConsole.Prompt(new SelectionPrompt<string>()
.Title("Select an [green]option[/]:")
.AddChoices(menuValues.Keys));

menuValues[choice]();
}
}
}
}
28 changes: 28 additions & 0 deletions CodingTracker.Solomonlol/Model/CodingSession.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
using Spectre.Console;
using System;
using System.Collections.Generic;
using System.Text;

namespace CodingTracker.Solomonlol.Model
{
internal class CodingSession
{
public int? Id { get; set; } = null;
public string Date { get; set; }
public string StartTime { get; set; }
public string EndTime { get; set; }
public string Duration { get; set; }

public CodingSession()
{ }

public CodingSession(DateTime startTime, DateTime endTime, int? id = null)
{
Id = id;
Date = DateOnly.FromDateTime(startTime).ToString();
StartTime = TimeOnly.FromDateTime(startTime).ToString();
EndTime = TimeOnly.FromDateTime(endTime).ToString();
Duration = ((int)endTime.Subtract(startTime).TotalMinutes) + " minutes";
}
}
}
29 changes: 29 additions & 0 deletions CodingTracker.Solomonlol/Model/MenuValues.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
using CodingTracker.Solomonlol.Controllers;


namespace CodingTracker.Solomonlol.Model
{
public static class MenuValues
{
internal static CodingController cod = new();
public static Dictionary<string, Action> menuValues = new()
{
{ "Print all records", () => cod.PrintOrderby() },
{ "New record", () => cod.CreateData() },
{ "Update record", () => cod.UpdateData() },
{ "Delete record", () => cod.DeleteData() },
{ "Timer", ()=>cod.StartTimer() },
{ "Exit", () => cod.Exit() }
};

public static Dictionary<string, Action<string>> printValues = new()
{
{ "Print", (s) => cod.PrintData() },
{ "Order by Date Ascending", (s) => cod.PrintData("SELECT * FROM CodingSessions ORDER BY Date ASC") },
{ "Order by Date Descending", (s) => cod.PrintData("SELECT * FROM CodingSessions ORDER BY Date DESC") },
{ "Order by Duration Ascending", (s) => cod.PrintData("SELECT * FROM CodingSessions ORDER BY Duration ASC") },
{ "Order by Duration Descending", (s) => cod.PrintData("SELECT * FROM CodingSessions ORDER BY Duration DESC") },
};

}
}
8 changes: 8 additions & 0 deletions CodingTracker.Solomonlol/Program.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
using CodingTracker.Solomonlol;
using Microsoft.Extensions.Configuration;
using Spectre.Console;



Menu menu = new();
Menu.MainMenu();
15 changes: 15 additions & 0 deletions CodingTracker.Solomonlol/appsetings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
}
},
"AllowedHosts": "*",
"DatabaseSettings": {
"SQLiteDbPath": "ApplicationDatabase.db"
},
"ConnectionStrings": {
"SQLiteConnection": "Data Source=ApplicationDatabase.db;"
}
}
Loading