diff --git a/.idea/codeStyles/Project.xml b/.idea/codeStyles/Project.xml index 1bec35e..2dee5fc 100644 --- a/.idea/codeStyles/Project.xml +++ b/.idea/codeStyles/Project.xml @@ -3,6 +3,12 @@ + + diff --git a/resources/sql/migrations/0000-init_schema.down.sql b/resources/sql/migrations/0000-init_schema.down.sql new file mode 100644 index 0000000..544b18d --- /dev/null +++ b/resources/sql/migrations/0000-init_schema.down.sql @@ -0,0 +1,42 @@ +-- Stats +drop table if exists resource_view; + +-- Extra resources +drop table if exists follow_article; +drop table if exists follow_constitution; +drop table if exists follow_citizen; +drop table if exists follow; + +drop table if exists vote_for_article; +drop table if exists vote_for_constitution; +drop table if exists vote_for_comment_on_article; +drop table if exists vote_for_comment_on_constitution; +drop table if exists vote; + +drop table if exists comment_on_article; +drop table if exists comment_on_constitution; +drop table if exists comment; + +drop table if exists extra; + +-- Article & Contitution +drop table if exists article_relations; +drop trigger if exists set_constitution_link_trigger on article_on_title; +drop table if exists article_in_title; +drop table if exists title; +drop function if exists set_constitution_link(); + +drop trigger if exists generate_version_number_trigger on article; +drop table if exists article; +drop function if exists generate_version_number(regclass, uuid); +drop trigger if exists generate_version_number_trigger on constitution; +drop table if exists constitution; +drop function if exists set_version_number(); + +-- User +drop table if exists moderator; +drop table if exists citizen_in_workgroup; +drop table if exists workgroup; +drop table if exists citizen; +drop table if exists "user"; +drop type if exists public."name"; diff --git a/resources/sql/migrations/0000-init_schema.up.sql b/resources/sql/migrations/0000-init_schema.up.sql new file mode 100644 index 0000000..8ec5264 --- /dev/null +++ b/resources/sql/migrations/0000-init_schema.up.sql @@ -0,0 +1,276 @@ +-- Users +create extension if not exists pgcrypto; +-- select * +-- from "user" +-- where username = lower('nick@example.com') +-- and password = crypt('12346', password); + +create table "user" +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + updated_at timestamptz default now() not null check ( updated_at >= created_at ), + blocked_at timestamptz default null null, + username varchar(64) not null check ( username != '' and lower(username) = username) unique, + password text not null check ( password != '' ) +); + +create type "name" as ( + first_name text, + last_name text, + civility text + ); + +create table citizen +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + name "name" not null check ( name != '' ), + birthday date not null, + user_id uuid not null references "user" (id), + vote_annonymous boolean default true not null, + follow_annonymous boolean default true not null +); + +create table workgroup +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + updated_at timestamptz default now() not null check ( updated_at >= created_at ), + created_by_id uuid not null references citizen (id), + name varchar(128) not null, + description text null, + annonymous boolean default false not null, + logo text null, + owner_id uuid not null references citizen (id) +); + +create table citizen_in_workgroup +( + citizen_id uuid not null references citizen (id), + workgroup uuid not null references workgroup (id), + created_at timestamptz default now() not null, + primary key (citizen_id, workgroup) +); + +create table moderator +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + updated_at timestamptz default now() not null check ( updated_at >= created_at ), + assigned_period tstzrange[] default '{}' not null, + user_id uuid not null references "user" (id) +); + +-- Article & Contitution + +create or replace function generate_version_number(tablename regclass, version_id uuid) returns int + language plpgsql as +$$ +begin + return random(); -- TODO +end; +$$; + +create or replace function set_version_number() returns trigger + language plpgsql as +$$ +begin + new.version_number = generate_version_number(tg_table_name::regclass, new.version_id); +end; +$$; + +create table article +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + created_by_id uuid not null references citizen (id), + version_id uuid default uuid_generate_v4() not null, + version_number int not null unique, + title text not null, + annonymous boolean default false not null, + content text not null check ( content != '' ), + description text, + tags varchar(32)[] default '{}' not null +); + +create trigger generate_version_number_trigger + before insert + on article +execute procedure set_version_number(); + +create table constitution +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + created_by_id uuid not null references citizen (id), + version_id uuid default uuid_generate_v4() not null, + version_number int not null, + title text not null, + annonymous boolean default false not null +); + +create trigger generate_version_number_trigger + before insert + on constitution +execute procedure set_version_number(); + +create table title +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + created_by_id uuid not null references citizen (id), + name text not null check ( name != '' ), + rank int not null, + constitution_id uuid not null references constitution (id) +); + +create table article_in_title +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + created_by_id uuid not null references citizen (id), + rank int not null, + title_id uuid not null references title (id), + article_id uuid not null references article (id), + constitution_id uuid not null references constitution (id) +); + +create or replace function set_constitution_link() returns trigger + language plpgsql as +$$ +begin + new.constitution_id = ( + select t.constitution_id + from title as t + where t.id = new.title_id + ); +end; +$$; + +create trigger set_constitution_link_trigger + before insert + on article_in_title +execute procedure set_constitution_link(); + +create table article_relations +( + source_id uuid references article, + target_id uuid references article check ( source_id != target_id ), + created_at timestamptz default now(), + created_by_id uuid not null references citizen (id), + primary key (source_id, target_id) +); + +-- Extra resources + +create table extra +( + id uuid default uuid_generate_v4() not null primary key, + created_at timestamptz default now() not null, + citizen_id uuid not null references citizen (id), + target_id uuid not null, + target_reference regclass not null +); + +create table follow +( + foreign key (citizen_id) references citizen (id), + primary key (id) +) inherits (extra); + +create table follow_article +( + foreign key (citizen_id) references citizen (id), + foreign key (target_id) references article (id), + primary key (id) +) inherits (follow); + +create table follow_constitution +( + foreign key (citizen_id) references citizen (id), + foreign key (target_id) references constitution (id), + primary key (id) +) inherits (follow); + +create table follow_citizen +( + foreign key (citizen_id) references citizen (id), + foreign key (target_id) references citizen (id), + primary key (id) +) inherits (follow); + + + +create table comment +( + updated_at timestamptz default now() not null check ( updated_at >= created_at ), + "content" text not null check ( content != '' ), + parent_id uuid null references comment (id), + foreign key (citizen_id) references citizen (id), + primary key (id) +) inherits (extra); + +create table comment_on_article +( + foreign key (citizen_id) references citizen (id), + foreign key (target_id) references article (id), + foreign key (parent_id) references comment_on_article (id), + primary key (id) +) inherits (comment); + +create table comment_on_constitution +( + foreign key (citizen_id) references citizen (id), + foreign key (target_id) references constitution (id), + foreign key (parent_id) references comment_on_constitution (id), + primary key (id) +) inherits (comment); + + + +create table vote +( + anonymous boolean default true not null, + note int not null check ( note >= -1 and note <= 1 ), + foreign key (citizen_id) references citizen (id), + primary key (id) +) inherits (extra); + +create table vote_for_article +( + foreign key (target_id) references article (id), + foreign key (citizen_id) references citizen (id), + primary key (id) +) inherits (vote); + +create table vote_for_constitution +( + foreign key (target_id) references constitution (id), + foreign key (citizen_id) references citizen (id), + primary key (id) +) inherits (vote); + +create table vote_for_comment_on_article +( + foreign key (target_id) references comment_on_article (id), + foreign key (citizen_id) references citizen (id), + primary key (id) +) inherits (vote); + +create table vote_for_comment_on_constitution +( + primary key (id), + foreign key (target_id) references comment_on_constitution (id), + foreign key (target_id) references citizen (id) +) inherits (vote); + +-- Stats +create table resource_view +( + id uuid default uuid_generate_v4() not null primary key, + type regclass not null, + created_at timestamptz default now() not null, + created_by_id uuid null references citizen (id), + ip cidr null +); \ No newline at end of file