diff --git a/lib/GADS.pm b/lib/GADS.pm index 408bb4860..ae792b5ad 100644 --- a/lib/GADS.pm +++ b/lib/GADS.pm @@ -26,6 +26,7 @@ use File::Temp qw/ tempfile /; use GADS::Alert; use GADS::Approval; use GADS::Audit; +use GADS::Authentication; use GADS::Layout; use GADS::Column; use GADS::Column::Autocur; @@ -154,6 +155,13 @@ sub _update_csrf_token { session csrf_token => Session::Token->new(length => 32)->get; } +sub get_and_clear_session_value { + my $id = shift; + my $value = session $id; + session $id => undef; + return $value; +} + hook before => sub { schema->site_id(undef); @@ -168,6 +176,7 @@ hook before => sub { my $site_id = $site->id; trace __x"Site ID is {id}", id => $site_id; schema->site_id($site_id); + schema->resultset('Authentication')->create_default_provider; } else { my $site = schema->resultset('Site')->next; @@ -482,26 +491,65 @@ get '/saml' => sub { redirect '/'; }; -post '/saml' => sub { +post '/saml' => \&saml_post; + +post '/:unique_id/saml' => \&saml_post; + +sub saml_post { + + my $unique_id = route_parameters->get('unique_id'); + my $relaystate = body_parameters->get('RelayState'); + + my $authentication = schema->resultset('Authentication')->find({saml2_unique_id => $unique_id}) + or warn "Error finding authentication provider from unique_id" if defined $unique_id; + + $authentication = schema->resultset('Authentication')->find(session 'authentication_id') + or error "Error finding authentication provider" if !defined $authentication; + + error __"Invalid unique_id in POST request" if $authentication->saml2_unique_id ne $unique_id; + + my $request_id; + # If the relaystates match this should be an IdP initiated login + # otherwise get the AuthnReq request id from the session + if ($authentication->saml2_relaystate ne $relaystate) { + $request_id = get_and_clear_session_value('request_id'); + } my $saml = GADS::SAML->new( - request_id => session('request_id'), + authentication => $authentication, + request_id => $request_id, base_url => request->base, ); + my $callback = $saml->callback( saml_response => body_parameters->get('SAMLResponse'), + defined $authentication->cacert ? + (cacert => $authentication->cacert) : (), + defined $authentication->sp_key ? + (sp_key => $authentication->sp_key) : (), + defined $relaystate ? (relaystate => $relaystate) : (), ); - my $authentication = schema->resultset('Authentication')->find(session 'authentication_id') - or error "Error finding authentication provider"; + my $username; + if (! defined ($username = $callback->{nameid})) { + error __"Missing nameid in SAML response"; + my $msg = $authentication->saml_provider_match_error; + return forwardHome({ danger => __x($msg, username => $username) }, 'saml_login' ) + } - my $username = $callback->{nameid}; my $user = schema->resultset('User')->active->search({ username => $username })->next; + # FIXME: Here we could create the user if the relaystate matches a provider + if (!defined $user or ($user->provider->id ne $authentication->id)) { + my $msg = $authentication->saml_provider_match_error; + $user = undef; + return forwardHome({ danger => __x($msg, username => $username) }, 'saml_login' ) + } + if (!$user) { my $msg = $authentication->user_not_found_error; - return forwardHome({ danger => __x($msg, username => $username) }, 'login?password=1' ); + return forwardHome({ danger => __x($msg, username => $username) }, 'saml_login' ); } $user->update_attributes($callback->{attributes}); @@ -546,6 +594,15 @@ sub _successful_login lastfail => undef, }); + unless($user->provider) { + my $provider = schema->resultset('Authentication')->find( + 1, # Default to first provider + ); + $user->find_or_create_related('provider', { + id => $provider->id, + }); + } + # Load previous settings my $session_settings; try { $session_settings = decode_json $user->session_settings }; @@ -566,6 +623,32 @@ sub _successful_login } } +any ['get', 'post'] => '/saml_login' => sub { + + my $audit = GADS::Audit->new(schema => schema); + my $user = logged_in_user; + + # Don't allow login page to be displayed when logged-in, to prevent + # user thinking they are logged out when they are not + return forwardHome() if $user; + + my $users = GADS::Users->new(schema => schema, config => config); + my $output = template 'login_saml' => { + username => cookie('remember_me'), + titles => $users->titles, + organisations => $users->organisations, + departments => $users->departments, + teams => $users->teams, + providers => $users->providers, + register_text => var('site')->register_text, + page => 'login', + body_class => 'p-0', + container_class => 'login container-fluid', + main_class => 'login__main row', + }; + $output; +}; + any ['get', 'post'] => '/login' => sub { my $audit = GADS::Audit->new(schema => schema); @@ -575,13 +658,24 @@ any ['get', 'post'] => '/login' => sub { # user thinking they are logged out when they are not return forwardHome() if $user; - # Get authentication provider - my $enabled = schema->resultset('Authentication')->enabled; + my $enabled; + if ((my $saml_user = param('username')) && !query_parameters->get('password')) { + my $users = GADS::Users->new(schema => schema, config => config); + my $user_search = $users->user_rs->search({ + username => $saml_user, + }); + my $user = $user_search->next; + $enabled = schema->resultset('Authentication')->by_id($user->provider->id) if defined $user; + } + else { + # Get authentication provider + $enabled = schema->resultset('Authentication')->enabled; + } - if ($enabled->count == 1 && !query_parameters->get('password')) + if (defined $enabled && $enabled->count ge 1 && !query_parameters->get('password')) { my $auth = $enabled->next; - if ($auth->type eq 'saml2') + if ($auth->type == 1) { my $saml = GADS::SAML->new( authentication => $auth, @@ -669,6 +763,7 @@ any ['get', 'post'] => '/login' => sub { organisations => $users->organisations, departments => $users->departments, teams => $users->teams, + providers => $users->providers, register_text => var('site')->register_text, page => 'login', body_class => 'p-0', @@ -738,6 +833,7 @@ any ['get', 'post'] => '/register' => sub { organisations => $users->organisations, departments => $users->departments, teams => $users->teams, + providers => $users->providers, register_text => var('site')->register_text, page => 'register', body_class => 'p-0', @@ -777,6 +873,8 @@ any ['get', 'post'] => '/myaccount/?' => require_login sub { my %update; foreach my $field (var('site')->user_fields) { + # FIXME The user should not be able to change their own authentication provider + next if $field->{name} eq 'provider' && not logged_in_user->permission->{superadmin}; next if !$field->{editable}; $update{$field->{name}} = param($field->{name}) || undef; } @@ -797,6 +895,7 @@ any ['get', 'post'] => '/myaccount/?' => require_login sub { organisation => $users->organisations, department_id => $users->departments, team_id => $users->teams, + provider => $users->providers, }, }; }; @@ -1511,6 +1610,29 @@ any ['get', 'post'] => '/user_export/?' => require_any_role [qw/useradmin supera }; }; +any ['get', 'post'] => '/authentication_providers/' => require_any_role [qw/useradmin superadmin/] => sub { + + my @name_ids = ( + { label_plain => 'emailAddress', value => 'emailAddress' }, + { label_plain => 'unspecified', value => 'unspecified' }, + { label_plain => 'X509SubjectName', value => 'X509SubjectName' }, + { label_plain => 'WindowsDomainQualifiedName', value => 'WindowsDomainQualifiedName' }, + { label_plain => 'entity', value => 'entity' }, + { label_plain => 'transient', value => 'transient' }, + { label_plain => 'persistent', value => 'persistent' }, + ); + + my $auth = GADS::Authentication->new(schema => schema); + template 'authentication/providers' => { + providers => $auth, + permissions => "permisission", #$auth->permissions, + values => { + saml2_nameid => \@name_ids, + }, + page => 'system_settings', + }; +}; + any ['get', 'post'] => '/user_overview/' => require_any_role [qw/useradmin superadmin/] => sub { my $userso = GADS::Users->new(schema => schema); @@ -1545,6 +1667,7 @@ any ['get', 'post'] => '/user_overview/' => require_any_role [qw/useradmin super organisation => $userso->organisations, department_id => $userso->departments, team_id => $userso->teams, + provider => $userso->providers, }, permissions => $userso->permissions, page => 'user', @@ -1587,6 +1710,131 @@ any ['get', 'post'] => '/user_requests/' => require_any_role [qw/useradmin super }; }; +any ['get'] => '/metadata/:id' => require_any_role [qw/useradmin superadmin/] => sub { + my $id = route_parameters->get('id'); + + my $provider = rset('Authentication')->providers->search({id => $id})->next + or error __x"Authentication provider id {id} not found", id => $id; + + if (defined $provider) + { + if ($provider->type == 1) + { + my $saml = GADS::SAML->new( + authentication => $provider, + base_url => request->base, + ); + response_header 'Content-Disposition' => "attachment; filename=\"saml.xml\""; + return send_file(\$saml->metadata, content_type => 'application/xml'); + } + } +}; + +any ['get', 'post'] => '/authentication_providers/:id' => require_any_role [qw/useradmin superadmin/] => sub { + my $user = logged_in_user; + my $userso = GADS::Users->new(schema => schema); + my $auth = GADS::Authentication->new(schema => schema); + my $id = route_parameters->get('id'); + my $audit = GADS::Audit->new(schema => schema, user => $user); + + if (!$id) { + error __x"Authentication proovider not available"; + } + + my $editProvider = rset('Authentication')->providers->search({id => $id})->next + or error __x"Authentication provider id {id} not found", id => $id; + + # FIXME: Is this true in the case of a provider + # The submit button will still be triggered on a REPLACE_THIS creation, + # if the user has pressed enter, in which case ignore it + if (param('submit')) + { + my %values = ( + name => param('name'), + type => param('type'), + saml2_firstname => param('saml2_firstname'), + saml2_surname => param('saml2_surname'), + xml => param('xml'), + cacert => param('cacert'), + # updating sp_cert or sp_key independantly will cause issues + (defined param('sp_cert') and defined param('sp_key')) ? ( + sp_cert => param('sp_cert'), + sp_key => param('sp_key'), + ) : (), + saml2_relaystate => param('saml2_relaystate'), + saml2_groupname => param('saml2_groupname'), + saml2_nameid => param('saml2_nameid'), + enabled => param('enabled'), + ); + # FIXME: Remove permissions below + $values{permissions} = [body_parameters->get_all('permission')] + if logged_in_user->permission->{superadmin}; + # FIXME: Remove above + + if (process sub { + # FIXME: permissions note + # Don't use DBIC update directly, so that permissions etc are updated properly + $editProvider->update_provider(current_user => logged_in_user, %values); + }) + { + return forwardHome( + { success => "Authentication Provider has been updated successfully" }, 'authentication_providers/' ); + } + } + elsif (my $delete_id = param('delete')) + { + return forwardHome( + { danger => "You do not have permission to delete an authentication provider" } ) + if !logged_in_user->permission->{superadmin}; + my $usero = rset('Authentication')->find($delete_id); + return forwardHome( + { danger => "Cannot delete the built in authentication provider" } ) + if $usero->type == 0; + + # FIXME: Should change this so cannot delete enabled provider for current user + return forwardHome( + { danger => "Cannot delete an enabled authentication provider" } ) + if $usero->enabled; + # FIXME: Will panic here if a user is still associated with this provider + # timlegge - fix + if (process( sub { $usero->retire(current_user => logged_in_user) })) + { + #FIXME: fix audit + $audit->login_change("Authentication Provider ID $delete_id deleted"); + return forwardHome( + { success => "Authentication Provider has been updated successfully" }, 'authentication_providers/' ); + } + } + + my @types = ( + { 'label_plain' => 'saml2', value => 'saml2' }, + { 'label_plain' => 'builtin', value => 'builtin'}, + ); + + my @name_ids = ( + { label_plain => 'emailAddress', value => 'emailAddress' }, + { label_plain => 'unspecified', value => 'unspecified' }, + { label_plain => 'X509SubjectName', value => 'X509SubjectName' }, + { label_plain => 'WindowsDomainQualifiedName', value => 'WindowsDomainQualifiedName' }, + { label_plain => 'entity', value => 'entity' }, + { label_plain => 'transient', value => 'transient' }, + { label_plain => 'persistent', value => 'persistent' }, + ); + + # FIXME need to revise what is passed to the template + my $output = template 'authentication/provider_edit' => { + editprovider => $editProvider, + groups => GADS::Groups->new(schema => schema)->all, + values => { + type => \@types, + saml2_nameid => \@name_ids, + }, + permissions => $userso->permissions, + page => 'admin', + }; + $output; +}; + any ['get', 'post'] => '/user/:id' => require_any_role [qw/useradmin superadmin/] => sub { my $user = logged_in_user; my $userso = GADS::Users->new(schema => schema); @@ -1617,6 +1865,7 @@ any ['get', 'post'] => '/user/:id' => require_any_role [qw/useradmin superadmin/ team_id => param('team_id') || undef, account_request => param('account_request'), account_request_notes => param('account_request_notes'), + provider => param('provider') || 1, view_limits => [body_parameters->get_all('view_limits')], groups => [body_parameters->get_all('groups')], ); @@ -1654,6 +1903,7 @@ any ['get', 'post'] => '/user/:id' => require_any_role [qw/useradmin superadmin/ organisation => $userso->organisations, department_id => $userso->departments, team_id => $userso->teams, + provider => $userso->providers, }, permissions => $userso->permissions, page => 'user', diff --git a/lib/GADS/API.pm b/lib/GADS/API.pm index 43a484215..1e3b3ef32 100644 --- a/lib/GADS/API.pm +++ b/lib/GADS/API.pm @@ -556,6 +556,10 @@ post '/api/table_request' => require_login sub { _post_table_request(); }; +post '/api/authentication_providers/?:id?' => require_login sub { + _post_add_authentication_providers(); +}; + # AJAX record browse any ['get', 'post'] => '/api/:sheet/records' => require_login sub { _get_records(); @@ -750,6 +754,7 @@ sub _post_add_user_account freetext1 => $body->{freetext1}, freetext2 => $body->{freetext2}, title => $body->{title}, + provider => $body->{provider} || 1, organisation => $body->{organisation}, department_id => $body->{department_id}, team_id => $body->{team_id}, @@ -770,6 +775,51 @@ sub _post_add_user_account return _success("$msg"); } +sub _post_add_authentication_providers +{ + my $body = _decode_json_body(); + + my $logged_in_user = logged_in_user; + + my $id = route_parameters->get('id'); + my $update_provider; + if ($id) + { + $update_provider = schema->resultset('Authentication')->find($id) + or error __x"Authentication id {id} not found", id => $id; + } + + error __"Unauthorised access" + unless $logged_in_user->permission->{superadmin} || $logged_in_user->permission->{useradmin}; + + my %values = ( + name => $body->{name}, + type => $body->{type}, + saml2_firstname => $body->{saml2_firstname}, + saml2_surname => $body->{saml2_surname}, + xml => $body->{xml}, + cacert => $body->{cacert}, + sp_cert => $body->{sp_cert}, + sp_key => $body->{sp_key}, + saml2_relaystate => $body->{saml2_relaystate}, + saml2_groupname => $body->{saml2_groupname}, + saml2_unique_id => $body->{saml2_unique_id}, + saml2_nameid => $body->{saml2_nameid}, + enabled => $body->{enabled}, + ); + + # FIXME remove permissions? + $values{permissions} = $body->{permissions} + if $logged_in_user->permission->{superadmin}; + + # Any exceptions/errors generated here will be automatically sent back as JSON error + $id ? $update_provider->update_provider(%values, current_user => $logged_in_user) + : schema->resultset('Authentication')->create_provider(%values, current_user => $logged_in_user, request_base => request->base); + + my $msg = __x"Authentication Provider {type} successfully", type => $id ? 'updated' : 'created'; + return _success("$msg"); +} + sub _create_table { my $params = shift; @@ -1346,6 +1396,95 @@ sub _error error __x $msg; } +any ['get', 'post'] => '/api/providers' => require_any_role [qw/useradmin superadmin/] => sub { + + # Allow parameters to be passed by URL query or in the body. Flatten into + # one parameters object + my $params = Hash::MultiValue->new(query_parameters->flatten, body_parameters->flatten); + + my $site = var 'site'; + if ($params->get('cols')) + { + # Get columns to be shown in the users table summary + my @cols = qw/site_id type name xml saml2_firstname saml2_surname cacert sp_cert sp_key enabled error_messages/; + my @return = map { { name => $_, data => $_ } } @cols; + content_type 'application/json; charset=UTF-8'; + return encode_json \@return; + } + + my $start = $params->get('start') || 0; + my $length = $params->get('length') || 10; + + my $auth = GADS::Authentication->new(schema => schema)->authentication_summary_rs; + + my $total = $auth->count; + my $col_order = $params->get('order[0][column]'); + my $sort_by = defined $col_order && $params->get("columns[${col_order}][name]"); + my $dir = $params->get('order[0][dir]'); + my $search = $params->get('search[value]'); + + # FIXME possibly need to revise this + if (my $sort_field = $site->user_field_by_description($sort_by)) + { + $sort_by = $sort_field->{name} eq 'site_id' + ? 'me.site_id' + : $sort_field->{name} eq 'type' + ? 'me.type' + : $sort_field->{name} eq 'name' + ? 'me.name' + : $sort_field->{name} eq 'enabled' + ? 'me.enabled' + : $sort_field->{name} eq 'error_messages' + ? 'me.error_messages' + : 'me.id'; + } + elsif ($sort_by && $sort_by eq 'ID') + { + $sort_by = 'me.id'; + } + else { + $sort_by = 'me.name'; + } + + my @sr; + foreach my $s (split /\s+/, $search) + { + $s or next; + $s =~ s/\_/\\\_/g; # Escape special like char + push @sr, [ + 'me.id' => $s =~ /^[0-9]+$/ ? $s : undef, + # FIXME should some of these be case sensitive in database + 'me.site_id' => { -like => "%$s%" }, + 'me.type' => { -like => "%$s%" }, + 'me.name' => { -like => "%$s%" }, + 'me.saml2_firstname' => { -like => "%$s%" }, + 'me.saml2_surname' => { -like => "%$s%" }, + 'me.enabled' => { -like => "%$s%" }, + ]; + } + + $auth = $auth->search({ + -and => \@sr, + },{ + order_by => { $dir && $dir eq 'asc' ? -asc : -desc => $sort_by }, + }); + my $filtered_count = $auth->count; + my $auth_render = $auth->search({},{ + offset => $start, + rows => $length, + }); + + my $return = { + draw => $params->get('draw'), + recordsTotal => $total, + recordsFiltered => $filtered_count, + data => [map $_->for_data_table(site => $site), $auth_render->all], + }; + + content_type 'application/json; charset=UTF-8'; + return encode_json $return; +}; + any ['get', 'post'] => '/api/users' => require_any_role [qw/useradmin superadmin/] => sub { # Allow parameters to be passed by URL query or in the body. Flatten into # one parameters object diff --git a/lib/GADS/Audit.pm b/lib/GADS/Audit.pm index f2da65450..c14c4646a 100644 --- a/lib/GADS/Audit.pm +++ b/lib/GADS/Audit.pm @@ -70,8 +70,22 @@ has filtering => ( builder => sub { +{} }, ); -sub audit_types{ [qw/user_action login_change login_success logout login_failure/] }; +sub audit_types{ [qw/user_action login_change login_success logout login_failure auth_provider_change/] }; +sub auth_provider_change +{ my ($self, %options) = @_; + + my $layout = $options{layout}; + $self->schema->resultset('Audit')->create({ + user_id => $self->user_id, + description => $options{description}, + type => 'auth_provider_change', + method => $options{method}, + url => $options{url}, + datetime => DateTime->now, + instance_id => $layout && $layout->instance_id, + }); +} sub user_action { my ($self, %options) = @_; diff --git a/lib/GADS/Authentication.pm b/lib/GADS/Authentication.pm new file mode 100644 index 000000000..43a576547 --- /dev/null +++ b/lib/GADS/Authentication.pm @@ -0,0 +1,64 @@ +=pod +GADS - Globally Accessible Data Store +Copyright (C) 2024 Ctrl O Ltd + +This program is free software: you can redistribute it and/or modify +it under the terms of the GNU Affero General Public License as +published by the Free Software Foundation, either version 3 of the +License, or (at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU Affero General Public License for more details. + +You should have received a copy of the GNU Affero General Public License +along with this program. If not, see . +=cut + +package GADS::Authentication; + +use GADS::Email; +use GADS::Util; +use Log::Report 'linkspace'; +use POSIX (); +use Scope::Guard qw(guard); + +use Moo; +use MooX::Types::MooseLike::Base qw(:all); + +has schema => ( + is => 'ro', + required => 1, +); + +has all => ( + is => 'lazy', + isa => ArrayRef, +); + +sub authentication_rs +{ my $self = shift; + $self->schema->resultset('Authentication')->providers; +} + +sub authentication_summary_rs +{ my $self = shift; + my $summary = $self->authentication_rs->search_rs({},{ + columns => [ + 'me.id', 'me.site_id', 'me.type', 'me.name', 'me.enabled', 'me.error_messages', + #FIXME remove 'me.xml', 'me.sp_key', + ], + order_by => 'name', + collapse => 1, + }); + return $summary; +} + +sub _build_all +{ my $self = shift; + my @authentication = $self->authentication_summary_rs->all; + \@authentication; +} + +1; diff --git a/lib/GADS/DBIC.pm b/lib/GADS/DBIC.pm index 06589b5ec..99292beb6 100644 --- a/lib/GADS/DBIC.pm +++ b/lib/GADS/DBIC.pm @@ -32,6 +32,7 @@ sub insert my $return = $self->next::method(@_); $self->after_create if $self->can('after_create'); + $self->_after_create_or_update(@_); $guard->commit; $return; } @@ -45,8 +46,12 @@ sub delete sub update { my $self = shift; + $self->_validate(@_); + my $guard = $self->result_source->schema->txn_scope_guard; + $self->_before_update(@_); $self->next::method(@_); + $guard->commit; } sub _validate @@ -68,5 +73,16 @@ sub _before_create if $self->can('before_create'); }; +sub _before_update +{ my $self = shift; + $self->before_update + if $self->can('before_update'); +}; + +sub _after_create_or_update +{ my $self = shift; + $self->after_create_or_update + if $self->can('after_create_or_update'); +}; 1; diff --git a/lib/GADS/SAML.pm b/lib/GADS/SAML.pm index cff8efb39..50ff07c4c 100644 --- a/lib/GADS/SAML.pm +++ b/lib/GADS/SAML.pm @@ -4,17 +4,22 @@ use Log::Report 'linkspace'; use Moo; +use Net::SAML2 0.67; use Net::SAML2::Binding::POST; use Net::SAML2::Binding::Redirect; use Net::SAML2::IdP; +use Net::SAML2::SP; use Net::SAML2::Protocol::Assertion; use Net::SAML2::Protocol::AuthnRequest; +use URN::OASIS::SAML2 qw(:bindings :urn :nameid); + use MIME::Base64; use IO::Compress::RawDeflate qw/rawdeflate/; use URI; use URI::QueryParam; use URL::Encode qw/url_encode/; +use File::Temp qw/ tempfile /; has request_id => ( is => 'rw', @@ -38,6 +43,30 @@ has sso_xml => ( is => 'lazy', ); +has sp_key => ( + is => 'lazy', +); + +sub _build_sp_key +{ my $self = shift; + my $key_fh = File::Temp->new; + print $key_fh $self->authentication->sp_key; + $key_fh->close; + $key_fh; +} + +has sp_cert => ( + is => 'lazy', +); + +sub _build_sp_cert +{ my $self = shift; + my $cert_fh = File::Temp->new; + print $cert_fh $self->authentication->sp_cert; + $cert_fh->close; + $cert_fh; +} + sub _build_sso_xml { my $self = shift; $self->base_url.'saml/xml'; @@ -46,22 +75,67 @@ sub _build_sso_xml sub callback { my ($self, %params) = @_; - my $post = Net::SAML2::Binding::POST->new; + my $cacert_fh; + my $relaystate = $params{relaystate} if defined $params{relaystate}; + + # Save CA cert locally if configured + if (my $cacert = $params{cacert}) + { + $cacert_fh = File::Temp->new; + print $cacert_fh $cacert; + $cacert_fh->close + } + + my $post = Net::SAML2::Binding::POST->new( + $cacert_fh ? (cacert => $cacert_fh->filename) : (), + ); + my $saml_response = $params{saml_response}; - if (my $return = $post->handle_response($saml_response)) + my $return; + eval { + $return = $post->handle_response($saml_response); + }; + if ($@) { + my $msg = "Error validating SAML response"; + $msg = "Could not verify CA Certificate" if ($@ =~ "Could not verify CA certificate"); + warn $@; + GADS::forwardHome({ danger => __x($msg)}, 'saml_login' ); + } + + if ($return) { + my $key_fh; + if (defined $params{sp_key}) { + $key_fh = File::Temp->new; + print $key_fh $params{sp_key}; + $key_fh->close; + } + my $assertion = Net::SAML2::Protocol::Assertion->new_from_xml( - xml => decode_base64($saml_response) + xml => decode_base64($saml_response), + $key_fh ? (key_file => $key_fh->filename) : (), + $cacert_fh ? (cacert => $cacert_fh->filename) : (), ); - error __x"Invalid SSO assertion received. Expected request ID {request_id}", - request_id => $self->request_id - if !$assertion->valid($self->sso_xml, $self->request_id); + + if (!$assertion->valid($self->authentication->sso_xml, $self->request_id)) { + my $auth = $self->authentication; + + my $msg = $auth->saml_assertion_invalid_error; + GADS::forwardHome( + { danger => __x($msg, + saml_request_id => $self->request_id, + status => $assertion->response_status, + substatus => $assertion->response_substatus, + ) }, 'saml_login' ); + } return { nameid => $assertion->nameid, attributes => $assertion->attributes, } } + unlink $cacert_fh->filename; + }; has redirect => ( @@ -75,28 +149,173 @@ has authentication => ( sub initiate { my ($self, %params) = @_; + my $cacert_fh; + if (my $cacert = $self->authentication->cacert) + { + $cacert_fh = File::Temp->new; + print $cacert_fh $cacert; + $cacert_fh->close; + } + + error __"Missing Provider Metadata. Please upload to Authentication Settings" + if !$self->authentication->xml; + my $idp = Net::SAML2::IdP->new_from_xml( xml => $self->authentication->xml, + $cacert_fh ? (cacert => $cacert_fh->filename) : (), ); - my $sso_url = $idp->sso_url('urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect'); + unlink $cacert_fh->filename; + + my $sso_url; + my $binding; + foreach ('redirect', 'post') { + $binding = $_; + $sso_url = $idp->sso_url($idp->binding($_)); + # FIXME: we should probably allow the admin to choose + # which to use but right now we are defaulting to redirect + # which should be fine. + last if defined $sso_url; + } + + my %name_ids = ( + emailAddress => NAMEID_EMAIL, + unspecified => NAMEID_UNSPECIFIED, + X509SubjectName => NAMEID_X509_SUBJECT_NAME, + WindowsDomainQualifiedName => NAMEID_WINDOWS_DOMAIN_QUALIFIED_NAME, + entity => NAMEID_FORMAT_ENTITY, + transient => NAMEID_TRANSIENT, + persistent => NAMEID_PERSISTENT, + ); + # saml2_nameid can be undefined, blank or a value. Undefined will result in + # the previous behaviour of requesting the email address. Blank will not + # send the format request ($nameid will be undefined) + my $nameid = defined $self->authentication->saml2_nameid + ? $name_ids{$self->authentication->saml2_nameid} : NAMEID_EMAIL; my $authnreq = Net::SAML2::Protocol::AuthnRequest->new( - issuer => $self->sso_xml, - destination => $sso_url, + issuer => $self->authentication->sso_xml, + destination => $idp->sso_url($idp->binding($binding)), + $nameid ? (nameidpolicy_format => $nameid) : (), # don't send nameidpolicy_format if $nameid is undefined + assertion_url => $self->authentication->sso_url, ); $self->request_id($authnreq->id); my $x = $authnreq->as_xml; - my $redirect = Net::SAML2::Binding::Redirect->new( - url => $sso_url, - param => 'SAMLRequest', - insecure => 1, + my $key_fh; + if (defined $self->authentication->sp_key and $self->authentication->sp_key ne ''){ + my $sp_key = $self->authentication->sp_key; + $key_fh = File::Temp->new; + print $key_fh $sp_key; + $key_fh->close; + } + + my $cert_fh; + if ($binding eq 'post' and defined $self->authentication->sp_cert and $self->authentication->sp_cert ne ''){ + my $sp_cert = $self->authentication->sp_cert; + $cert_fh = File::Temp->new; + print $cert_fh $sp_cert; + $cert_fh->close; + } + + # FIXME: Requires a key in the database + # This is setup to allow a POST request but needs a template + # with the POST parameters as a automatic post + # FIXME: overide the post and hope for the best as we need to + # implement the auto post template referenced at the end of this + # function for POST support Change 2nd Redirect to POST if supported + + my $saml2_binding = 'Net::SAML2::Binding::' . ($binding eq 'redirect' ? 'Redirect' : 'Redirect'); + my $method = $saml2_binding->new( + $key_fh ? (key => $key_fh->filename) : (), + url => $idp->sso_url($idp->binding($binding)), + param => 'SAMLRequest', + $key_fh ? (insecure => 0) : (insecure => 1), + sig_hash => 'sha256', # Hard coded - may want allow as an option + $binding eq 'post' ? (cert => $cert_fh->filename,) : (), ); - my $url = $redirect->get_redirect_uri($x); - $self->redirect("$url"); + # FIXME rempve next line if we support POST in the future after the + # template is done below + $binding = 'redirect' if $binding eq 'post'; + if ($binding eq 'redirect') { + my $url = $method->get_redirect_uri($x); + $self->redirect("$url"); + } else { + # FIXME At this point we would need to send the user a page + # that would automatically post the SAMLRequest as $signed_xml + # and the RelayState if in use. + my $signed_xml = $method->sign_xml($x); + } }; +sub metadata +{ my $self = shift; + my $sign = shift; + + my $sp = $self->_sp; + + $sp->{sign_metadata} = $sign; + # Appears to be a Net::SAML2 bug. I would likely wrap this in a version check + my $version = $Net::SAML2::VERSION; + my $metadata; + if ($version gt "0.69" ) { + $metadata = $sp->metadata; + } else { + $metadata = $sign ? '' : '' . "\n"; + $metadata .= $sp->metadata; + } + + return $metadata->stringify(); +} + +sub _sp +{ my $self = shift; + my $host = $self->{base_url}->host; + my $url = "$self->{base_url}"; + $url =~ s/\/$//; + + my $key_fh = $self->sp_key; + my $cert_fh = $self->sp_cert; + + my $sp = Net::SAML2::SP->new( + id => $self->authentication->sso_xml, + url => $url, + $cert_fh ? (cert => $cert_fh->filename) : (), + encryption_key => $cert_fh->filename, + $key_fh ? (key => $key_fh->filename) : (), + #cacert => "XXX", + single_logout_service => [ + { + Binding => BINDING_HTTP_REDIRECT, + Location => $self->authentication->sso_url, + isDefault => 'true', + index => 1, + }, + { + Binding => BINDING_HTTP_POST, + Location => $self->authentication->sso_url, + isDefault => 'false', + index => 2, + }], + assertion_consumer_service => [ + { + Binding => BINDING_HTTP_POST, + Location => $self->authentication->sso_url, + isDefault => 'true', + # optionally + index => 1, + }], + error_url => "$url/support", + + org_name => $host, + org_display_name => $host, + org_contact => "admin\@$host", + authnreq_signed => 1, + ); + + $sp; +} + 1; diff --git a/lib/GADS/Schema.pm b/lib/GADS/Schema.pm index 063383913..94af6ddbc 100644 --- a/lib/GADS/Schema.pm +++ b/lib/GADS/Schema.pm @@ -8,7 +8,7 @@ use base 'DBIx::Class::Schema'; __PACKAGE__->load_namespaces; -our $VERSION = 111; +our $VERSION = 112; our $IGNORE_PERMISSIONS; our $IGNORE_PERMISSIONS_SEARCH; diff --git a/lib/GADS/Schema/Result/Authentication.pm b/lib/GADS/Schema/Result/Authentication.pm index eb16aa871..a10adf0b1 100644 --- a/lib/GADS/Schema/Result/Authentication.pm +++ b/lib/GADS/Schema/Result/Authentication.pm @@ -8,8 +8,12 @@ use base 'DBIx::Class::Core'; use JSON qw(decode_json); use Log::Report 'linkspace'; +use File::Slurper qw/read_text/; +use IPC::Run qw/run/; -__PACKAGE__->load_components("InflateColumn::DateTime"); +__PACKAGE__->load_components("+GADS::DBIC"); + +#__PACKAGE__->load_components("InflateColumn::DateTime"); __PACKAGE__->table("authentication"); @@ -19,23 +23,47 @@ __PACKAGE__->add_columns( "site_id", { data_type => "integer", is_foreign_key => 1, is_nullable => 1 }, "type", - { data_type => "varchar", is_nullable => 1, size => 32 }, + { data_type => "varchar", is_nullable => 0 }, "name", { data_type => "text", is_nullable => 1 }, "xml", { data_type => "text", is_nullable => 1 }, + "cacert", + { data_type => "text", is_nullable => 1 }, + "sp_cert", + { data_type => "text", is_nullable => 1 }, + "sp_key", + { data_type => "text", is_nullable => 1 }, "saml2_firstname", { data_type => "text", is_nullable => 1 }, "saml2_surname", { data_type => "text", is_nullable => 1 }, + "saml2_groupname", + { data_type => "text", is_nullable => 1 }, + "saml2_relaystate", + { data_type => "varchar", is_nullable => 1, size => 80 }, "enabled", { data_type => "smallint", default_value => 0, is_nullable => 0 }, + "saml2_unique_id", + { data_type => "varchar", is_nullable => 1, size => 80 }, + "saml2_nameid", + { data_type => "varchar", is_nullable => 1, size => 30 }, "error_messages", { data_type => "text", is_nullable => 1 }, ); __PACKAGE__->set_primary_key("id"); +__PACKAGE__->add_unique_constraint("authentication_ux_saml2_relaystate", ["saml2_relaystate"]); +__PACKAGE__->add_unique_constraint("authentication_ux_saml2_unique_id", ["saml2_unique_id"]); + +__PACKAGE__->has_many( + "users", + "GADS::Schema::Result::User", + { "foreign.provider" => "self.id" }, + { cascade_copy => 0, cascade_delete => 0 }, +); + __PACKAGE__->belongs_to( "site", "GADS::Schema::Result::Site", @@ -48,6 +76,106 @@ __PACKAGE__->belongs_to( }, ); +sub sso_unique_url +{ my $self = shift; + my $host = $self->site->host; + my $id = $self->saml2_unique_id; + "https://$host/$id/saml"; +} + +sub sso_url +{ my $self = shift; + my $id = $self->saml2_unique_id; + return $self->sso_unique_url; # if $self->saml2_use_unique_id; + #return $self->sso_standard_url; +} + +sub sso_unique_xml +{ my $self = shift; + my $host = $self->site->host; + my $id = $self->saml2_unique_id; + "https://$host/$id/saml/xml"; +} + +sub sso_xml +{ my $self = shift; + my $id = $self->saml2_unique_id; + return $self->sso_unique_xml; # if $self->saml2_use_unique_id; + #return $self->sso_standard_xml; +} + +sub get_saml2_relaystate +{ my $self = shift; + return $self->saml2_relaystate + if defined $self->saml2_relaystate; + my $code = Session::Token->new(length => 32)->get; + { + local $SL::Schema::NO_USERID = 1; + while ($self->result_source->resultset->search({ saml2_relaystate => $code })->next) + { + $code = Session::Token->new(length => 32)->get; + } + } + + return $code; + #$self->update({ + # saml2_relaystate => $code, + #}); +} + +sub get_saml2_unique_id +{ my $self = shift; + return $self->saml2_unique_id + if $self->saml2_unique_id; + my $code = Session::Token->new(length => 32)->get; + { + local $SL::Schema::NO_USERID = 1; + while ($self->result_source->resultset->search({ saml2_unique_id => $code })->next) + { + $code = Session::Token->new(length => 32)->get; + } + } + + $self->update({ + saml2_unique_id => $code, + }); +} + +sub for_data_table +{ my ($self, %params) = @_; + my $site = $params{site}; + my $return = { + _id => $self->id, + ID => { + type => 'id', + name => 'ID', + values => [$self->id] + }, + "Site ID" => { + type => 'string', + name => 'Site ID', + values => [$self->site_id], + }, + Type => { + type => 'string', + name => 'Type', + values => [$self->type ? "SAML2" : "Built In"], + }, + Name => { + type => 'string', + name => 'Name', + values => [$self->name], + }, + enabled => { + type => 'string', + name => 'enabled', + values => [$self->enabled ? "Enabled" : "Disabled"], + }, + }; + + $return; +} + sub error_messages_decoded { my $self = shift; my $json = $self->error_messages @@ -61,4 +189,123 @@ sub user_not_found_error || "Username {username} not found"; } +sub saml_provider_match_error +{ my $self = shift; + $self->error_messages_decoded->{saml_provider_match} + || "SAML provider does not match the authentication provider for {username}"; +} + +sub saml_assertion_invalid_error +{ my $self = shift; + $self->error_messages_decoded->{saml_assertion_invalid} + || "SAML assertion is invalid for:\nRequest: {saml_request_id}\nStatus: {status}\nSubstatus: {substatus}"; +} + +sub update_provider +{ my ($self, %params) = @_; + + my $guard = $self->result_source->schema->txn_scope_guard; + + # FIXME: Is this comment required + # This was originally a delete call, does this now create an issue as + # it's required for the internal "update" call within `create user` + my $current_user = $params{current_user}; + + my $site = $self->result_source->schema->resultset('Site')->next; + + # FIXME: may need this for provider + # Set null values where required for database insertions + #delete $params{title} if !$params{title} && !$site->user_field_is_editable('title'); + + my $values; + + + my $original_name = $self->name; + + foreach my $field ($site->provider_fields) + { + next if !exists $params{$field->{name}}; + my $fname = $field->{name}; + $self->$fname($params{$fname}); + } + + my $audit = GADS::Audit->new(schema => $self->result_source->schema, user => $current_user); + + $audit->auth_provider_change("Provider $original_name (id ".$self->id.") being changed to ".$self->name) + if $original_name && $self->is_column_changed('name'); + + error __"You do not have permission to update an authentication provider" + if !$current_user->permission->{superadmin}; + + $self->update($values); + + my $required = 0; + + length $params{name} <= 128 + or error __"Name must be less than 128 characters"; + length $params{saml2_surname} <= 128 + or error __"Surname attribute must be less than 128 characters" + if defined $params{saml2_surname}; + length $params{saml2_firstname} <= 128 + or error __"Firstname attribute must be less than 128 characters" + if defined $params{saml2_firstname}; + length $params{saml2_groupname} <= 128 + or error __"Groupname attribute must be less than 128 characters" + if defined $params{saml2_groupname}; + !defined $params{organisation} || $params{organisation} =~ /^[0-9]+$/ + or error __x"Invalid organisation {id}", id => $params{organisation}; + + my $msg = __x"Authentication Provider updated: ID {id}, name: {name}", + id => $self->id, name => $params{name}; + + $audit->auth_provider_change(description => $msg); + + $guard->commit; +} + +sub retire +{ my ($self, %options) = @_; + + my $schema = $self->result_source->schema; + my $current_user = $options{current_user}; + + error __"You do not have permission to delete an authentication provider" + if !$current_user->permission->{superadmin}; + + my $audit = GADS::Audit->new(schema => $self->result_source->schema, user => $current_user); + + my $msg = __x"Authentication Provider: ID {id}, name: {name} was deleted", + id => $self->id, name => $self->name; + $audit->auth_provider_change(description => $msg); + + $self->delete(); +} + +sub after_create +{ my $self = shift; + + # Create service provider key and cert if this is SAML2 + return unless $self->type == 1; + + my $schema = $self->result_source->schema; + my ($stdout, $stderr); + my $key_file = File::Temp->new; + my $cert_file = File::Temp->new; + my $cn = $self->site->host; + + my @command = ('/usr/bin/openssl', 'req', '-x509', '-newkey', 'rsa:4096', '-sha256', '-days', '720', '-nodes', + '-keyout', $key_file->filename, '-out', $cert_file->filename, '-subj', "/CN=$cn", '-addext', + "subjectAltName=DNS:$cn" + ); + + my $rcode = run [ @command ], '>', \$stdout, '2>', \$stderr; + + $self->update({ + saml2_relaystate => $self->get_saml2_relaystate(), + sp_key => read_text($key_file->filename), + sp_cert => read_text($cert_file->filename), + } + ); +} + 1; diff --git a/lib/GADS/Schema/Result/Site.pm b/lib/GADS/Schema/Result/Site.pm index 1656c016e..c39fdd82c 100644 --- a/lib/GADS/Schema/Result/Site.pm +++ b/lib/GADS/Schema/Result/Site.pm @@ -87,6 +87,8 @@ __PACKAGE__->add_columns( { data_type => "smallint", default_value => 0, is_nullable => 0 }, "register_show_title", { data_type => "smallint", default_value => 1, is_nullable => 0 }, + "register_show_provider", + { data_type => "smallint", default_value => 0, is_nullable => 0 }, "hide_account_request", { data_type => "smallint", default_value => 0, is_nullable => 0 }, "remember_user_location", @@ -181,6 +183,13 @@ __PACKAGE__->has_many( { cascade_copy => 0, cascade_delete => 0 }, ); +__PACKAGE__->has_many( + "providers", + "GADS::Schema::Result::Authentication", + { "foreign.site_id" => "self.id" }, + { cascade_copy => 0, cascade_delete => 0 }, +); + sub has_main_homepage { my $self = shift; return 1 if $self->homepage_text && $self->homepage_text !~ /^\s*$/; @@ -263,6 +272,105 @@ sub user_field_by_description $field; } +sub provider_fields +{ my $self = shift; + + my @fields = ( + { + name => 'name', + description => 'Provider Name', + type => 'freetext', + placeholder => 'Provider Name', + is_required => 1, + }, + { + name => 'type', + description => 'Type', + type => 'radio', + is_required => 1, + }, + { + name => 'enabled', + description => 'Enabled', + type => 'radio', + placeholder => '', + }, + { + name => 'sso_xml', + description => 'Entity ID', + type => 'freetext', + placeholder => 'Entity ID', + }, + { + name => 'sso_url', + description => 'Reply URL / SSO URL / ACS URL', + type => 'freetext', + placeholder => '', + }, + { + name => 'saml2_firstname', + description => 'User attribute for first name (optional)', + type => 'freetext', + placeholder => 'http://schemas.xmlsoap.org/ws/2005/05/identity/claims/givenname', + }, + { + name => 'saml2_surname', + description => 'User attribute for surname (optional)', + type => 'freetext', + placeholder => 'http://schemas.xmlsoap.org/ws/2005/05/identity/claims/surname', + }, + { + name => 'saml2_groupname', + description => 'Attribute for groupname (optional)', + type => 'freetext', + placeholder => 'http://schemas.xmlsoap.org/claims/Group', + }, + { + name => 'saml2_nameid', + description => 'SAML NameID format', + type => 'dropdown', + is_required => 1, + }, + { + name => 'xml', + description => 'Identity Provider Metadata XML', + type => 'file', + placeholder => '', + }, + { + name => 'cacert', + description => 'Identity provider Signing/Encryption Certificate', + type => 'file', + placeholder => '', + }, + { + name => 'sp_key', + description => 'LinkSpace Encryption/Signing Key', + type => 'file', + placeholder => '', + }, + { + name => 'sp_cert', + description => 'LinkSpace Encryption/Signing Certificate', + type => 'file', + placeholder => '', + }, + { + name => 'saml2_relaystate', + description => 'RelayState', + type => 'freetext', + placeholder => '', + }, + ); + + my $user_editable = decode_json($self->user_editable_fields || '{}'); + + $_->{editable} = $user_editable->{$_->{name}} // 1 # Default to editable + foreach @fields; + + return @fields; +} + sub user_fields { my $self = shift; @@ -310,6 +418,12 @@ sub user_fields table => 'organisation', field => 'name', } if $self->register_show_organisation; + push @fields, { + name => 'provider', + description => 'Authentication Provider', + type => 'dropdown', + placeholder => 'Select provider', + } if $self->register_show_provider; push @fields, { name => 'department_id', description => $self->department_name, diff --git a/lib/GADS/Schema/Result/User.pm b/lib/GADS/Schema/Result/User.pm index 8bc7559d4..07cec80ea 100644 --- a/lib/GADS/Schema/Result/User.pm +++ b/lib/GADS/Schema/Result/User.pm @@ -32,6 +32,187 @@ __PACKAGE__->load_components("InflateColumn::DateTime", "+GADS::DBIC"); __PACKAGE__->table("user"); +=head1 ACCESSORS + +=head2 id + + data_type: 'bigint' + is_auto_increment: 1 + is_nullable: 0 + +=head2 site_id + + data_type: 'integer' + is_foreign_key: 1 + is_nullable: 1 + +=head2 firstname + + data_type: 'varchar' + is_nullable: 1 + size: 128 + +=head2 surname + + data_type: 'varchar' + is_nullable: 1 + size: 128 + +=head2 email + + data_type: 'text' + is_nullable: 1 + +=head2 username + + data_type: 'text' + is_nullable: 1 + +=head2 title + + data_type: 'integer' + is_foreign_key: 1 + is_nullable: 1 + +=head2 organisation + + data_type: 'integer' + is_foreign_key: 1 + is_nullable: 1 + +=head2 department_id + + data_type: 'integer' + is_foreign_key: 1 + is_nullable: 1 + +=head2 team_id + + data_type: 'integer' + is_foreign_key: 1 + is_nullable: 1 + +=head2 freetext1 + + data_type: 'text' + is_nullable: 1 + +=head2 freetext2 + + data_type: 'text' + is_nullable: 1 + +=head2 password + + data_type: 'varchar' + is_nullable: 1 + size: 128 + +=head2 pwchanged + + data_type: 'datetime' + datetime_undef_if_invalid: 1 + is_nullable: 1 + +=head2 resetpw + + data_type: 'varchar' + is_nullable: 1 + size: 32 + +=head2 deleted + + data_type: 'datetime' + datetime_undef_if_invalid: 1 + is_nullable: 1 + +=head2 lastlogin + + data_type: 'datetime' + datetime_undef_if_invalid: 1 + is_nullable: 1 + +=head2 lastfail + + data_type: 'datetime' + datetime_undef_if_invalid: 1 + is_nullable: 1 + +=head2 failcount + + data_type: 'integer' + is_nullable: 1 + +=head2 lastrecord + + data_type: 'bigint' + is_foreign_key: 1 + is_nullable: 1 + +=head2 lastview + + data_type: 'bigint' + is_foreign_key: 1 + is_nullable: 1 + +=head2 session_settings + + data_type: 'text' + is_nullable: 1 + +=head2 value + + data_type: 'text' + is_nullable: 1 + +=head2 account_request + + data_type: 'smallint' + default_value: 0 + is_nullable: 1 + +=head2 account_request_notes + + data_type: 'text' + is_nullable: 1 + +=head2 aup_accepted + + data_type: 'datetime' + datetime_undef_if_invalid: 1 + is_nullable: 1 + +=head2 limit_to_view + + data_type: 'bigint' + is_foreign_key: 1 + is_nullable: 1 + +=head2 stylesheet + + data_type: 'text' + is_nullable: 1 + +=head2 created + + data_type: 'datetime' + datetime_undef_if_invalid: 1 + is_nullable: 1 + +=head2 debug_login + + data_type: 'smallint' + default_value: 0 + is_nullable: 1 + +=head2 provider + + data_type: 'integer' + is_foreign_key: 1 + is_nullable: 1 + +=cut + __PACKAGE__->add_columns( "id", { data_type => "bigint", is_auto_increment => 1, is_nullable => 0 }, @@ -142,6 +323,8 @@ __PACKAGE__->add_columns( {data_type => "datetime", datetime_undef_if_invalid => 1, is_nullable => 1 }, "mfa_failcount", { data_type => "integer", default_value => 0, is_nullable => 0 }, + "provider", + { data_type => "integer", is_foreign_key => 1, is_nullable => 1 }, ); __PACKAGE__->set_primary_key("id"); @@ -313,6 +496,34 @@ __PACKAGE__->belongs_to( }, ); +=head2 provider + +Type: belongs_to + +Related object: L + +=cut + +__PACKAGE__->belongs_to( + "provider", + "GADS::Schema::Result::Authentication", + { "id" => "provider" }, + { + is_deferrable => 1, + join_type => "LEFT", + on_delete => "NO ACTION", + on_update => "NO ACTION", + }, +); + +=head2 user_graphs + +Type: has_many + +Related object: L + +=cut + __PACKAGE__->has_many( "user_graphs", "GADS::Schema::Result::UserGraph", @@ -529,6 +740,7 @@ sub update_user delete $params{department_id} if !$params{department_id} && !$site->user_field_is_editable('department_id'); delete $params{team_id} if !$params{team_id} && !$site->user_field_is_editable('team_id'); delete $params{title} if !$params{title} && !$site->user_field_is_editable('title'); + delete $params{provider} if !$params{provider} && !$site->user_field_is_editable('provider'); my $values = { account_request_notes => $params{account_request_notes}, @@ -585,8 +797,10 @@ sub update_user if ($params{permissions} && ref $params{permissions} eq 'ARRAY') { - error __"You do not have permission to set global user permissions" - if !$current_user->permission->{superadmin}; + # FIXME: SAML should be able to set groups + # error __"You do not have permission to set global user permissions" + # if !$current_user->permission->{superadmin}; + # $self->permissions(@{$params{permissions}}); # Clear and rebuild permissions, in case of form submission failure. We # need to rebuild now, otherwise the transaction may have rolled-back @@ -784,7 +998,12 @@ sub has_draft sub update_attributes { my ($self, $attributes) = @_; - my $authentication = $self->result_source->schema->resultset('Authentication')->saml2_provider; + my $authentication = $self->provider; + my $site = $self->result_source->schema->resultset('Site')->next; + + # Automatically update the firstname and surname if the + # SAML provider has the proper attributes set + # How do we know if this provider is used for this user??? if (my $at = $authentication->saml2_firstname) { $self->update({ firstname => $attributes->{$at}->[0] }); @@ -793,6 +1012,53 @@ sub update_attributes { $self->update({ surname => $attributes->{$at}->[0] }); } + + # Automatically update the groups and permissions for the user from the SAML2 attributes + if (my $at = $authentication->saml2_groupname) + { + #FIXME - Move this to the UI and allow users to map + my %permission_map = ( + 'GADS-SuperAdmin' => 'superadmin', + 'GADS-UserAdmin' => 'useradmin', + 'GADS-Audit' => 'audit', + ); + + my @permissions; + for my $permission (@{$attributes->{$at}}) { + # FIXME: hard coded permission? + push @permissions, $permission_map{$permission} if defined $permission_map{$permission} and $permission =~ /^GADS-/; + } + if (@permissions) + { + # FIXME: SAML should be able to set groups + # error __"You do not have permission to set global user permissions" + # if !$self->permission->{superadmin}; + $self->permissions(@permissions); + # Clear and rebuild permissions, in case of form submission failure. We + # need to rebuild now, otherwise the transaction may have rolled-back + # to the old version by the time it is built in the template + $self->clear_permission; + $self->permission; + } + + my $schema = $self->result_source->schema; + + my @groups; + # Automatically update the groups for the user from the SAML2 attributes + for my $group (@{$attributes->{$at}}) { + next if defined $permission_map{$group}; + #FIXME: There is likely a much better way to do this + my @groups1 = $schema->resultset('Group')->search({name => $group}, {order_by => 'me.name'})->first; + next if ! defined $groups1[0]; + push @groups, $groups1[0]->id if $groups1[0]->name eq $group; + } + if (@groups) + { + $self->groups($self, \@groups); + $self->clear_has_group; + $self->has_group; + } + } my $value = _user_value({firstname => $self->firstname, surname => $self->surname}); $self->update({ value => $value }); } @@ -867,6 +1133,11 @@ sub for_data_table name => $site->register_freetext1_name, values => [$self->freetext1], } if $site->register_freetext1_name; + $return->{Authentication} = { + type => 'string', + name => 'Authentication Provider', + values => [$self->provider && $self->provider->name], + } if $site->register_show_provider; $return; } diff --git a/lib/GADS/Schema/ResultSet/Authentication.pm b/lib/GADS/Schema/ResultSet/Authentication.pm index 2ac99a19b..c358d549c 100644 --- a/lib/GADS/Schema/ResultSet/Authentication.pm +++ b/lib/GADS/Schema/ResultSet/Authentication.pm @@ -3,21 +3,123 @@ package GADS::Schema::ResultSet::Authentication; use strict; use warnings; +use GADS::SAML; +use GADS::Util; +use Session::Token; + use parent 'DBIx::Class::ResultSet'; use Log::Report 'linkspace'; +__PACKAGE__->load_components(qw(Helper::ResultSet::CorrelateRelationship)); + +sub providers +{ my ($self, %search) = @_; + + $self->search({ + %search, + }); +} + sub enabled { shift->search({ 'me.enabled' => 1, + 'me.type' => 0, + }); +} + +sub by_id +{ + my $self = shift; + my $id = shift; + $self->search({ + 'me.id' => $id, + 'me.enabled' => 1, }); } sub saml2_provider { my $self = shift; $self->enabled->search({ - type => 'saml2', + 'me.type' => 1, })->next; } +sub ordered +{ shift->search({ + },{ + order_by => 'me.name', + }); +} + +sub create_provider +{ my ($self, %params) = @_; + + my $guard = $self->result_source->schema->txn_scope_guard; + + # This should already be set by `resultset` sub in GADS::Schema so shouldn't be needed here + my $site = $self->result_source->schema->resultset('Site')->next; # I don't think this will work for Multi? + + error __"A name must be specified for the provider" + if !$params{name}; + + error __x"Provider {name} already exists", name => $params{name} + if $self->providers(name => $params{name})->count; + + my $code = Session::Token->new( length => 32 )->get; + my $request_base = $params{request_base}; + + my $provider = $self->create({ + name => $params{name}, + type => $params{type}, + enabled => defined $params{enabled} ? $params{enabled} : 0, + saml2_firstname => $params{saml2_firstname}, + saml2_surname => $params{saml2_surname}, + xml => $params{xml}, + cacert => $params{cacert}, + sp_cert => $params{sp_cert}, + sp_key => $params{sp_key}, + saml2_unique_id => $params{saml2_unique_id}, + saml2_relaystate => $params{saml2_relaystate}, + saml2_groupname => $params{saml2_groupname}, + saml2_nameid => $params{saml2_nameid}, + }); + + my $audit = GADS::Audit->new(schema => $self->result_source->schema, user => $params{auth_provider_change}); + + $audit->login_change( + __x"Provider created, id: {id}, provider: {provider}", + id => $provider->id, provider => $params{name} + ); + + $guard->commit; + + return $provider; +} + +sub create_default_provider { + my $self = shift; + + my $schema = $self->result_source->schema; + + $schema->storage->ensure_connected; + my $txn = $self->result_source->schema->txn_scope_guard; + $schema->storage->svp_begin ('create_default_provider'); + my $exists = $self->search({ + type => 0, + name => 'builtin', + })->count; + if ($exists) { + $schema->storage->svp_release ('create_default_provider'); + return; + } + my $provider = $self->create({ + type => 0, + name => 'builtin', + enabled => 1, + }); + $schema->storage->svp_release ('create_default_provider'); + $txn->commit; +} + 1; diff --git a/lib/GADS/Schema/ResultSet/User.pm b/lib/GADS/Schema/ResultSet/User.pm index 0bfaffb70..1f2abca5f 100644 --- a/lib/GADS/Schema/ResultSet/User.pm +++ b/lib/GADS/Schema/ResultSet/User.pm @@ -119,6 +119,7 @@ sub create_user resetpw => $code, created => DateTime->now, account_request_notes => $params{notes}, + provider => $params{provider}, }); my $audit = GADS::Audit->new(schema => $self->result_source->schema, user => $params{current_user}); @@ -128,6 +129,11 @@ sub create_user id => $user->id, username => $params{username} ); + # FIXME - If you ever add after_create in GADS::Schema::Result::User + # this will break the functionality. The above create will create the record + # after_create will fire and properly update the database. + # then update_user will pass the original parameter which will undo any + # changes the after_insert did for values in %params $user->update_user(%params); # Delete account request user if this is a new account request @@ -205,6 +211,7 @@ sub upload my %organisations = map { lc $_->name => $_->id } $schema->resultset('Organisation')->ordered->all; my %departments = map { lc $_->name => $_->id } $schema->resultset('Department')->ordered->all; my %teams = map { lc $_->name => $_->id } $schema->resultset('Team')->ordered->all; + my %providers = map { lc $_->name => $_->id } $schema->resultset('Authentication')->ordered->all; $count = 0; my @errors; my @welcome_emails; @@ -250,6 +257,16 @@ sub upload error => qq(Title "$name" not found), } if !$title_id; } + my $provider_id; + if (defined $user_mapping{provider}) + { + my $name = $row->[$user_mapping{provider}]; + $provider_id = $providers{lc $name}; + push @errors, { + row => join (',', @$row), + error => qq(Authentication provider "$name" not found), + } if !$provider_id; + } my %values = ( firstname => defined $user_mapping{forename} ? $row->[$user_mapping{forename}] : '', surname => defined $user_mapping{surname} ? $row->[$user_mapping{surname}] : '', @@ -263,6 +280,7 @@ sub upload view_limits => $options{view_limits}, groups => $options{groups}, permissions => $options{permissions}, + provider => $provider_id, ); $values{value} = _user_value(\%values); diff --git a/lib/GADS/Users.pm b/lib/GADS/Users.pm index 72c0d88ed..9d67f7274 100644 --- a/lib/GADS/Users.pm +++ b/lib/GADS/Users.pm @@ -82,6 +82,11 @@ has register_requests => ( isa => ArrayRef, ); +has providers => ( + is => 'lazy', + isa => ArrayRef, +); + sub user_rs { my $self = shift; $self->schema->resultset('User')->active; @@ -174,6 +179,12 @@ sub _build_register_requests \@users; } +sub _build_providers +{ my $self = shift; + my @providers = $self->schema->resultset('Authentication')->ordered->all; + [map {+{label_plain => $_->name, value => $_->id}} @providers]; +} + sub title_new { my ($self, $params) = @_; $self->schema->resultset('Title')->create({ name => $params->{name} }); @@ -194,6 +205,11 @@ sub team_new $self->schema->resultset('Team')->create({ name => $params->{name} }); } +sub provider_new +{ my ($self, $params) = @_; + $self->schema->resultset('Authentication')->create({ name => $params->{name} }); +} + sub register { my ($self, $params) = @_; @@ -223,6 +239,7 @@ sub register $new{organisation} or delete $new{organisation}; $new{department_id} or delete $new{department_id}; $new{team_id} or delete $new{team_id}; + $new{provider} or delete $new{provider}; my $user; try { $user = $self->schema->resultset('User')->create(\%new) }; @@ -242,6 +259,7 @@ sub register $text .= "surname: $new{surname}, "; $text .= "email: $new{email}, "; $text .= "title: ".$user->title->name.", " if $user && $user->title; + $text .= "provider: ".$user->provider->name.", " if $user && $user->provider; $text .= $site->register_freetext1_name.": $new{freetext1}, " if $new{freetext1}; $text .= $site->register_freetext2_name.": $new{freetext2}, " if $new{freetext2}; $text .= $site->register_organisation_name.": ".$user->organisation->name.", " if $user && $user->organisation; @@ -319,6 +337,7 @@ sub _produce_csv push @columns, $site->team_name if $site->register_show_team; push @columns, $site->register_freetext1_name if $site->register_freetext1_name; push @columns, $site->register_freetext2_name if $site->register_freetext2_name; + push @columns, 'Authentication Provider' if $site->register_show_provider; push @columns, 'Notes', 'Permissions', 'Groups'; push @columns, 'Page hits last month'; push @columns, 'Last hit to table "'.$_->name.'"' foreach @{$instances->all}; @@ -387,6 +406,10 @@ sub _produce_csv max => 'account_request_notes', -as => 'account_request_notes_max', }, + { + max => 'provider.name', + -as => 'provider_max', + }, ); my @select_columns2 = ( @@ -425,7 +448,7 @@ sub _produce_csv },{ select => [@common_columns, @select_columns], join => [ - 'organisation', 'department', 'team', 'title', + 'organisation', 'department', 'team', 'title', 'authentication', ], order_by => ['surname_max', 'id_max'], group_by => 'me.id', @@ -475,6 +498,7 @@ sub _produce_csv push @csv, $user->get_column('team_max') if $site->register_show_team; push @csv, $user->get_column('freetext1_max') if $site->register_freetext1_name; push @csv, $user->get_column('freetext2_max') if $site->register_freetext2_name; + push @csv, $user->get_column('provider_max') if $site->register_show_provider; push @csv, $user->get_column('account_request_notes_max'); push @csv, join '; ', map { $_->permission->description } @{$user_permissions{$id}}; push @csv, join '; ', map { $_->group->name } @{$user_groups{$id}}; diff --git a/share/fixtures/112/conf/all_tables.json b/share/fixtures/112/conf/all_tables.json new file mode 100644 index 000000000..d5d4923df --- /dev/null +++ b/share/fixtures/112/conf/all_tables.json @@ -0,0 +1,285 @@ +{ + "might_have" : { + "fetch" : 0 + }, + "sets" : [ + { + "quantity" : "all", + "class" : "Rag" + }, + { + "quantity" : "all", + "class" : "Filter" + }, + { + "quantity" : "all", + "class" : "Widget" + }, + { + "class" : "Export", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Department" + }, + { + "quantity" : "all", + "class" : "Person" + }, + { + "class" : "Fileval", + "quantity" : "all" + }, + { + "class" : "Instance", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Team" + }, + { + "class" : "MetricGroup", + "quantity" : "all" + }, + { + "class" : "Date", + "quantity" : "all" + }, + { + "class" : "UserLastrecord", + "quantity" : "all" + }, + { + "class" : "Permission", + "quantity" : "all" + }, + { + "class" : "AlertSend", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Ragval" + }, + { + "class" : "File", + "quantity" : "all" + }, + { + "class" : "Calc", + "quantity" : "all" + }, + { + "class" : "ReportLayout", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "UserGraph" + }, + { + "class" : "Report", + "quantity" : "all" + }, + { + "class" : "Oauthclient", + "quantity" : "all" + }, + { + "class" : "Current", + "quantity" : "all" + }, + { + "class" : "LayoutDepend", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Import" + }, + { + "class" : "Submission", + "quantity" : "all" + }, + { + "class" : "Calcval", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Changed" + }, + { + "class" : "CurvalField", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Authentication" + }, + { + "class" : "Layout", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Curval" + }, + { + "class" : "FileOption", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "FilteredValue" + }, + { + "quantity" : "all", + "class" : "Intgr" + }, + { + "class" : "String", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "View" + }, + { + "class" : "DisplayField", + "quantity" : "all" + }, + { + "class" : "Enum", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "ReportGroup" + }, + { + "class" : "Audit", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "UserGroup" + }, + { + "class" : "Site", + "quantity" : "all" + }, + { + "class" : "Group", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "ViewLayout" + }, + { + "class" : "Dashboard", + "quantity" : "all" + }, + { + "class" : "GraphColor", + "quantity" : "all" + }, + { + "class" : "Enumval", + "quantity" : "all" + }, + { + "class" : "Alert", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "LayoutGroup" + }, + { + "quantity" : "all", + "class" : "InstanceGroup" + }, + { + "quantity" : "all", + "class" : "Title" + }, + { + "quantity" : "all", + "class" : "CalcUnique" + }, + { + "quantity" : "all", + "class" : "Organisation" + }, + { + "class" : "User", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "InstanceRag" + }, + { + "quantity" : "all", + "class" : "Topic" + }, + { + "class" : "ViewGroup", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Daterange" + }, + { + "class" : "ViewLimit", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "ImportRow" + }, + { + "class" : "AlertColumn", + "quantity" : "all" + }, + { + "class" : "Record", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "UserPermission" + }, + { + "class" : "Sort", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Graph" + }, + { + "quantity" : "all", + "class" : "Metric" + }, + { + "quantity" : "all", + "class" : "AlertCache" + }, + { + "quantity" : "all", + "class" : "Oauthtoken" + } + ], + "belongs_to" : { + "fetch" : 0 + }, + "has_many" : { + "fetch" : 0 + } +} diff --git a/share/fixtures/112/conf/current.json b/share/fixtures/112/conf/current.json new file mode 100644 index 000000000..9fb298aae --- /dev/null +++ b/share/fixtures/112/conf/current.json @@ -0,0 +1,73 @@ +{ + "has_many" : { + "fetch" : 0 + }, + "might_have" : { + "fetch" : 0 + }, + "belongs_to" : { + "fetch" : 0 + }, + "sets" : [ + { + "class" : "Current", + "fetch" : [ + { + "rel": "records", + "quantity": "all", + "fetch": [ + { + "rel": "calcvals", + "quantity": "all" + }, + { + "rel": "curvals", + "quantity": "all" + }, + { + "rel": "dateranges", + "quantity": "all" + }, + { + "rel": "dates", + "quantity": "all" + }, + { + "rel": "enums", + "quantity": "all" + }, + { + "rel": "files", + "quantity": "all", + "fetch": [ + { + "rel": "value", + "quantity": "all" + } + ] + }, + { + "rel": "intgrs", + "quantity": "all" + }, + { + "rel": "people", + "quantity": "all" + }, + { + "rel": "ragvals", + "quantity": "all" + }, + { + "rel": "strings", + "quantity": "all" + } + ] + } + ], + "ids" : [ + "1766" + ] + } + ] +} diff --git a/share/fixtures/112/conf/graphs.json b/share/fixtures/112/conf/graphs.json new file mode 100644 index 000000000..6e742f676 --- /dev/null +++ b/share/fixtures/112/conf/graphs.json @@ -0,0 +1,17 @@ +{ + "has_many" : { + "fetch" : 0 + }, + "might_have" : { + "fetch" : 0 + }, + "belongs_to" : { + "fetch" : 0 + }, + "sets" : [ + { + "class" : "Graph", + "quantity" : "all" + } + ] +} diff --git a/share/fixtures/112/conf/layout.json b/share/fixtures/112/conf/layout.json new file mode 100644 index 000000000..557c20279 --- /dev/null +++ b/share/fixtures/112/conf/layout.json @@ -0,0 +1,53 @@ +{ + "has_many" : { + "fetch" : 0 + }, + "might_have" : { + "fetch" : 0 + }, + "belongs_to" : { + "fetch" : 0 + }, + "sets" : [ + { + "class" : "Calc", + "quantity" : "all" + }, + { + "class" : "Enumval", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "CurvalField" + }, + { + "class" : "Instance", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "LayoutGroup" + }, + { + "class" : "Layout", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "FileOption" + }, + { + "quantity" : "all", + "class" : "LayoutDepend" + }, + { + "class" : "Rag", + "quantity" : "all" + }, + { + "quantity" : "all", + "class" : "Group" + } + ] +} diff --git a/share/fixtures/112/conf/permissions.json b/share/fixtures/112/conf/permissions.json new file mode 100644 index 000000000..c55636c86 --- /dev/null +++ b/share/fixtures/112/conf/permissions.json @@ -0,0 +1,17 @@ +{ + "might_have" : { + "fetch" : 0 + }, + "belongs_to" : { + "fetch" : 0 + }, + "has_many" : { + "fetch" : 0 + }, + "sets" : [ + { + "class" : "Permission", + "quantity" : "all" + } + ] +} diff --git a/share/fixtures/112/conf/views_global.json b/share/fixtures/112/conf/views_global.json new file mode 100644 index 000000000..7a675dce7 --- /dev/null +++ b/share/fixtures/112/conf/views_global.json @@ -0,0 +1,28 @@ +{ + "has_many" : { + "fetch" : 0 + }, + "might_have" : { + "fetch" : 0 + }, + "belongs_to" : { + "fetch" : 0 + }, + "sets" : [ + { + "class" : "View", + "quantity" : "all", + "cond": { "global": 1 }, + "fetch": [ + { + "rel": "view_layouts", + "quantity": "all" + }, + { + "rel": "sorts", + "quantity": "all" + } + ] + } + ] +} diff --git a/share/fixtures/112/permissions/_config_set b/share/fixtures/112/permissions/_config_set new file mode 100644 index 000000000..b737787ab --- /dev/null +++ b/share/fixtures/112/permissions/_config_set @@ -0,0 +1,17 @@ +$VAR1 = { + 'has_many' => { + 'fetch' => 0 + }, + 'might_have' => { + 'fetch' => 0 + }, + 'sets' => [ + { + 'class' => 'Permission', + 'quantity' => 'all' + } + ], + 'belongs_to' => { + 'fetch' => 0 + } + }; diff --git a/share/fixtures/112/permissions/_dumper_version b/share/fixtures/112/permissions/_dumper_version new file mode 100644 index 000000000..55eb15ebd --- /dev/null +++ b/share/fixtures/112/permissions/_dumper_version @@ -0,0 +1 @@ +1.001039 \ No newline at end of file diff --git a/share/fixtures/112/permissions/permission/10.fix b/share/fixtures/112/permissions/permission/10.fix new file mode 100644 index 000000000..dbcc7ff19 --- /dev/null +++ b/share/fixtures/112/permissions/permission/10.fix @@ -0,0 +1,7 @@ +$HASH1 = { + description + => 'User can access audit data', + id => 10, + name => 'audit', + order => 11 + }; diff --git a/share/fixtures/112/permissions/permission/12.fix b/share/fixtures/112/permissions/permission/12.fix new file mode 100644 index 000000000..902d83660 --- /dev/null +++ b/share/fixtures/112/permissions/permission/12.fix @@ -0,0 +1,7 @@ +$HASH1 = { + description + => 'Super-administrator', + id => 12, + name => 'superadmin', + order => undef + }; diff --git a/share/fixtures/112/permissions/permission/3.fix b/share/fixtures/112/permissions/permission/3.fix new file mode 100644 index 000000000..50be3fde3 --- /dev/null +++ b/share/fixtures/112/permissions/permission/3.fix @@ -0,0 +1,7 @@ +$HASH1 = { + description + => 'User can manage other user accounts', + id => 3, + name => 'useradmin', + order => 3 + }; diff --git a/share/migrations/MySQL/deploy/112/001-auto-__VERSION.sql b/share/migrations/MySQL/deploy/112/001-auto-__VERSION.sql new file mode 100644 index 000000000..3db19c81c --- /dev/null +++ b/share/migrations/MySQL/deploy/112/001-auto-__VERSION.sql @@ -0,0 +1,18 @@ +-- +-- Created by SQL::Translator::Producer::MySQL +-- Created on Tue Sep 1 12:20:24 2026 +-- +; +SET foreign_key_checks=0; +-- +-- Table: `dbix_class_deploymenthandler_versions` +-- +CREATE TABLE `dbix_class_deploymenthandler_versions` ( + `id` integer NOT NULL auto_increment, + `version` varchar(50) NOT NULL, + `ddl` text NULL, + `upgrade_sql` text NULL, + PRIMARY KEY (`id`), + UNIQUE `dbix_class_deploymenthandler_versions_version` (`version`) +); +SET foreign_key_checks=1; diff --git a/share/migrations/MySQL/deploy/112/001-auto.sql b/share/migrations/MySQL/deploy/112/001-auto.sql new file mode 100644 index 000000000..a92040886 --- /dev/null +++ b/share/migrations/MySQL/deploy/112/001-auto.sql @@ -0,0 +1,1305 @@ +-- +-- Created by SQL::Translator::Producer::MySQL +-- Created on Tue Sep 1 12:20:24 2026 +-- +; +SET foreign_key_checks=0; +-- +-- Table: `alert` +-- +CREATE TABLE `alert` ( + `id` integer NOT NULL auto_increment, + `view_id` bigint NOT NULL, + `user_id` bigint NOT NULL, + `frequency` integer NOT NULL DEFAULT 0, + INDEX `alert_idx_user_id` (`user_id`), + INDEX `alert_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + CONSTRAINT `alert_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `alert_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `alert_cache` +-- +CREATE TABLE `alert_cache` ( + `id` bigint NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `view_id` bigint NOT NULL, + `current_id` bigint NOT NULL, + `user_id` bigint NULL, + INDEX `alert_cache_idx_current_id` (`current_id`), + INDEX `alert_cache_idx_layout_id` (`layout_id`), + INDEX `alert_cache_idx_user_id` (`user_id`), + INDEX `alert_cache_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + CONSTRAINT `alert_cache_fk_current_id` FOREIGN KEY (`current_id`) REFERENCES `current` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `alert_cache_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `alert_cache_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `alert_cache_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `alert_column` +-- +CREATE TABLE `alert_column` ( + `id` integer NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `instance_id` integer NOT NULL, + INDEX `alert_column_idx_instance_id` (`instance_id`), + INDEX `alert_column_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + CONSTRAINT `alert_column_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `alert_column_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `alert_send` +-- +CREATE TABLE `alert_send` ( + `id` bigint NOT NULL auto_increment, + `layout_id` integer NULL, + `alert_id` integer NOT NULL, + `current_id` bigint NOT NULL, + `status` char(7) NULL, + INDEX `alert_send_idx_alert_id` (`alert_id`), + INDEX `alert_send_idx_current_id` (`current_id`), + INDEX `alert_send_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + UNIQUE `alert_send_all` (`layout_id`, `alert_id`, `current_id`, `status`), + CONSTRAINT `alert_send_fk_alert_id` FOREIGN KEY (`alert_id`) REFERENCES `alert` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `alert_send_fk_current_id` FOREIGN KEY (`current_id`) REFERENCES `current` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `alert_send_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `audit` +-- +CREATE TABLE `audit` ( + `id` bigint NOT NULL auto_increment, + `site_id` integer NULL, + `user_id` bigint NULL, + `type` varchar(45) NULL, + `datetime` datetime NULL, + `method` varchar(45) NULL, + `url` text NULL, + `description` text NULL, + `instance_id` integer NULL, + INDEX `audit_idx_instance_id` (`instance_id`), + INDEX `audit_idx_site_id` (`site_id`), + INDEX `audit_idx_user_id` (`user_id`), + INDEX `audit_idx_datetime` (`datetime`), + INDEX `audit_idx_user_instance_datetime` (`user_id`, `instance_id`, `datetime`), + PRIMARY KEY (`id`), + CONSTRAINT `audit_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `audit_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `audit_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `authentication` +-- +CREATE TABLE `authentication` ( + `id` bigint NOT NULL auto_increment, + `site_id` integer NULL, + `type` varchar(255) NOT NULL, + `name` text NULL, + `xml` text NULL, + `cacert` text NULL, + `sp_cert` text NULL, + `sp_key` text NULL, + `saml2_firstname` text NULL, + `saml2_surname` text NULL, + `saml2_groupname` text NULL, + `saml2_relaystate` varchar(80) NULL, + `enabled` smallint NOT NULL DEFAULT 0, + `saml2_unique_id` varchar(80) NULL, + `saml2_nameid` varchar(30) NULL, + `error_messages` text NULL, + INDEX `authentication_idx_site_id` (`site_id`), + PRIMARY KEY (`id`), + UNIQUE `authentication_ux_saml2_relaystate` (`saml2_relaystate`), + UNIQUE `authentication_ux_saml2_unique_id` (`saml2_unique_id`), + CONSTRAINT `authentication_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `calc` +-- +CREATE TABLE `calc` ( + `id` integer NOT NULL auto_increment, + `layout_id` integer NULL, + `calc` mediumtext NULL, + `code` mediumtext NULL, + `return_format` varchar(45) NULL, + `decimal_places` smallint NULL, + INDEX `calc_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + CONSTRAINT `calc_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `calc_unique` +-- +CREATE TABLE `calc_unique` ( + `id` bigint NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `value_text` text NULL, + `value_int` bigint NULL, + `value_date` date NULL, + `value_numeric` decimal(20, 5) NULL, + `value_date_from` datetime NULL, + `value_date_to` datetime NULL, + INDEX `calc_unique_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + UNIQUE `calc_unique_ux_layout_date` (`layout_id`, `value_date`), + UNIQUE `calc_unique_ux_layout_daterange` (`layout_id`, `value_date_from`, `value_date_to`), + UNIQUE `calc_unique_ux_layout_int` (`layout_id`, `value_int`), + UNIQUE `calc_unique_ux_layout_numeric` (`layout_id`, `value_numeric`), + UNIQUE `calc_unique_ux_layout_text` (`layout_id`, `value_text`), + CONSTRAINT `calc_unique_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `calcval` +-- +CREATE TABLE `calcval` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + `value_text` text NULL, + `value_int` bigint NULL, + `value_date` date NULL, + `value_numeric` decimal(20, 5) NULL, + `value_date_from` datetime NULL, + `value_date_to` datetime NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `calcval_idx_layout_id` (`layout_id`), + INDEX `calcval_idx_purged_by` (`purged_by`), + INDEX `calcval_idx_record_id` (`record_id`), + INDEX `calcval_idx_value_text` (`value_text`(64)), + INDEX `calcval_idx_value_numeric` (`value_numeric`), + INDEX `calcval_idx_value_int` (`value_int`), + INDEX `calcval_idx_value_date` (`value_date`), + PRIMARY KEY (`id`), + CONSTRAINT `calcval_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `calcval_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `calcval_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `current` +-- +CREATE TABLE `current` ( + `id` bigint NOT NULL auto_increment, + `serial` bigint NULL, + `current_version_id` bigint NULL, + `parent_id` bigint NULL, + `instance_id` integer NULL, + `linked_id` bigint NULL, + `deleted` datetime NULL, + `deletedby` bigint NULL, + `draftuser_id` bigint NULL, + INDEX `current_idx_current_version_id` (`current_version_id`), + INDEX `current_idx_deletedby` (`deletedby`), + INDEX `current_idx_draftuser_id` (`draftuser_id`), + INDEX `current_idx_instance_id` (`instance_id`), + INDEX `current_idx_linked_id` (`linked_id`), + INDEX `current_idx_parent_id` (`parent_id`), + PRIMARY KEY (`id`), + UNIQUE `current_ux_instance_serial` (`instance_id`, `serial`), + CONSTRAINT `current_fk_current_version_id` FOREIGN KEY (`current_version_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `current_fk_deletedby` FOREIGN KEY (`deletedby`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `current_fk_draftuser_id` FOREIGN KEY (`draftuser_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `current_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `current_fk_linked_id` FOREIGN KEY (`linked_id`) REFERENCES `current` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `current_fk_parent_id` FOREIGN KEY (`parent_id`) REFERENCES `current` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `curval` +-- +CREATE TABLE `curval` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NULL, + `layout_id` integer NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` bigint NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `curval_idx_layout_id` (`layout_id`), + INDEX `curval_idx_purged_by` (`purged_by`), + INDEX `curval_idx_record_id` (`record_id`), + INDEX `curval_idx_value` (`value`), + PRIMARY KEY (`id`), + CONSTRAINT `curval_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `curval_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `curval_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `curval_fk_value` FOREIGN KEY (`value`) REFERENCES `current` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `curval_fields` +-- +CREATE TABLE `curval_fields` ( + `id` integer NOT NULL auto_increment, + `parent_id` integer NOT NULL, + `child_id` integer NOT NULL, + INDEX `curval_fields_idx_child_id` (`child_id`), + INDEX `curval_fields_idx_parent_id` (`parent_id`), + PRIMARY KEY (`id`), + CONSTRAINT `curval_fields_fk_child_id` FOREIGN KEY (`child_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `curval_fields_fk_parent_id` FOREIGN KEY (`parent_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `dashboard` +-- +CREATE TABLE `dashboard` ( + `id` integer NOT NULL auto_increment, + `site_id` integer NULL, + `instance_id` integer NULL, + `user_id` integer NULL, + INDEX `dashboard_idx_instance_id` (`instance_id`), + INDEX `dashboard_idx_site_id` (`site_id`), + INDEX `dashboard_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `dashboard_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `dashboard_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `dashboard_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `date` +-- +CREATE TABLE `date` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` date NULL, + `purged_by` bigint NULL, + `purged_on` timestamp NULL, + INDEX `date_idx_layout_id` (`layout_id`), + INDEX `date_idx_purged_by` (`purged_by`), + INDEX `date_idx_record_id` (`record_id`), + INDEX `date_idx_value` (`value`), + PRIMARY KEY (`id`), + CONSTRAINT `date_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `date_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `date_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `daterange` +-- +CREATE TABLE `daterange` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + `from` date NULL, + `to` date NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` varchar(45) NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `daterange_idx_layout_id` (`layout_id`), + INDEX `daterange_idx_purged_by` (`purged_by`), + INDEX `daterange_idx_record_id` (`record_id`), + INDEX `daterange_idx_from` (`from`), + INDEX `daterange_idx_to` (`to`), + INDEX `daterange_idx_value` (`value`), + PRIMARY KEY (`id`), + CONSTRAINT `daterange_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `daterange_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `daterange_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `department` +-- +CREATE TABLE `department` ( + `id` integer NOT NULL auto_increment, + `name` varchar(128) NULL, + `site_id` integer NULL, + `deleted` smallint NOT NULL DEFAULT 0, + INDEX `department_idx_site_id` (`site_id`), + PRIMARY KEY (`id`), + CONSTRAINT `department_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `display_field` +-- +CREATE TABLE `display_field` ( + `id` integer NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `display_field_id` integer NOT NULL, + `regex` text NULL, + `operator` varchar(16) NULL, + INDEX `display_field_idx_display_field_id` (`display_field_id`), + INDEX `display_field_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + CONSTRAINT `display_field_fk_display_field_id` FOREIGN KEY (`display_field_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `display_field_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `enum` +-- +CREATE TABLE `enum` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NULL, + `layout_id` integer NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` integer NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `enum_idx_layout_id` (`layout_id`), + INDEX `enum_idx_purged_by` (`purged_by`), + INDEX `enum_idx_record_id` (`record_id`), + INDEX `enum_idx_value` (`value`), + PRIMARY KEY (`id`), + CONSTRAINT `enum_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `enum_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `enum_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `enum_fk_value` FOREIGN KEY (`value`) REFERENCES `enumval` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `enumval` +-- +CREATE TABLE `enumval` ( + `id` integer NOT NULL auto_increment, + `value` text NULL, + `layout_id` integer NULL, + `deleted` smallint NOT NULL DEFAULT 0, + `parent` integer NULL, + `position` integer NULL, + INDEX `enumval_idx_layout_id` (`layout_id`), + INDEX `enumval_idx_parent` (`parent`), + INDEX `enumval_idx_value` (`value`(64)), + PRIMARY KEY (`id`), + CONSTRAINT `enumval_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `enumval_fk_parent` FOREIGN KEY (`parent`) REFERENCES `enumval` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `export` +-- +CREATE TABLE `export` ( + `id` integer NOT NULL auto_increment, + `site_id` integer NULL, + `user_id` bigint NOT NULL, + `type` varchar(45) NULL, + `started` datetime NULL, + `completed` datetime NULL, + `result` text NULL, + `result_internal` text NULL, + `mimetype` text NULL, + `content` longblob NULL, + INDEX `export_idx_site_id` (`site_id`), + INDEX `export_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `export_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `export_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `file` +-- +CREATE TABLE `file` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NULL, + `layout_id` integer NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` bigint NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `file_idx_layout_id` (`layout_id`), + INDEX `file_idx_purged_by` (`purged_by`), + INDEX `file_idx_record_id` (`record_id`), + INDEX `file_idx_value` (`value`), + PRIMARY KEY (`id`), + CONSTRAINT `file_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `file_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `file_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `file_fk_value` FOREIGN KEY (`value`) REFERENCES `fileval` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `file_option` +-- +CREATE TABLE `file_option` ( + `id` integer NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `filesize` integer NULL, + INDEX `file_option_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + CONSTRAINT `file_option_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `fileval` +-- +CREATE TABLE `fileval` ( + `id` bigint NOT NULL auto_increment, + `name` text NULL, + `mimetype` text NULL, + `is_independent` smallint NOT NULL DEFAULT 0, + `edit_user_id` bigint NULL, + INDEX `fileval_idx_edit_user_id` (`edit_user_id`), + INDEX `fileval_idx_name` (`name`(64)), + PRIMARY KEY (`id`), + CONSTRAINT `fileval_fk_edit_user_id` FOREIGN KEY (`edit_user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `filter` +-- +CREATE TABLE `filter` ( + `id` bigint NOT NULL auto_increment, + `view_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + INDEX `filter_idx_layout_id` (`layout_id`), + INDEX `filter_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + CONSTRAINT `filter_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `filter_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `filtered_value` +-- +CREATE TABLE `filtered_value` ( + `id` integer NOT NULL auto_increment, + `submission_id` integer NULL, + `layout_id` integer NULL, + `current_id` integer NULL, + INDEX `filtered_value_idx_current_id` (`current_id`), + INDEX `filtered_value_idx_layout_id` (`layout_id`), + INDEX `filtered_value_idx_submission_id` (`submission_id`), + PRIMARY KEY (`id`), + UNIQUE `ux_submission_layout_current` (`submission_id`, `layout_id`, `current_id`), + CONSTRAINT `filtered_value_fk_current_id` FOREIGN KEY (`current_id`) REFERENCES `current` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `filtered_value_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `filtered_value_fk_submission_id` FOREIGN KEY (`submission_id`) REFERENCES `submission` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `graph` +-- +CREATE TABLE `graph` ( + `id` integer NOT NULL auto_increment, + `title` text NULL, + `description` text NULL, + `y_axis` integer NULL, + `y_axis_link` integer NULL, + `y_axis_stack` varchar(45) NULL, + `y_axis_label` text NULL, + `x_axis` integer NULL, + `x_axis_link` integer NULL, + `x_axis_grouping` varchar(45) NULL, + `group_by` integer NULL, + `stackseries` smallint NOT NULL DEFAULT 0, + `as_percent` smallint NOT NULL DEFAULT 0, + `type` varchar(45) NULL, + `metric_group` integer NULL, + `instance_id` integer NULL, + `is_shared` smallint NOT NULL DEFAULT 0, + `user_id` bigint NULL, + `group_id` integer NULL, + `trend` varchar(45) NULL, + `from` date NULL, + `to` date NULL, + `x_axis_range` varchar(45) NULL, + INDEX `graph_idx_group_id` (`group_id`), + INDEX `graph_idx_group_by` (`group_by`), + INDEX `graph_idx_instance_id` (`instance_id`), + INDEX `graph_idx_metric_group` (`metric_group`), + INDEX `graph_idx_user_id` (`user_id`), + INDEX `graph_idx_x_axis` (`x_axis`), + INDEX `graph_idx_x_axis_link` (`x_axis_link`), + INDEX `graph_idx_y_axis` (`y_axis`), + INDEX `graph_idx_y_axis_link` (`y_axis_link`), + PRIMARY KEY (`id`), + CONSTRAINT `graph_fk_group_id` FOREIGN KEY (`group_id`) REFERENCES `group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_group_by` FOREIGN KEY (`group_by`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_metric_group` FOREIGN KEY (`metric_group`) REFERENCES `metric_group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_x_axis` FOREIGN KEY (`x_axis`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_x_axis_link` FOREIGN KEY (`x_axis_link`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_y_axis` FOREIGN KEY (`y_axis`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `graph_fk_y_axis_link` FOREIGN KEY (`y_axis_link`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `graph_color` +-- +CREATE TABLE `graph_color` ( + `id` bigint NOT NULL auto_increment, + `name` varchar(128) NULL, + `color` char(6) NULL, + PRIMARY KEY (`id`), + UNIQUE `ux_graph_color_name` (`name`) +); +-- +-- Table: `group` +-- +CREATE TABLE `group` ( + `id` integer NOT NULL auto_increment, + `name` varchar(128) NULL, + `default_read` smallint NOT NULL DEFAULT 0, + `default_write_new` smallint NOT NULL DEFAULT 0, + `default_write_existing` smallint NOT NULL DEFAULT 0, + `default_approve_new` smallint NOT NULL DEFAULT 0, + `default_approve_existing` smallint NOT NULL DEFAULT 0, + `default_write_new_no_approval` smallint NOT NULL DEFAULT 0, + `default_write_existing_no_approval` smallint NOT NULL DEFAULT 0, + `site_id` integer NULL, + INDEX `group_idx_site_id` (`site_id`), + PRIMARY KEY (`id`), + CONSTRAINT `group_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `import` +-- +CREATE TABLE `import` ( + `id` integer NOT NULL auto_increment, + `site_id` integer NULL, + `instance_id` integer NULL, + `user_id` bigint NOT NULL, + `type` varchar(45) NULL, + `row_count` integer NOT NULL DEFAULT 0, + `started` datetime NULL, + `completed` datetime NULL, + `written_count` integer NOT NULL DEFAULT 0, + `error_count` integer NOT NULL DEFAULT 0, + `skipped_count` integer NOT NULL DEFAULT 0, + `result` text NULL, + INDEX `import_idx_instance_id` (`instance_id`), + INDEX `import_idx_site_id` (`site_id`), + INDEX `import_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `import_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `import_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `import_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `import_row` +-- +CREATE TABLE `import_row` ( + `id` bigint NOT NULL auto_increment, + `import_id` integer NOT NULL, + `status` varchar(45) NULL, + `content` text NULL, + `errors` text NULL, + `changes` text NULL, + INDEX `import_row_idx_import_id` (`import_id`), + PRIMARY KEY (`id`), + CONSTRAINT `import_row_fk_import_id` FOREIGN KEY (`import_id`) REFERENCES `import` (`id`) ON DELETE CASCADE ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `instance` +-- +CREATE TABLE `instance` ( + `id` integer NOT NULL auto_increment, + `name` text NULL, + `name_short` varchar(64) NULL, + `site_id` integer NULL, + `sort_layout_id` integer NULL, + `sort_type` varchar(45) NULL, + `view_limit_id` integer NULL, + `default_view_limit_extra_id` integer NULL, + `homepage_text` text NULL, + `homepage_text2` text NULL, + `record_name` text NULL, + `forget_history` smallint NULL DEFAULT 0, + `no_overnight_update` smallint NULL DEFAULT 0, + `api_index_layout_id` integer NULL, + `forward_record_after_create` smallint NULL DEFAULT 0, + `no_hide_blank` smallint NOT NULL DEFAULT 0, + `no_download_pdf` smallint NOT NULL DEFAULT 0, + `no_copy_record` smallint NOT NULL DEFAULT 0, + `hide_in_selector` smallint NOT NULL DEFAULT 0, + `security_marking` text NULL, + INDEX `instance_idx_api_index_layout_id` (`api_index_layout_id`), + INDEX `instance_idx_default_view_limit_extra_id` (`default_view_limit_extra_id`), + INDEX `instance_idx_site_id` (`site_id`), + INDEX `instance_idx_sort_layout_id` (`sort_layout_id`), + INDEX `instance_idx_view_limit_id` (`view_limit_id`), + PRIMARY KEY (`id`), + CONSTRAINT `instance_fk_api_index_layout_id` FOREIGN KEY (`api_index_layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `instance_fk_default_view_limit_extra_id` FOREIGN KEY (`default_view_limit_extra_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `instance_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `instance_fk_sort_layout_id` FOREIGN KEY (`sort_layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `instance_fk_view_limit_id` FOREIGN KEY (`view_limit_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `instance_group` +-- +CREATE TABLE `instance_group` ( + `id` integer NOT NULL auto_increment, + `instance_id` integer NOT NULL, + `group_id` integer NOT NULL, + `permission` varchar(45) NOT NULL, + INDEX `instance_group_idx_group_id` (`group_id`), + INDEX `instance_group_idx_instance_id` (`instance_id`), + PRIMARY KEY (`id`), + UNIQUE `instance_group_ux_instance_group_permission` (`instance_id`, `group_id`, `permission`), + CONSTRAINT `instance_group_fk_group_id` FOREIGN KEY (`group_id`) REFERENCES `group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `instance_group_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `instance_rag` +-- +CREATE TABLE `instance_rag` ( + `id` integer NOT NULL auto_increment, + `instance_id` integer NOT NULL, + `rag` varchar(16) NOT NULL, + `enabled` smallint NOT NULL DEFAULT 0, + `description` text NULL, + INDEX `instance_rag_idx_instance_id` (`instance_id`), + PRIMARY KEY (`id`), + UNIQUE `instance_rag_ux_instance_rag` (`instance_id`, `rag`), + CONSTRAINT `instance_rag_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `intgr` +-- +CREATE TABLE `intgr` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` bigint NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `intgr_idx_layout_id` (`layout_id`), + INDEX `intgr_idx_purged_by` (`purged_by`), + INDEX `intgr_idx_record_id` (`record_id`), + INDEX `intgr_idx_value` (`value`), + PRIMARY KEY (`id`), + CONSTRAINT `intgr_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `intgr_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `intgr_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `layout` +-- +CREATE TABLE `layout` ( + `id` integer NOT NULL auto_increment, + `name` text NULL, + `name_short` varchar(64) NULL, + `type` varchar(45) NULL, + `permission` integer NOT NULL DEFAULT 0, + `optional` smallint NOT NULL DEFAULT 0, + `remember` smallint NOT NULL DEFAULT 0, + `isunique` smallint NOT NULL DEFAULT 0, + `textbox` smallint NOT NULL DEFAULT 0, + `typeahead` smallint NOT NULL DEFAULT 0, + `force_regex` text NULL, + `position` integer NULL, + `ordering` varchar(45) NULL, + `end_node_only` smallint NOT NULL DEFAULT 0, + `multivalue` smallint NOT NULL DEFAULT 0, + `can_child` smallint NOT NULL DEFAULT 0, + `internal` smallint NOT NULL DEFAULT 0, + `description` text NULL, + `helptext` text NULL, + `options` text NULL, + `display_field` integer NULL, + `display_regex` text NULL, + `display_condition` char(3) NULL, + `display_matchtype` text NULL, + `instance_id` integer NULL, + `link_parent` integer NULL, + `related_field` integer NULL, + `width` integer NOT NULL DEFAULT 50, + `filter` text NULL, + `topic_id` integer NULL, + `aggregate` varchar(45) NULL, + `group_display` varchar(45) NULL, + `lookup_endpoint` text NULL, + `lookup_group` smallint NULL, + `notes` text NULL, + INDEX `layout_idx_display_field` (`display_field`), + INDEX `layout_idx_instance_id` (`instance_id`), + INDEX `layout_idx_link_parent` (`link_parent`), + INDEX `layout_idx_related_field` (`related_field`), + INDEX `layout_idx_topic_id` (`topic_id`), + PRIMARY KEY (`id`), + UNIQUE `layout_ux_instance_name_short` (`instance_id`, `name_short`), + CONSTRAINT `layout_fk_display_field` FOREIGN KEY (`display_field`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `layout_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `layout_fk_link_parent` FOREIGN KEY (`link_parent`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `layout_fk_related_field` FOREIGN KEY (`related_field`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `layout_fk_topic_id` FOREIGN KEY (`topic_id`) REFERENCES `topic` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `layout_depend` +-- +CREATE TABLE `layout_depend` ( + `id` integer NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `depends_on` integer NOT NULL, + INDEX `layout_depend_idx_depends_on` (`depends_on`), + INDEX `layout_depend_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + CONSTRAINT `layout_depend_fk_depends_on` FOREIGN KEY (`depends_on`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `layout_depend_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `layout_group` +-- +CREATE TABLE `layout_group` ( + `id` integer NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `group_id` integer NOT NULL, + `permission` varchar(45) NOT NULL, + INDEX `layout_group_idx_group_id` (`group_id`), + INDEX `layout_group_idx_layout_id` (`layout_id`), + INDEX `layout_group_idx_permission` (`permission`), + PRIMARY KEY (`id`), + UNIQUE `layout_group_ux_layout_group_permission` (`layout_id`, `group_id`, `permission`), + CONSTRAINT `layout_group_fk_group_id` FOREIGN KEY (`group_id`) REFERENCES `group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `layout_group_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `metric` +-- +CREATE TABLE `metric` ( + `id` integer NOT NULL auto_increment, + `metric_group` integer NOT NULL, + `x_axis_value` text NULL, + `target` bigint NULL, + `y_axis_grouping_value` text NULL, + INDEX `metric_idx_metric_group` (`metric_group`), + PRIMARY KEY (`id`), + CONSTRAINT `metric_fk_metric_group` FOREIGN KEY (`metric_group`) REFERENCES `metric_group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `metric_group` +-- +CREATE TABLE `metric_group` ( + `id` integer NOT NULL auto_increment, + `name` text NULL, + `instance_id` integer NULL, + INDEX `metric_group_idx_instance_id` (`instance_id`), + PRIMARY KEY (`id`), + CONSTRAINT `metric_group_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `oauthclient` +-- +CREATE TABLE `oauthclient` ( + `id` bigint NOT NULL auto_increment, + `client_id` varchar(64) NOT NULL, + `client_secret` varchar(64) NOT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB; +-- +-- Table: `oauthtoken` +-- +CREATE TABLE `oauthtoken` ( + `token` varchar(128) NOT NULL, + `related_token` varchar(128) NOT NULL, + `oauthclient_id` integer NOT NULL, + `user_id` bigint NOT NULL, + `type` varchar(12) NOT NULL, + `expires` integer NULL, + INDEX `oauthtoken_idx_oauthclient_id` (`oauthclient_id`), + INDEX `oauthtoken_idx_user_id` (`user_id`), + PRIMARY KEY (`token`), + CONSTRAINT `oauthtoken_fk_oauthclient_id` FOREIGN KEY (`oauthclient_id`) REFERENCES `oauthclient` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `oauthtoken_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `organisation` +-- +CREATE TABLE `organisation` ( + `id` integer NOT NULL auto_increment, + `name` varchar(128) NULL, + `site_id` integer NULL, + `deleted` smallint NOT NULL DEFAULT 0, + INDEX `organisation_idx_site_id` (`site_id`), + PRIMARY KEY (`id`), + CONSTRAINT `organisation_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `permission` +-- +CREATE TABLE `permission` ( + `id` integer NOT NULL auto_increment, + `name` varchar(128) NOT NULL, + `description` text NULL, + `order` integer NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB; +-- +-- Table: `person` +-- +CREATE TABLE `person` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NULL, + `layout_id` integer NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` bigint NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `person_idx_layout_id` (`layout_id`), + INDEX `person_idx_purged_by` (`purged_by`), + INDEX `person_idx_record_id` (`record_id`), + INDEX `person_idx_value` (`value`), + PRIMARY KEY (`id`), + CONSTRAINT `person_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `person_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `person_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `person_fk_value` FOREIGN KEY (`value`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `rag` +-- +CREATE TABLE `rag` ( + `id` integer NOT NULL auto_increment, + `layout_id` integer NOT NULL, + `red` text NULL, + `amber` text NULL, + `green` text NULL, + `code` mediumtext NULL, + INDEX `rag_idx_layout_id` (`layout_id`), + PRIMARY KEY (`id`), + CONSTRAINT `rag_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `ragval` +-- +CREATE TABLE `ragval` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + `value` varchar(16) NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `ragval_idx_layout_id` (`layout_id`), + INDEX `ragval_idx_purged_by` (`purged_by`), + INDEX `ragval_idx_record_id` (`record_id`), + INDEX `ragval_idx_value` (`value`), + PRIMARY KEY (`id`), + UNIQUE `ragval_ux_record_layout` (`record_id`, `layout_id`), + CONSTRAINT `ragval_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `ragval_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `ragval_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `record` +-- +CREATE TABLE `record` ( + `id` bigint NOT NULL auto_increment, + `created` datetime NOT NULL, + `current_id` bigint NOT NULL DEFAULT 0, + `createdby` bigint NULL, + `approvedby` bigint NULL, + `record_id` bigint NULL, + `approval` smallint NOT NULL DEFAULT 0, + INDEX `record_idx_approvedby` (`approvedby`), + INDEX `record_idx_createdby` (`createdby`), + INDEX `record_idx_current_id` (`current_id`), + INDEX `record_idx_record_id` (`record_id`), + INDEX `record_idx_approval` (`approval`), + PRIMARY KEY (`id`), + CONSTRAINT `record_fk_approvedby` FOREIGN KEY (`approvedby`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `record_fk_createdby` FOREIGN KEY (`createdby`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `record_fk_current_id` FOREIGN KEY (`current_id`) REFERENCES `current` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `record_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `report` +-- +CREATE TABLE `report` ( + `id` bigint NOT NULL auto_increment, + `name` text NOT NULL, + `title` text NULL, + `description` text NULL, + `user_id` bigint NULL, + `createdby` bigint NULL, + `created` datetime NULL, + `instance_id` bigint NULL, + `deleted` datetime NULL, + `security_marking` text NULL, + INDEX `report_idx_createdby` (`createdby`), + INDEX `report_idx_instance_id` (`instance_id`), + INDEX `report_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `report_fk_createdby` FOREIGN KEY (`createdby`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `report_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `report_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `report_group` +-- +CREATE TABLE `report_group` ( + `id` integer NOT NULL auto_increment, + `report_id` integer NOT NULL, + `group_id` integer NOT NULL, + INDEX `report_group_idx_group_id` (`group_id`), + INDEX `report_group_idx_report_id` (`report_id`), + PRIMARY KEY (`id`), + CONSTRAINT `report_group_fk_group_id` FOREIGN KEY (`group_id`) REFERENCES `group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `report_group_fk_report_id` FOREIGN KEY (`report_id`) REFERENCES `report` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `report_layout` +-- +CREATE TABLE `report_layout` ( + `id` integer NOT NULL auto_increment, + `report_id` integer NOT NULL, + `layout_id` bigint NOT NULL, + `order` integer NULL, + INDEX `report_layout_idx_layout_id` (`layout_id`), + INDEX `report_layout_idx_report_id` (`report_id`), + PRIMARY KEY (`id`), + CONSTRAINT `report_layout_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `report_layout_fk_report_id` FOREIGN KEY (`report_id`) REFERENCES `report` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `site` +-- +CREATE TABLE `site` ( + `id` integer NOT NULL auto_increment, + `host` varchar(128) NULL, + `name` text NULL, + `created` datetime NULL, + `email_welcome_text` text NULL, + `email_welcome_subject` text NULL, + `email_delete_text` text NULL, + `email_delete_subject` text NULL, + `email_reject_text` text NULL, + `email_reject_subject` text NULL, + `register_text` text NULL, + `homepage_text` text NULL, + `homepage_text2` text NULL, + `register_title_help` text NULL, + `register_freetext1_help` text NULL, + `register_freetext2_help` text NULL, + `register_email_help` text NULL, + `register_organisation_help` text NULL, + `register_organisation_name` text NULL, + `register_organisation_mandatory` smallint NOT NULL DEFAULT 0, + `register_department_help` text NULL, + `register_department_name` text NULL, + `register_department_mandatory` smallint NOT NULL DEFAULT 0, + `register_team_help` text NULL, + `register_team_name` text NULL, + `register_team_mandatory` smallint NOT NULL DEFAULT 0, + `register_notes_help` text NULL, + `register_freetext1_name` text NULL, + `register_freetext2_name` text NULL, + `register_show_organisation` smallint NOT NULL DEFAULT 1, + `register_show_department` smallint NOT NULL DEFAULT 0, + `register_show_team` smallint NOT NULL DEFAULT 0, + `register_show_title` smallint NOT NULL DEFAULT 1, + `register_show_provider` smallint NOT NULL DEFAULT 0, + `hide_account_request` smallint NOT NULL DEFAULT 0, + `remember_user_location` smallint NOT NULL DEFAULT 1, + `user_editable_fields` text NULL, + `register_freetext1_placeholder` text NULL, + `register_freetext2_placeholder` text NULL, + `account_request_notes_name` text NULL, + `account_request_notes_placeholder` text NULL, + `security_marking` text NULL, + `site_logo` longblob NULL, + `force_mfa` char(3) NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB; +-- +-- Table: `sort` +-- +CREATE TABLE `sort` ( + `id` integer NOT NULL auto_increment, + `view_id` bigint NOT NULL, + `layout_id` integer NULL, + `parent_id` integer NULL, + `type` varchar(45) NULL, + `order` integer NULL, + INDEX `sort_idx_layout_id` (`layout_id`), + INDEX `sort_idx_parent_id` (`parent_id`), + INDEX `sort_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + CONSTRAINT `sort_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `sort_fk_parent_id` FOREIGN KEY (`parent_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `sort_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `string` +-- +CREATE TABLE `string` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + `child_unique` smallint NOT NULL DEFAULT 0, + `value` text NULL, + `value_index` varchar(128) NULL, + `purged_by` bigint NULL, + `purged_on` datetime NULL, + INDEX `string_idx_layout_id` (`layout_id`), + INDEX `string_idx_purged_by` (`purged_by`), + INDEX `string_idx_record_id` (`record_id`), + INDEX `string_idx_value_index` (`value_index`), + PRIMARY KEY (`id`), + CONSTRAINT `string_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `string_fk_purged_by` FOREIGN KEY (`purged_by`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `string_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `submission` +-- +CREATE TABLE `submission` ( + `id` integer NOT NULL auto_increment, + `token` varchar(64) NOT NULL, + `created` datetime NULL, + `submitted` smallint NOT NULL DEFAULT 0, + PRIMARY KEY (`id`), + UNIQUE `ux_submission_token` (`token`, `submitted`) +) ENGINE=InnoDB; +-- +-- Table: `team` +-- +CREATE TABLE `team` ( + `id` integer NOT NULL auto_increment, + `name` varchar(128) NULL, + `site_id` integer NULL, + `deleted` smallint NOT NULL DEFAULT 0, + INDEX `team_idx_site_id` (`site_id`), + PRIMARY KEY (`id`), + CONSTRAINT `team_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `title` +-- +CREATE TABLE `title` ( + `id` integer NOT NULL auto_increment, + `name` varchar(128) NULL, + `site_id` integer NULL, + `deleted` smallint NOT NULL DEFAULT 0, + INDEX `title_idx_site_id` (`site_id`), + PRIMARY KEY (`id`), + CONSTRAINT `title_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `topic` +-- +CREATE TABLE `topic` ( + `id` integer NOT NULL auto_increment, + `instance_id` integer NULL, + `name` text NULL, + `description` text NULL, + `initial_state` varchar(32) NULL, + `click_to_edit` smallint NOT NULL DEFAULT 0, + `prevent_edit_topic_id` integer NULL, + INDEX `topic_idx_instance_id` (`instance_id`), + INDEX `topic_idx_prevent_edit_topic_id` (`prevent_edit_topic_id`), + PRIMARY KEY (`id`), + CONSTRAINT `topic_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `topic_fk_prevent_edit_topic_id` FOREIGN KEY (`prevent_edit_topic_id`) REFERENCES `topic` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `user` +-- +CREATE TABLE `user` ( + `id` bigint NOT NULL auto_increment, + `site_id` integer NULL, + `firstname` varchar(128) NULL, + `surname` varchar(128) NULL, + `email` text NULL, + `username` text NULL, + `title` integer NULL, + `organisation` integer NULL, + `department_id` integer NULL, + `team_id` integer NULL, + `freetext1` text NULL, + `freetext2` text NULL, + `password` varchar(128) NULL, + `pwchanged` datetime NULL, + `resetpw` varchar(32) NULL, + `deleted` datetime NULL, + `lastlogin` datetime NULL, + `lastfail` datetime NULL, + `failcount` integer NOT NULL DEFAULT 0, + `lastrecord` bigint NULL, + `lastview` bigint NULL, + `session_settings` text NULL, + `value` text NULL, + `account_request` smallint NULL DEFAULT 0, + `account_request_notes` text NULL, + `aup_accepted` datetime NULL, + `limit_to_view` bigint NULL, + `stylesheet` text NULL, + `created` datetime NULL, + `debug_login` smallint NULL DEFAULT 0, + `mfa_type` char(3) NULL, + `mobile` text NULL, + `mobile_verified` smallint NOT NULL DEFAULT 0, + `mfa_secret` text NULL, + `mfa_sms_token` text NULL, + `mfa_sms_created` datetime NULL, + `mfa_token_previous` text NULL, + `mfa_token_previous_type` char(3) NULL, + `mfa_token_previous_used` datetime NULL, + `mfa_token_previous_key` text NULL, + `mfa_lastfail` datetime NULL, + `mfa_failcount` integer NOT NULL DEFAULT 0, + `provider` integer NULL, + INDEX `user_idx_department_id` (`department_id`), + INDEX `user_idx_lastrecord` (`lastrecord`), + INDEX `user_idx_lastview` (`lastview`), + INDEX `user_idx_limit_to_view` (`limit_to_view`), + INDEX `user_idx_organisation` (`organisation`), + INDEX `user_idx_provider` (`provider`), + INDEX `user_idx_site_id` (`site_id`), + INDEX `user_idx_team_id` (`team_id`), + INDEX `user_idx_title` (`title`), + INDEX `user_idx_value` (`value`(64)), + INDEX `user_idx_email` (`email`(64)), + INDEX `user_idx_username` (`username`(64)), + PRIMARY KEY (`id`), + CONSTRAINT `user_fk_department_id` FOREIGN KEY (`department_id`) REFERENCES `department` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_lastrecord` FOREIGN KEY (`lastrecord`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_lastview` FOREIGN KEY (`lastview`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_limit_to_view` FOREIGN KEY (`limit_to_view`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_organisation` FOREIGN KEY (`organisation`) REFERENCES `organisation` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_provider` FOREIGN KEY (`provider`) REFERENCES `authentication` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_site_id` FOREIGN KEY (`site_id`) REFERENCES `site` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_team_id` FOREIGN KEY (`team_id`) REFERENCES `team` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_fk_title` FOREIGN KEY (`title`) REFERENCES `title` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `user_graph` +-- +CREATE TABLE `user_graph` ( + `id` bigint NOT NULL auto_increment, + `user_id` bigint NOT NULL, + `graph_id` integer NOT NULL, + INDEX `user_graph_idx_graph_id` (`graph_id`), + INDEX `user_graph_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `user_graph_fk_graph_id` FOREIGN KEY (`graph_id`) REFERENCES `graph` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_graph_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `user_group` +-- +CREATE TABLE `user_group` ( + `id` bigint NOT NULL auto_increment, + `user_id` bigint NOT NULL, + `group_id` integer NOT NULL, + INDEX `user_group_idx_group_id` (`group_id`), + INDEX `user_group_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `user_group_fk_group_id` FOREIGN KEY (`group_id`) REFERENCES `group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_group_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `user_lastrecord` +-- +CREATE TABLE `user_lastrecord` ( + `id` bigint NOT NULL auto_increment, + `record_id` bigint NOT NULL, + `instance_id` integer NOT NULL, + `user_id` bigint NOT NULL, + INDEX `user_lastrecord_idx_instance_id` (`instance_id`), + INDEX `user_lastrecord_idx_record_id` (`record_id`), + INDEX `user_lastrecord_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `user_lastrecord_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_lastrecord_fk_record_id` FOREIGN KEY (`record_id`) REFERENCES `record` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_lastrecord_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `user_permission` +-- +CREATE TABLE `user_permission` ( + `id` bigint NOT NULL auto_increment, + `user_id` bigint NOT NULL, + `permission_id` integer NOT NULL, + INDEX `user_permission_idx_permission_id` (`permission_id`), + INDEX `user_permission_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `user_permission_fk_permission_id` FOREIGN KEY (`permission_id`) REFERENCES `permission` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `user_permission_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `view` +-- +CREATE TABLE `view` ( + `id` bigint NOT NULL auto_increment, + `user_id` bigint NULL, + `group_id` integer NULL, + `name` varchar(128) NULL, + `global` smallint NOT NULL DEFAULT 0, + `is_admin` smallint NOT NULL DEFAULT 0, + `is_limit_extra` smallint NOT NULL DEFAULT 0, + `filter` text NULL, + `instance_id` integer NULL, + `created` datetime NULL, + `createdby` bigint NULL, + INDEX `view_idx_createdby` (`createdby`), + INDEX `view_idx_group_id` (`group_id`), + INDEX `view_idx_instance_id` (`instance_id`), + INDEX `view_idx_user_id` (`user_id`), + PRIMARY KEY (`id`), + CONSTRAINT `view_fk_createdby` FOREIGN KEY (`createdby`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `view_fk_group_id` FOREIGN KEY (`group_id`) REFERENCES `group` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `view_fk_instance_id` FOREIGN KEY (`instance_id`) REFERENCES `instance` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `view_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `view_group` +-- +CREATE TABLE `view_group` ( + `id` integer NOT NULL auto_increment, + `view_id` bigint NOT NULL, + `layout_id` integer NULL, + `parent_id` integer NULL, + `order` integer NULL, + INDEX `view_group_idx_layout_id` (`layout_id`), + INDEX `view_group_idx_parent_id` (`parent_id`), + INDEX `view_group_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + CONSTRAINT `view_group_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `view_group_fk_parent_id` FOREIGN KEY (`parent_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `view_group_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `view_layout` +-- +CREATE TABLE `view_layout` ( + `id` integer NOT NULL auto_increment, + `view_id` bigint NOT NULL, + `layout_id` integer NOT NULL, + `order` integer NULL, + INDEX `view_layout_idx_layout_id` (`layout_id`), + INDEX `view_layout_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + CONSTRAINT `view_layout_fk_layout_id` FOREIGN KEY (`layout_id`) REFERENCES `layout` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `view_layout_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `view_limit` +-- +CREATE TABLE `view_limit` ( + `id` bigint NOT NULL auto_increment, + `view_id` bigint NOT NULL, + `user_id` bigint NOT NULL, + INDEX `view_limit_idx_user_id` (`user_id`), + INDEX `view_limit_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + CONSTRAINT `view_limit_fk_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `view_limit_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +-- +-- Table: `widget` +-- +CREATE TABLE `widget` ( + `id` integer NOT NULL auto_increment, + `grid_id` varchar(64) NULL, + `dashboard_id` integer NULL, + `type` varchar(16) NULL, + `title` text NULL, + `static` smallint NOT NULL DEFAULT 0, + `h` smallint NULL DEFAULT 0, + `w` smallint NULL DEFAULT 0, + `x` smallint NULL DEFAULT 0, + `y` smallint NULL DEFAULT 0, + `content` text NULL, + `view_id` integer NULL, + `graph_id` integer NULL, + `rows` integer NULL, + `tl_options` text NULL, + `globe_options` text NULL, + INDEX `widget_idx_dashboard_id` (`dashboard_id`), + INDEX `widget_idx_graph_id` (`graph_id`), + INDEX `widget_idx_view_id` (`view_id`), + PRIMARY KEY (`id`), + UNIQUE `widget_ux_dashboard_grid` (`dashboard_id`, `grid_id`), + CONSTRAINT `widget_fk_dashboard_id` FOREIGN KEY (`dashboard_id`) REFERENCES `dashboard` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `widget_fk_graph_id` FOREIGN KEY (`graph_id`) REFERENCES `graph` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, + CONSTRAINT `widget_fk_view_id` FOREIGN KEY (`view_id`) REFERENCES `view` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION +) ENGINE=InnoDB; +SET foreign_key_checks=1; diff --git a/share/migrations/PostgreSQL/deploy/112/001-auto-__VERSION.sql b/share/migrations/PostgreSQL/deploy/112/001-auto-__VERSION.sql new file mode 100644 index 000000000..3970402f9 --- /dev/null +++ b/share/migrations/PostgreSQL/deploy/112/001-auto-__VERSION.sql @@ -0,0 +1,18 @@ +-- +-- Created by SQL::Translator::Producer::PostgreSQL +-- Created on Tue Sep 1 12:20:24 2026 +-- +; +-- +-- Table: dbix_class_deploymenthandler_versions +-- +CREATE TABLE "dbix_class_deploymenthandler_versions" ( + "id" serial NOT NULL, + "version" character varying(50) NOT NULL, + "ddl" text, + "upgrade_sql" text, + PRIMARY KEY ("id"), + CONSTRAINT "dbix_class_deploymenthandler_versions_version" UNIQUE ("version") +); + +; diff --git a/share/migrations/PostgreSQL/deploy/112/001-auto.sql b/share/migrations/PostgreSQL/deploy/112/001-auto.sql new file mode 100644 index 000000000..b9f15d9f5 --- /dev/null +++ b/share/migrations/PostgreSQL/deploy/112/001-auto.sql @@ -0,0 +1,1931 @@ +-- +-- Created by SQL::Translator::Producer::PostgreSQL +-- Created on Tue Sep 1 12:20:24 2026 +-- +; +-- +-- Table: alert +-- +CREATE TABLE "alert" ( + "id" serial NOT NULL, + "view_id" bigint NOT NULL, + "user_id" bigint NOT NULL, + "frequency" integer DEFAULT 0 NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "alert_idx_user_id" on "alert" ("user_id"); +CREATE INDEX "alert_idx_view_id" on "alert" ("view_id"); + +; +-- +-- Table: alert_cache +-- +CREATE TABLE "alert_cache" ( + "id" bigserial NOT NULL, + "layout_id" integer NOT NULL, + "view_id" bigint NOT NULL, + "current_id" bigint NOT NULL, + "user_id" bigint, + PRIMARY KEY ("id") +); +CREATE INDEX "alert_cache_idx_current_id" on "alert_cache" ("current_id"); +CREATE INDEX "alert_cache_idx_layout_id" on "alert_cache" ("layout_id"); +CREATE INDEX "alert_cache_idx_user_id" on "alert_cache" ("user_id"); +CREATE INDEX "alert_cache_idx_view_id" on "alert_cache" ("view_id"); + +; +-- +-- Table: alert_column +-- +CREATE TABLE "alert_column" ( + "id" serial NOT NULL, + "layout_id" integer NOT NULL, + "instance_id" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "alert_column_idx_instance_id" on "alert_column" ("instance_id"); +CREATE INDEX "alert_column_idx_layout_id" on "alert_column" ("layout_id"); + +; +-- +-- Table: alert_send +-- +CREATE TABLE "alert_send" ( + "id" bigserial NOT NULL, + "layout_id" integer, + "alert_id" integer NOT NULL, + "current_id" bigint NOT NULL, + "status" character(7), + PRIMARY KEY ("id"), + CONSTRAINT "alert_send_all" UNIQUE ("layout_id", "alert_id", "current_id", "status") +); +CREATE INDEX "alert_send_idx_alert_id" on "alert_send" ("alert_id"); +CREATE INDEX "alert_send_idx_current_id" on "alert_send" ("current_id"); +CREATE INDEX "alert_send_idx_layout_id" on "alert_send" ("layout_id"); + +; +-- +-- Table: audit +-- +CREATE TABLE "audit" ( + "id" bigserial NOT NULL, + "site_id" integer, + "user_id" bigint, + "type" character varying(45), + "datetime" timestamp, + "method" character varying(45), + "url" text, + "description" text, + "instance_id" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "audit_idx_instance_id" on "audit" ("instance_id"); +CREATE INDEX "audit_idx_site_id" on "audit" ("site_id"); +CREATE INDEX "audit_idx_user_id" on "audit" ("user_id"); +CREATE INDEX "audit_idx_datetime" on "audit" ("datetime"); +CREATE INDEX "audit_idx_user_instance_datetime" on "audit" ("user_id", "instance_id", "datetime"); + +; +-- +-- Table: authentication +-- +CREATE TABLE "authentication" ( + "id" bigserial NOT NULL, + "site_id" integer, + "type" character varying(32), + "name" text, + "xml" text, + "cacert" text, + "sp_cert" text, + "sp_key" text, + "saml2_firstname" text, + "saml2_surname" text, + "saml2_groupname" text, + "saml2_relaystate" character varying(80), + "enabled" smallint DEFAULT 0 NOT NULL, + "saml2_unique_id" character varying(80), + "saml2_nameid" character varying(30), + "error_messages" text, + PRIMARY KEY ("id"), + CONSTRAINT "authentication_ux_saml2_relaystate" UNIQUE ("saml2_relaystate"), + CONSTRAINT "authentication_ux_saml2_unique_id" UNIQUE ("saml2_unique_id") +); +CREATE INDEX "authentication_idx_site_id" on "authentication" ("site_id"); + +; +-- +-- Table: calc +-- +CREATE TABLE "calc" ( + "id" serial NOT NULL, + "layout_id" integer, + "calc" text, + "code" text, + "return_format" character varying(45), + "decimal_places" smallint, + PRIMARY KEY ("id") +); +CREATE INDEX "calc_idx_layout_id" on "calc" ("layout_id"); + +; +-- +-- Table: calc_unique +-- +CREATE TABLE "calc_unique" ( + "id" bigserial NOT NULL, + "layout_id" integer NOT NULL, + "value_text" citext, + "value_int" bigint, + "value_date" date, + "value_numeric" numeric(20,5), + "value_date_from" timestamp, + "value_date_to" timestamp, + PRIMARY KEY ("id"), + CONSTRAINT "calc_unique_ux_layout_date" UNIQUE ("layout_id", "value_date"), + CONSTRAINT "calc_unique_ux_layout_daterange" UNIQUE ("layout_id", "value_date_from", "value_date_to"), + CONSTRAINT "calc_unique_ux_layout_int" UNIQUE ("layout_id", "value_int"), + CONSTRAINT "calc_unique_ux_layout_numeric" UNIQUE ("layout_id", "value_numeric"), + CONSTRAINT "calc_unique_ux_layout_text" UNIQUE ("layout_id", "value_text") +); +CREATE INDEX "calc_unique_idx_layout_id" on "calc_unique" ("layout_id"); + +; +-- +-- Table: calcval +-- +CREATE TABLE "calcval" ( + "id" bigserial NOT NULL, + "record_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + "value_text" citext, + "value_int" bigint, + "value_date" date, + "value_numeric" numeric(20,5), + "value_date_from" timestamp, + "value_date_to" timestamp, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "calcval_idx_layout_id" on "calcval" ("layout_id"); +CREATE INDEX "calcval_idx_purged_by" on "calcval" ("purged_by"); +CREATE INDEX "calcval_idx_record_id" on "calcval" ("record_id"); +CREATE INDEX "calcval_idx_value_text" on "calcval" ("value_text"); +CREATE INDEX "calcval_idx_value_numeric" on "calcval" ("value_numeric"); +CREATE INDEX "calcval_idx_value_int" on "calcval" ("value_int"); +CREATE INDEX "calcval_idx_value_date" on "calcval" ("value_date"); + +; +-- +-- Table: current +-- +CREATE TABLE "current" ( + "id" bigserial NOT NULL, + "serial" bigint, + "current_version_id" bigint, + "parent_id" bigint, + "instance_id" integer, + "linked_id" bigint, + "deleted" timestamp, + "deletedby" bigint, + "draftuser_id" bigint, + PRIMARY KEY ("id"), + CONSTRAINT "current_ux_instance_serial" UNIQUE ("instance_id", "serial") +); +CREATE INDEX "current_idx_current_version_id" on "current" ("current_version_id"); +CREATE INDEX "current_idx_deletedby" on "current" ("deletedby"); +CREATE INDEX "current_idx_draftuser_id" on "current" ("draftuser_id"); +CREATE INDEX "current_idx_instance_id" on "current" ("instance_id"); +CREATE INDEX "current_idx_linked_id" on "current" ("linked_id"); +CREATE INDEX "current_idx_parent_id" on "current" ("parent_id"); + +; +-- +-- Table: curval +-- +CREATE TABLE "curval" ( + "id" bigserial NOT NULL, + "record_id" bigint, + "layout_id" integer, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" bigint, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "curval_idx_layout_id" on "curval" ("layout_id"); +CREATE INDEX "curval_idx_purged_by" on "curval" ("purged_by"); +CREATE INDEX "curval_idx_record_id" on "curval" ("record_id"); +CREATE INDEX "curval_idx_value" on "curval" ("value"); + +; +-- +-- Table: curval_fields +-- +CREATE TABLE "curval_fields" ( + "id" serial NOT NULL, + "parent_id" integer NOT NULL, + "child_id" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "curval_fields_idx_child_id" on "curval_fields" ("child_id"); +CREATE INDEX "curval_fields_idx_parent_id" on "curval_fields" ("parent_id"); + +; +-- +-- Table: dashboard +-- +CREATE TABLE "dashboard" ( + "id" serial NOT NULL, + "site_id" integer, + "instance_id" integer, + "user_id" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "dashboard_idx_instance_id" on "dashboard" ("instance_id"); +CREATE INDEX "dashboard_idx_site_id" on "dashboard" ("site_id"); +CREATE INDEX "dashboard_idx_user_id" on "dashboard" ("user_id"); + +; +-- +-- Table: date +-- +CREATE TABLE "date" ( + "id" bigserial NOT NULL, + "record_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" date, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "date_idx_layout_id" on "date" ("layout_id"); +CREATE INDEX "date_idx_purged_by" on "date" ("purged_by"); +CREATE INDEX "date_idx_record_id" on "date" ("record_id"); +CREATE INDEX "date_idx_value" on "date" ("value"); + +; +-- +-- Table: daterange +-- +CREATE TABLE "daterange" ( + "id" bigserial NOT NULL, + "record_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + "from" date, + "to" date, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" citext, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "daterange_idx_layout_id" on "daterange" ("layout_id"); +CREATE INDEX "daterange_idx_purged_by" on "daterange" ("purged_by"); +CREATE INDEX "daterange_idx_record_id" on "daterange" ("record_id"); +CREATE INDEX "daterange_idx_from" on "daterange" ("from"); +CREATE INDEX "daterange_idx_to" on "daterange" ("to"); +CREATE INDEX "daterange_idx_value" on "daterange" ("value"); + +; +-- +-- Table: department +-- +CREATE TABLE "department" ( + "id" serial NOT NULL, + "name" citext, + "site_id" integer, + "deleted" smallint DEFAULT 0 NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "department_idx_site_id" on "department" ("site_id"); + +; +-- +-- Table: display_field +-- +CREATE TABLE "display_field" ( + "id" serial NOT NULL, + "layout_id" integer NOT NULL, + "display_field_id" integer NOT NULL, + "regex" text, + "operator" character varying(16), + PRIMARY KEY ("id") +); +CREATE INDEX "display_field_idx_display_field_id" on "display_field" ("display_field_id"); +CREATE INDEX "display_field_idx_layout_id" on "display_field" ("layout_id"); + +; +-- +-- Table: enum +-- +CREATE TABLE "enum" ( + "id" bigserial NOT NULL, + "record_id" bigint, + "layout_id" integer, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" integer, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "enum_idx_layout_id" on "enum" ("layout_id"); +CREATE INDEX "enum_idx_purged_by" on "enum" ("purged_by"); +CREATE INDEX "enum_idx_record_id" on "enum" ("record_id"); +CREATE INDEX "enum_idx_value" on "enum" ("value"); + +; +-- +-- Table: enumval +-- +CREATE TABLE "enumval" ( + "id" serial NOT NULL, + "value" citext, + "layout_id" integer, + "deleted" smallint DEFAULT 0 NOT NULL, + "parent" integer, + "position" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "enumval_idx_layout_id" on "enumval" ("layout_id"); +CREATE INDEX "enumval_idx_parent" on "enumval" ("parent"); +CREATE INDEX "enumval_idx_value" on "enumval" ("value"); + +; +-- +-- Table: export +-- +CREATE TABLE "export" ( + "id" serial NOT NULL, + "site_id" integer, + "user_id" bigint NOT NULL, + "type" character varying(45), + "started" timestamp, + "completed" timestamp, + "result" text, + "result_internal" text, + "mimetype" text, + "content" bytea, + PRIMARY KEY ("id") +); +CREATE INDEX "export_idx_site_id" on "export" ("site_id"); +CREATE INDEX "export_idx_user_id" on "export" ("user_id"); + +; +-- +-- Table: file +-- +CREATE TABLE "file" ( + "id" bigserial NOT NULL, + "record_id" bigint, + "layout_id" integer, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" bigint, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "file_idx_layout_id" on "file" ("layout_id"); +CREATE INDEX "file_idx_purged_by" on "file" ("purged_by"); +CREATE INDEX "file_idx_record_id" on "file" ("record_id"); +CREATE INDEX "file_idx_value" on "file" ("value"); + +; +-- +-- Table: file_option +-- +CREATE TABLE "file_option" ( + "id" serial NOT NULL, + "layout_id" integer NOT NULL, + "filesize" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "file_option_idx_layout_id" on "file_option" ("layout_id"); + +; +-- +-- Table: fileval +-- +CREATE TABLE "fileval" ( + "id" bigserial NOT NULL, + "name" text, + "mimetype" text, + "is_independent" smallint DEFAULT 0 NOT NULL, + "edit_user_id" bigint, + PRIMARY KEY ("id") +); +CREATE INDEX "fileval_idx_edit_user_id" on "fileval" ("edit_user_id"); +CREATE INDEX "fileval_idx_name" on "fileval" ("name"); + +; +-- +-- Table: filter +-- +CREATE TABLE "filter" ( + "id" bigserial NOT NULL, + "view_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "filter_idx_layout_id" on "filter" ("layout_id"); +CREATE INDEX "filter_idx_view_id" on "filter" ("view_id"); + +; +-- +-- Table: filtered_value +-- +CREATE TABLE "filtered_value" ( + "id" serial NOT NULL, + "submission_id" integer, + "layout_id" integer, + "current_id" integer, + PRIMARY KEY ("id"), + CONSTRAINT "ux_submission_layout_current" UNIQUE ("submission_id", "layout_id", "current_id") +); +CREATE INDEX "filtered_value_idx_current_id" on "filtered_value" ("current_id"); +CREATE INDEX "filtered_value_idx_layout_id" on "filtered_value" ("layout_id"); +CREATE INDEX "filtered_value_idx_submission_id" on "filtered_value" ("submission_id"); + +; +-- +-- Table: graph +-- +CREATE TABLE "graph" ( + "id" serial NOT NULL, + "title" text, + "description" text, + "y_axis" integer, + "y_axis_link" integer, + "y_axis_stack" character varying(45), + "y_axis_label" text, + "x_axis" integer, + "x_axis_link" integer, + "x_axis_grouping" character varying(45), + "group_by" integer, + "stackseries" smallint DEFAULT 0 NOT NULL, + "as_percent" smallint DEFAULT 0 NOT NULL, + "type" character varying(45), + "metric_group" integer, + "instance_id" integer, + "is_shared" smallint DEFAULT 0 NOT NULL, + "user_id" bigint, + "group_id" integer, + "trend" character varying(45), + "from" date, + "to" date, + "x_axis_range" character varying(45), + PRIMARY KEY ("id") +); +CREATE INDEX "graph_idx_group_id" on "graph" ("group_id"); +CREATE INDEX "graph_idx_group_by" on "graph" ("group_by"); +CREATE INDEX "graph_idx_instance_id" on "graph" ("instance_id"); +CREATE INDEX "graph_idx_metric_group" on "graph" ("metric_group"); +CREATE INDEX "graph_idx_user_id" on "graph" ("user_id"); +CREATE INDEX "graph_idx_x_axis" on "graph" ("x_axis"); +CREATE INDEX "graph_idx_x_axis_link" on "graph" ("x_axis_link"); +CREATE INDEX "graph_idx_y_axis" on "graph" ("y_axis"); +CREATE INDEX "graph_idx_y_axis_link" on "graph" ("y_axis_link"); + +; +-- +-- Table: graph_color +-- +CREATE TABLE "graph_color" ( + "id" bigserial NOT NULL, + "name" character varying(128), + "color" character(6), + PRIMARY KEY ("id"), + CONSTRAINT "ux_graph_color_name" UNIQUE ("name") +); + +; +-- +-- Table: group +-- +CREATE TABLE "group" ( + "id" serial NOT NULL, + "name" character varying(128), + "default_read" smallint DEFAULT 0 NOT NULL, + "default_write_new" smallint DEFAULT 0 NOT NULL, + "default_write_existing" smallint DEFAULT 0 NOT NULL, + "default_approve_new" smallint DEFAULT 0 NOT NULL, + "default_approve_existing" smallint DEFAULT 0 NOT NULL, + "default_write_new_no_approval" smallint DEFAULT 0 NOT NULL, + "default_write_existing_no_approval" smallint DEFAULT 0 NOT NULL, + "site_id" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "group_idx_site_id" on "group" ("site_id"); + +; +-- +-- Table: import +-- +CREATE TABLE "import" ( + "id" serial NOT NULL, + "site_id" integer, + "instance_id" integer, + "user_id" bigint NOT NULL, + "type" character varying(45), + "row_count" integer DEFAULT 0 NOT NULL, + "started" timestamp, + "completed" timestamp, + "written_count" integer DEFAULT 0 NOT NULL, + "error_count" integer DEFAULT 0 NOT NULL, + "skipped_count" integer DEFAULT 0 NOT NULL, + "result" text, + PRIMARY KEY ("id") +); +CREATE INDEX "import_idx_instance_id" on "import" ("instance_id"); +CREATE INDEX "import_idx_site_id" on "import" ("site_id"); +CREATE INDEX "import_idx_user_id" on "import" ("user_id"); + +; +-- +-- Table: import_row +-- +CREATE TABLE "import_row" ( + "id" bigserial NOT NULL, + "import_id" integer NOT NULL, + "status" character varying(45), + "content" text, + "errors" text, + "changes" text, + PRIMARY KEY ("id") +); +CREATE INDEX "import_row_idx_import_id" on "import_row" ("import_id"); + +; +-- +-- Table: instance +-- +CREATE TABLE "instance" ( + "id" serial NOT NULL, + "name" text, + "name_short" character varying(64), + "site_id" integer, + "sort_layout_id" integer, + "sort_type" character varying(45), + "view_limit_id" integer, + "default_view_limit_extra_id" integer, + "homepage_text" text, + "homepage_text2" text, + "record_name" text, + "forget_history" smallint DEFAULT 0, + "no_overnight_update" smallint DEFAULT 0, + "api_index_layout_id" integer, + "forward_record_after_create" smallint DEFAULT 0, + "no_hide_blank" smallint DEFAULT 0 NOT NULL, + "no_download_pdf" smallint DEFAULT 0 NOT NULL, + "no_copy_record" smallint DEFAULT 0 NOT NULL, + "hide_in_selector" smallint DEFAULT 0 NOT NULL, + "security_marking" text, + PRIMARY KEY ("id") +); +CREATE INDEX "instance_idx_api_index_layout_id" on "instance" ("api_index_layout_id"); +CREATE INDEX "instance_idx_default_view_limit_extra_id" on "instance" ("default_view_limit_extra_id"); +CREATE INDEX "instance_idx_site_id" on "instance" ("site_id"); +CREATE INDEX "instance_idx_sort_layout_id" on "instance" ("sort_layout_id"); +CREATE INDEX "instance_idx_view_limit_id" on "instance" ("view_limit_id"); + +; +-- +-- Table: instance_group +-- +CREATE TABLE "instance_group" ( + "id" serial NOT NULL, + "instance_id" integer NOT NULL, + "group_id" integer NOT NULL, + "permission" character varying(45) NOT NULL, + PRIMARY KEY ("id"), + CONSTRAINT "instance_group_ux_instance_group_permission" UNIQUE ("instance_id", "group_id", "permission") +); +CREATE INDEX "instance_group_idx_group_id" on "instance_group" ("group_id"); +CREATE INDEX "instance_group_idx_instance_id" on "instance_group" ("instance_id"); + +; +-- +-- Table: instance_rag +-- +CREATE TABLE "instance_rag" ( + "id" serial NOT NULL, + "instance_id" integer NOT NULL, + "rag" character varying(16) NOT NULL, + "enabled" smallint DEFAULT 0 NOT NULL, + "description" text, + PRIMARY KEY ("id"), + CONSTRAINT "instance_rag_ux_instance_rag" UNIQUE ("instance_id", "rag") +); +CREATE INDEX "instance_rag_idx_instance_id" on "instance_rag" ("instance_id"); + +; +-- +-- Table: intgr +-- +CREATE TABLE "intgr" ( + "id" bigserial NOT NULL, + "record_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" bigint, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "intgr_idx_layout_id" on "intgr" ("layout_id"); +CREATE INDEX "intgr_idx_purged_by" on "intgr" ("purged_by"); +CREATE INDEX "intgr_idx_record_id" on "intgr" ("record_id"); +CREATE INDEX "intgr_idx_value" on "intgr" ("value"); + +; +-- +-- Table: layout +-- +CREATE TABLE "layout" ( + "id" serial NOT NULL, + "name" text, + "name_short" character varying(64), + "type" character varying(45), + "permission" integer DEFAULT 0 NOT NULL, + "optional" smallint DEFAULT 0 NOT NULL, + "remember" smallint DEFAULT 0 NOT NULL, + "isunique" smallint DEFAULT 0 NOT NULL, + "textbox" smallint DEFAULT 0 NOT NULL, + "typeahead" smallint DEFAULT 0 NOT NULL, + "force_regex" text, + "position" integer, + "ordering" character varying(45), + "end_node_only" smallint DEFAULT 0 NOT NULL, + "multivalue" smallint DEFAULT 0 NOT NULL, + "can_child" smallint DEFAULT 0 NOT NULL, + "internal" smallint DEFAULT 0 NOT NULL, + "description" text, + "helptext" text, + "options" text, + "display_field" integer, + "display_regex" text, + "display_condition" character(3), + "display_matchtype" text, + "instance_id" integer, + "link_parent" integer, + "related_field" integer, + "width" integer DEFAULT 50 NOT NULL, + "filter" text, + "topic_id" integer, + "aggregate" character varying(45), + "group_display" character varying(45), + "lookup_endpoint" text, + "lookup_group" smallint, + "notes" text, + PRIMARY KEY ("id"), + CONSTRAINT "layout_ux_instance_name_short" UNIQUE ("instance_id", "name_short") +); +CREATE INDEX "layout_idx_display_field" on "layout" ("display_field"); +CREATE INDEX "layout_idx_instance_id" on "layout" ("instance_id"); +CREATE INDEX "layout_idx_link_parent" on "layout" ("link_parent"); +CREATE INDEX "layout_idx_related_field" on "layout" ("related_field"); +CREATE INDEX "layout_idx_topic_id" on "layout" ("topic_id"); + +; +-- +-- Table: layout_depend +-- +CREATE TABLE "layout_depend" ( + "id" serial NOT NULL, + "layout_id" integer NOT NULL, + "depends_on" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "layout_depend_idx_depends_on" on "layout_depend" ("depends_on"); +CREATE INDEX "layout_depend_idx_layout_id" on "layout_depend" ("layout_id"); + +; +-- +-- Table: layout_group +-- +CREATE TABLE "layout_group" ( + "id" serial NOT NULL, + "layout_id" integer NOT NULL, + "group_id" integer NOT NULL, + "permission" character varying(45) NOT NULL, + PRIMARY KEY ("id"), + CONSTRAINT "layout_group_ux_layout_group_permission" UNIQUE ("layout_id", "group_id", "permission") +); +CREATE INDEX "layout_group_idx_group_id" on "layout_group" ("group_id"); +CREATE INDEX "layout_group_idx_layout_id" on "layout_group" ("layout_id"); +CREATE INDEX "layout_group_idx_permission" on "layout_group" ("permission"); + +; +-- +-- Table: metric +-- +CREATE TABLE "metric" ( + "id" serial NOT NULL, + "metric_group" integer NOT NULL, + "x_axis_value" text, + "target" bigint, + "y_axis_grouping_value" text, + PRIMARY KEY ("id") +); +CREATE INDEX "metric_idx_metric_group" on "metric" ("metric_group"); + +; +-- +-- Table: metric_group +-- +CREATE TABLE "metric_group" ( + "id" serial NOT NULL, + "name" text, + "instance_id" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "metric_group_idx_instance_id" on "metric_group" ("instance_id"); + +; +-- +-- Table: oauthclient +-- +CREATE TABLE "oauthclient" ( + "id" bigserial NOT NULL, + "client_id" character varying(64) NOT NULL, + "client_secret" character varying(64) NOT NULL, + PRIMARY KEY ("id") +); + +; +-- +-- Table: oauthtoken +-- +CREATE TABLE "oauthtoken" ( + "token" character varying(128) NOT NULL, + "related_token" character varying(128) NOT NULL, + "oauthclient_id" integer NOT NULL, + "user_id" bigint NOT NULL, + "type" character varying(12) NOT NULL, + "expires" integer, + PRIMARY KEY ("token") +); +CREATE INDEX "oauthtoken_idx_oauthclient_id" on "oauthtoken" ("oauthclient_id"); +CREATE INDEX "oauthtoken_idx_user_id" on "oauthtoken" ("user_id"); + +; +-- +-- Table: organisation +-- +CREATE TABLE "organisation" ( + "id" serial NOT NULL, + "name" citext, + "site_id" integer, + "deleted" smallint DEFAULT 0 NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "organisation_idx_site_id" on "organisation" ("site_id"); + +; +-- +-- Table: permission +-- +CREATE TABLE "permission" ( + "id" serial NOT NULL, + "name" character varying(128) NOT NULL, + "description" text, + "order" integer, + PRIMARY KEY ("id") +); + +; +-- +-- Table: person +-- +CREATE TABLE "person" ( + "id" bigserial NOT NULL, + "record_id" bigint, + "layout_id" integer, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" bigint, + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "person_idx_layout_id" on "person" ("layout_id"); +CREATE INDEX "person_idx_purged_by" on "person" ("purged_by"); +CREATE INDEX "person_idx_record_id" on "person" ("record_id"); +CREATE INDEX "person_idx_value" on "person" ("value"); + +; +-- +-- Table: rag +-- +CREATE TABLE "rag" ( + "id" serial NOT NULL, + "layout_id" integer NOT NULL, + "red" text, + "amber" text, + "green" text, + "code" text, + PRIMARY KEY ("id") +); +CREATE INDEX "rag_idx_layout_id" on "rag" ("layout_id"); + +; +-- +-- Table: ragval +-- +CREATE TABLE "ragval" ( + "id" bigserial NOT NULL, + "record_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + "value" character varying(16), + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id"), + CONSTRAINT "ragval_ux_record_layout" UNIQUE ("record_id", "layout_id") +); +CREATE INDEX "ragval_idx_layout_id" on "ragval" ("layout_id"); +CREATE INDEX "ragval_idx_purged_by" on "ragval" ("purged_by"); +CREATE INDEX "ragval_idx_record_id" on "ragval" ("record_id"); +CREATE INDEX "ragval_idx_value" on "ragval" ("value"); + +; +-- +-- Table: record +-- +CREATE TABLE "record" ( + "id" bigserial NOT NULL, + "created" timestamp NOT NULL, + "current_id" bigint DEFAULT 0 NOT NULL, + "createdby" bigint, + "approvedby" bigint, + "record_id" bigint, + "approval" smallint DEFAULT 0 NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "record_idx_approvedby" on "record" ("approvedby"); +CREATE INDEX "record_idx_createdby" on "record" ("createdby"); +CREATE INDEX "record_idx_current_id" on "record" ("current_id"); +CREATE INDEX "record_idx_record_id" on "record" ("record_id"); +CREATE INDEX "record_idx_approval" on "record" ("approval"); + +; +-- +-- Table: report +-- +CREATE TABLE "report" ( + "id" bigserial NOT NULL, + "name" text NOT NULL, + "title" text, + "description" text, + "user_id" bigint, + "createdby" bigint, + "created" timestamp, + "instance_id" bigint, + "deleted" timestamp, + "security_marking" text, + PRIMARY KEY ("id") +); +CREATE INDEX "report_idx_createdby" on "report" ("createdby"); +CREATE INDEX "report_idx_instance_id" on "report" ("instance_id"); +CREATE INDEX "report_idx_user_id" on "report" ("user_id"); + +; +-- +-- Table: report_group +-- +CREATE TABLE "report_group" ( + "id" serial NOT NULL, + "report_id" integer NOT NULL, + "group_id" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "report_group_idx_group_id" on "report_group" ("group_id"); +CREATE INDEX "report_group_idx_report_id" on "report_group" ("report_id"); + +; +-- +-- Table: report_layout +-- +CREATE TABLE "report_layout" ( + "id" serial NOT NULL, + "report_id" integer NOT NULL, + "layout_id" bigint NOT NULL, + "order" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "report_layout_idx_layout_id" on "report_layout" ("layout_id"); +CREATE INDEX "report_layout_idx_report_id" on "report_layout" ("report_id"); + +; +-- +-- Table: site +-- +CREATE TABLE "site" ( + "id" serial NOT NULL, + "host" character varying(128), + "name" text, + "created" timestamp, + "email_welcome_text" text, + "email_welcome_subject" text, + "email_delete_text" text, + "email_delete_subject" text, + "email_reject_text" text, + "email_reject_subject" text, + "register_text" text, + "homepage_text" text, + "homepage_text2" text, + "register_title_help" text, + "register_freetext1_help" text, + "register_freetext2_help" text, + "register_email_help" text, + "register_organisation_help" text, + "register_organisation_name" text, + "register_organisation_mandatory" smallint DEFAULT 0 NOT NULL, + "register_department_help" text, + "register_department_name" text, + "register_department_mandatory" smallint DEFAULT 0 NOT NULL, + "register_team_help" text, + "register_team_name" text, + "register_team_mandatory" smallint DEFAULT 0 NOT NULL, + "register_notes_help" text, + "register_freetext1_name" text, + "register_freetext2_name" text, + "register_show_organisation" smallint DEFAULT 1 NOT NULL, + "register_show_department" smallint DEFAULT 0 NOT NULL, + "register_show_team" smallint DEFAULT 0 NOT NULL, + "register_show_title" smallint DEFAULT 1 NOT NULL, + "register_show_provider" smallint DEFAULT 0 NOT NULL, + "hide_account_request" smallint DEFAULT 0 NOT NULL, + "remember_user_location" smallint DEFAULT 1 NOT NULL, + "user_editable_fields" text, + "register_freetext1_placeholder" text, + "register_freetext2_placeholder" text, + "account_request_notes_name" text, + "account_request_notes_placeholder" text, + "security_marking" text, + "site_logo" bytea, + "force_mfa" character(3), + PRIMARY KEY ("id") +); + +; +-- +-- Table: sort +-- +CREATE TABLE "sort" ( + "id" serial NOT NULL, + "view_id" bigint NOT NULL, + "layout_id" integer, + "parent_id" integer, + "type" character varying(45), + "order" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "sort_idx_layout_id" on "sort" ("layout_id"); +CREATE INDEX "sort_idx_parent_id" on "sort" ("parent_id"); +CREATE INDEX "sort_idx_view_id" on "sort" ("view_id"); + +; +-- +-- Table: string +-- +CREATE TABLE "string" ( + "id" bigserial NOT NULL, + "record_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + "child_unique" smallint DEFAULT 0 NOT NULL, + "value" citext, + "value_index" character varying(128), + "purged_by" bigint, + "purged_on" timestamp, + PRIMARY KEY ("id") +); +CREATE INDEX "string_idx_layout_id" on "string" ("layout_id"); +CREATE INDEX "string_idx_purged_by" on "string" ("purged_by"); +CREATE INDEX "string_idx_record_id" on "string" ("record_id"); +CREATE INDEX "string_idx_value_index" on "string" ("value_index"); + +; +-- +-- Table: submission +-- +CREATE TABLE "submission" ( + "id" serial NOT NULL, + "token" character varying(64) NOT NULL, + "created" timestamp, + "submitted" smallint DEFAULT 0 NOT NULL, + PRIMARY KEY ("id"), + CONSTRAINT "ux_submission_token" UNIQUE ("token", "submitted") +); + +; +-- +-- Table: team +-- +CREATE TABLE "team" ( + "id" serial NOT NULL, + "name" citext, + "site_id" integer, + "deleted" smallint DEFAULT 0 NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "team_idx_site_id" on "team" ("site_id"); + +; +-- +-- Table: title +-- +CREATE TABLE "title" ( + "id" serial NOT NULL, + "name" character varying(128), + "site_id" integer, + "deleted" smallint DEFAULT 0 NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "title_idx_site_id" on "title" ("site_id"); + +; +-- +-- Table: topic +-- +CREATE TABLE "topic" ( + "id" serial NOT NULL, + "instance_id" integer, + "name" text, + "description" text, + "initial_state" character varying(32), + "click_to_edit" smallint DEFAULT 0 NOT NULL, + "prevent_edit_topic_id" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "topic_idx_instance_id" on "topic" ("instance_id"); +CREATE INDEX "topic_idx_prevent_edit_topic_id" on "topic" ("prevent_edit_topic_id"); + +; +-- +-- Table: user +-- +CREATE TABLE "user" ( + "id" bigserial NOT NULL, + "site_id" integer, + "firstname" character varying(128), + "surname" character varying(128), + "email" citext, + "username" citext, + "title" integer, + "organisation" integer, + "department_id" integer, + "team_id" integer, + "freetext1" text, + "freetext2" text, + "password" character varying(128), + "pwchanged" timestamp, + "resetpw" character varying(32), + "deleted" timestamp, + "lastlogin" timestamp, + "lastfail" timestamp, + "failcount" integer DEFAULT 0 NOT NULL, + "lastrecord" bigint, + "lastview" bigint, + "session_settings" text, + "value" citext, + "account_request" smallint DEFAULT 0, + "account_request_notes" text, + "aup_accepted" timestamp, + "limit_to_view" bigint, + "stylesheet" text, + "created" timestamp, + "debug_login" smallint DEFAULT 0, + "mfa_type" character(3), + "mobile" text, + "mobile_verified" smallint DEFAULT 0 NOT NULL, + "mfa_secret" text, + "mfa_sms_token" text, + "mfa_sms_created" timestamp, + "mfa_token_previous" text, + "mfa_token_previous_type" character(3), + "mfa_token_previous_used" timestamp, + "mfa_token_previous_key" text, + "mfa_lastfail" timestamp, + "mfa_failcount" integer DEFAULT 0 NOT NULL, + "provider" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "user_idx_department_id" on "user" ("department_id"); +CREATE INDEX "user_idx_lastrecord" on "user" ("lastrecord"); +CREATE INDEX "user_idx_lastview" on "user" ("lastview"); +CREATE INDEX "user_idx_limit_to_view" on "user" ("limit_to_view"); +CREATE INDEX "user_idx_organisation" on "user" ("organisation"); +CREATE INDEX "user_idx_provider" on "user" ("provider"); +CREATE INDEX "user_idx_site_id" on "user" ("site_id"); +CREATE INDEX "user_idx_team_id" on "user" ("team_id"); +CREATE INDEX "user_idx_title" on "user" ("title"); +CREATE INDEX "user_idx_value" on "user" ("value"); +CREATE INDEX "user_idx_email" on "user" ("email"); +CREATE INDEX "user_idx_username" on "user" ("username"); + +; +-- +-- Table: user_graph +-- +CREATE TABLE "user_graph" ( + "id" bigserial NOT NULL, + "user_id" bigint NOT NULL, + "graph_id" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "user_graph_idx_graph_id" on "user_graph" ("graph_id"); +CREATE INDEX "user_graph_idx_user_id" on "user_graph" ("user_id"); + +; +-- +-- Table: user_group +-- +CREATE TABLE "user_group" ( + "id" bigserial NOT NULL, + "user_id" bigint NOT NULL, + "group_id" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "user_group_idx_group_id" on "user_group" ("group_id"); +CREATE INDEX "user_group_idx_user_id" on "user_group" ("user_id"); + +; +-- +-- Table: user_lastrecord +-- +CREATE TABLE "user_lastrecord" ( + "id" bigserial NOT NULL, + "record_id" bigint NOT NULL, + "instance_id" integer NOT NULL, + "user_id" bigint NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "user_lastrecord_idx_instance_id" on "user_lastrecord" ("instance_id"); +CREATE INDEX "user_lastrecord_idx_record_id" on "user_lastrecord" ("record_id"); +CREATE INDEX "user_lastrecord_idx_user_id" on "user_lastrecord" ("user_id"); + +; +-- +-- Table: user_permission +-- +CREATE TABLE "user_permission" ( + "id" bigserial NOT NULL, + "user_id" bigint NOT NULL, + "permission_id" integer NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "user_permission_idx_permission_id" on "user_permission" ("permission_id"); +CREATE INDEX "user_permission_idx_user_id" on "user_permission" ("user_id"); + +; +-- +-- Table: view +-- +CREATE TABLE "view" ( + "id" bigserial NOT NULL, + "user_id" bigint, + "group_id" integer, + "name" character varying(128), + "global" smallint DEFAULT 0 NOT NULL, + "is_admin" smallint DEFAULT 0 NOT NULL, + "is_limit_extra" smallint DEFAULT 0 NOT NULL, + "filter" text, + "instance_id" integer, + "created" timestamp, + "createdby" bigint, + PRIMARY KEY ("id") +); +CREATE INDEX "view_idx_createdby" on "view" ("createdby"); +CREATE INDEX "view_idx_group_id" on "view" ("group_id"); +CREATE INDEX "view_idx_instance_id" on "view" ("instance_id"); +CREATE INDEX "view_idx_user_id" on "view" ("user_id"); + +; +-- +-- Table: view_group +-- +CREATE TABLE "view_group" ( + "id" serial NOT NULL, + "view_id" bigint NOT NULL, + "layout_id" integer, + "parent_id" integer, + "order" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "view_group_idx_layout_id" on "view_group" ("layout_id"); +CREATE INDEX "view_group_idx_parent_id" on "view_group" ("parent_id"); +CREATE INDEX "view_group_idx_view_id" on "view_group" ("view_id"); + +; +-- +-- Table: view_layout +-- +CREATE TABLE "view_layout" ( + "id" serial NOT NULL, + "view_id" bigint NOT NULL, + "layout_id" integer NOT NULL, + "order" integer, + PRIMARY KEY ("id") +); +CREATE INDEX "view_layout_idx_layout_id" on "view_layout" ("layout_id"); +CREATE INDEX "view_layout_idx_view_id" on "view_layout" ("view_id"); + +; +-- +-- Table: view_limit +-- +CREATE TABLE "view_limit" ( + "id" bigserial NOT NULL, + "view_id" bigint NOT NULL, + "user_id" bigint NOT NULL, + PRIMARY KEY ("id") +); +CREATE INDEX "view_limit_idx_user_id" on "view_limit" ("user_id"); +CREATE INDEX "view_limit_idx_view_id" on "view_limit" ("view_id"); + +; +-- +-- Table: widget +-- +CREATE TABLE "widget" ( + "id" serial NOT NULL, + "grid_id" character varying(64), + "dashboard_id" integer, + "type" character varying(16), + "title" text, + "static" smallint DEFAULT 0 NOT NULL, + "h" smallint DEFAULT 0, + "w" smallint DEFAULT 0, + "x" smallint DEFAULT 0, + "y" smallint DEFAULT 0, + "content" text, + "view_id" integer, + "graph_id" integer, + "rows" integer, + "tl_options" text, + "globe_options" text, + PRIMARY KEY ("id"), + CONSTRAINT "widget_ux_dashboard_grid" UNIQUE ("dashboard_id", "grid_id") +); +CREATE INDEX "widget_idx_dashboard_id" on "widget" ("dashboard_id"); +CREATE INDEX "widget_idx_graph_id" on "widget" ("graph_id"); +CREATE INDEX "widget_idx_view_id" on "widget" ("view_id"); + +; +-- +-- Foreign Key Definitions +-- + +; +ALTER TABLE "alert" ADD CONSTRAINT "alert_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert" ADD CONSTRAINT "alert_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_cache" ADD CONSTRAINT "alert_cache_fk_current_id" FOREIGN KEY ("current_id") + REFERENCES "current" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_cache" ADD CONSTRAINT "alert_cache_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_cache" ADD CONSTRAINT "alert_cache_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_cache" ADD CONSTRAINT "alert_cache_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_column" ADD CONSTRAINT "alert_column_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_column" ADD CONSTRAINT "alert_column_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_send" ADD CONSTRAINT "alert_send_fk_alert_id" FOREIGN KEY ("alert_id") + REFERENCES "alert" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_send" ADD CONSTRAINT "alert_send_fk_current_id" FOREIGN KEY ("current_id") + REFERENCES "current" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "alert_send" ADD CONSTRAINT "alert_send_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "audit" ADD CONSTRAINT "audit_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "audit" ADD CONSTRAINT "audit_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "audit" ADD CONSTRAINT "audit_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "authentication" ADD CONSTRAINT "authentication_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "calc" ADD CONSTRAINT "calc_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "calc_unique" ADD CONSTRAINT "calc_unique_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "calcval" ADD CONSTRAINT "calcval_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "calcval" ADD CONSTRAINT "calcval_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "calcval" ADD CONSTRAINT "calcval_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "current" ADD CONSTRAINT "current_fk_current_version_id" FOREIGN KEY ("current_version_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "current" ADD CONSTRAINT "current_fk_deletedby" FOREIGN KEY ("deletedby") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "current" ADD CONSTRAINT "current_fk_draftuser_id" FOREIGN KEY ("draftuser_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "current" ADD CONSTRAINT "current_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "current" ADD CONSTRAINT "current_fk_linked_id" FOREIGN KEY ("linked_id") + REFERENCES "current" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "current" ADD CONSTRAINT "current_fk_parent_id" FOREIGN KEY ("parent_id") + REFERENCES "current" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "curval" ADD CONSTRAINT "curval_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "curval" ADD CONSTRAINT "curval_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "curval" ADD CONSTRAINT "curval_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "curval" ADD CONSTRAINT "curval_fk_value" FOREIGN KEY ("value") + REFERENCES "current" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "curval_fields" ADD CONSTRAINT "curval_fields_fk_child_id" FOREIGN KEY ("child_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "curval_fields" ADD CONSTRAINT "curval_fields_fk_parent_id" FOREIGN KEY ("parent_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "dashboard" ADD CONSTRAINT "dashboard_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "dashboard" ADD CONSTRAINT "dashboard_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "dashboard" ADD CONSTRAINT "dashboard_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "date" ADD CONSTRAINT "date_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "date" ADD CONSTRAINT "date_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "date" ADD CONSTRAINT "date_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "daterange" ADD CONSTRAINT "daterange_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "daterange" ADD CONSTRAINT "daterange_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "daterange" ADD CONSTRAINT "daterange_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "department" ADD CONSTRAINT "department_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "display_field" ADD CONSTRAINT "display_field_fk_display_field_id" FOREIGN KEY ("display_field_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "display_field" ADD CONSTRAINT "display_field_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "enum" ADD CONSTRAINT "enum_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "enum" ADD CONSTRAINT "enum_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "enum" ADD CONSTRAINT "enum_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "enum" ADD CONSTRAINT "enum_fk_value" FOREIGN KEY ("value") + REFERENCES "enumval" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "enumval" ADD CONSTRAINT "enumval_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "enumval" ADD CONSTRAINT "enumval_fk_parent" FOREIGN KEY ("parent") + REFERENCES "enumval" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "export" ADD CONSTRAINT "export_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "export" ADD CONSTRAINT "export_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "file" ADD CONSTRAINT "file_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "file" ADD CONSTRAINT "file_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "file" ADD CONSTRAINT "file_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "file" ADD CONSTRAINT "file_fk_value" FOREIGN KEY ("value") + REFERENCES "fileval" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "file_option" ADD CONSTRAINT "file_option_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "fileval" ADD CONSTRAINT "fileval_fk_edit_user_id" FOREIGN KEY ("edit_user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "filter" ADD CONSTRAINT "filter_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "filter" ADD CONSTRAINT "filter_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "filtered_value" ADD CONSTRAINT "filtered_value_fk_current_id" FOREIGN KEY ("current_id") + REFERENCES "current" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "filtered_value" ADD CONSTRAINT "filtered_value_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "filtered_value" ADD CONSTRAINT "filtered_value_fk_submission_id" FOREIGN KEY ("submission_id") + REFERENCES "submission" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_group_id" FOREIGN KEY ("group_id") + REFERENCES "group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_group_by" FOREIGN KEY ("group_by") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_metric_group" FOREIGN KEY ("metric_group") + REFERENCES "metric_group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_x_axis" FOREIGN KEY ("x_axis") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_x_axis_link" FOREIGN KEY ("x_axis_link") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_y_axis" FOREIGN KEY ("y_axis") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "graph" ADD CONSTRAINT "graph_fk_y_axis_link" FOREIGN KEY ("y_axis_link") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "group" ADD CONSTRAINT "group_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "import" ADD CONSTRAINT "import_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "import" ADD CONSTRAINT "import_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "import" ADD CONSTRAINT "import_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "import_row" ADD CONSTRAINT "import_row_fk_import_id" FOREIGN KEY ("import_id") + REFERENCES "import" ("id") ON DELETE CASCADE ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance" ADD CONSTRAINT "instance_fk_api_index_layout_id" FOREIGN KEY ("api_index_layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance" ADD CONSTRAINT "instance_fk_default_view_limit_extra_id" FOREIGN KEY ("default_view_limit_extra_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance" ADD CONSTRAINT "instance_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance" ADD CONSTRAINT "instance_fk_sort_layout_id" FOREIGN KEY ("sort_layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance" ADD CONSTRAINT "instance_fk_view_limit_id" FOREIGN KEY ("view_limit_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance_group" ADD CONSTRAINT "instance_group_fk_group_id" FOREIGN KEY ("group_id") + REFERENCES "group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance_group" ADD CONSTRAINT "instance_group_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "instance_rag" ADD CONSTRAINT "instance_rag_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "intgr" ADD CONSTRAINT "intgr_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "intgr" ADD CONSTRAINT "intgr_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "intgr" ADD CONSTRAINT "intgr_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout" ADD CONSTRAINT "layout_fk_display_field" FOREIGN KEY ("display_field") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout" ADD CONSTRAINT "layout_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout" ADD CONSTRAINT "layout_fk_link_parent" FOREIGN KEY ("link_parent") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout" ADD CONSTRAINT "layout_fk_related_field" FOREIGN KEY ("related_field") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout" ADD CONSTRAINT "layout_fk_topic_id" FOREIGN KEY ("topic_id") + REFERENCES "topic" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout_depend" ADD CONSTRAINT "layout_depend_fk_depends_on" FOREIGN KEY ("depends_on") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout_depend" ADD CONSTRAINT "layout_depend_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout_group" ADD CONSTRAINT "layout_group_fk_group_id" FOREIGN KEY ("group_id") + REFERENCES "group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "layout_group" ADD CONSTRAINT "layout_group_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "metric" ADD CONSTRAINT "metric_fk_metric_group" FOREIGN KEY ("metric_group") + REFERENCES "metric_group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "metric_group" ADD CONSTRAINT "metric_group_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "oauthtoken" ADD CONSTRAINT "oauthtoken_fk_oauthclient_id" FOREIGN KEY ("oauthclient_id") + REFERENCES "oauthclient" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "oauthtoken" ADD CONSTRAINT "oauthtoken_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "organisation" ADD CONSTRAINT "organisation_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "person" ADD CONSTRAINT "person_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "person" ADD CONSTRAINT "person_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "person" ADD CONSTRAINT "person_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "person" ADD CONSTRAINT "person_fk_value" FOREIGN KEY ("value") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "rag" ADD CONSTRAINT "rag_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "ragval" ADD CONSTRAINT "ragval_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "ragval" ADD CONSTRAINT "ragval_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "ragval" ADD CONSTRAINT "ragval_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "record" ADD CONSTRAINT "record_fk_approvedby" FOREIGN KEY ("approvedby") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "record" ADD CONSTRAINT "record_fk_createdby" FOREIGN KEY ("createdby") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "record" ADD CONSTRAINT "record_fk_current_id" FOREIGN KEY ("current_id") + REFERENCES "current" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "record" ADD CONSTRAINT "record_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "report" ADD CONSTRAINT "report_fk_createdby" FOREIGN KEY ("createdby") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "report" ADD CONSTRAINT "report_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "report" ADD CONSTRAINT "report_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "report_group" ADD CONSTRAINT "report_group_fk_group_id" FOREIGN KEY ("group_id") + REFERENCES "group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "report_group" ADD CONSTRAINT "report_group_fk_report_id" FOREIGN KEY ("report_id") + REFERENCES "report" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "report_layout" ADD CONSTRAINT "report_layout_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "report_layout" ADD CONSTRAINT "report_layout_fk_report_id" FOREIGN KEY ("report_id") + REFERENCES "report" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "sort" ADD CONSTRAINT "sort_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "sort" ADD CONSTRAINT "sort_fk_parent_id" FOREIGN KEY ("parent_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "sort" ADD CONSTRAINT "sort_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "string" ADD CONSTRAINT "string_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "string" ADD CONSTRAINT "string_fk_purged_by" FOREIGN KEY ("purged_by") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "string" ADD CONSTRAINT "string_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "team" ADD CONSTRAINT "team_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "title" ADD CONSTRAINT "title_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "topic" ADD CONSTRAINT "topic_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "topic" ADD CONSTRAINT "topic_fk_prevent_edit_topic_id" FOREIGN KEY ("prevent_edit_topic_id") + REFERENCES "topic" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_department_id" FOREIGN KEY ("department_id") + REFERENCES "department" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_lastrecord" FOREIGN KEY ("lastrecord") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_lastview" FOREIGN KEY ("lastview") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_limit_to_view" FOREIGN KEY ("limit_to_view") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_organisation" FOREIGN KEY ("organisation") + REFERENCES "organisation" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_provider" FOREIGN KEY ("provider") + REFERENCES "authentication" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_site_id" FOREIGN KEY ("site_id") + REFERENCES "site" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_team_id" FOREIGN KEY ("team_id") + REFERENCES "team" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user" ADD CONSTRAINT "user_fk_title" FOREIGN KEY ("title") + REFERENCES "title" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_graph" ADD CONSTRAINT "user_graph_fk_graph_id" FOREIGN KEY ("graph_id") + REFERENCES "graph" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_graph" ADD CONSTRAINT "user_graph_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_group" ADD CONSTRAINT "user_group_fk_group_id" FOREIGN KEY ("group_id") + REFERENCES "group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_group" ADD CONSTRAINT "user_group_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_lastrecord" ADD CONSTRAINT "user_lastrecord_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_lastrecord" ADD CONSTRAINT "user_lastrecord_fk_record_id" FOREIGN KEY ("record_id") + REFERENCES "record" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_lastrecord" ADD CONSTRAINT "user_lastrecord_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_permission" ADD CONSTRAINT "user_permission_fk_permission_id" FOREIGN KEY ("permission_id") + REFERENCES "permission" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "user_permission" ADD CONSTRAINT "user_permission_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view" ADD CONSTRAINT "view_fk_createdby" FOREIGN KEY ("createdby") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view" ADD CONSTRAINT "view_fk_group_id" FOREIGN KEY ("group_id") + REFERENCES "group" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view" ADD CONSTRAINT "view_fk_instance_id" FOREIGN KEY ("instance_id") + REFERENCES "instance" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view" ADD CONSTRAINT "view_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view_group" ADD CONSTRAINT "view_group_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view_group" ADD CONSTRAINT "view_group_fk_parent_id" FOREIGN KEY ("parent_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view_group" ADD CONSTRAINT "view_group_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view_layout" ADD CONSTRAINT "view_layout_fk_layout_id" FOREIGN KEY ("layout_id") + REFERENCES "layout" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view_layout" ADD CONSTRAINT "view_layout_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view_limit" ADD CONSTRAINT "view_limit_fk_user_id" FOREIGN KEY ("user_id") + REFERENCES "user" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "view_limit" ADD CONSTRAINT "view_limit_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "widget" ADD CONSTRAINT "widget_fk_dashboard_id" FOREIGN KEY ("dashboard_id") + REFERENCES "dashboard" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "widget" ADD CONSTRAINT "widget_fk_graph_id" FOREIGN KEY ("graph_id") + REFERENCES "graph" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; +ALTER TABLE "widget" ADD CONSTRAINT "widget_fk_view_id" FOREIGN KEY ("view_id") + REFERENCES "view" ("id") ON DELETE NO ACTION ON UPDATE NO ACTION DEFERRABLE; + +; diff --git a/share/migrations/_source/deploy/112/001-auto-__VERSION.yml b/share/migrations/_source/deploy/112/001-auto-__VERSION.yml new file mode 100644 index 000000000..dcd1f1b3d --- /dev/null +++ b/share/migrations/_source/deploy/112/001-auto-__VERSION.yml @@ -0,0 +1,92 @@ +--- +schema: + procedures: {} + tables: + dbix_class_deploymenthandler_versions: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - version + match_type: '' + name: dbix_class_deploymenthandler_versions_version + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + fields: + ddl: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: ddl + order: 3 + size: + - 0 + id: + data_type: int + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + upgrade_sql: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: upgrade_sql + order: 4 + size: + - 0 + version: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: version + order: 2 + size: + - 50 + indices: [] + name: dbix_class_deploymenthandler_versions + options: [] + order: 1 + triggers: {} + views: {} +translator: + add_drop_table: 0 + filename: ~ + no_comments: 0 + parser_args: + sources: + - __VERSION + parser_type: SQL::Translator::Parser::DBIx::Class + producer_args: + mysql_version: 5.7 + producer_type: SQL::Translator::Producer::YAML + show_warnings: 0 + trace: 0 + version: 1.66 diff --git a/share/migrations/_source/deploy/112/001-auto.yml b/share/migrations/_source/deploy/112/001-auto.yml new file mode 100644 index 000000000..b25cd6cb8 --- /dev/null +++ b/share/migrations/_source/deploy/112/001-auto.yml @@ -0,0 +1,10027 @@ +--- +schema: + procedures: {} + tables: + alert: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: alert_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: alert_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + frequency: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: frequency + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 3 + size: + - 0 + view_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 2 + size: + - 0 + indices: + - fields: + - user_id + name: alert_idx_user_id + options: [] + type: NORMAL + - fields: + - view_id + name: alert_idx_view_id + options: [] + type: NORMAL + name: alert + options: [] + order: 1 + alert_cache: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - current_id + match_type: '' + name: alert_cache_fk_current_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: current + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: alert_cache_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: alert_cache_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: alert_cache_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + current_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: current_id + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 2 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 5 + size: + - 0 + view_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 3 + size: + - 0 + indices: + - fields: + - current_id + name: alert_cache_idx_current_id + options: [] + type: NORMAL + - fields: + - layout_id + name: alert_cache_idx_layout_id + options: [] + type: NORMAL + - fields: + - user_id + name: alert_cache_idx_user_id + options: [] + type: NORMAL + - fields: + - view_id + name: alert_cache_idx_view_id + options: [] + type: NORMAL + name: alert_cache + options: [] + order: 2 + alert_column: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: alert_column_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: alert_column_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 3 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 2 + size: + - 0 + indices: + - fields: + - instance_id + name: alert_column_idx_instance_id + options: [] + type: NORMAL + - fields: + - layout_id + name: alert_column_idx_layout_id + options: [] + type: NORMAL + name: alert_column + options: [] + order: 3 + alert_send: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + - alert_id + - current_id + - status + match_type: '' + name: alert_send_all + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - alert_id + match_type: '' + name: alert_send_fk_alert_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: alert + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - current_id + match_type: '' + name: alert_send_fk_current_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: current + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: alert_send_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + alert_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: alert_id + order: 3 + size: + - 0 + current_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: current_id + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: layout_id + order: 2 + size: + - 0 + status: + data_type: char + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: status + order: 5 + size: + - 7 + indices: + - fields: + - alert_id + name: alert_send_idx_alert_id + options: [] + type: NORMAL + - fields: + - current_id + name: alert_send_idx_current_id + options: [] + type: NORMAL + - fields: + - layout_id + name: alert_send_idx_layout_id + options: [] + type: NORMAL + name: alert_send + options: [] + order: 4 + audit: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: audit_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: audit_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: audit_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + datetime: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: datetime + order: 5 + size: + - 0 + description: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: description + order: 8 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 9 + size: + - 0 + method: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: method + order: 6 + size: + - 45 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 2 + size: + - 0 + type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: type + order: 4 + size: + - 45 + url: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: url + order: 7 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 3 + size: + - 0 + indices: + - fields: + - instance_id + name: audit_idx_instance_id + options: [] + type: NORMAL + - fields: + - site_id + name: audit_idx_site_id + options: [] + type: NORMAL + - fields: + - user_id + name: audit_idx_user_id + options: [] + type: NORMAL + - fields: + - datetime + name: audit_idx_datetime + options: [] + type: NORMAL + - fields: + - user_id + - instance_id + - datetime + name: audit_idx_user_instance_datetime + options: [] + type: NORMAL + name: audit + options: [] + order: 5 + authentication: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - saml2_relaystate + match_type: '' + name: authentication_ux_saml2_relaystate + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - saml2_unique_id + match_type: '' + name: authentication_ux_saml2_unique_id + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: authentication_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + fields: + cacert: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: cacert + order: 6 + size: + - 0 + enabled: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: enabled + order: 13 + size: + - 0 + error_messages: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: error_messages + order: 16 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 4 + size: + - 0 + saml2_firstname: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: saml2_firstname + order: 9 + size: + - 0 + saml2_groupname: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: saml2_groupname + order: 11 + size: + - 0 + saml2_nameid: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: saml2_nameid + order: 15 + size: + - 30 + saml2_relaystate: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: saml2_relaystate + order: 12 + size: + - 80 + saml2_surname: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: saml2_surname + order: 10 + size: + - 0 + saml2_unique_id: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: saml2_unique_id + order: 14 + size: + - 80 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 2 + size: + - 0 + sp_cert: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: sp_cert + order: 7 + size: + - 0 + sp_key: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: sp_key + order: 8 + size: + - 0 + type: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: type + order: 3 + size: + - 0 + xml: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: xml + order: 5 + size: + - 0 + indices: + - fields: + - site_id + name: authentication_idx_site_id + options: [] + type: NORMAL + name: authentication + options: [] + order: 6 + calc: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: calc_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + calc: + data_type: mediumtext + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: calc + order: 3 + size: + - 0 + code: + data_type: mediumtext + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: code + order: 4 + size: + - 0 + decimal_places: + data_type: smallint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: decimal_places + order: 6 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 2 + size: + - 0 + return_format: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: return_format + order: 5 + size: + - 45 + indices: + - fields: + - layout_id + name: calc_idx_layout_id + options: [] + type: NORMAL + name: calc + options: [] + order: 7 + calc_unique: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + - value_date + match_type: '' + name: calc_unique_ux_layout_date + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - layout_id + - value_date_from + - value_date_to + match_type: '' + name: calc_unique_ux_layout_daterange + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - layout_id + - value_int + match_type: '' + name: calc_unique_ux_layout_int + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - layout_id + - value_numeric + match_type: '' + name: calc_unique_ux_layout_numeric + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - layout_id + - value_text + match_type: '' + name: calc_unique_ux_layout_text + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: calc_unique_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: layout_id + order: 2 + size: + - 0 + value_date: + data_type: date + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: value_date + order: 5 + size: + - 0 + value_date_from: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: value_date_from + order: 7 + size: + - 0 + value_date_to: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: value_date_to + order: 8 + size: + - 0 + value_int: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: value_int + order: 4 + size: + - 0 + value_numeric: + data_type: decimal + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: value_numeric + order: 6 + size: + - 20 + - 5 + value_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: value_text + order: 3 + size: + - 0 + indices: + - fields: + - layout_id + name: calc_unique_idx_layout_id + options: [] + type: NORMAL + name: calc_unique + options: [] + order: 8 + calcval: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: calcval_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: calcval_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: calcval_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + fields: + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 10 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 11 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value_date: + data_type: date + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value_date + order: 6 + size: + - 0 + value_date_from: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value_date_from + order: 8 + size: + - 0 + value_date_to: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value_date_to + order: 9 + size: + - 0 + value_int: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value_int + order: 5 + size: + - 0 + value_numeric: + data_type: decimal + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value_numeric + order: 7 + size: + - 20 + - 5 + value_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value_text + order: 4 + size: + - 0 + indices: + - fields: + - layout_id + name: calcval_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: calcval_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: calcval_idx_record_id + options: [] + type: NORMAL + - fields: + - name: value_text + prefix_length: 64 + name: calcval_idx_value_text + options: [] + type: NORMAL + - fields: + - value_numeric + name: calcval_idx_value_numeric + options: [] + type: NORMAL + - fields: + - value_int + name: calcval_idx_value_int + options: [] + type: NORMAL + - fields: + - value_date + name: calcval_idx_value_date + options: [] + type: NORMAL + name: calcval + options: [] + order: 9 + current: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + - serial + match_type: '' + name: current_ux_instance_serial + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - current_version_id + match_type: '' + name: current_fk_current_version_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - deletedby + match_type: '' + name: current_fk_deletedby + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - draftuser_id + match_type: '' + name: current_fk_draftuser_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: current_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - linked_id + match_type: '' + name: current_fk_linked_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: current + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - parent_id + match_type: '' + name: current_fk_parent_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: current + type: FOREIGN KEY + fields: + current_version_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: current_version_id + order: 3 + size: + - 0 + deleted: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 7 + size: + - 0 + deletedby: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: deletedby + order: 8 + size: + - 0 + draftuser_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: draftuser_id + order: 9 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: instance_id + order: 5 + size: + - 0 + linked_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: linked_id + order: 6 + size: + - 0 + parent_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: parent_id + order: 4 + size: + - 0 + serial: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: serial + order: 2 + size: + - 0 + indices: + - fields: + - current_version_id + name: current_idx_current_version_id + options: [] + type: NORMAL + - fields: + - deletedby + name: current_idx_deletedby + options: [] + type: NORMAL + - fields: + - draftuser_id + name: current_idx_draftuser_id + options: [] + type: NORMAL + - fields: + - instance_id + name: current_idx_instance_id + options: [] + type: NORMAL + - fields: + - linked_id + name: current_idx_linked_id + options: [] + type: NORMAL + - fields: + - parent_id + name: current_idx_parent_id + options: [] + type: NORMAL + name: current + options: [] + order: 10 + curval: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: curval_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: curval_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: curval_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - value + match_type: '' + name: curval_fk_value + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: current + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 6 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 7 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 5 + size: + - 0 + indices: + - fields: + - layout_id + name: curval_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: curval_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: curval_idx_record_id + options: [] + type: NORMAL + - fields: + - value + name: curval_idx_value + options: [] + type: NORMAL + name: curval + options: [] + order: 11 + curval_fields: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - child_id + match_type: '' + name: curval_fields_fk_child_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - parent_id + match_type: '' + name: curval_fields_fk_parent_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + child_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_id + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + parent_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: parent_id + order: 2 + size: + - 0 + indices: + - fields: + - child_id + name: curval_fields_idx_child_id + options: [] + type: NORMAL + - fields: + - parent_id + name: curval_fields_idx_parent_id + options: [] + type: NORMAL + name: curval_fields + options: [] + order: 12 + dashboard: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: dashboard_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: dashboard_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: dashboard_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 3 + size: + - 0 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 2 + size: + - 0 + user_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 4 + size: + - 0 + indices: + - fields: + - instance_id + name: dashboard_idx_instance_id + options: [] + type: NORMAL + - fields: + - site_id + name: dashboard_idx_site_id + options: [] + type: NORMAL + - fields: + - user_id + name: dashboard_idx_user_id + options: [] + type: NORMAL + name: dashboard + options: [] + order: 13 + date: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: date_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: date_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: date_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 6 + size: + - 0 + purged_on: + data_type: timestamp + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 7 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value: + data_type: date + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 5 + size: + - 0 + indices: + - fields: + - layout_id + name: date_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: date_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: date_idx_record_id + options: [] + type: NORMAL + - fields: + - value + name: date_idx_value + options: [] + type: NORMAL + name: date + options: [] + order: 14 + daterange: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: daterange_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: daterange_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: daterange_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 6 + size: + - 0 + from: + data_type: date + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: from + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 8 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 9 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + to: + data_type: date + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: to + order: 5 + size: + - 0 + value: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 7 + size: + - 45 + indices: + - fields: + - layout_id + name: daterange_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: daterange_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: daterange_idx_record_id + options: [] + type: NORMAL + - fields: + - from + name: daterange_idx_from + options: [] + type: NORMAL + - fields: + - to + name: daterange_idx_to + options: [] + type: NORMAL + - fields: + - value + name: daterange_idx_value + options: [] + type: NORMAL + name: daterange + options: [] + order: 15 + department: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: department_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + fields: + deleted: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 128 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 3 + size: + - 0 + indices: + - fields: + - site_id + name: department_idx_site_id + options: [] + type: NORMAL + name: department + options: [] + order: 16 + display_field: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - display_field_id + match_type: '' + name: display_field_fk_display_field_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: display_field_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + display_field_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: display_field_id + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 2 + size: + - 0 + operator: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: operator + order: 5 + size: + - 16 + regex: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: regex + order: 4 + size: + - 0 + indices: + - fields: + - display_field_id + name: display_field_idx_display_field_id + options: [] + type: NORMAL + - fields: + - layout_id + name: display_field_idx_layout_id + options: [] + type: NORMAL + name: display_field + options: [] + order: 17 + enum: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: enum_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: enum_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: enum_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - value + match_type: '' + name: enum_fk_value + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: enumval + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 6 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 7 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 5 + size: + - 0 + indices: + - fields: + - layout_id + name: enum_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: enum_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: enum_idx_record_id + options: [] + type: NORMAL + - fields: + - value + name: enum_idx_value + options: [] + type: NORMAL + name: enum + options: [] + order: 18 + enumval: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: enumval_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - parent + match_type: '' + name: enumval_fk_parent + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: enumval + type: FOREIGN KEY + fields: + deleted: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + parent: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: parent + order: 5 + size: + - 0 + position: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: position + order: 6 + size: + - 0 + value: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 2 + size: + - 0 + indices: + - fields: + - layout_id + name: enumval_idx_layout_id + options: [] + type: NORMAL + - fields: + - parent + name: enumval_idx_parent + options: [] + type: NORMAL + - fields: + - name: value + prefix_length: 64 + name: enumval_idx_value + options: [] + type: NORMAL + name: enumval + options: [] + order: 19 + export: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: export_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: export_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + completed: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: completed + order: 6 + size: + - 0 + content: + data_type: longblob + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: content + order: 10 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + mimetype: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mimetype + order: 9 + size: + - 0 + result: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: result + order: 7 + size: + - 0 + result_internal: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: result_internal + order: 8 + size: + - 0 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 2 + size: + - 0 + started: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: started + order: 5 + size: + - 0 + type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: type + order: 4 + size: + - 45 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 3 + size: + - 0 + indices: + - fields: + - site_id + name: export_idx_site_id + options: [] + type: NORMAL + - fields: + - user_id + name: export_idx_user_id + options: [] + type: NORMAL + name: export + options: [] + order: 20 + file: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: file_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: file_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: file_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - value + match_type: '' + name: file_fk_value + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: fileval + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 6 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 7 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 5 + size: + - 0 + indices: + - fields: + - layout_id + name: file_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: file_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: file_idx_record_id + options: [] + type: NORMAL + - fields: + - value + name: file_idx_value + options: [] + type: NORMAL + name: file + options: [] + order: 21 + file_option: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: file_option_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + filesize: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: filesize + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 2 + size: + - 0 + indices: + - fields: + - layout_id + name: file_option_idx_layout_id + options: [] + type: NORMAL + name: file_option + options: [] + order: 22 + fileval: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - edit_user_id + match_type: '' + name: fileval_fk_edit_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + edit_user_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: edit_user_id + order: 5 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + is_independent: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: is_independent + order: 4 + size: + - 0 + mimetype: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mimetype + order: 3 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 0 + indices: + - fields: + - edit_user_id + name: fileval_idx_edit_user_id + options: [] + type: NORMAL + - fields: + - name: name + prefix_length: 64 + name: fileval_idx_name + options: [] + type: NORMAL + name: fileval + options: [] + order: 23 + filter: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: filter_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: filter_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + view_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 2 + size: + - 0 + indices: + - fields: + - layout_id + name: filter_idx_layout_id + options: [] + type: NORMAL + - fields: + - view_id + name: filter_idx_view_id + options: [] + type: NORMAL + name: filter + options: [] + order: 24 + filtered_value: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - submission_id + - layout_id + - current_id + match_type: '' + name: ux_submission_layout_current + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - current_id + match_type: '' + name: filtered_value_fk_current_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: current + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: filtered_value_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - submission_id + match_type: '' + name: filtered_value_fk_submission_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: submission + type: FOREIGN KEY + fields: + current_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: current_id + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: layout_id + order: 3 + size: + - 0 + submission_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: submission_id + order: 2 + size: + - 0 + indices: + - fields: + - current_id + name: filtered_value_idx_current_id + options: [] + type: NORMAL + - fields: + - layout_id + name: filtered_value_idx_layout_id + options: [] + type: NORMAL + - fields: + - submission_id + name: filtered_value_idx_submission_id + options: [] + type: NORMAL + name: filtered_value + options: [] + order: 25 + graph: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - group_id + match_type: '' + name: graph_fk_group_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: group + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - group_by + match_type: '' + name: graph_fk_group_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: graph_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - metric_group + match_type: '' + name: graph_fk_metric_group + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: metric_group + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: graph_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - x_axis + match_type: '' + name: graph_fk_x_axis + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - x_axis_link + match_type: '' + name: graph_fk_x_axis_link + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - y_axis + match_type: '' + name: graph_fk_y_axis + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - y_axis_link + match_type: '' + name: graph_fk_y_axis_link + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + as_percent: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: as_percent + order: 13 + size: + - 0 + description: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: description + order: 3 + size: + - 0 + from: + data_type: date + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: from + order: 21 + size: + - 0 + group_by: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: group_by + order: 11 + size: + - 0 + group_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: group_id + order: 19 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 16 + size: + - 0 + is_shared: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: is_shared + order: 17 + size: + - 0 + metric_group: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: metric_group + order: 15 + size: + - 0 + stackseries: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: stackseries + order: 12 + size: + - 0 + title: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: title + order: 2 + size: + - 0 + to: + data_type: date + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: to + order: 22 + size: + - 0 + trend: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: trend + order: 20 + size: + - 45 + type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: type + order: 14 + size: + - 45 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 18 + size: + - 0 + x_axis: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: x_axis + order: 8 + size: + - 0 + x_axis_grouping: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: x_axis_grouping + order: 10 + size: + - 45 + x_axis_link: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: x_axis_link + order: 9 + size: + - 0 + x_axis_range: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: x_axis_range + order: 23 + size: + - 45 + y_axis: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: y_axis + order: 4 + size: + - 0 + y_axis_label: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: y_axis_label + order: 7 + size: + - 0 + y_axis_link: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: y_axis_link + order: 5 + size: + - 0 + y_axis_stack: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: y_axis_stack + order: 6 + size: + - 45 + indices: + - fields: + - group_id + name: graph_idx_group_id + options: [] + type: NORMAL + - fields: + - group_by + name: graph_idx_group_by + options: [] + type: NORMAL + - fields: + - instance_id + name: graph_idx_instance_id + options: [] + type: NORMAL + - fields: + - metric_group + name: graph_idx_metric_group + options: [] + type: NORMAL + - fields: + - user_id + name: graph_idx_user_id + options: [] + type: NORMAL + - fields: + - x_axis + name: graph_idx_x_axis + options: [] + type: NORMAL + - fields: + - x_axis_link + name: graph_idx_x_axis_link + options: [] + type: NORMAL + - fields: + - y_axis + name: graph_idx_y_axis + options: [] + type: NORMAL + - fields: + - y_axis_link + name: graph_idx_y_axis_link + options: [] + type: NORMAL + name: graph + options: [] + order: 26 + graph_color: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - name + match_type: '' + name: ux_graph_color_name + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + fields: + color: + data_type: char + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: color + order: 3 + size: + - 6 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: name + order: 2 + size: + - 128 + indices: [] + name: graph_color + options: [] + order: 27 + group: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: group_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + fields: + default_approve_existing: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: default_approve_existing + order: 7 + size: + - 0 + default_approve_new: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: default_approve_new + order: 6 + size: + - 0 + default_read: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: default_read + order: 3 + size: + - 0 + default_write_existing: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: default_write_existing + order: 5 + size: + - 0 + default_write_existing_no_approval: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: default_write_existing_no_approval + order: 9 + size: + - 0 + default_write_new: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: default_write_new + order: 4 + size: + - 0 + default_write_new_no_approval: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: default_write_new_no_approval + order: 8 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 128 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 10 + size: + - 0 + indices: + - fields: + - site_id + name: group_idx_site_id + options: [] + type: NORMAL + name: group + options: [] + order: 28 + import: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: import_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: import_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: import_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + completed: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: completed + order: 8 + size: + - 0 + error_count: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: error_count + order: 10 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 3 + size: + - 0 + result: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: result + order: 12 + size: + - 0 + row_count: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: row_count + order: 6 + size: + - 0 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 2 + size: + - 0 + skipped_count: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: skipped_count + order: 11 + size: + - 0 + started: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: started + order: 7 + size: + - 0 + type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: type + order: 5 + size: + - 45 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 4 + size: + - 0 + written_count: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: written_count + order: 9 + size: + - 0 + indices: + - fields: + - instance_id + name: import_idx_instance_id + options: [] + type: NORMAL + - fields: + - site_id + name: import_idx_site_id + options: [] + type: NORMAL + - fields: + - user_id + name: import_idx_user_id + options: [] + type: NORMAL + name: import + options: [] + order: 29 + import_row: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - import_id + match_type: '' + name: import_row_fk_import_id + on_delete: CASCADE + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: import + type: FOREIGN KEY + fields: + changes: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: changes + order: 6 + size: + - 0 + content: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: content + order: 4 + size: + - 0 + errors: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: errors + order: 5 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + import_id: + data_type: int + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: import_id + order: 2 + size: + - 0 + status: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: status + order: 3 + size: + - 45 + indices: + - fields: + - import_id + name: import_row_idx_import_id + options: [] + type: NORMAL + name: import_row + options: [] + order: 30 + instance: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - api_index_layout_id + match_type: '' + name: instance_fk_api_index_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - default_view_limit_extra_id + match_type: '' + name: instance_fk_default_view_limit_extra_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: instance_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - sort_layout_id + match_type: '' + name: instance_fk_sort_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_limit_id + match_type: '' + name: instance_fk_view_limit_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + api_index_layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: api_index_layout_id + order: 14 + size: + - 0 + default_view_limit_extra_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: default_view_limit_extra_id + order: 8 + size: + - 0 + forget_history: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: forget_history + order: 12 + size: + - 0 + forward_record_after_create: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: forward_record_after_create + order: 15 + size: + - 0 + hide_in_selector: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: hide_in_selector + order: 19 + size: + - 0 + homepage_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: homepage_text + order: 9 + size: + - 0 + homepage_text2: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: homepage_text2 + order: 10 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 0 + name_short: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name_short + order: 3 + size: + - 64 + no_copy_record: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: no_copy_record + order: 18 + size: + - 0 + no_download_pdf: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: no_download_pdf + order: 17 + size: + - 0 + no_hide_blank: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: no_hide_blank + order: 16 + size: + - 0 + no_overnight_update: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: no_overnight_update + order: 13 + size: + - 0 + record_name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: record_name + order: 11 + size: + - 0 + security_marking: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: security_marking + order: 20 + size: + - 0 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 4 + size: + - 0 + sort_layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: sort_layout_id + order: 5 + size: + - 0 + sort_type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: sort_type + order: 6 + size: + - 45 + view_limit_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: view_limit_id + order: 7 + size: + - 0 + indices: + - fields: + - api_index_layout_id + name: instance_idx_api_index_layout_id + options: [] + type: NORMAL + - fields: + - default_view_limit_extra_id + name: instance_idx_default_view_limit_extra_id + options: [] + type: NORMAL + - fields: + - site_id + name: instance_idx_site_id + options: [] + type: NORMAL + - fields: + - sort_layout_id + name: instance_idx_sort_layout_id + options: [] + type: NORMAL + - fields: + - view_limit_id + name: instance_idx_view_limit_id + options: [] + type: NORMAL + name: instance + options: [] + order: 31 + instance_group: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + - group_id + - permission + match_type: '' + name: instance_group_ux_instance_group_permission + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - group_id + match_type: '' + name: instance_group_fk_group_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: group + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: instance_group_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + fields: + group_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: group_id + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: instance_id + order: 2 + size: + - 0 + permission: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: permission + order: 4 + size: + - 45 + indices: + - fields: + - group_id + name: instance_group_idx_group_id + options: [] + type: NORMAL + - fields: + - instance_id + name: instance_group_idx_instance_id + options: [] + type: NORMAL + name: instance_group + options: [] + order: 32 + instance_rag: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + - rag + match_type: '' + name: instance_rag_ux_instance_rag + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: instance_rag_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + fields: + description: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: description + order: 5 + size: + - 0 + enabled: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: enabled + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: instance_id + order: 2 + size: + - 0 + rag: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: rag + order: 3 + size: + - 16 + indices: + - fields: + - instance_id + name: instance_rag_idx_instance_id + options: [] + type: NORMAL + name: instance_rag + options: [] + order: 33 + intgr: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: intgr_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: intgr_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: intgr_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 6 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 7 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 5 + size: + - 0 + indices: + - fields: + - layout_id + name: intgr_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: intgr_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: intgr_idx_record_id + options: [] + type: NORMAL + - fields: + - value + name: intgr_idx_value + options: [] + type: NORMAL + name: intgr + options: [] + order: 34 + layout: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + - name_short + match_type: '' + name: layout_ux_instance_name_short + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - display_field + match_type: '' + name: layout_fk_display_field + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: layout_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - link_parent + match_type: '' + name: layout_fk_link_parent + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - related_field + match_type: '' + name: layout_fk_related_field + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - topic_id + match_type: '' + name: layout_fk_topic_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: topic + type: FOREIGN KEY + fields: + aggregate: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: aggregate + order: 31 + size: + - 45 + can_child: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: can_child + order: 16 + size: + - 0 + description: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: description + order: 18 + size: + - 0 + display_condition: + data_type: char + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: display_condition + order: 23 + size: + - 3 + display_field: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: display_field + order: 21 + size: + - 0 + display_matchtype: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: display_matchtype + order: 24 + size: + - 0 + display_regex: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: display_regex + order: 22 + size: + - 0 + end_node_only: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: end_node_only + order: 14 + size: + - 0 + filter: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: filter + order: 29 + size: + - 0 + force_regex: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: force_regex + order: 11 + size: + - 0 + group_display: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: group_display + order: 32 + size: + - 45 + helptext: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: helptext + order: 19 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: instance_id + order: 25 + size: + - 0 + internal: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: internal + order: 17 + size: + - 0 + isunique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: isunique + order: 8 + size: + - 0 + link_parent: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: link_parent + order: 26 + size: + - 0 + lookup_endpoint: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: lookup_endpoint + order: 33 + size: + - 0 + lookup_group: + data_type: smallint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: lookup_group + order: 34 + size: + - 0 + multivalue: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: multivalue + order: 15 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 0 + name_short: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: name_short + order: 3 + size: + - 64 + notes: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: notes + order: 35 + size: + - 0 + optional: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: optional + order: 6 + size: + - 0 + options: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: options + order: 20 + size: + - 0 + ordering: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: ordering + order: 13 + size: + - 45 + permission: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: permission + order: 5 + size: + - 0 + position: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: position + order: 12 + size: + - 0 + related_field: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: related_field + order: 27 + size: + - 0 + remember: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: remember + order: 7 + size: + - 0 + textbox: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: textbox + order: 9 + size: + - 0 + topic_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: topic_id + order: 30 + size: + - 0 + type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: type + order: 4 + size: + - 45 + typeahead: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: typeahead + order: 10 + size: + - 0 + width: + data_type: integer + default_value: 50 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: width + order: 28 + size: + - 0 + indices: + - fields: + - display_field + name: layout_idx_display_field + options: [] + type: NORMAL + - fields: + - instance_id + name: layout_idx_instance_id + options: [] + type: NORMAL + - fields: + - link_parent + name: layout_idx_link_parent + options: [] + type: NORMAL + - fields: + - related_field + name: layout_idx_related_field + options: [] + type: NORMAL + - fields: + - topic_id + name: layout_idx_topic_id + options: [] + type: NORMAL + name: layout + options: [] + order: 35 + layout_depend: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - depends_on + match_type: '' + name: layout_depend_fk_depends_on + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: layout_depend_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + depends_on: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: depends_on + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 2 + size: + - 0 + indices: + - fields: + - depends_on + name: layout_depend_idx_depends_on + options: [] + type: NORMAL + - fields: + - layout_id + name: layout_depend_idx_layout_id + options: [] + type: NORMAL + name: layout_depend + options: [] + order: 36 + layout_group: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + - group_id + - permission + match_type: '' + name: layout_group_ux_layout_group_permission + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - group_id + match_type: '' + name: layout_group_fk_group_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: group + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: layout_group_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + group_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: group_id + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: layout_id + order: 2 + size: + - 0 + permission: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: permission + order: 4 + size: + - 45 + indices: + - fields: + - group_id + name: layout_group_idx_group_id + options: [] + type: NORMAL + - fields: + - layout_id + name: layout_group_idx_layout_id + options: [] + type: NORMAL + - fields: + - permission + name: layout_group_idx_permission + options: [] + type: NORMAL + name: layout_group + options: [] + order: 37 + metric: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - metric_group + match_type: '' + name: metric_fk_metric_group + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: metric_group + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + metric_group: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: metric_group + order: 2 + size: + - 0 + target: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: target + order: 4 + size: + - 0 + x_axis_value: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: x_axis_value + order: 3 + size: + - 0 + y_axis_grouping_value: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: y_axis_grouping_value + order: 5 + size: + - 0 + indices: + - fields: + - metric_group + name: metric_idx_metric_group + options: [] + type: NORMAL + name: metric + options: [] + order: 38 + metric_group: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: metric_group_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 3 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 0 + indices: + - fields: + - instance_id + name: metric_group_idx_instance_id + options: [] + type: NORMAL + name: metric_group + options: [] + order: 39 + oauthclient: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + fields: + client_id: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: client_id + order: 2 + size: + - 64 + client_secret: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: client_secret + order: 3 + size: + - 64 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + indices: [] + name: oauthclient + options: [] + order: 40 + oauthtoken: + constraints: + - deferrable: 1 + expression: '' + fields: + - token + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - oauthclient_id + match_type: '' + name: oauthtoken_fk_oauthclient_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: oauthclient + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: oauthtoken_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + expires: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: expires + order: 6 + size: + - 0 + oauthclient_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: oauthclient_id + order: 3 + size: + - 0 + related_token: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: related_token + order: 2 + size: + - 128 + token: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: token + order: 1 + size: + - 128 + type: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: type + order: 5 + size: + - 12 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 4 + size: + - 0 + indices: + - fields: + - oauthclient_id + name: oauthtoken_idx_oauthclient_id + options: [] + type: NORMAL + - fields: + - user_id + name: oauthtoken_idx_user_id + options: [] + type: NORMAL + name: oauthtoken + options: [] + order: 41 + organisation: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: organisation_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + fields: + deleted: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 128 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 3 + size: + - 0 + indices: + - fields: + - site_id + name: organisation_idx_site_id + options: [] + type: NORMAL + name: organisation + options: [] + order: 42 + permission: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + fields: + description: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: description + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 128 + order: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: order + order: 4 + size: + - 0 + indices: [] + name: permission + options: [] + order: 43 + person: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: person_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: person_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: person_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - value + match_type: '' + name: person_fk_value + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 6 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 7 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 5 + size: + - 0 + indices: + - fields: + - layout_id + name: person_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: person_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: person_idx_record_id + options: [] + type: NORMAL + - fields: + - value + name: person_idx_value + options: [] + type: NORMAL + name: person + options: [] + order: 44 + rag: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: rag_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + fields: + amber: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: amber + order: 4 + size: + - 0 + code: + data_type: mediumtext + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: code + order: 6 + size: + - 0 + green: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: green + order: 5 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 2 + size: + - 0 + red: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: red + order: 3 + size: + - 0 + indices: + - fields: + - layout_id + name: rag_idx_layout_id + options: [] + type: NORMAL + name: rag + options: [] + order: 45 + ragval: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - record_id + - layout_id + match_type: '' + name: ragval_ux_record_layout + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: ragval_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: ragval_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: ragval_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + fields: + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 5 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 6 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: record_id + order: 2 + size: + - 0 + value: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 4 + size: + - 16 + indices: + - fields: + - layout_id + name: ragval_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: ragval_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: ragval_idx_record_id + options: [] + type: NORMAL + - fields: + - value + name: ragval_idx_value + options: [] + type: NORMAL + name: ragval + options: [] + order: 46 + record: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - approvedby + match_type: '' + name: record_fk_approvedby + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - createdby + match_type: '' + name: record_fk_createdby + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - current_id + match_type: '' + name: record_fk_current_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: current + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: record_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + fields: + approval: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: approval + order: 7 + size: + - 0 + approvedby: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: approvedby + order: 5 + size: + - 0 + created: + data_type: datetime + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: created + order: 2 + size: + - 0 + createdby: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: createdby + order: 4 + size: + - 0 + current_id: + data_type: bigint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: current_id + order: 3 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 6 + size: + - 0 + indices: + - fields: + - approvedby + name: record_idx_approvedby + options: [] + type: NORMAL + - fields: + - createdby + name: record_idx_createdby + options: [] + type: NORMAL + - fields: + - current_id + name: record_idx_current_id + options: [] + type: NORMAL + - fields: + - record_id + name: record_idx_record_id + options: [] + type: NORMAL + - fields: + - approval + name: record_idx_approval + options: [] + type: NORMAL + name: record + options: [] + order: 47 + report: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - createdby + match_type: '' + name: report_fk_createdby + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: report_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: report_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + created: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: created + order: 7 + size: + - 0 + createdby: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: createdby + order: 6 + size: + - 0 + deleted: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 9 + size: + - 0 + description: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: description + order: 4 + size: + - 128 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 8 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 128 + security_marking: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: security_marking + order: 10 + size: + - 0 + title: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: title + order: 3 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 5 + size: + - 0 + indices: + - fields: + - createdby + name: report_idx_createdby + options: [] + type: NORMAL + - fields: + - instance_id + name: report_idx_instance_id + options: [] + type: NORMAL + - fields: + - user_id + name: report_idx_user_id + options: [] + type: NORMAL + name: report + options: [] + order: 48 + report_group: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - group_id + match_type: '' + name: report_group_fk_group_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: group + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - report_id + match_type: '' + name: report_group_fk_report_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: report + type: FOREIGN KEY + fields: + group_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: group_id + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + report_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: report_id + order: 2 + size: + - 0 + indices: + - fields: + - group_id + name: report_group_idx_group_id + options: [] + type: NORMAL + - fields: + - report_id + name: report_group_idx_report_id + options: [] + type: NORMAL + name: report_group + options: [] + order: 49 + report_layout: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: report_layout_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - report_id + match_type: '' + name: report_layout_fk_report_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: report + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + order: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: order + order: 4 + size: + - 0 + report_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: report_id + order: 2 + size: + - 0 + indices: + - fields: + - layout_id + name: report_layout_idx_layout_id + options: [] + type: NORMAL + - fields: + - report_id + name: report_layout_idx_report_id + options: [] + type: NORMAL + name: report_layout + options: [] + order: 50 + site: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + fields: + account_request_notes_name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: account_request_notes_name + order: 40 + size: + - 0 + account_request_notes_placeholder: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: account_request_notes_placeholder + order: 41 + size: + - 0 + created: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: created + order: 4 + size: + - 0 + email_delete_subject: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: email_delete_subject + order: 8 + size: + - 0 + email_delete_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: email_delete_text + order: 7 + size: + - 0 + email_reject_subject: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: email_reject_subject + order: 10 + size: + - 0 + email_reject_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: email_reject_text + order: 9 + size: + - 0 + email_welcome_subject: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: email_welcome_subject + order: 6 + size: + - 0 + email_welcome_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: email_welcome_text + order: 5 + size: + - 0 + force_mfa: + data_type: char + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: force_mfa + order: 44 + size: + - 3 + hide_account_request: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: hide_account_request + order: 35 + size: + - 0 + homepage_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: homepage_text + order: 12 + size: + - 0 + homepage_text2: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: homepage_text2 + order: 13 + size: + - 0 + host: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: host + order: 2 + size: + - 128 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 3 + size: + - 0 + register_department_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_department_help + order: 21 + size: + - 0 + register_department_mandatory: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_department_mandatory + order: 23 + size: + - 0 + register_department_name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_department_name + order: 22 + size: + - 0 + register_email_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_email_help + order: 17 + size: + - 0 + register_freetext1_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_freetext1_help + order: 15 + size: + - 0 + register_freetext1_name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_freetext1_name + order: 28 + size: + - 0 + register_freetext1_placeholder: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_freetext1_placeholder + order: 38 + size: + - 0 + register_freetext2_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_freetext2_help + order: 16 + size: + - 0 + register_freetext2_name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_freetext2_name + order: 29 + size: + - 0 + register_freetext2_placeholder: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_freetext2_placeholder + order: 39 + size: + - 0 + register_notes_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_notes_help + order: 27 + size: + - 0 + register_organisation_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_organisation_help + order: 18 + size: + - 0 + register_organisation_mandatory: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_organisation_mandatory + order: 20 + size: + - 0 + register_organisation_name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_organisation_name + order: 19 + size: + - 0 + register_show_department: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_show_department + order: 31 + size: + - 0 + register_show_organisation: + data_type: smallint + default_value: 1 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_show_organisation + order: 30 + size: + - 0 + register_show_provider: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_show_provider + order: 34 + size: + - 0 + register_show_team: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_show_team + order: 32 + size: + - 0 + register_show_title: + data_type: smallint + default_value: 1 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_show_title + order: 33 + size: + - 0 + register_team_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_team_help + order: 24 + size: + - 0 + register_team_mandatory: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: register_team_mandatory + order: 26 + size: + - 0 + register_team_name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_team_name + order: 25 + size: + - 0 + register_text: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_text + order: 11 + size: + - 0 + register_title_help: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: register_title_help + order: 14 + size: + - 0 + remember_user_location: + data_type: smallint + default_value: 1 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: remember_user_location + order: 36 + size: + - 0 + security_marking: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: security_marking + order: 42 + size: + - 0 + site_logo: + data_type: longblob + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_logo + order: 43 + size: + - 0 + user_editable_fields: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: user_editable_fields + order: 37 + size: + - 0 + indices: [] + name: site + options: [] + order: 51 + sort: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: sort_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - parent_id + match_type: '' + name: sort_fk_parent_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: sort_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + order: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: order + order: 6 + size: + - 0 + parent_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: parent_id + order: 4 + size: + - 0 + type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: type + order: 5 + size: + - 45 + view_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 2 + size: + - 0 + indices: + - fields: + - layout_id + name: sort_idx_layout_id + options: [] + type: NORMAL + - fields: + - parent_id + name: sort_idx_parent_id + options: [] + type: NORMAL + - fields: + - view_id + name: sort_idx_view_id + options: [] + type: NORMAL + name: sort + options: [] + order: 52 + string: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: string_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - purged_by + match_type: '' + name: string_fk_purged_by + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: string_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + fields: + child_unique: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: child_unique + order: 4 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + purged_by: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_by + order: 7 + size: + - 0 + purged_on: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: purged_on + order: 8 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + value: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 5 + size: + - 0 + value_index: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value_index + order: 6 + size: + - 128 + indices: + - fields: + - layout_id + name: string_idx_layout_id + options: [] + type: NORMAL + - fields: + - purged_by + name: string_idx_purged_by + options: [] + type: NORMAL + - fields: + - record_id + name: string_idx_record_id + options: [] + type: NORMAL + - fields: + - value_index + name: string_idx_value_index + options: [] + type: NORMAL + name: string + options: [] + order: 53 + submission: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - token + - submitted + match_type: '' + name: ux_submission_token + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + fields: + created: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: created + order: 3 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + submitted: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: submitted + order: 4 + size: + - 0 + token: + data_type: varchar + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 1 + name: token + order: 2 + size: + - 64 + indices: [] + name: submission + options: [] + order: 54 + team: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: team_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + fields: + deleted: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 128 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 3 + size: + - 0 + indices: + - fields: + - site_id + name: team_idx_site_id + options: [] + type: NORMAL + name: team + options: [] + order: 55 + title: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: title_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + fields: + deleted: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 2 + size: + - 128 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 3 + size: + - 0 + indices: + - fields: + - site_id + name: title_idx_site_id + options: [] + type: NORMAL + name: title + options: [] + order: 56 + topic: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: topic_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - prevent_edit_topic_id + match_type: '' + name: topic_fk_prevent_edit_topic_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: topic + type: FOREIGN KEY + fields: + click_to_edit: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: click_to_edit + order: 6 + size: + - 0 + description: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: description + order: 4 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + initial_state: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: initial_state + order: 5 + size: + - 32 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 2 + size: + - 0 + name: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 3 + size: + - 0 + prevent_edit_topic_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: prevent_edit_topic_id + order: 7 + size: + - 0 + indices: + - fields: + - instance_id + name: topic_idx_instance_id + options: [] + type: NORMAL + - fields: + - prevent_edit_topic_id + name: topic_idx_prevent_edit_topic_id + options: [] + type: NORMAL + name: topic + options: [] + order: 57 + user: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - department_id + match_type: '' + name: user_fk_department_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: department + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - lastrecord + match_type: '' + name: user_fk_lastrecord + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - lastview + match_type: '' + name: user_fk_lastview + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - limit_to_view + match_type: '' + name: user_fk_limit_to_view + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - organisation + match_type: '' + name: user_fk_organisation + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: organisation + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - provider + match_type: '' + name: user_fk_provider + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: authentication + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - site_id + match_type: '' + name: user_fk_site_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: site + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - team_id + match_type: '' + name: user_fk_team_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: team + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - title + match_type: '' + name: user_fk_title + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: title + type: FOREIGN KEY + fields: + account_request: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: account_request + order: 24 + size: + - 0 + account_request_notes: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: account_request_notes + order: 25 + size: + - 0 + aup_accepted: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: aup_accepted + order: 26 + size: + - 0 + created: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: created + order: 29 + size: + - 0 + debug_login: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: debug_login + order: 30 + size: + - 0 + deleted: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: deleted + order: 16 + size: + - 0 + department_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: department_id + order: 9 + size: + - 0 + email: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: email + order: 5 + size: + - 0 + failcount: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: failcount + order: 19 + size: + - 0 + firstname: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: firstname + order: 3 + size: + - 128 + freetext1: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: freetext1 + order: 11 + size: + - 0 + freetext2: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: freetext2 + order: 12 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + lastfail: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: lastfail + order: 18 + size: + - 0 + lastlogin: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: lastlogin + order: 17 + size: + - 0 + lastrecord: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: lastrecord + order: 20 + size: + - 0 + lastview: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: lastview + order: 21 + size: + - 0 + limit_to_view: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: limit_to_view + order: 27 + size: + - 0 + mfa_failcount: + data_type: integer + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: mfa_failcount + order: 42 + size: + - 0 + mfa_lastfail: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_lastfail + order: 41 + size: + - 0 + mfa_secret: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_secret + order: 34 + size: + - 0 + mfa_sms_created: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_sms_created + order: 36 + size: + - 0 + mfa_sms_token: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_sms_token + order: 35 + size: + - 0 + mfa_token_previous: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_token_previous + order: 37 + size: + - 0 + mfa_token_previous_key: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_token_previous_key + order: 40 + size: + - 0 + mfa_token_previous_type: + data_type: char + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_token_previous_type + order: 38 + size: + - 3 + mfa_token_previous_used: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_token_previous_used + order: 39 + size: + - 0 + mfa_type: + data_type: char + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mfa_type + order: 31 + size: + - 3 + mobile: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: mobile + order: 32 + size: + - 0 + mobile_verified: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: mobile_verified + order: 33 + size: + - 0 + organisation: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: organisation + order: 8 + size: + - 0 + password: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: password + order: 13 + size: + - 128 + provider: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: provider + order: 43 + size: + - 0 + pwchanged: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: pwchanged + order: 14 + size: + - 0 + resetpw: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: resetpw + order: 15 + size: + - 32 + session_settings: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: session_settings + order: 22 + size: + - 0 + site_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: site_id + order: 2 + size: + - 0 + stylesheet: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: stylesheet + order: 28 + size: + - 0 + surname: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: surname + order: 4 + size: + - 128 + team_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: team_id + order: 10 + size: + - 0 + title: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: title + order: 7 + size: + - 0 + username: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: username + order: 6 + size: + - 0 + value: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: value + order: 23 + size: + - 0 + indices: + - fields: + - department_id + name: user_idx_department_id + options: [] + type: NORMAL + - fields: + - lastrecord + name: user_idx_lastrecord + options: [] + type: NORMAL + - fields: + - lastview + name: user_idx_lastview + options: [] + type: NORMAL + - fields: + - limit_to_view + name: user_idx_limit_to_view + options: [] + type: NORMAL + - fields: + - organisation + name: user_idx_organisation + options: [] + type: NORMAL + - fields: + - provider + name: user_idx_provider + options: [] + type: NORMAL + - fields: + - site_id + name: user_idx_site_id + options: [] + type: NORMAL + - fields: + - team_id + name: user_idx_team_id + options: [] + type: NORMAL + - fields: + - title + name: user_idx_title + options: [] + type: NORMAL + - fields: + - name: value + prefix_length: 64 + name: user_idx_value + options: [] + type: NORMAL + - fields: + - name: email + prefix_length: 64 + name: user_idx_email + options: [] + type: NORMAL + - fields: + - name: username + prefix_length: 64 + name: user_idx_username + options: [] + type: NORMAL + name: user + options: [] + order: 58 + user_graph: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - graph_id + match_type: '' + name: user_graph_fk_graph_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: graph + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: user_graph_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + graph_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: graph_id + order: 3 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 2 + size: + - 0 + indices: + - fields: + - graph_id + name: user_graph_idx_graph_id + options: [] + type: NORMAL + - fields: + - user_id + name: user_graph_idx_user_id + options: [] + type: NORMAL + name: user_graph + options: [] + order: 59 + user_group: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - group_id + match_type: '' + name: user_group_fk_group_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: group + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: user_group_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + group_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: group_id + order: 3 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 2 + size: + - 0 + indices: + - fields: + - group_id + name: user_group_idx_group_id + options: [] + type: NORMAL + - fields: + - user_id + name: user_group_idx_user_id + options: [] + type: NORMAL + name: user_group + options: [] + order: 60 + user_lastrecord: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: user_lastrecord_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - record_id + match_type: '' + name: user_lastrecord_fk_record_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: record + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: user_lastrecord_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 3 + size: + - 0 + record_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: record_id + order: 2 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 4 + size: + - 0 + indices: + - fields: + - instance_id + name: user_lastrecord_idx_instance_id + options: [] + type: NORMAL + - fields: + - record_id + name: user_lastrecord_idx_record_id + options: [] + type: NORMAL + - fields: + - user_id + name: user_lastrecord_idx_user_id + options: [] + type: NORMAL + name: user_lastrecord + options: [] + order: 61 + user_permission: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - permission_id + match_type: '' + name: user_permission_fk_permission_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: permission + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: user_permission_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + permission_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: permission_id + order: 3 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 2 + size: + - 0 + indices: + - fields: + - permission_id + name: user_permission_idx_permission_id + options: [] + type: NORMAL + - fields: + - user_id + name: user_permission_idx_user_id + options: [] + type: NORMAL + name: user_permission + options: [] + order: 62 + view: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - createdby + match_type: '' + name: view_fk_createdby + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - group_id + match_type: '' + name: view_fk_group_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: group + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - instance_id + match_type: '' + name: view_fk_instance_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: instance + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: view_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + fields: + created: + data_type: datetime + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: created + order: 10 + size: + - 0 + createdby: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: createdby + order: 11 + size: + - 0 + filter: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: filter + order: 8 + size: + - 0 + global: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: global + order: 5 + size: + - 0 + group_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: group_id + order: 3 + size: + - 0 + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + instance_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: instance_id + order: 9 + size: + - 0 + is_admin: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: is_admin + order: 6 + size: + - 0 + is_limit_extra: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: is_limit_extra + order: 7 + size: + - 0 + name: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: name + order: 4 + size: + - 128 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 2 + size: + - 0 + indices: + - fields: + - createdby + name: view_idx_createdby + options: [] + type: NORMAL + - fields: + - group_id + name: view_idx_group_id + options: [] + type: NORMAL + - fields: + - instance_id + name: view_idx_instance_id + options: [] + type: NORMAL + - fields: + - user_id + name: view_idx_user_id + options: [] + type: NORMAL + name: view + options: [] + order: 63 + view_group: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: view_group_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - parent_id + match_type: '' + name: view_group_fk_parent_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: view_group_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + order: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: order + order: 5 + size: + - 0 + parent_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: parent_id + order: 4 + size: + - 0 + view_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 2 + size: + - 0 + indices: + - fields: + - layout_id + name: view_group_idx_layout_id + options: [] + type: NORMAL + - fields: + - parent_id + name: view_group_idx_parent_id + options: [] + type: NORMAL + - fields: + - view_id + name: view_group_idx_view_id + options: [] + type: NORMAL + name: view_group + options: [] + order: 64 + view_layout: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - layout_id + match_type: '' + name: view_layout_fk_layout_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: layout + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: view_layout_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + layout_id: + data_type: integer + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: layout_id + order: 3 + size: + - 0 + order: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: order + order: 4 + size: + - 0 + view_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 2 + size: + - 0 + indices: + - fields: + - layout_id + name: view_layout_idx_layout_id + options: [] + type: NORMAL + - fields: + - view_id + name: view_layout_idx_view_id + options: [] + type: NORMAL + name: view_layout + options: [] + order: 65 + view_limit: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - user_id + match_type: '' + name: view_limit_fk_user_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: user + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: view_limit_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + id: + data_type: bigint + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + user_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: user_id + order: 3 + size: + - 0 + view_id: + data_type: bigint + default_value: ~ + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 2 + size: + - 0 + indices: + - fields: + - user_id + name: view_limit_idx_user_id + options: [] + type: NORMAL + - fields: + - view_id + name: view_limit_idx_view_id + options: [] + type: NORMAL + name: view_limit + options: [] + order: 66 + widget: + constraints: + - deferrable: 1 + expression: '' + fields: + - id + match_type: '' + name: '' + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: PRIMARY KEY + - deferrable: 1 + expression: '' + fields: + - dashboard_id + - grid_id + match_type: '' + name: widget_ux_dashboard_grid + on_delete: '' + on_update: '' + options: [] + reference_fields: [] + reference_table: '' + type: UNIQUE + - deferrable: 1 + expression: '' + fields: + - dashboard_id + match_type: '' + name: widget_fk_dashboard_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: dashboard + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - graph_id + match_type: '' + name: widget_fk_graph_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: graph + type: FOREIGN KEY + - deferrable: 1 + expression: '' + fields: + - view_id + match_type: '' + name: widget_fk_view_id + on_delete: NO ACTION + on_update: NO ACTION + options: [] + reference_fields: + - id + reference_table: view + type: FOREIGN KEY + fields: + content: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: content + order: 11 + size: + - 0 + dashboard_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: dashboard_id + order: 3 + size: + - 0 + globe_options: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: globe_options + order: 16 + size: + - 0 + graph_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: graph_id + order: 13 + size: + - 0 + grid_id: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 1 + name: grid_id + order: 2 + size: + - 64 + h: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: h + order: 7 + size: + - 0 + id: + data_type: integer + default_value: ~ + is_auto_increment: 1 + is_nullable: 0 + is_primary_key: 1 + is_unique: 0 + name: id + order: 1 + size: + - 0 + rows: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: rows + order: 14 + size: + - 0 + static: + data_type: smallint + default_value: 0 + is_nullable: 0 + is_primary_key: 0 + is_unique: 0 + name: static + order: 6 + size: + - 0 + title: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: title + order: 5 + size: + - 0 + tl_options: + data_type: text + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: tl_options + order: 15 + size: + - 0 + type: + data_type: varchar + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: type + order: 4 + size: + - 16 + view_id: + data_type: integer + default_value: ~ + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: view_id + order: 12 + size: + - 0 + w: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: w + order: 8 + size: + - 0 + x: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: x + order: 9 + size: + - 0 + y: + data_type: smallint + default_value: 0 + is_nullable: 1 + is_primary_key: 0 + is_unique: 0 + name: y + order: 10 + size: + - 0 + indices: + - fields: + - dashboard_id + name: widget_idx_dashboard_id + options: [] + type: NORMAL + - fields: + - graph_id + name: widget_idx_graph_id + options: [] + type: NORMAL + - fields: + - view_id + name: widget_idx_view_id + options: [] + type: NORMAL + name: widget + options: [] + order: 67 + triggers: {} + views: {} +translator: + add_drop_table: 0 + filename: ~ + no_comments: 0 + parser_args: + sources: + - Alert + - AlertCache + - AlertColumn + - AlertSend + - Audit + - Authentication + - Calc + - CalcUnique + - Calcval + - Changed + - Current + - Curval + - CurvalField + - Dashboard + - Date + - Daterange + - Department + - DisplayField + - Enum + - Enumval + - Export + - File + - FileOption + - Fileval + - Filter + - FilteredValue + - Graph + - GraphColor + - Group + - Import + - ImportRow + - Instance + - InstanceGroup + - InstanceRag + - Intgr + - Layout + - LayoutDepend + - LayoutGroup + - Metric + - MetricGroup + - Oauthclient + - Oauthtoken + - Organisation + - Permission + - Person + - Rag + - Ragval + - Record + - Report + - ReportGroup + - ReportLayout + - Site + - Sort + - String + - Submission + - Team + - Title + - Topic + - User + - UserGraph + - UserGroup + - UserLastrecord + - UserPermission + - View + - ViewGroup + - ViewLayout + - ViewLimit + - Widget + parser_type: SQL::Translator::Parser::DBIx::Class + producer_args: + mysql_version: 5.7 + producer_type: SQL::Translator::Producer::YAML + show_warnings: 0 + trace: 0 + version: 1.66 diff --git a/src/frontend/components/form-group/input/lib/fileComponent.ts b/src/frontend/components/form-group/input/lib/fileComponent.ts index 5a8af7d19..5d277d6e3 100644 --- a/src/frontend/components/form-group/input/lib/fileComponent.ts +++ b/src/frontend/components/form-group/input/lib/fileComponent.ts @@ -14,7 +14,7 @@ class FileComponent { constructor(el: HTMLElement | JQuery) { this.el = el instanceof HTMLElement ? $(el) : el; - this.fileInput = this.el.find('.form-control-file') as JQuery; + this.fileInput = this.el.find('.form-control-file'); this.fileName = this.el.find('.file__name'); this.fileDelete = this.el.find('.file__delete'); this.inputFileLabel = this.el.find('.input__file-label'); @@ -64,6 +64,7 @@ class FileComponent { }; changeFile = (ev: JQuery.ChangeEvent) => { + if(!ev.target.files || ev.target.files.length === 0) return; const [file] = ev.target.files!; const { name: fileName } = file; diff --git a/src/frontend/components/modal/modals/provider/index.js b/src/frontend/components/modal/modals/provider/index.js new file mode 100644 index 000000000..3d080cfc5 --- /dev/null +++ b/src/frontend/components/modal/modals/provider/index.js @@ -0,0 +1,4 @@ +import { initializeComponent } from 'component' +import ProviderModalComponent from './lib/component' + +export default (scope) => initializeComponent(scope, '.modal--provider', ProviderModalComponent) diff --git a/src/frontend/components/modal/modals/provider/lib/component.js b/src/frontend/components/modal/modals/provider/lib/component.js new file mode 100644 index 000000000..93e50170d --- /dev/null +++ b/src/frontend/components/modal/modals/provider/lib/component.js @@ -0,0 +1,100 @@ +import { modal } from '../../../lib/modal' +import ModalComponent from '../../../lib/component' + +class ProviderModalComponent extends ModalComponent { + constructor(element) { + super(element) + this.el = $(this.element) + this.providerField = this.el.find('input[name="name"]') + this.providerText = this.el.find('.js-provider') + this.data={}; + + this.initProviderModal() + } + + // Initialize the modal + initProviderModal() { + this.el.on('show.bs.modal', (ev) => { + this.toggleContent(ev) + modal.validate() + this.updateProvider() + this.providerField.on("keyup", () => { this.updateProvider() }) + }); + + $('input[type="file"]').on('change', (ev)=>{ + if(ev.target.files.length === 0) return; + const file = ev.originalEvent.target.files[0]; + const reader = new FileReader(); + reader.onload = (e) => { + const fileContent = e.target.result; + this.data[ev.target.name] = fileContent; // Store the file content in data + console.log(`File ${ev.target.name} loaded:`, fileContent); + }; + reader.readAsText(file); // Read the file as a Data URL + }); + } + + // Toggle the right content (add user or approve account) + toggleContent(ev) { + if ($(ev.relatedTarget).hasClass('btn-add')) { + modal.clear() + this.el.find('.js-add-provider').show() + this.el.find('.btn-js-save .btn__title').html('Create provider') + } else { + this.el.find('.js-add-provider').hide() + } + } + + // Update the text container for the provider address + updateProvider() { + this.providerText.html(this.providerField.val()) + } + + // Get all data from all fields in the modal + getData() { + const data = { + ...this.data, + } + + this.el.find('input, textarea').each((i, field) => { + if($(field).prop('type')==='file') return; + if (($(field).prop('type') === 'radio' || $(field).prop('type') === 'checkbox')) { + if ($(field).prop('checked')) { + const fieldValue = isNaN($(field).val()) ? $(field).val() : parseInt($(field).val()) + if (Array.isArray(data[$(field).attr('name')])) { + data[$(field).attr('name')].push(fieldValue) + } else { + data[$(field).attr('name')] = fieldValue + } + } + } else if ($(field).val() !== '') { + const fieldValue = $(field).val() + const fieldParsedValue = isNaN(fieldValue) ? this.parseValue(fieldValue) : parseInt(fieldValue) + if (Array.isArray(data[$(field).attr('name')])) { + data[$(field).attr('name')].push(fieldParsedValue) + } else { + data[$(field).attr('name')] = fieldParsedValue + } + } + }); + + return data + } + + parseValue(val) { + return val === 'true' ? true : val === 'false' ? false : val + } + + // Handle save + handleSave() { + modal.upload(this.getData()) + } + + // Handle close + handleClose() { + super.handleClose() + this.providerText.html("PROVIDER") + } +} + +export default ProviderModalComponent diff --git a/src/frontend/components/provider/_provider.scss b/src/frontend/components/provider/_provider.scss new file mode 100644 index 000000000..5f070d8f7 --- /dev/null +++ b/src/frontend/components/provider/_provider.scss @@ -0,0 +1,38 @@ +.provider { + display: flex; + position: relative; + align-items: center; + gap: $padding-base-horizontal; + margin: 0; + padding: 0; + list-style-type: none; +} + +.provider__item { + &:not(:last-child) { + padding-right: $padding-base-horizontal; + border-right: 1px solid $gray; + } +} + +.provider__link { + &::before { + @extend %icon-font; + + color: $brand-primary; + font-size: 1.25rem; + } + + span { + @include visually-hidden; + } +} + +.provider__link--details::before { + content: "\E81a"; + font-size: 24px; +} + +.provider__link--logout::before { + content: "\E812"; +} diff --git a/src/frontend/css/stylesheets/general.scss b/src/frontend/css/stylesheets/general.scss index dc91e1c30..c177b8870 100644 --- a/src/frontend/css/stylesheets/general.scss +++ b/src/frontend/css/stylesheets/general.scss @@ -1,5 +1,7 @@ @import "definitions/variables"; +$primary: $brand-primary; + // Bootstrap 4.6 @import "~bootstrap/scss/bootstrap", "~datatables.net-bs4/css/dataTables.bootstrap4.min.css", diff --git a/src/frontend/js/site.js b/src/frontend/js/site.js index 7780c57f8..3fc714b9f 100644 --- a/src/frontend/js/site.js +++ b/src/frontend/js/site.js @@ -46,6 +46,7 @@ import HelpView from "components/help-view"; import PeopleFilterComponent from "components/form-group/people-filter"; import handleActions from "util/actionsHandler"; import FieldLengthComponent from "components/form-group/field-length"; +import ProviderModalComponent from 'components/modal/modals/provider' // Register them registerComponent(AddTableModalComponent); @@ -86,6 +87,7 @@ registerComponent(HelpView); registerComponent(PeopleFilterComponent); registerComponent(AutosaveComponent); registerComponent(FieldLengthComponent); +registerComponent(ProviderModalComponent); // Initialize all components at some point initializeRegisteredComponents(document.body); diff --git a/views/admin/admin_settings.tt b/views/admin/admin_settings.tt index 0b193191b..02e86f905 100644 --- a/views/admin/admin_settings.tt +++ b/views/admin/admin_settings.tt @@ -132,6 +132,21 @@ + + [% END %] diff --git a/views/authentication/provider_edit.tt b/views/authentication/provider_edit.tt new file mode 100644 index 000000000..5f27d240e --- /dev/null +++ b/views/authentication/provider_edit.tt @@ -0,0 +1,189 @@ +[%- + # add standardized page header + INCLUDE layouts/page_header.tt + title = "Edit provider: " _ editprovider.name + description = "In this window you can edit an authentication provider in the system." + back_button = { url = url.page _ "/authentication_providers/" }; +-%] +[% + IF editprovider.type == 1 +%] + Download Metadata +[% END %] +
+
+ [% + IF editprovider.type == 1 + %] +
+ My details + [%- + INCLUDE fields/hidden.tt name="csrf_token" value=csrf_token; + INCLUDE fields/hidden.tt name="page" value=page; + INCLUDE fields/hidden.tt name="username" value=user.username filter="html_entity"; + INCLUDE fields/hidden.tt name="id" value=editprovider.id; + INCLUDE fields/hidden.tt name="unique_saml_id" value=editprovider.get_saml2_unique_id; + + field_counter = 0; + + IF site.provider_fields.size > 0; + -%] +
+ [% END %] + [% FOREACH field IN site.provider_fields %] + [% IF field_counter > 0 AND field_counter % 2 == 0 %] +
+
+ [% END %] +
+ [% + IF field.type == "freetext" AND (field.name != 'sso_url' AND field.name != 'sso_xml'); + INCLUDE fields/input.tt + id = field.name + name = field.name + value = editprovider.${field.name} + label = field.description + placeholder = field.placeholder + type = "text" + filter = "html" + sub_field = "" + sub_params = {}; + + ELSIF field.type == "freetext" AND (field.name == 'sso_url' OR field.name == 'sso_xml'); + INCLUDE fields/input.tt + id = field.name + name = field.name + value = editprovider.${field.name} + label = field.description + placeholder = field.placeholder + type = "text" + is_readonly = 1 + sub_field = "" + sub_params = {}; + + ELSIF field.type == "dropdown"; + INCLUDE fields/select_single.tt + id = field.name + name = field.name + value = editprovider.get_column(field.name) + label = field.description + placeholder = field.placeholder + items = values.${field.name} + sub_field = "" + sub_params = {}; + + ELSIF field.type == "textarea" and field.name != 'sp_key'; + INCLUDE fields/textarea.tt + id = field.name + name = field.name + value = editprovider.${field.name} + label = field.description + rows = 10 + placeholder = field.placeholder + filter = "html" + sub_field = "" + sub_params = {}; + ELSIF field.type == "radio" and field.name == 'type'; + INCLUDE fields/radio.tt + id = field.name + name = field.name + label = field.description + value = editprovider.${field.name} + items = [ + {id = "1", name = "SAML2"}, + {id = "0", name = "Built In"} + ]; + ELSIF field.type == "radio" and field.name == 'enabled'; + INCLUDE fields/radio.tt + id = field.name + name = field.name + label = field.description + value = editprovider.${field.name} + items = [ + {id = "1", name = "Enable Authentication Provider"}, + {id = "0", name = "Disable Authentication Provider"} + ]; + ELSIF field.type == "dropdown"; + INCLUDE fields/select.tt + id = field.name + name = field.name + label = field.description + placeholder = field.placeholder + items = values.${field.name} + filter = "html" + sub_field = sub_field + sub_params = sub_params; + + END; + %] +
+ [% + field_counter = field_counter + 1; + END; + %] + [% IF site.provider_fields.size > 0 %] +
+ [% END %] + +
+[% ELSE %] +

The built in authentication provider cannot be edited.

+[% END %] + +[% + IF editprovider.type != 0; +%] + [% + INCLUDE navigation/button_bar.tt + row_class = "row mt-5" + columns = [{ + class = "col-sm-auto mb-3 mb-sm-0", + buttons = [{ + type = "link", + class = "btn btn-cancel", + target = url.page _ "/authentication_providers/", + label = "Cancel" + }] + }, { + class = "col-sm-auto", + buttons = [{ + type = "modal_button", + modalId = "deleteModal", + dataTitle = editprovider.name, + dataId = editprovider.id, + class = "btn btn-danger btn-js-delete", + label = "Delete provider" + }, { + type = "button", + name = "submit", + value = "submit", + class = "btn btn-default btn-js-save", + label = "Save changes" + }] + }]; + %] +[% ELSE %] + [% + INCLUDE navigation/button_bar.tt + row_class = "row mt-5" + columns = [{ + class = "col-sm-auto mb-3 mb-sm-0", + buttons = [{ + type = "link", + class = "btn btn-cancel", + target = url.page _ "/authentication_providers/", + label = "Cancel" + }] + }, + ]; + %] +[% END %] +
+
+ +[% + INCLUDE wizard/delete.tt + modalId = "deleteModal" + label = "Delete " _ editprovider.name + description = "Are you sure you want to delete this provider? You cannot undo this step."; +%] diff --git a/views/authentication/providers.tt b/views/authentication/providers.tt new file mode 100644 index 000000000..63e881a26 --- /dev/null +++ b/views/authentication/providers.tt @@ -0,0 +1,72 @@ +[% + # prepare table config + table_class = 'table-striped table-hover'; + table_dom = '<"row row--header"<"col"f><"col-lg-auto dataTables_length_wrapper"l>><"row row--main"<"col-sm-12"tr>><"row row--footer"<"col-sm-12 col-lg-6"p><"col-sm-12 col-lg-6 dataTables_info_wrapper"i>>'; + table_language = { + emptyTable => "There is no data available in this table", + lengthMenu => "Rows per page _MENU_", + paginate => { + next => "Next page", + previous => "Previous page" + }, + search => "Search in authentication providers:", + searchPlaceholder => "Search through your providers" + } + table_ajax = url.page _ "/api/providers?csrf-token=" _ csrf_token; + table_ajax_target = url.page _ "/authentication_providers"; # will be appended with /{id} by JS + table_save_state = 1; + table_unresponsive = 0; + table_caption = "Table to show list of authentication providers"; + + table_columns = [{ + name = "ID" + orderable = 1 + },{ + name = "Site ID" + orderable = 1 + },{ + name = "Type" + orderable = 1 + },{ + name = "Name" + orderable = 1 + },{ + name = "enabled" + orderable = 1 + },{ + name = "error_messages" + orderable = 1 + }]; + + # add standardized page header + INCLUDE layouts/page_header.tt + title = "Authentication Providers" + description = "This is an overview of all the authentication providers within your Linkspace system." + aside_buttons = ! user.permission.useradmin ? [] : [{ + type = "modal_button" + modalId = "providerModal" + class = "btn btn-add" + label = "Add an authentication provider" + }]; +%] + +
+
+
+
+ +
+
+
+ + [% INCLUDE tables/basic_table.tt; %] +
+ +[%- + INCLUDE wizard/provider_add.tt endpoint="/api/authentication_providers" modalId="providerModal"; +-%] diff --git a/views/layouts/main.tt b/views/layouts/main.tt old mode 100755 new mode 100644 diff --git a/views/login.tt b/views/login.tt old mode 100755 new mode 100644 index 244d3cd9c..b3479503a --- a/views/login.tt +++ b/views/login.tt @@ -56,6 +56,9 @@ + [% UNLESS site.hide_account_request %]