]> ruin.nu Git - ndwebbie.git/blob - lib/NDWeb/Controller/Settings.pm
Add discord_id
[ndwebbie.git] / lib / NDWeb / Controller / Settings.pm
1 package NDWeb::Controller::Settings;
2
3 use strict;
4 use warnings;
5 use feature ":5.10";
6 use parent 'Catalyst::Controller';
7
8 use NDWeb::Include;
9
10 use DateTime::TimeZone;
11 use Mail::Sendmail;
12 use Email::Valid;
13
14 =head1 NAME
15
16 NDWeb::Controller::Settings - Catalyst Controller
17
18 =head1 DESCRIPTION
19
20 Catalyst Controller.
21
22 =head1 METHODS
23
24 =cut
25
26
27 =head2 index 
28
29 =cut
30
31 sub index :Path :Args(0) {
32         my ( $self, $c ) = @_;
33         my $dbh = $c->model;
34
35         $c->stash(error => $c->flash->{error});
36
37         my @stylesheets = ('Default');
38         my $dir = $c->path_to('root/static/css/black.css')->dir;
39         while (my $file = $dir->next){
40                 if(!$file->is_dir && $file->basename =~ m{^(\w+)\.css$}){
41                         push @stylesheets,$1;
42                 }
43         }
44         $c->stash(stylesheets => \@stylesheets);
45
46         my ($birthday,$timezone,$email,$discord_id) = $dbh->selectrow_array(q{
47 SELECT birthday,timezone,email,discord_id FROM users WHERE uid = $1
48                 },undef,$c->user->id);
49         $c->stash(birthday => $birthday);
50         $c->stash(email =>  $c->flash->{email} // $email);
51         $c->stash(discord_id =>  $c->flash->{discord_id} // $discord_id);
52
53         my @timezone = split m{/},$timezone,2;
54         $c->stash(timezone => \@timezone);
55
56         my @cat = DateTime::TimeZone->categories;
57         unshift @cat, 'GMT';
58         $c->stash(tzcategories => \@cat);
59
60         my @countries = DateTime::TimeZone->names_in_category($timezone[0]);
61         $c->stash(tzcountries => \@countries);
62 }
63
64 sub changeStylesheet : Local {
65         my ( $self, $c ) = @_;
66         my $dbh = $c->model;
67
68         my $query = $dbh->prepare(q{UPDATE users SET css = NULLIF($2,'Default')
69                 WHERE uid = $1
70         });
71         $query->execute($c->user->id,html_escape $c->req->param('stylesheet'));
72
73         $c->res->redirect($c->uri_for(''));
74 }
75
76 sub changeBirthday : Local {
77         my ( $self, $c ) = @_;
78         my $dbh = $c->model;
79
80         my $query = $dbh->prepare(q{UPDATE users SET birthday = NULLIF($2,'')::date
81                 WHERE uid = $1
82                 });
83         eval{
84                 $query->execute($c->user->id,html_escape $c->req->param('birthday'));
85         };
86         if ($@){
87                 if ($@ =~ /invalid input syntax for type date/){
88                         $c->flash(error => 'Bad syntax for day, use YYYY-MM-DD.');
89                 }else{
90                         $c->flash(error => $@);
91                 }
92         }
93         $c->res->redirect($c->uri_for(''));
94 }
95
96 sub changeTimezone : Local {
97         my ( $self, $c ) = @_;
98         my $dbh = $c->model;
99
100         my $timezone = $c->req->param('timezone');
101         my $query = $dbh->prepare(q{UPDATE users SET timezone = $2 WHERE uid = $1});
102         eval{
103                 $dbh->selectrow_array(q{SELECT NOW() AT TIME ZONE $1},undef,$timezone);
104                 $query->execute($c->user->id,$timezone );
105         };
106         if ($@){
107                 $c->flash(error => $@);
108         }
109         $c->res->redirect($c->uri_for(''));
110 }
111
112 sub changePassword : Local {
113         my ( $self, $c ) = @_;
114         my $dbh = $c->model;
115
116         if (length $c->req->param('pass') < 4) {
117                 $c->flash(error => "Your password need to be at least 4 characters");
118         } else {
119                 my $query = $dbh->prepare(q{UPDATE users SET password = $1
120                         WHERE password = crypt($2,password) AND uid = $3
121                 });
122                 $query->execute($c->req->param('pass'),$c->req->param('oldpass'),$c->user->id);
123
124                 $c->flash(error => "Old password was invalid") unless $query->rows;
125         }
126
127         $c->res->redirect($c->uri_for(''));
128 }
129
130 sub changeEmail : Local {
131         my ( $self, $c ) = @_;
132         my $dbh = $c->model;
133
134         my $email = $c->req->param('email');
135
136         if ($email =~ /^s?$/) {
137                 my $update = $dbh->prepare(q{
138 UPDATE users SET email = NULL WHERE uid = $1;
139                         });
140                 $update->execute($c->user->id);
141                 $c->flash(error => 'email cleared');
142                 $c->res->redirect($c->uri_for(''));
143                 return,
144         }
145
146         unless (Email::Valid->address($email)){
147                 $c->flash(email => $email);
148                 $c->flash(error => 'Invalid email address');
149                 $c->res->redirect($c->uri_for(''));
150                 return,
151         }
152
153         eval{
154                 my $insert = $dbh->prepare(q{
155 INSERT INTO email_change (uid,email) VALUES ($1,$2) RETURNING id;
156                         });
157                 $insert->execute($c->user->id,$email);
158
159                 my ($id) = $insert->fetchrow_array;
160
161                 my %mail = (
162                         smtp => 'localhost',
163                         To      => $email,
164                         From    => 'NewDawn Command <nd@ruin.nu>',
165                         'Content-type' => 'text/plain; charset="UTF-8"',
166                         Subject => 'Change email address',
167                         Message => qq{
168 You have requested to change email address on the NewDawn website.
169 If that is not the case, then feel free to ignore this email. Otherwise
170 use the following url to confirm the change:
171
172 }.$c->uri_for('confirmEmail',$id)."\n",
173                 );
174
175                 if (sendmail %mail) {
176                         $c->flash(error => 'Sent mail for confirmation.');
177                 }else {
178                         $c->flash(error => $Mail::Sendmail::error);
179                 }
180         };
181         if($@){
182                 if($@ =~ /duplicate key value violates unique constraint/){
183                         $c->flash(email => $email);
184                         $c->flash(error => 'Something went wrong, try to set the email again');
185                 }else{
186                         die $@;
187                 }
188         }
189         $c->res->redirect($c->uri_for(''));
190 }
191
192 sub changeDiscordId : Local {
193         my ( $self, $c ) = @_;
194         my $dbh = $c->model;
195
196         my $discord_id = $c->req->param('discord_id');
197
198         if ($discord_id =~ /^\s*$/) {
199                 my $update = $dbh->prepare(q{
200 UPDATE users SET discord_id = NULL WHERE uid = $1;
201                         });
202                 $update->execute($c->user->id);
203                 $c->flash(error => 'discord id cleared');
204                 $c->res->redirect($c->uri_for(''));
205                 return,
206         }
207
208         eval{
209                 my $update = $dbh->prepare(q{
210 UPDATE users SET discord_id = $2 WHERE uid = $1;
211                         });
212                 $update->execute($c->user->id,$discord_id);
213         };
214         if($@){
215                 if($@ =~ /duplicate key value violates unique constraint/){
216                         $c->flash(discord_id => $discord_id);
217                         $c->flash(error => 'Someone else is using this discord id, duplicate account?');
218                 }else{
219                         die $@;
220                 }
221         }
222         $c->res->redirect($c->uri_for(''));
223 }
224
225 sub confirmEmail : Local {
226         my ( $self, $c, $id ) = @_;
227         my $dbh = $c->model;
228
229         $dbh->begin_work;
230         my $query = $dbh->prepare(q{
231 UPDATE email_change SET confirmed = TRUE
232 WHERE uid = $1 AND id = $2 AND NOT confirmed
233 RETURNING email
234                 });
235         $query->execute($c->user->id,$id);
236         my ($email) = $query->fetchrow_array;
237
238         if ($email){
239                 $dbh->do(q{UPDATE users SET email = $2 WHERE uid = $1}
240                         ,undef,$c->user->id,$email);
241                 $c->flash(error => "Email updated.");
242         }else{
243                 $c->flash(error => "$id is not a valid change id for your account, or already confirmed");
244         }
245         $dbh->commit;
246         $c->res->redirect($c->uri_for(''));
247 }
248
249
250 =head1 AUTHOR
251
252 Michael Andreen (harv@ruin.nu)
253
254 =head1 LICENSE
255
256 GPL 2.0, or later.
257
258 =cut
259
260 1;