Added cache control on all photos and album

beta
anulax1225 ago%!(EXTRA string=3 days)
parent 5d36ac33c2
commit a8fb1ee866
  1. 13
      app/Http/Controllers/AlbumController.php
  2. 16
      app/Http/Controllers/S3Controller.php
  3. 2
      app/Models/Album.php
  4. 2
      app/Models/Photo.php
  5. 20
      resources/js/Pages/Album/Partials/Edit.vue
  6. 12
      resources/js/Pages/Album/Partials/Show.vue
  7. 3
      resources/js/Pages/Photo/Partials/Modal.vue
  8. 3
      resources/js/Pages/Photo/Partials/PanelShow.vue
  9. 5
      resources/js/Pages/Photo/Partials/Show.vue
  10. 14
      resources/js/utils.js

@ -109,6 +109,19 @@ public function store(Request $request)
return redirect(route("album.index"))->with(["message" => "Photo ajouté avec success"]);
}
public function update(Request $request, string $id)
{
$request->validate([
"name" => "required|string|max:255",
]);
$album = Album::where("uuid", $request->id)->first();
if(!$album) redirect()->back()->withErrors(["uuid" => "Album introuvable" ]);
$album->update([
"name" => $request->name
]);
return redirect(route("album.index"))->with(["message" => "Album modifié avec success"]);
}
public function addPhotos(Request $request)
{
$album = Album::where("uuid", $request->id)->first();

@ -98,8 +98,20 @@ public function ProxyS3(Request $request)
public function Download(Request $request)
{
$url = S3::signUrl($request->key);
return redirect($url);
if(!$request->key) return redirect()->back()->withErrors("error", "Aucun fichier a été télécharger.");
$url = $request->key;
$filename = pathinfo($request->key, PATHINFO_BASENAME);
if(!Storage::disk("s3")->exists($url)) return redirect()->back()->withErrors("error", "Fichier introuvable.");
$path = pathinfo($url, PATHINFO_DIRNAME);
return response()->streamDownload(function() use ($url) {
$stream = Storage::disk('s3')->readStream($url);
while (!feof($stream)) {
echo fread($stream, 256 * 1024);
flush();
}
fclose($stream);
}, $filename, ['Cache-Control' => "max-age=86400" ]);
}
}

@ -20,7 +20,7 @@ public function jsonSerialize():array
'uuid' => $this->uuid,
'name' => $this->name,
'path' => $this->path,
'image' => S3::signUrl($this->path),
'image' => $this->path,
'user' => $this->user,
'created_at' => date("d.m.Y", strtotime($this->created_at)),
];

@ -20,7 +20,7 @@ public function jsonSerialize():array
return [
'uuid' => $this->uuid,
'name' => $this->name,
'path' => S3::signUrl($this->path),
'path' => $this->path,
'user' => $this->user,
'created_at' => date("d.m.Y", strtotime($this->created_at)),
];

@ -1,5 +1,6 @@
<script setup>
import TextInput from '@/Components/TextInput.vue';
import Utils from '@/utils';
import { useForm } from '@inertiajs/vue3';
const props = defineProps({
@ -16,25 +17,24 @@ const form = useForm({
const emits = defineEmits(["close"]);
const submit = () => {
form.post("/photo/" + props.photo.uuid , {
form.post(route("album.update", props.album.uuid) , {
headers: {
"Content-Type": "application/json",
"X-CSRF-Token": document.querySelector('input[name=_token]').value,
},
});
form.name = "";
emits("close");
}
</script>
<template>
<div class="text-left text-black shadow-md shadow-gray-500 rounded-lg
bg-gray-50 overflow-hidden border border-gray-300 p-2 w-72" >
<form @submit.prevent="submit">
<TextInput :placeholder="'Changer le nom de la photo'" :class="'w-full'" v-model="form.name"/>
<div class="w-full flex mt-3">
<button type="submit" class="text-white font-semibold p-1 px-2 bg-primary rounded-md">Changer</button>
</div>
</form>
<div class="text-left text-black shadow-md shadow-gray-500 rounded-lg z-40
bg-gray-50 overflow-hidden border border-gray-300 p-2 w-72 pointer-events-none">
<form>
<TextInput :placeholder="'Changer le nom de la album'" :class="'w-full'" v-model="form.name"/>
<div class="w-full flex mt-3">
<button @click.prevent="submit" class="text-white font-semibold p-1 px-2 bg-primary rounded-md">Changer</button>
</div>
</form>
</div>
</template>

@ -42,6 +42,7 @@ const deleteAlbum = async (e) => {
</script>
<template>
<div class="relative w-full">
<Link :href="'/album/' + props.album.uuid" :class="{
'border-r': (props.index + 1) % props.columns != 0,
'border-b': props.index < props.length - props.columns,
@ -51,14 +52,6 @@ const deleteAlbum = async (e) => {
class="group relative w-full overflow-hidden border-white hover:scale-[1.003] flex items-center bg-black/90">
<div class="hidden absolute left-0 right-0 top-0 p-2 group-hover:flex justify-between">
<div class="flex items-center">
<div class="relative">
<button @click="(e) => { Utils.Prevent(e); albumState.edit = !albumState.edit; }" class="bg-black/50 p-1 rounded-md mr-2"><img src="/icons/modify.svg" class="h-6 invert"></button>
<!-- <Edit v-if="albumState.edit"
@close="() => albumState.edit = false"
:album="props.album"
:class="'absolute left-0 top-full mt-2'"
/> -->
</div>
<button @click="deleteAlbum" class="bg-red-600 p-1 rounded-md"><img src="/icons/delete.png" class="h-6 invert"></button>
</div>
</div>
@ -66,6 +59,7 @@ const deleteAlbum = async (e) => {
<p class="laptop:text-sm text-xs text-white bg-black/30 p-1 px-3 rounded">{{ props.album.name }}</p>
<p class="laptop:text-sm text-xs text-white bg-black/30 p-1 px-3 rounded">publier par {{ props.album.user.name }}</p>
</div>
<img :src="props.album.image" class="w-full bg-white">
<img :src="Utils.DownloadUrl(props.album.image)" class="w-full bg-white">
</Link>
</div>
</template>

@ -1,4 +1,5 @@
<script setup>
import Utils from '@/utils';
import { reactive } from 'vue';
@ -69,7 +70,7 @@ const closeOnEscape = (e) => {
<img src="/icons/next.svg" class="h-16 rotate-180">
</button>
<div class="relative h-full laptop:w-full w-[300px] flex items-center justify-center">
<img :src="photo.path" class="laptop:h-full">
<img :src="Utils.DownloadUrl(photo.path)" class="laptop:h-full">
</div>
<button @click="nextPhoto" class="pl-3 hover:scale-105">
<img src="/icons/next.svg" class="h-16">

@ -4,6 +4,7 @@ import { useForm } from '@inertiajs/vue3';
import { reactive } from 'vue';
import Edit from './Edit.vue';
import axios from 'axios';
import Utils from '@/utils';
const props = defineProps({
photo: {
@ -58,6 +59,6 @@ const imageChange = () => {
<p class="text-sm text-white">publier par {{ props.photo.user.name }}</p>
</div>
</div>
<img :src="props.photo.path" class="w-full bg-white">
<img :src="Utils.DownloadUrl(props.photo.path)" class="w-full bg-white">
</div>
</template>

@ -4,6 +4,7 @@ import { useForm } from '@inertiajs/vue3';
import { reactive } from 'vue';
import Edit from './Edit.vue';
import axios from 'axios';
import Utils from '@/utils';
const props = defineProps({
photo: {
@ -47,7 +48,7 @@ const emits = defineEmits(["full-screen", "delete-photo"]);
<div class="flex items-center">
<button @click="() => emits('full-screen', props.photo.uuid)" class="bg-black/50 p-1 rounded-md mr-2"><img src="/icons/full-screen.svg" class="h-6 invert"></button>
<div class="laptop:relative">
<button v-if="!props.noEdit"@click="photoState.edit = !photoState.edit" class="bg-black/50 p-1 rounded-md mr-2"><img src="/icons/modify.svg" class="h-6 invert"></button>
<button v-if="!props.noEdit" @click="photoState.edit = !photoState.edit" class="bg-black/50 p-1 rounded-md mr-2"><img src="/icons/modify.svg" class="h-6 invert"></button>
<Edit v-if="photoState.edit && !props.noEdit"
@close="() => photoState.edit = false"
:photo="props.photo"
@ -64,6 +65,6 @@ const emits = defineEmits(["full-screen", "delete-photo"]);
<p class="laptop:text-sm text-xs text-white">publier par {{ props.photo.user.name }}</p>
</div>
</div>
<img :src="props.photo.path" class="w-full bg-white">
<img :src="Utils.DownloadUrl(props.photo.path)" class="w-full bg-white">
</div>
</template>

@ -3,4 +3,18 @@ export default class Utils {
e.preventDefault();
e.stopPropagation();
}
static openInNewTab(url) {
window.open(url, '_blank').focus();
}
static openInThisTab(url) {
window.location.href = url;
}
static DownloadUrl(key)
{
return route("s3.download") + "?key=" + key;
}
}

Loading…
Cancel
Save