refatoração LivroRepository
This commit is contained in:
parent
734b66090a
commit
c98b329df3
@ -30,7 +30,7 @@ Content-Type: application/json
|
||||
|
||||
### Obtém um livro individual
|
||||
|
||||
GET {{url}}/livros/abc1
|
||||
GET {{url}}/livros/a
|
||||
Accept: application/json
|
||||
|
||||
### Remove um livro
|
||||
|
||||
@ -2,6 +2,7 @@ namespace Biblioteca.Models;
|
||||
|
||||
public class Livro
|
||||
{
|
||||
public long Id { get; set; }
|
||||
public string? Isbn { get; set; }
|
||||
public string? Titulo { get; set; }
|
||||
public string? Autor { get; set; }
|
||||
|
||||
@ -24,29 +24,29 @@ app.MapPost("/livros", async (Livro livro) =>
|
||||
});
|
||||
|
||||
// Edita um livro.
|
||||
app.MapPut("/livros/{isbn}", async (string isbn, Livro livro) =>
|
||||
app.MapPut("/livros/{id}", async (long id, Livro livro) =>
|
||||
{
|
||||
var repo = new LivroRepository();
|
||||
var res = await repo.Editar(isbn, livro);
|
||||
var res = await repo.Editar(id, livro);
|
||||
|
||||
return res;
|
||||
});
|
||||
|
||||
// Obtém os dados de um livro individual.
|
||||
app.MapGet("/livros/{isbn}", async (string isbn) =>
|
||||
app.MapGet("/livros/{id}", async (long id) =>
|
||||
{
|
||||
var repo = new LivroRepository();
|
||||
var res = await repo.Obter(isbn);
|
||||
var res = await repo.Obter(id);
|
||||
|
||||
return res;
|
||||
});
|
||||
|
||||
// Remove um livro.
|
||||
app.MapDelete("/livros/{isbn}", async (string isbn) =>
|
||||
app.MapDelete("/livros/{id}", async (long id) =>
|
||||
{
|
||||
var repo = new LivroRepository();
|
||||
|
||||
await repo.Desativar(isbn);
|
||||
await repo.Desativar(id);
|
||||
});
|
||||
|
||||
app.Run();
|
||||
@ -18,7 +18,7 @@ public class LivroRepository
|
||||
var offset = take * Math.Max(pagina-1, 0);
|
||||
var lista = new List<Livro>();
|
||||
|
||||
cmd.CommandText = "SELECT Isbn, Titulo, Autor, Genero, Descricao, Foto, Keywords, Ativo, CriadoEm, AtualizadoEm FROM Livro ORDER BY CriadoEm LIMIT @offset,@take";
|
||||
cmd.CommandText = "SELECT Id, Isbn, Titulo, Autor, Genero, Descricao, Foto, Keywords, Ativo, CriadoEm, AtualizadoEm FROM Livro ORDER BY CriadoEm LIMIT @offset,@take";
|
||||
cmd.Parameters.AddWithValue("offset", offset);
|
||||
cmd.Parameters.AddWithValue("take", take);
|
||||
|
||||
@ -28,16 +28,17 @@ public class LivroRepository
|
||||
{
|
||||
lista.Add(new()
|
||||
{
|
||||
Isbn = reader.GetString(0),
|
||||
Titulo = reader.GetString(1),
|
||||
Autor = reader.GetString(2),
|
||||
Genero = reader.GetString(3),
|
||||
Descricao = reader.GetString(4),
|
||||
Foto = reader.GetString(5),
|
||||
Keywords = reader.GetString(6),
|
||||
Ativo = reader.GetBoolean(7),
|
||||
CriadoEm = reader.GetDateTime(8),
|
||||
AtualizadoEm = reader.GetDateTime(9),
|
||||
Id = reader.GetInt64(0),
|
||||
Isbn = reader.GetString(1),
|
||||
Titulo = reader.GetString(2),
|
||||
Autor = reader.GetString(3),
|
||||
Genero = reader.GetString(4),
|
||||
Descricao = reader.GetString(5),
|
||||
Foto = reader.GetString(6),
|
||||
Keywords = reader.GetString(7),
|
||||
Ativo = reader.GetBoolean(8),
|
||||
CriadoEm = reader.GetDateTime(9),
|
||||
AtualizadoEm = reader.GetDateTime(10),
|
||||
});
|
||||
}
|
||||
|
||||
@ -49,15 +50,15 @@ public class LivroRepository
|
||||
/// </summary>
|
||||
/// <param name="isbn"></param>
|
||||
/// <returns></returns>
|
||||
public async Task<Livro> Obter(string isbn)
|
||||
public async Task<Livro> Obter(long id)
|
||||
{
|
||||
using var conn = new MySqlConnection(ConnString);
|
||||
using var cmd = conn.CreateCommand();
|
||||
|
||||
await conn.OpenAsync();
|
||||
|
||||
cmd.CommandText = "SELECT Isbn, Titulo, Autor, Genero, Descricao, Foto, Keywords, Ativo, CriadoEm, AtualizadoEm FROM Livro WHERE Isbn=@isbn";
|
||||
cmd.Parameters.AddWithValue("isbn", isbn);
|
||||
cmd.CommandText = "SELECT Id, Isbn, Titulo, Autor, Genero, Descricao, Foto, Keywords, Ativo, CriadoEm, AtualizadoEm FROM Livro WHERE Id=@id";
|
||||
cmd.Parameters.AddWithValue("id", id);
|
||||
|
||||
using var reader = await cmd.ExecuteReaderAsync();
|
||||
|
||||
@ -65,21 +66,22 @@ public class LivroRepository
|
||||
|
||||
if (!existe)
|
||||
{
|
||||
throw new Exception($"Livro com ISBN {isbn} não encontrado");
|
||||
throw new Exception($"Livro {id} não encontrado");
|
||||
}
|
||||
|
||||
return new()
|
||||
{
|
||||
Isbn = reader.GetString(0),
|
||||
Titulo = reader.GetString(1),
|
||||
Autor = reader.GetString(2),
|
||||
Genero = reader.GetString(3),
|
||||
Descricao = reader.GetString(4),
|
||||
Foto = reader.GetString(5),
|
||||
Keywords = reader.GetString(6),
|
||||
Ativo = reader.GetBoolean(7),
|
||||
CriadoEm = reader.GetDateTime(8),
|
||||
AtualizadoEm = reader.GetDateTime(9),
|
||||
Id = reader.GetInt64(0),
|
||||
Isbn = reader.GetString(1),
|
||||
Titulo = reader.GetString(2),
|
||||
Autor = reader.GetString(3),
|
||||
Genero = reader.GetString(4),
|
||||
Descricao = reader.GetString(5),
|
||||
Foto = reader.GetString(6),
|
||||
Keywords = reader.GetString(7),
|
||||
Ativo = reader.GetBoolean(8),
|
||||
CriadoEm = reader.GetDateTime(9),
|
||||
AtualizadoEm = reader.GetDateTime(10),
|
||||
};
|
||||
}
|
||||
|
||||
@ -104,11 +106,6 @@ public class LivroRepository
|
||||
AtualizadoEm = default,
|
||||
};
|
||||
|
||||
if (livro.Isbn == "")
|
||||
{
|
||||
throw new Exception("O ISBN do livro é obrigatório.");
|
||||
}
|
||||
|
||||
if (livro.Titulo == "")
|
||||
{
|
||||
throw new Exception("O título do livro é obrigatório.");
|
||||
@ -138,14 +135,14 @@ public class LivroRepository
|
||||
return livro;
|
||||
}
|
||||
|
||||
public async Task<Livro> Editar(string isbn, Livro dados)
|
||||
public async Task<Livro> Editar(long id, Livro dados)
|
||||
{
|
||||
using var conn = new MySqlConnection(ConnString);
|
||||
using var cmd = conn.CreateCommand();
|
||||
|
||||
await conn.OpenAsync();
|
||||
|
||||
var livro = await Obter(isbn);
|
||||
var livro = await Obter(id);
|
||||
|
||||
livro.Titulo = dados.Titulo?.Trim() ?? "";
|
||||
livro.Autor = dados.Autor?.Trim() ?? "";
|
||||
@ -159,10 +156,10 @@ public class LivroRepository
|
||||
@"
|
||||
UPDATE Livro SET
|
||||
Titulo=@titulo, Autor=@autor, Genero=@genero, Descricao=@descricao, Foto=@foto, Keywords=@keywords, AtualizadoEm=@atualizadoem
|
||||
WHERE Isbn=@isbn
|
||||
WHERE Id=@id
|
||||
";
|
||||
|
||||
cmd.Parameters.AddWithValue("isbn", isbn);
|
||||
cmd.Parameters.AddWithValue("id", id);
|
||||
cmd.Parameters.AddWithValue("titulo", livro.Titulo);
|
||||
cmd.Parameters.AddWithValue("autor", livro.Autor);
|
||||
cmd.Parameters.AddWithValue("genero", livro.Genero);
|
||||
@ -176,15 +173,15 @@ public class LivroRepository
|
||||
return livro;
|
||||
}
|
||||
|
||||
public async Task Desativar(string isbn)
|
||||
public async Task Desativar(long id)
|
||||
{
|
||||
using var conn = new MySqlConnection(ConnString);
|
||||
using var cmd = conn.CreateCommand();
|
||||
|
||||
await conn.OpenAsync();
|
||||
|
||||
cmd.CommandText = "UPDATE Livro SET Ativo=false WHERE Isbn=@isbn";
|
||||
cmd.Parameters.AddWithValue("isbn", isbn);
|
||||
cmd.CommandText = "UPDATE Livro SET Ativo=false WHERE Id=@id";
|
||||
cmd.Parameters.AddWithValue("id", id);
|
||||
|
||||
await cmd.ExecuteNonQueryAsync();
|
||||
}
|
||||
|
||||
71
scripts/books.py
Normal file
71
scripts/books.py
Normal file
@ -0,0 +1,71 @@
|
||||
#
|
||||
# books.py
|
||||
# Gera um arquivo .sql com INSERTs de livros obtidos do Project Gutemberg
|
||||
# https://gutendex.com/
|
||||
#
|
||||
|
||||
import http.client
|
||||
import json
|
||||
import time
|
||||
from urllib.parse import urlparse
|
||||
|
||||
API_URL = "https://gutendex.com/books/"
|
||||
BOOKS_COUNT = 1000
|
||||
FETCH_DELAY = 1#s
|
||||
OUTPUT = "./books.sql"
|
||||
|
||||
def fetch(resource):
|
||||
url = urlparse(resource)
|
||||
client = http.client.HTTPSConnection if url.scheme == "https" else http.client.HTTPConnection
|
||||
conn = client(url.netloc)
|
||||
|
||||
conn.request("GET", f"{url.path}?{url.query}")
|
||||
res = conn.getresponse()
|
||||
|
||||
if res.status < 200 or res.status > 299:
|
||||
return {}
|
||||
|
||||
return json.loads(res.read())
|
||||
|
||||
def write_inserts(file, page):
|
||||
data = fetch(f"{API_URL}?page={page}")
|
||||
books = data["results"]
|
||||
lines = []
|
||||
|
||||
esc = lambda str: str.replace('"', '\\"')
|
||||
|
||||
for book in books:
|
||||
summaries = book["summaries"]
|
||||
imgs = [book["formats"][f] for f in book["formats"] if f.startswith("image/")]
|
||||
|
||||
isbn = ""
|
||||
titulo = book["title"]
|
||||
autor = ",".join([a["name"] for a in book["authors"]])
|
||||
genero = ",".join(book["subjects"])
|
||||
descricao = summaries[0] if len(summaries) > 0 else ""
|
||||
foto = imgs[0] if len(imgs) > 0 else ""
|
||||
keywords = ",".join(book["bookshelves"])
|
||||
|
||||
lines.append(f'("{esc(isbn)}", "{esc(titulo)}", "{esc(autor)}", "{esc(genero)}", "{esc(descricao)}", "{esc(foto)}", "{esc(keywords)}", true, NOW(), NOW())')
|
||||
|
||||
values = ",\n".join(lines)
|
||||
insert = f"INSERT INTO Livro (Isbn, Titulo, Autor, Genero, Descricao, Foto, Keywords, Ativo, CriadoEm, AtualizadoEm) VALUES {values};\n"
|
||||
|
||||
file.write(insert)
|
||||
|
||||
return len(lines)
|
||||
|
||||
def collect(n, file, _page=1):
|
||||
if n <= 0:
|
||||
return
|
||||
|
||||
written = write_inserts(file, _page)
|
||||
|
||||
time.sleep(FETCH_DELAY)
|
||||
collect(n-written, file, _page+1)
|
||||
|
||||
def run():
|
||||
with open(OUTPUT, "w") as file:
|
||||
collect(BOOKS_COUNT, file)
|
||||
|
||||
run()
|
||||
1024
scripts/books.sql
Normal file
1024
scripts/books.sql
Normal file
File diff suppressed because it is too large
Load Diff
@ -1,5 +1,6 @@
|
||||
CREATE TABLE Livro (
|
||||
Isbn VARCHAR(255) PRIMARY KEY NOT NULL,
|
||||
Id BIGINT PRIMARY KEY NOT NULL AUTO_INCREMENT,
|
||||
Isbn VARCHAR(255) NOT NULL,
|
||||
Titulo VARCHAR(512) NOT NULL,
|
||||
Autor TEXT NOT NULL,
|
||||
Genero TEXT NOT NULL,
|
||||
@ -10,6 +11,7 @@ CREATE TABLE Livro (
|
||||
CriadoEm DATETIME NOT NULL,
|
||||
AtualizadoEm DATETIME NOT NULL,
|
||||
|
||||
FULLTEXT (Titulo, Autor, Genero, Descricao, Keywords),
|
||||
INDEX (CriadoEm)
|
||||
INDEX (Isbn),
|
||||
INDEX (CriadoEm),
|
||||
FULLTEXT (Titulo, Autor, Genero, Descricao, Keywords)
|
||||
);
|
||||
Loading…
x
Reference in New Issue
Block a user