discourse-legacysite-perl/site/glist/lib/GList/SQL.pm
2024-06-17 21:49:12 +10:00

449 lines
22 KiB
Perl

# ==================================================================
# Gossamer List - enhanced mailing list management system
#
# Website : http://gossamer-threads.com/
# Support : http://gossamer-threads.com/scripts/support/
# CVS Info :
# Revision : $Id: SQL.pm,v 1.40 2004/10/05 22:02:27 bao Exp $
#
# Copyright (c) 2004 Gossamer Threads Inc. All Rights Reserved.
# Redistribution in part or in whole strictly prohibited. Please
# see LICENSE file for full details.
# ==================================================================
#
package GList::SQL;
use strict;
use vars qw/@TABLES $EMAIL_RE/;
use GList qw/$DB $CFG/;
@TABLES = qw/Users Users_Sessions EmailTemplates Messages Lists Subscribers
MailingIndex EmailMailings CatMessages CatMailing MessageAttachments
MailingAttachments StopLists/;
$EMAIL_RE = '.@\S+\.\S+$';
# Index naming format:
#
# a_bcd[_q]
#
# Where "a" is (usually) the capital letters from the table name (i.e. EmailTemplates gets "et"),
# except for CatMailing, which is cml, and MailingAttachments, which is mla.
#
# b,c,d,... correspond to the following:
#
# b - sub_bounced
# c - *_cat_id_fk | eml_code
# d - session_date | mli_delete
# e - usr_email | sub_email | stl_email
# l - *_list_id_fk
# m - *_message_id_fk
# n - tpl_name | mli_done
# t - lst_title
# u - *_user_id_fk
# v - sub_validated
#
# Finally, the optional "_q" is used for unique indices.
#
sub tables {
#----------------------------------------------------------------
# Defines the SQL tables
#
my $action = shift || 'warn';
my $output = '';
#---------- Users Table -----------------
create_table(\$output, 'Users', $action,
cols => [
usr_username => { type => 'CHAR', size => 50, not_null => 1, form_display => 'User Name' },
usr_email => { type => 'CHAR', size => 50, not_null => 1, form_display => 'Email Address', form_regex => $EMAIL_RE },
usr_password => { type => 'CHAR', size => 100, not_null => 1, form_display => 'Password' },
usr_type => { type => 'TINYINT', not_null => 1, default => 1, form_display => 'Type' },
usr_reply_email => { type => 'CHAR', size => 100, not_null => 0, form_display => 'Reply to Email', form_regex => $EMAIL_RE },
usr_bounce_email => { type => 'CHAR', size => 100, not_null => 0, form_display => 'Bounce Email', form_regex => $EMAIL_RE },
usr_date_format => { type => 'CHAR', size => 50, form_display => 'Date Format' },
usr_compose_mode => { type => 'CHAR', size => 5, form_display => 'Editor Advanced', default => 'text' },
usr_editor_advanced => { type => 'TINYINT', not_null => 1, default => 0 },
usr_status => { type => 'TINYINT', default => '1', form_display => 'Status' },
usr_limit_list => { type => 'INT', default => '0', form_display => 'Limit Number of List' },
usr_limit_sublist => { type => 'INT', default => '0', form_display => 'Limit Number of subscriber per List' },
usr_limit_email30 => { type => 'INT', default => '0', form_display => 'Limit Number of Email Sending in The Last 30 days' },
usr_mail_host => { type => 'CHAR', size => 100, form_display => 'Server Mail hostname' },
usr_mail_port => { type => 'CHAR', size => 3, form_display => 'Server Mail port' },
usr_mail_account => { type => 'CHAR', size => 50, form_display => 'Mail Account' },
usr_mail_password => { type => 'CHAR', size => 20, form_display => 'Mail Password' },
usr_validate_code => { type => 'CHAR', size => 32, binary => 1, form_display => 'Validate Code' },
usr_updated => { type => 'TINYINT', default => '0', form_display => 'Account Updated' },
usr_header_html => { type => 'TEXT', default => '', form_display => 'Mailing Header' },
usr_header_text => { type => 'TEXT', default => '', form_display => 'Mailing Header' },
usr_footer_html => { type => 'TEXT', default => '', form_display => 'Mailing Footer' },
usr_footer_text => { type => 'TEXT', default => '', form_display => 'Mailing Footer' },
pro_first_name => { type => 'CHAR', size => 20, not_null => 1, form_display => 'First Name', form_size => '35' },
pro_last_name => { type => 'CHAR', size => 30, not_null => 1, form_display => 'Last Name', form_size => '35' },
pro_company => { type => 'CHAR', size => 100, form_display => 'Company Name', form_size => '35' },
pro_url => { type => 'CHAR', size => 255, form_display => 'URL', form_size => '35' },
],
pk => 'usr_username',
unique => {
u_e_q => ['usr_email']
}
);
#---------- Users_Sessions Table -----------------
create_table(\$output, 'Users_Sessions', $action,
cols => [
session_id => { type => 'CHAR', binary => 1, size => 32, not_null => 1 },
session_user_id => { type => 'CHAR', size => 50 },
session_date => { type => 'INT', not_null => 1 },
session_data => { type => 'TEXT' }
],
pk => 'session_id',
fk => {
Users => { session_user_id => 'usr_username' }
},
index => {
us_d => ['session_date']
}
);
#---------- EmailTemplates Table -----------------
create_table(\$output, 'EmailTemplates', $action,
cols => [
tpl_id => { type => 'INT', not_null=> 1, form_display => 'ID' },
tpl_user_id_fk => { type => 'CHAR', size => 50, not_null => 1, form_display => 'User Name' },
tpl_name => { type => 'CHAR', size => 50, not_null => 1, form_display => 'Template Name' },
tpl_to => { type => 'CHAR', size => 50, not_null => 1, form_display => 'To' },
tpl_subject => { type => 'CHAR', size => 100,not_null => 1, form_display => 'Subject' },
tpl_from => { type => 'CHAR', size => 100,not_null => 1, form_display => 'From' },
tpl_extra => { type => 'CHAR', size => 255, form_display => 'Extra Header' },
tpl_body => { type => 'TEXT', not_null=> 1, form_display => 'Email Body' },
],
pk => 'tpl_id',
ai => 'tpl_id',
unique => {
et_un_q => [qw/tpl_user_id_fk tpl_name/]
},
fk => { Users => { tpl_user_id_fk => 'usr_username' } }
);
#---------- CatMessages Table -----------------
create_table(\$output, 'CatMessages', $action,
cols => [
cms_id => { type => 'INT', not_null => 1, form_display => 'ID' },
cms_name => { type => 'CHAR', not_null => 1, size => 30, form_display => 'Folder Name' },
cms_user_id_fk => { type => 'CHAR', not_null => 1, size => 50, form_display => 'User ID' },
],
pk => 'cms_id',
ai => 'cms_id',
index => {
cm_u => ['cms_user_id_fk']
},
fk => { Users => { cms_user_id_fk => 'usr_username' } }
);
#---------- Messages Table -----------------
create_table(\$output, 'Messages', $action,
cols => [
msg_id => { type => 'INT', not_null => 1, form_display => 'Message ID' },
msg_mode => { type => 'CHAR', size => 5, default => 'text', form_display => 'Message Mode' },
msg_charset => { type => 'CHAR', size => 15, not_null => 1, default => 'us-ascii', form_display => 'Charset'},
msg_subject => { type => 'CHAR', size => 100, not_null => 1, form_display => 'Subject', 'weight' => '1' },
msg_from_name => { type => 'CHAR', size => 70, form_display => 'From Name' },
msg_from_email => { type => 'CHAR', size => 100, not_null => 1, form_display => 'From Email', form_regex => $EMAIL_RE },
msg_reply_to => { type => 'CHAR', size => 100, not_null => 1, form_display => 'Reply to Email', form_regex => $EMAIL_RE },
msg_bounce_email => { type => 'CHAR', size => 100, not_null => 1, form_display => 'Bounce Email', form_regex => $EMAIL_RE },
msg_created => { type => 'INT', form_display => 'Name' },
msg_content_text => { type => 'LONGTEXT', form_display => 'TEXT Content', 'weight' => '1' },
msg_content_html => { type => 'LONGTEXT', form_display => 'HTML Content', 'weight' => '1' },
msg_cat_id_fk => { type => 'INT', default => 0, not_null => 1, form_display => 'Category ID' },
msg_status => { type => 'TINYINT', default => 0, form_display => 'Status' },
msg_track_open => { type => 'TINYINT', not_null => 1, default => 0, form_display => 'Track Number of Users opening this message' },
msg_track_click => { type => 'TINYINT', not_null => 1, default => 0, form_display => 'Track Number of Clicks' },
msg_user_id_fk => { type => 'CHAR', size => 50, not_null => 1, form_display => 'User ID' },
],
pk => 'msg_id',
ai => 'msg_id',
fk => {
Users => { msg_user_id_fk => 'usr_username' },
CatMessages => { msg_cat_id_fk => 'cms_id' }
},
index => {
m_uc => [qw/msg_user_id_fk msg_cat_id_fk/]
}
);
#---------- MessageAttachments Table -----------------
create_table(\$output, 'MessageAttachments', $action,
cols => [
att_id => { type => 'INT', not_null => 1, form_display => 'ID' },
att_message_id_fk => { type => 'INT', not_null => 1, form_display => 'Campaign ID' },
att_file_name => { type => 'CHAR', size => 255, form_display => 'File Name' },
att_file_size => { type => 'INT', form_display => 'File Size' },
],
pk => 'att_id',
ai => 'att_id',
fk => { Messages => { att_message_id_fk => 'msg_id' } },
index => {
ma_m => ['att_message_id_fk']
}
);
#---------- Lists Table -----------------
create_table(\$output, 'Lists', $action,
cols => [
lst_id => { type => 'INT', not_null => 1, form_display => 'List ID' },
lst_title => { type => 'CHAR', size => 50, not_null => 1, form_display => 'List Name', weight => '1' },
lst_description => { type => 'TEXT', form_display => 'Name', weight => '1' },
lst_opt => { type => 'TINYINT', form_display => 'Double Opt In', default => '0' },
lst_opt_template => { type => 'CHAR', size => 50, form_display => 'Opt In Template' },
lst_subs_template => { type => 'CHAR', size => 50, form_display => 'Subscriber Template' },
lst_unsubs_template => { type => 'CHAR', size => 50, form_display => 'Unsubscriber Template' },
lst_date_created => { type => 'INT', form_display => 'Created' },
lst_url_subscribe_success => { type => 'CHAR', size => 255, form_display => 'Success Subscribe URL' },
lst_url_validate_success => { type => 'CHAR', size => 255, form_display => 'Success Validate URL' },
lst_url_unsubscribe_success => { type => 'CHAR', size => 255, form_display => 'Success Unsubscribe URL' },
lst_url_subscribe_failure => { type => 'CHAR', size => 255, form_display => 'Failure Subscribe URL' },
lst_url_unsubscribe_failure => { type => 'CHAR', size => 255, form_display => 'Failure Unsubscribe URL' },
lst_user_id_fk => { type => 'CHAR', size => 50, not_null => 1, form_display => 'User ID' },
],
pk => 'lst_id',
ai => 'lst_id',
fk => { Users => { lst_user_id_fk => 'usr_username' } },
index => {
l_ut => [qw/lst_user_id_fk lst_title/]
}
);
#---------- Subscribers Table -----------------
create_table(\$output, 'Subscribers', $action,
cols => [
sub_id => { type => 'INT', not_null => 1, form_display => 'Subscriber ID' },
sub_email => { type => 'CHAR', size => 50, not_null => 1, form_display => 'Subscriber Email', form_regex => $EMAIL_RE, weight => '1' },
sub_name => { type => 'CHAR', size => 50, form_display => 'Subscriber Name', weight => '1' },
sub_created => { type => 'INT', form_display => 'Created' },
sub_list_id_fk => { type => 'INT', not_null => 1, form_display => 'List ID' },
sub_validated => { type => 'TINYINT', not_null => 1, default => 1, form_display => 'Validated' },
sub_val_code => { type => 'CHAR', size => 50, form_display => 'Validation Code' },
sub_bounced => { type => 'INT', not_null => 1, default => 0, form_display => 'Bounced Email' },
sub_user_id_fk => { type => 'CHAR', size => 50, not_null => 1, form_display => 'User ID' },
],
pk => 'sub_id',
ai => 'sub_id',
fk => {
Lists => { sub_list_id_fk => 'lst_id' },
Users => { sub_user_id_fk => 'usr_username' }
},
index => {
s_lb => [qw/sub_list_id_fk sub_bounced/],
s_lvb => [qw/sub_list_id_fk sub_validated sub_bounced/],
s_ue => [qw/sub_user_id_fk sub_email/],
s_e => [qw/sub_email/]
},
unique => {
s_le_q => [qw/sub_list_id_fk sub_email/]
}
);
#---------- CatMailing Table -----------------
create_table(\$output, 'CatMailing', $action,
cols => [
cm_id => { type => 'INT', not_null => 1, form_display => 'ID' },
cm_name => { type => 'CHAR', not_null => 1, size => 30, form_display => 'Folder Name' },
cm_type => { type => 'TINYINT', default => '1', form_display => 'Type' },
cm_user_id_fk => { type => 'CHAR', not_null => 1, size => 50, form_display => 'User ID' },
],
pk => 'cm_id',
ai => 'cm_id',
fk => { Users => { cm_user_id_fk => 'usr_username' } },
index => {
cml_u => ['cm_user_id_fk']
}
);
#---------- MailingIndex Table -----------------
create_table(\$output, 'MailingIndex', $action,
cols => [
mli_id => { type => 'INT', not_null => 1, form_display => 'Mailing ID' },
mli_done => { type => 'INT', default => 0, form_display => 'Done' },
mli_from => { type => 'CHAR', size => 100, form_display => 'From Email', form_regex => $EMAIL_RE },
mli_name => { type => 'CHAR', size => 50, form_display => 'From Name' },
mli_reply_to => { type => 'CHAR', size => 100, form_display => 'Reply To Email', form_regex => $EMAIL_RE },
mli_bounce_email => { type => 'CHAR', size => 100, form_display => 'Bounce Email', form_regex => $EMAIL_RE },
mli_charset => { type => 'CHAR', size => 15, not_null => 1, default => 'us-ascii', form_display => 'Charset'},
mli_subject => { type => 'CHAR', size => 100, form_display => 'Subject', 'weight' => '1' },
mli_message_text => { type => 'LONGTEXT', form_display => 'TEXT Message', 'weight' => '1' },
mli_message_html => { type => 'LONGTEXT', form_display => 'HTML Message', 'weight' => '1' },
mli_cat_id_fk => { type => 'INT', not_null => 1, default => 0, form_display => 'Category ID' },
mli_delete => { type => 'TINYINT', not_null => 1, default => 0, form_display => 'Delete' },
mli_track_open => { type => 'TINYINT', not_null => 1, default => 0, form_display => 'Track Number of Users opening this message' },
mli_track_click => { type => 'TINYINT', not_null => 1, default => 0, form_display => 'Track Number of clicks' },
mli_num_opened => { type => 'INT', not_null => 1, default => 0, form_display => 'Number of Users opening this message' },
mli_num_clicked => { type => 'INT', not_null => 1, default => 0, form_display => 'Number of clicks' },
mli_scheduled => { type => 'TINYINT', not_null => 1, default => 0, form_display => 'Scheduled Mailing' },
mli_user_id_fk => { type => 'CHAR', size => 50, not_null => 1, form_display => 'User ID' }
],
pk => 'mli_id',
ai => 'mli_id',
fk => {
Users => { mli_user_id_fk => 'usr_username' },
CatMailing => { mli_cat_id_fk => 'cm_id' }
},
index => {
mi_ucdn => [qw/mli_user_id_fk mli_cat_id_fk mli_delete mli_done/],
mi_c => ['mli_cat_id_fk']
}
);
#---------- EmailMailings Table -----------------
create_table(\$output, 'EmailMailings', $action,
cols => [
eml_id => { type => 'INT', not_null => 1, form_display => 'ID' },
eml_mailing_id_fk => { type => 'INT', not_null => 1, form_display => 'Mailing ID' },
eml_email => { type => 'CHAR', size => 50, not_null => 1, form_display => 'Email Address', form_regex => $EMAIL_RE },
eml_name => { type => 'CHAR', size => 50, form_display => 'Name' },
eml_sent => { type => 'INT', not_null => 1, default => 0 },
eml_bounced => { type => 'TINYINT', not_null => 1, default => 0 },
eml_skipped => { type => 'TINYINT', not_null => 1, default => 0 },
eml_opened => { type => 'INT', not_null => 1, default => 0 },
eml_code => { type => 'CHAR', size => 100 => not_null => 1 },
eml_lists => { type => 'TEXT', default => '' },
],
pk => 'eml_id',
ai => 'eml_id',
fk => { MailingIndex => { eml_mailing_id_fk => 'mli_id' } },
index => {
em_mb => [qw/eml_mailing_id_fk eml_bounced/],
em_ms => [qw/eml_mailing_id_fk eml_sent/],
em_mo => [qw/eml_mailing_id_fk eml_opened/],
em_e => [qw/eml_email/],
em_c => [qw/eml_code/],
},
unique => {
em_me_q => [qw/eml_mailing_id_fk eml_email/]
}
);
#---------- ScheduledMailings Table -----------------
create_table(\$output, 'ScheduledMailings', $action,
cols => [
scm_id => { type => 'INT', not_null => 1, form_display => 'Schedule ID'},
scm_hour => { type => 'INT', default => 0, form_display => 'Hour' },
scm_minute => { type => 'INT', default => 0, form_display => 'Minute' },
scm_type => { type => 'TINYINT', default => 0, form_display => 'Schedule Type' },
scm_option => { type => 'CHAR', size => 10, default => '', form_display => 'Option' },
scm_text_url => { type => 'CHAR', size => 225, default => '', form_display => 'Text URL' },
scm_html_url => { type => 'CHAR', size => 225, default => '', form_display => 'Html URL' },
scm_inprocess => { type => 'TINYINT', default => 0, form_display => 'In Process' },
scm_sent => { type => 'INT', default => 0, form_display => 'Sent Time' },
scm_mailing_id_fk => { type => 'INT', default => 0, form_display => 'Mailing ID' },
],
ai => 'scm_id',
pk => 'scm_id',
unique => {
sm_m_q => [qw/scm_mailing_id_fk/]
},
fk => { MailingIndex => { scm_mailing_id_fk => 'mli_id' } }
);
#---------- MailingAttachments Table -----------------
create_table(\$output, 'MailingAttachments', $action,
cols => [
mat_id => { type => 'INT', not_null => 1, form_display => 'ID' },
mat_mailing_id_fk => { type => 'INT', not_null => 1, form_display => 'Mailing ID' },
mat_file_name => { type => 'CHAR', size => 255, form_display => 'File Name' },
mat_file_size => { type => 'INT', form_display => 'File Size' },
],
pk => 'mat_id',
ai => 'mat_id',
fk => { MailingIndex => { mat_mailing_id_fk => 'mli_id' } },
index => {
mla_m => ['mat_mailing_id_fk']
}
);
#---------- StopLists Table -----------------
create_table(\$output, 'StopLists', $action,
cols => [
stl_id => { type => 'INT', not_null => 1, form_display => 'ID' },
stl_email => { type => 'CHAR', size => 50, not_null => 1, form_display => 'Email Address', form_regex => $EMAIL_RE },
],
pk => 'stl_id',
ai => 'stl_id',
unique => {
s_e_q => ['stl_email']
}
);
return $output;
}
sub create_table {
my ($output, $table, $action, @def) = @_;
$$output .= "Creating $table table ... ";
my $c = $DB->creator($table);
$c->clear_schema() if $action eq 'force';
@def % 2 and die "Odd number of table defs passed to create_table()";
while (@def) {
my ($meth, $arg) = splice @def, 0, 2;
$c->$meth($arg);
}
if ($c->create($action)) {
$$output .= "okay\n";
return 1;
}
else {
$GT::SQL::errcode if 0; # silence "used only once" warnings
$$output .= $GT::SQL::errcode eq 'TBLEXISTS' ? "failed (table already exists)\n" : "failed ($GT::SQL::error)\n";
$c->set_defaults;
$c->save_schema;
return 0;
}
}
sub load_from_sql {
# ---------------------------------------------------------------
# Creates def files based on existing tables.
#
my ($output, $return);
foreach my $table (@TABLES) {
$output .= "$table .. ";
my $c = $DB->creator($table);
$return = $c->load_table($table);
if ($return) {
$output .= "ok\n";
$c->save_schema();
}
else {
$output .= "failed: $GT::SQL::error\n";
}
}
return $output;
}
sub load {
# ---------------------------------------------------------------
# Return a hash of current connection settings.
#
my %h = ();
$h{prefix} = $DB->prefix();
$h{database} = $DB->{connect}->{database};
$h{login} = $DB->{connect}->{login};
$h{password} = $DB->{connect}->{password};
$h{host} = $DB->{connect}->{host};
$h{host} .= ":" . $DB->{connect}->{port} if $DB->{connect}->{port};
$h{driver} = $DB->{connect}->{driver};
return \%h;
}
1;