App-Phoebe
view release on metacpan or search on metacpan
lib/App/Phoebe/Capsules.pm view on Meta::CPAN
my $backup_file = $backup_dir . "/" . encode_utf8($id);
mkdir($backup_dir) unless -d $backup_dir;
rename $file, $backup_file if -f $file;
result($stream, "30", to_url($stream, $host, $capsule_space, $capsule));
} else {
$log->info("Delete for $capsule");
success($stream);
$stream->write("# Delete a file in " . ucfirst($capsule) . "\n");
$stream->write("Deleting a file moves it to the backup.\n");
my @files;
@files = grep { $_ ne "backup" } read_dir($dir) if -d $dir;
if (not @files) {
$stream->write("There are no files to delete.\n") unless @files;
} else {
$stream->write("Files:\n");
for my $file (sort @files) {
print_link($stream, $host, $capsule_space, $file, "$capsule/delete/$file");
};
}
}
return 1;
}
sub serve_capsule_access {
my ($stream, $host, $capsule, $token) = @_;
my $fingerprint = $stream->handle->get_fingerprint();
my $target = first { $_->[1] eq $token } @capsule_tokens;
if (not $fingerprint) {
$log->info("Attempt to access a capsule without client certificate");
result($stream, "60", "You need a client certificate to access this capsule");
} elsif ($target) {
if ($fingerprint ne $target->[2]) {
$log->info("Access to capsule granted");
# if the user is testing it, then the two fingerprints are the same and no
# equivalency needs to be saved
$capsule_equivalent{$fingerprint} = $target->[2];
my $dir = $server->{wiki_dir};
write_binary("$dir/fingerprint_equivalents",
join("\n", map { $_ . " " . $capsule_equivalent{$_} }
keys %capsule_equivalent));
} else {
$log->info("Access to capsule unnecessary for the owner");
}
result($stream, "30", to_url($stream, $host, $capsule_space, $capsule));
} else {
$log->info("Access to capsule denied");
success($stream);
$stream->write("This password is invalid\n");
}
return 1;
}
sub serve_capsule_sharing {
my ($stream, $host, $capsule) = @_;
my $name = capsule_name($stream);
return 1 unless is_my_capsule($stream, $name, $capsule, 'share');
$log->info("Share capsule");
my $token = capsule_name(sprintf "-------%04X%04X%04X", rand(0xffff), rand(0xffff), rand(0xffff));
push(@capsule_tokens, [time, $token, $stream->handle->get_fingerprint()]);
# forget old access tokens in ten minutes
Mojo::IOLoop->timer(601 => \&capsule_token_cleanup);
success($stream);
$stream->write("# Share access to " . ucfirst($capsule) . "\n");
$stream->write("This password is valid for ten minutes: $token\n");
return 1;
}
sub is_my_capsule {
my ($stream, $name, $capsule, $verb) = @_;
if (not $name) {
$log->info("Attempt to $verb a capsule without client certificate");
result($stream, "60", "You need a client certificate to $verb this capsule");
return 0;
} elsif ($capsule and $name ne $capsule) {
$log->info("Attempt to $verb the wrong capsule");
result($stream, "60", "You need a different client certificate to $verb this capsule");
return 0;
}
return 1;
}
sub serve_capsule_page {
my ($stream, $host, $capsule, $id) = @_;
my $dir = capsule_dir($host, $capsule);
my $file = $dir . "/" . encode_utf8($id);
if (-f $file) {
$log->info("Serving $file");
# this works for text files, too!
success($stream, mime_type($id));
$stream->write(read_binary($file));
} else {
$log->info("Serving invitation to upload $file");
success($stream);
$stream->write("This file does not exist. Upload it using Titan!\n");
$stream->write("=> gemini://transjovian.org/titan What is Titan?\n");
}
return 1;
}
sub serve_capsule_menu {
my ($stream, $host, $capsule) = @_;
my $name = capsule_name($stream);
my $dir = capsule_dir($host, $capsule);
my @files;
@files = read_dir($dir) if -d $dir;
my $has_backup = first { $_ eq "backup" } @files;
@files = grep { $_ ne "backup" } @files if $has_backup;
success($stream);
$log->info("Serving $capsule");
$stream->write("# " . ucfirst($capsule) . "\n");
if ($name) {
if ($name eq $capsule) {
print_link($stream, $host, $capsule_space, "Specify file for upload", "$capsule/upload");
print_link($stream, $host, $capsule_space, "Delete file", "$capsule/delete") if @files;
print_link($stream, $host, $capsule_space, "Share access with other people or other devices", "$capsule/share");
print_link($stream, $host, $capsule_space, "Access backup", "$capsule/backup") if $has_backup;
print_link($stream, $host, $capsule_space, "Download archive", "$capsule/archive") if @files;
} elsif (@capsule_tokens) {
print_link($stream, $host, $capsule_space, "Access this capsule", "$capsule/access");
}
}
( run in 0.808 second using v1.01-cache-2.11-cpan-acf6aa7dc9e )