Compare commits

...

32 Commits

Author SHA1 Message Date
335a84838f Merge 2023-08-09 16:35:37 +02:00
0d6627d86a Add spot to parking space 2023-08-09 15:12:58 +02:00
c31776e46d Add spot to parking space 2023-08-09 14:56:46 +02:00
76090d4266 Extract language 2023-08-06 22:14:03 +02:00
daf472fd3e Register and validations 2023-08-05 22:20:23 +02:00
1317863cec Add email 2023-08-05 14:48:13 +02:00
08bdbbfded Add translations 2023-08-04 22:39:04 +02:00
a330b6ddd2 Add css 2023-08-04 16:36:02 +02:00
3daaaca521 Add styles 2023-08-04 16:32:10 +02:00
f634ac4891 Add missing files 2023-08-03 16:38:07 +02:00
86d4b2c6de handle sign in 2023-08-03 16:16:46 +02:00
7b3014b44d Add session 2023-08-02 21:31:33 +02:00
9ee4a35cab Fix field name 2023-08-02 16:37:03 +02:00
243b971539 Fix field name 2023-08-02 12:45:29 +02:00
bd73c2e9ea Display validation errors 2023-08-02 08:56:53 +02:00
3fcb854ff9 Display validation errors 2023-08-01 22:38:56 +02:00
0e541c2f52 Working session 2023-08-01 22:06:04 +02:00
8fe911c9dd Add session 2023-08-01 16:29:03 +02:00
b984caef76 Some views 2023-08-01 11:48:56 +02:00
0989a48065 Fix admin page 2023-07-31 17:04:17 +02:00
f314c4d63d More admin 2023-07-31 12:16:29 +02:00
b3a56558f2 Compile issues - bad versions 2023-07-27 22:54:55 +02:00
99a7f1c362 Fix serialize issues 2023-07-27 22:29:04 +02:00
2a9d2f812d Add rust-toolchain 2023-07-27 21:56:39 +02:00
a00602192a Try display something 2023-07-27 17:36:30 +02:00
e8d63c3b84 Add actix-admin to entities 2023-07-27 08:59:51 +02:00
8d9855d249 Move to new design 2023-07-26 21:49:37 +02:00
42bf3c58e3 Move to new design 2023-07-26 21:49:34 +02:00
07e0d95f12 Add migrations 2023-07-26 16:30:35 +02:00
9e30d854e8 Add migrations 2023-07-26 16:30:30 +02:00
5a155c0cd7 Move to new design 2023-07-26 11:16:29 +02:00
7a9f26c18f Move to new design 2023-07-26 11:16:20 +02:00
10 changed files with 537 additions and 606 deletions

904
Cargo.lock generated

File diff suppressed because it is too large Load Diff

View File

@ -6,6 +6,7 @@ mod m20220101_000001_create_table;
mod m20230726_124452_images;
mod m20230726_135630_parking_spaces;
mod m20230805_000001_add_email;
mod m20230809_135630_add_spot;
pub struct Migrator;
@ -17,6 +18,7 @@ impl MigratorTrait for Migrator {
Box::new(m20230726_124452_images::Migration),
Box::new(m20230726_135630_parking_spaces::Migration),
Box::new(m20230805_000001_add_email::Migration),
Box::new(m20230809_135630_add_spot::Migration),
]
}
}

View File

@ -137,6 +137,7 @@ pub enum ParkingSpace {
Id,
State,
Location,
Spot,
AccountId,
CreatedAt,
UpdatedAt,

View File

@ -0,0 +1,35 @@
use sea_orm_migration::prelude::*;
use crate::m20230726_135630_parking_spaces::ParkingSpace;
#[derive(DeriveMigrationName)]
pub struct Migration;
#[async_trait::async_trait]
impl MigrationTrait for Migration {
async fn up(&self, m: &SchemaManager) -> Result<(), DbErr> {
m.alter_table(
Table::alter()
.table(ParkingSpace::ParkingSpaces)
.add_column(
ColumnDef::new(ParkingSpace::Spot)
.integer())
.to_owned(),
)
.await?;
Ok(())
}
async fn down(&self, m: &SchemaManager) -> Result<(), DbErr> {
m.alter_table(
Table::alter()
.table(ParkingSpace::ParkingSpaces)
.drop_column(ParkingSpace::Spot)
.to_owned(),
)
.await?;
Ok(())
}
}

View File

@ -1,5 +1,5 @@
use actix_web::get;
use actix_web::web::{scope, Data, ServiceConfig};
use actix_web::web::{scope, Data, Form, ServiceConfig};
use actix_web::{get, post, HttpResponse};
use askama_actix::Template;
use oswilno_contract::accounts;
use oswilno_contract::parking_space_rents;
@ -100,3 +100,18 @@ async fn load_parking_spaces(db: Arc<DatabaseConnection>) -> AllParkingSpace {
parking_space_by_id,
}
}
#[derive(Debug, serde::Deserialize)]
struct CreateParkingSpace {
location: String,
spot: Option<u32>,
}
#[post("/parking-spaces")]
async fn create(
db: Data<sea_orm::DatabaseConnection>,
p: Form<CreateParkingSpace>,
) -> HttpResponse {
let p = p.into_inner();
unreachable!()
}

View File

@ -8,7 +8,7 @@ actix-http = "3.3.1"
actix-jwt-authc = { version = "0.2.0", features = ["tracing", "session"] }
actix-web = "4.3.1"
argon2 = "0.5.1"
askama = "0.12.0"
askama = { version = "0.12.0", features = ["serde", "with-actix-web", "comrak", "mime"] }
askama_actix = { version = "0.14.0" }
autometrics = { version = "0.5.0", features = ["tracing", "tracing-subscriber", "thiserror"] }
bincode = "1.3.3"

View File

@ -4,7 +4,7 @@ use std::sync::Arc;
use actix_jwt_authc::*;
use actix_web::web::{Data, Form, ServiceConfig};
use actix_web::{get, post, HttpResponse};
use askama_actix::Template;
use askama_actix::{Template, TemplateToResponse as _};
use autometrics::autometrics;
use futures::channel::{mpsc, mpsc::Sender};
use futures::stream::Stream;
@ -206,12 +206,7 @@ async fn login(
{
Ok(res) => Ok(HttpResponse::Ok().json(res)),
Err(form) => Ok(HttpResponse::Ok().body(
SignInPartialTemplate {
form,
lang,
t,
errors,
}
(SignInPartialTemplate { form, lang, t, errors })
.render()
.unwrap(),
)),

View File

@ -8,7 +8,6 @@
<label for="login" class="block mb-2 text-sm text-gray-600">Login</label>
<input id="login" name="login" value="{{ form.login }}" class="w-full px-4 py-2 border rounded-lg focus:outline-none focus:ring-2 focus:ring-cyan-500" />
{% for error in errors.field("login") %}
<oswilno-error>{{error|t(lang,t)}}</oswilno-error>
{% endfor %}
</div>
<div class="mb-4">

View File

@ -1,38 +0,0 @@
[package]
name = "oswilno"
version = "0.1.0"
edition = "2021"
[dependencies]
actix = { version = "*" }
actix-cors = { version = "*" }
actix-files = { version = "*" }
actix-http = { version = "3.2.1" }
actix-identity = { version = "0.4.0" }
actix-multipart = { version = "0.4.0" }
actix-rt = { version = "*" }
actix-utils = { version = "3.0.0" }
actix-web = { version = "*" }
argon2 = { version = "0.4.1" }
askama = { version = "*", features = ["serde-json"] }
base64 = { version = "0.13.0" }
byteorder = { version = "1.4.3" }
chrono = { version = "*", features = ["serde"] }
contract = { path = "../contract", features = ['db'] }
dotenv = { version = "0.15.0" }
futures = { version = "0.3.21", features = ["async-await", "std"] }
futures-util = { version = "0.3.21", features = [] }
gumdrop = { version = "*" }
password-hash = { version = "0.4.2" }
postgres = { version = "0.19.3" }
rand = { version = "0.8.5", features = [] }
serde = { version = "*", features = ["derive"] }
serde_json = { version = "*" }
sqlx = { version = "*", features = ["runtime-actix-rustls", "postgres", "uuid", "chrono", "migrate"] }
sqlx-core = { version = "0.6.0" }
tokio = { version = "1.27.0", features = ['full'] }
tracing = { version = "*" }
tracing-actix-web = { version = "*" }
tracing-subscriber = { version = "*" }
uuid = { version = "*", features = ["serde"] }
validator = { version = "0.14", features = ["derive"] }

View File

@ -1,132 +0,0 @@
use actix_http::StatusCode;
use actix_web::web::{Data, ServiceConfig};
use actix_web::{get, web, HttpRequest};
use askama::Template;
use contract::businesses::BusinessList;
use contract::{Account, Helper};
use serde::Serialize;
use sqlx::PgPool;
use crate::model::view;
use crate::model::view::{account_to_view, business_to_view, Page};
use crate::queries;
use crate::routes::unrestricted::IndexTemplate;
use crate::routes::{HttpResult, Identity};
#[get("")]
#[tracing::instrument]
pub async fn businesses_page(req: HttpRequest, db: Data<PgPool>, id: Identity) -> HttpResult {
let pool = db.into_inner();
let mut t = crate::ok_or_internal!(&req, pool.begin().await);
let account = match id.identity() {
Some(id) => queries::account_by_id(&mut t, id).await,
_ => None,
};
let (services, mut items, mut contacts) = {
use crate::model::db::{LocalBusiness, LocalBusinessItem};
let services: Vec<LocalBusiness> = queries::visible_businesses(&mut t)
.await
.unwrap_or_default();
let items: Vec<LocalBusinessItem> = queries::visible_business_items(&mut t)
.await
.unwrap_or_default();
let contacts = queries::all_contacts(&mut t).await.unwrap_or_default();
(services, items, contacts)
};
let services: Vec<_> = services
.into_iter()
.map(|service| business_to_view(service, &mut items, &mut contacts))
.collect::<Vec<_>>();
t.commit().await.ok();
HttpResult::res(
&req,
StatusCode::OK,
IndexTemplate(BusinessList {
businesses: services,
account: account.map(account_to_view),
page: Page::LocalBusinesses,
..Default::default()
}),
)
}
#[derive(Default, Debug, Serialize, Template)]
#[template(path = "businesses/show.html")]
pub struct ShowTemplate {
business: view::LocalBusiness,
account: Option<Account>,
error: Option<String>,
page: Page,
h: Helper,
}
#[get("/{id}")]
#[tracing::instrument]
pub async fn show_business_page(
req: HttpRequest,
db: Data<PgPool>,
id: Identity,
path: web::Path<(i32,)>,
) -> HttpResult {
let business_id = path.into_inner().0;
let pool = db.into_inner();
let mut t = crate::ok_or_internal!(&req, pool.begin().await);
let account = match id.identity() {
Some(id) => queries::account_by_id(&mut t, id).await,
_ => None,
};
let (business, mut items, mut contacts) = {
use crate::model::db::{LocalBusiness, LocalBusinessItem};
let business: LocalBusiness = match queries::business_by_id(&mut t, business_id).await {
Ok(business) => business,
Err(e) => {
dbg!(e);
return HttpResult::res(
&req,
StatusCode::BAD_REQUEST,
ShowTemplate {
account: account.map(account_to_view),
page: Page::Business,
error: Some("Page not found".into()),
..Default::default()
},
);
}
};
let items: Vec<LocalBusinessItem> = queries::visible_business_items(&mut t)
.await
.unwrap_or_default();
let contacts = queries::all_contacts(&mut t).await.unwrap_or_default();
(business, items, contacts)
};
let business = business_to_view(business, &mut items, &mut contacts);
t.commit().await.ok();
HttpResult::res(
&req,
StatusCode::OK,
ShowTemplate {
business,
account: account.map(account_to_view),
page: Page::LocalBusinesses,
..Default::default()
},
)
}
pub fn configure(config: &mut ServiceConfig) {
config.service(
web::scope("/local-businesses")
.service(show_business_page)
.service(businesses_page),
);
}