bitque/jirs-client/src/lib.rs

158 lines
4.0 KiB
Rust
Raw Normal View History

2020-04-05 15:15:09 +02:00
#[macro_use]
extern crate lazy_static;
2020-03-30 14:26:25 +02:00
use seed::fetch::FetchObject;
2020-03-30 08:16:26 +02:00
use seed::{prelude::*, *};
2020-03-27 12:17:27 +01:00
2020-03-31 22:05:18 +02:00
use jirs_data::IssueStatus;
2020-04-05 15:15:09 +02:00
use crate::api::ws;
use crate::model::{ModalType, Model, Page};
2020-04-02 08:45:43 +02:00
use crate::shared::styled_select::StyledSelectChange;
2020-03-30 23:19:00 +02:00
2020-03-30 14:26:25 +02:00
mod api;
2020-03-31 22:05:18 +02:00
mod api_handlers;
2020-03-30 14:26:25 +02:00
mod login;
mod modal;
2020-03-30 08:16:26 +02:00
mod model;
2020-03-30 14:26:25 +02:00
mod project;
mod project_settings;
mod register;
mod shared;
2020-03-30 08:16:26 +02:00
2020-03-31 11:11:06 +02:00
pub type UserId = i32;
2020-03-31 22:05:18 +02:00
pub type IssueId = i32;
2020-03-31 11:11:06 +02:00
pub type AvatarFilterActive = bool;
2020-04-02 08:45:43 +02:00
#[derive(Clone, Debug)]
pub enum FieldId {
2020-04-05 15:15:09 +02:00
// edit issue
2020-04-02 08:45:43 +02:00
IssueTypeEditModalTop,
2020-04-05 15:15:09 +02:00
// project boards
TextFilterBoard,
//
2020-04-03 16:15:56 +02:00
CopyButtonLabel,
2020-04-05 15:15:09 +02:00
// add issue
2020-04-04 17:42:02 +02:00
IssueTypeAddIssueModal,
2020-04-05 15:15:09 +02:00
SummaryAddIssueModal,
DescriptionAddIssueModal,
2020-04-03 16:15:56 +02:00
}
#[derive(Clone, Debug)]
pub enum FieldChange {
LinkCopied(FieldId, bool),
2020-04-02 08:45:43 +02:00
}
2020-03-30 14:26:25 +02:00
#[derive(Clone, Debug)]
pub enum Msg {
2020-03-31 22:05:18 +02:00
NoOp,
2020-04-02 08:45:43 +02:00
StyledSelectChanged(FieldId, StyledSelectChange),
2020-03-30 14:26:25 +02:00
ChangePage(model::Page),
CurrentProjectResult(FetchObject<String>),
CurrentUserResult(FetchObject<String>),
InternalFailure(String),
2020-03-30 23:19:00 +02:00
ToggleAboutTooltip,
// project
ProjectTextFilterChanged(String),
2020-03-31 11:11:06 +02:00
ProjectAvatarFilterChanged(UserId, AvatarFilterActive),
ProjectToggleOnlyMy,
2020-03-31 11:36:39 +02:00
ProjectToggleRecentlyUpdated,
2020-03-31 14:28:30 +02:00
ProjectClearFilters,
2020-03-31 22:05:18 +02:00
// dragging
IssueDragStarted(IssueId),
IssueDragStopped(IssueId),
IssueDropZone(IssueStatus),
2020-04-05 15:15:09 +02:00
// inputs
InputChanged(FieldId, String),
2020-03-31 22:05:18 +02:00
// issues
IssueUpdateResult(FetchObject<String>),
2020-04-04 17:42:02 +02:00
IssueDeleteResult(FetchObject<String>),
DeleteIssue(IssueId),
2020-04-01 18:30:01 +02:00
// modals
2020-04-03 16:15:56 +02:00
ModalOpened(ModalType),
ModalDropped,
ModalChanged(FieldChange),
2020-03-29 19:56:55 +02:00
}
2020-03-30 14:26:25 +02:00
fn update(msg: Msg, model: &mut model::Model, orders: &mut impl Orders<Msg>) {
if cfg!(debug_assertions) {
log!(msg);
}
2020-03-30 08:16:26 +02:00
match msg {
2020-03-30 14:26:25 +02:00
Msg::ChangePage(page) => {
model.page = page;
}
_ => (),
}
crate::shared::update(&msg, model, orders);
crate::modal::update(&msg, model, orders);
2020-03-30 14:26:25 +02:00
match model.page {
2020-04-04 17:42:02 +02:00
Page::Project | Page::AddIssue => project::update(msg, model, orders),
2020-04-01 10:36:05 +02:00
Page::EditIssue(_id) => project::update(msg, model, orders),
2020-03-30 14:26:25 +02:00
Page::ProjectSettings => project_settings::update(msg, model, orders),
Page::Login => login::update(msg, model, orders),
Page::Register => register::update(msg, model, orders),
}
if cfg!(debug_assertions) {
2020-03-31 22:05:18 +02:00
// debug!(model);
2020-03-29 19:56:55 +02:00
}
2020-03-30 08:16:26 +02:00
}
2020-03-29 19:56:55 +02:00
2020-03-30 14:26:25 +02:00
fn view(model: &model::Model) -> Node<Msg> {
match model.page {
2020-04-04 17:42:02 +02:00
Page::Project | Page::AddIssue => project::view(model),
2020-04-01 10:36:05 +02:00
Page::EditIssue(_id) => project::view(model),
2020-03-30 14:26:25 +02:00
Page::ProjectSettings => project_settings::view(model),
Page::Login => login::view(model),
Page::Register => register::view(model),
}
2020-03-30 08:16:26 +02:00
}
2020-03-29 19:56:55 +02:00
2020-03-30 08:16:26 +02:00
fn routes(url: Url) -> Option<Msg> {
if url.path.is_empty() {
2020-03-30 14:26:25 +02:00
return Some(Msg::ChangePage(model::Page::Project));
2020-03-30 08:16:26 +02:00
}
2020-03-29 19:56:55 +02:00
2020-03-30 08:16:26 +02:00
match url.path[0].as_ref() {
2020-03-30 14:26:25 +02:00
"board" => Some(Msg::ChangePage(model::Page::Project)),
2020-04-01 10:36:05 +02:00
"issues" => match url.path.get(1).as_ref().map(|s| s.parse::<i32>()) {
Some(Ok(id)) => Some(Msg::ChangePage(model::Page::EditIssue(id))),
_ => None,
},
2020-04-04 17:42:02 +02:00
"add-issue" => Some(Msg::ChangePage(Page::AddIssue)),
2020-03-30 14:26:25 +02:00
"project-settings" => Some(Msg::ChangePage(model::Page::ProjectSettings)),
"login" => Some(Msg::ChangePage(model::Page::Login)),
"register" => Some(Msg::ChangePage(model::Page::Register)),
_ => Some(Msg::ChangePage(model::Page::Project)),
}
}
pub static mut HOST_URL: String = String::new();
#[wasm_bindgen]
pub fn set_host_url(url: String) {
unsafe {
HOST_URL = url;
2020-03-29 19:56:55 +02:00
}
}
2020-04-05 15:15:09 +02:00
fn after_mount(_url: Url, _orders: &mut impl Orders<Msg>) -> AfterMount<Model> {
ws();
let model = Model::default();
AfterMount::new(model).url_handling(UrlHandling::None)
}
2020-03-30 14:26:25 +02:00
#[wasm_bindgen]
2020-03-30 08:16:26 +02:00
pub fn render() {
2020-04-05 15:15:09 +02:00
App::builder(update, view)
.routes(routes)
.after_mount(after_mount)
.build_and_start();
2020-03-29 19:56:55 +02:00
}