Fix/multiple bug reports (#1002)

* fix type issues for #999

* fix regression #995

* remove error from frontend and log error #996

* cleanup darkmode on login page

* keep primary color bg
This commit is contained in:
Hayden 2022-02-23 15:04:45 -09:00 committed by GitHub
parent 6ccffce320
commit ccfaa02b03
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 102 additions and 57 deletions

View File

@ -39,26 +39,29 @@
<span> Locked by Owner </span> <span> Locked by Owner </span>
</v-tooltip> </v-tooltip>
<RecipeContextMenu <ClientOnly>
show-print <RecipeContextMenu
:menu-top="false" show-print
:slug="slug" :menu-top="false"
:menu-icon="$globals.icons.mdiDotsHorizontal" :name="name"
fab :slug="slug"
color="info" :menu-icon="$globals.icons.mdiDotsHorizontal"
:card-menu="false" fab
:recipe-id="recipeId" color="info"
:use-items="{ :card-menu="false"
delete: false, :recipe-id="recipeId"
edit: false, :use-items="{
download: true, delete: false,
mealplanner: true, edit: false,
shoppingList: true, download: true,
print: true, mealplanner: true,
share: true, shoppingList: true,
}" print: true,
@print="$emit('print')" share: true,
/> }"
@print="$emit('print')"
/>
</ClientOnly>
</div> </div>
<div v-if="value" class="custom-btn-group mb-"> <div v-if="value" class="custom-btn-group mb-">
<v-btn <v-btn

View File

@ -23,7 +23,7 @@
<script lang="ts"> <script lang="ts">
import { computed, defineComponent, useContext } from "@nuxtjs/composition-api"; import { computed, defineComponent, useContext } from "@nuxtjs/composition-api";
import { useUserApi } from "~/composables/api"; import { useUserApi } from "~/composables/api";
import {UserOut} from "~/types/api-types/user"; import { UserOut } from "~/types/api-types/user";
export default defineComponent({ export default defineComponent({
props: { props: {
slug: { slug: {
@ -49,19 +49,15 @@ export default defineComponent({
const isFavorite = computed(() => user.value?.favoriteRecipes?.includes(props.slug)); const isFavorite = computed(() => user.value?.favoriteRecipes?.includes(props.slug));
async function toggleFavorite() { async function toggleFavorite() {
console.log("Favorited?");
if (!isFavorite.value) { if (!isFavorite.value) {
await api.users.addFavorite(user.value?.id, props.slug); await api.users.addFavorite(user.value?.id, props.slug);
} else { } else {
await api.users.removeFavorite(user.value?.id, props.slug); await api.users.removeFavorite(user.value?.id, props.slug);
} }
$auth.fetchUser(); $auth.fetchUser();
}; }
return { isFavorite, toggleFavorite }; return { isFavorite, toggleFavorite };
}, },
}); });
</script> </script>
<style lang="scss" scoped>
</style>

View File

@ -1,4 +1,18 @@
import { IncomingMessage } from "connect"; import { IncomingMessage } from "connect";
import { useDark } from "@vueuse/core";
import { useContext } from "@nuxtjs/composition-api";
export const useToggleDarkMode = () => {
const isDark = useDark();
const { $vuetify } = useContext();
function toggleDark() {
isDark.value = !$vuetify.theme.dark;
$vuetify.theme.dark = !$vuetify.theme.dark;
}
return toggleDark;
};
export const useAsyncKey = function () { export const useAsyncKey = function () {
return String(Date.now()); return String(Date.now());

View File

@ -62,11 +62,11 @@
<script lang="ts"> <script lang="ts">
import { computed, defineComponent, onMounted, ref, useContext } from "@nuxtjs/composition-api"; import { computed, defineComponent, onMounted, ref, useContext } from "@nuxtjs/composition-api";
import { useDark } from "@vueuse/core";
import AppHeader from "@/components/Layout/AppHeader.vue"; import AppHeader from "@/components/Layout/AppHeader.vue";
import AppSidebar from "@/components/Layout/AppSidebar.vue"; import AppSidebar from "@/components/Layout/AppSidebar.vue";
import TheSnackbar from "@/components/Layout/TheSnackbar.vue"; import TheSnackbar from "@/components/Layout/TheSnackbar.vue";
import { useCookbooks } from "~/composables/use-group-cookbooks"; import { useCookbooks } from "~/composables/use-group-cookbooks";
import { useToggleDarkMode } from "~/composables/use-utils";
export default defineComponent({ export default defineComponent({
components: { AppHeader, AppSidebar, TheSnackbar }, components: { AppHeader, AppSidebar, TheSnackbar },
@ -77,13 +77,7 @@ export default defineComponent({
const isAdmin = computed(() => $auth.user?.admin); const isAdmin = computed(() => $auth.user?.admin);
const isDark = useDark(); const toggleDark = useToggleDarkMode();
function toggleDark() {
isDark.value = !$vuetify.theme.dark;
$vuetify.theme.dark = !$vuetify.theme.dark;
console.log("toggleDark");
}
const sidebar = ref<boolean | null>(null); const sidebar = ref<boolean | null>(null);

View File

@ -45,10 +45,19 @@
{{ $t("general.test") }} {{ $t("general.test") }}
</BaseButton> </BaseButton>
<template v-if="tested"> <template v-if="tested">
<v-divider class="my-x"></v-divider> <v-divider class="my-x mt-6"></v-divider>
<v-card-text> <v-card-text class="px-0">
Email Test Result: {{ success ? "Succeeded" : "Failed" }} <h4>Email Test Results</h4>
<div>Errors: {{ error }}</div> <span class="pl-4">
{{ success ? "Succeeded" : "Failed" }}
</span>
<!-- <template v-if="errors">
<h4>Errors:</h4>
<span class="pl-4">
{{ errors }}
</span>
</template> -->
</v-card-text> </v-card-text>
</template> </template>
</div> </div>
@ -296,5 +305,4 @@ export default defineComponent({
}); });
</script> </script>
<style scoped> <style scoped></style>
</style>

View File

@ -1,5 +1,12 @@
<template> <template>
<v-container fill-height fluid class="d-flex justify-center align-center" style="background: #f5f8fa"> <v-container
fill-height
fluid
class="d-flex justify-center align-center"
:class="{
'bg-off-white': !$vuetify.theme.dark,
}"
>
<v-card tag="section" class="d-flex flex-column align-center" width="600px"> <v-card tag="section" class="d-flex flex-column align-center" width="600px">
<v-toolbar width="100%" color="primary" class="d-flex justify-center mb-4" dark> <v-toolbar width="100%" color="primary" class="d-flex justify-center mb-4" dark>
<v-toolbar-title class="headline text-h4"> Mealie </v-toolbar-title> <v-toolbar-title class="headline text-h4"> Mealie </v-toolbar-title>
@ -7,14 +14,12 @@
<div class="icon-container"> <div class="icon-container">
<v-divider class="icon-divider"></v-divider> <v-divider class="icon-divider"></v-divider>
<v-avatar size="102" color="grey lighten-2"> <v-avatar class="pa-2 icon-avatar" color="primary" size="100">
<v-avatar class="pa-2 icon-avatar" color="white" size="100"> <svg class="icon-white" style="width: 100px; height: 100px" viewBox="0 0 24 24">
<svg class="icon-primary" style="width: 100px; height: 100px" viewBox="0 0 24 24"> <path
<path d="M8.1,13.34L3.91,9.16C2.35,7.59 2.35,5.06 3.91,3.5L10.93,10.5L8.1,13.34M13.41,13L20.29,19.88L18.88,21.29L12,14.41L5.12,21.29L3.71,19.88L13.36,10.22L13.16,10C12.38,9.23 12.38,7.97 13.16,7.19L17.5,2.82L18.43,3.74L15.19,7L16.15,7.94L19.39,4.69L20.31,5.61L17.06,8.85L18,9.81L21.26,6.56L22.18,7.5L17.81,11.84C17.03,12.62 15.77,12.62 15,11.84L14.78,11.64L13.41,13Z"
d="M8.1,13.34L3.91,9.16C2.35,7.59 2.35,5.06 3.91,3.5L10.93,10.5L8.1,13.34M13.41,13L20.29,19.88L18.88,21.29L12,14.41L5.12,21.29L3.71,19.88L13.36,10.22L13.16,10C12.38,9.23 12.38,7.97 13.16,7.19L17.5,2.82L18.43,3.74L15.19,7L16.15,7.94L19.39,4.69L20.31,5.61L17.06,8.85L18,9.81L21.26,6.56L22.18,7.5L17.81,11.84C17.03,12.62 15.77,12.62 15,11.84L14.78,11.64L13.41,13Z" />
/> </svg>
</svg>
</v-avatar>
</v-avatar> </v-avatar>
</div> </div>
@ -91,16 +96,26 @@
</div> </div>
</v-card-text> </v-card-text>
</v-card> </v-card>
<v-btn absolute bottom center @click="toggleDark">
<v-icon left>
{{ $vuetify.theme.dark ? $globals.icons.weatherSunny : $globals.icons.weatherNight }}
</v-icon>
{{ $vuetify.theme.dark ? "Light Mode" : "Dark Mode" }}
</v-btn>
</v-container> </v-container>
</template> </template>
<script lang="ts"> <script lang="ts">
import { defineComponent, ref, useContext, computed, reactive } from "@nuxtjs/composition-api"; import { defineComponent, ref, useContext, computed, reactive } from "@nuxtjs/composition-api";
import { alert } from "~/composables/use-toast"; import { alert } from "~/composables/use-toast";
import { useToggleDarkMode } from "~/composables/use-utils";
export default defineComponent({ export default defineComponent({
layout: "blank", layout: "blank",
setup() { setup() {
const toggleDark = useToggleDarkMode();
const { $auth } = useContext(); const { $auth } = useContext();
const context = useContext(); const context = useContext();
@ -147,6 +162,7 @@ export default defineComponent({
loggingIn, loggingIn,
allowSignup, allowSignup,
authenticate, authenticate,
toggleDark,
}; };
}, },
@ -167,6 +183,10 @@ export default defineComponent({
fill: var(--v-primary-base); fill: var(--v-primary-base);
} }
.icon-white {
fill: white;
}
.icon-container { .icon-container {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
@ -185,4 +205,8 @@ export default defineComponent({
border-color: rgba(0, 0, 0, 0.12); border-color: rgba(0, 0, 0, 0.12);
border: 2px; border: 2px;
} }
.bg-off-white {
background: #f5f8fa;
}
</style> </style>

View File

@ -504,10 +504,12 @@ export default defineComponent({
async beforeRouteLeave(_to, _from, next) { async beforeRouteLeave(_to, _from, next) {
const isSame = JSON.stringify(this.recipe) === JSON.stringify(this.originalRecipe); const isSame = JSON.stringify(this.recipe) === JSON.stringify(this.originalRecipe);
console.log({ working: this.recipe, saved: this.originalRecipe });
if (this.form && !isSame && this.recipe?.slug !== undefined) { if (this.form && !isSame && this.recipe?.slug !== undefined) {
if (window.confirm("You have unsaved changes. Do you want to save before leaving?")) { if (
window.confirm(
"You have unsaved changes. Do you want to save before leaving?\n\nOkay to save, Cancel to discard changes."
)
) {
await this.api.recipes.updateOne(this.recipe.slug, this.recipe); await this.api.recipes.updateOne(this.recipe.slug, this.recipe);
} }
} }
@ -558,7 +560,6 @@ export default defineComponent({
invoke(async () => { invoke(async () => {
await until(recipe).not.toBeNull(); await until(recipe).not.toBeNull();
originalRecipe.value = deepCopy(recipe.value); originalRecipe.value = deepCopy(recipe.value);
}); });
@ -746,6 +747,7 @@ export default defineComponent({
useMeta(metaData); useMeta(metaData);
return { return {
originalRecipe,
createApiExtra, createApiExtra,
apiNewKey, apiNewKey,
enableLandscape, enableLandscape,

View File

@ -1,10 +1,10 @@
import { Plugin } from "@nuxt/types" import { Plugin } from "@nuxt/types";
import { NuxtAxiosInstance } from "@nuxtjs/axios"; import { NuxtAxiosInstance } from "@nuxtjs/axios";
import { alert } from "~/composables/use-toast"; import { alert } from "~/composables/use-toast";
const toastPlugin: Plugin = ({ $axios }: { $axios: NuxtAxiosInstance }) => { const toastPlugin: Plugin = ({ $axios }: { $axios: NuxtAxiosInstance }) => {
$axios.onResponse((response) => { $axios.onResponse((response) => {
if (response.data.message) { if (response?.data?.message) {
alert.info(response.data.message); alert.info(response.data.message);
} }
}); });
@ -13,6 +13,6 @@ const toastPlugin: Plugin = ({ $axios }: { $axios: NuxtAxiosInstance }) => {
alert.error(error.response.data.detail.message); alert.error(error.response.data.detail.message);
} }
}); });
} };
export default toastPlugin; export default toastPlugin;

View File

@ -1,6 +1,7 @@
from abc import ABC, abstractmethod from abc import ABC, abstractmethod
import emails import emails
from emails.backend.response import SMTPResponse
from mealie.core.root_logger import get_logger from mealie.core.root_logger import get_logger
from mealie.services._base_service import BaseService from mealie.services._base_service import BaseService
@ -29,7 +30,10 @@ class DefaultEmailSender(ABCEmailSender, BaseService):
smtp_options["user"] = self.settings.SMTP_USER smtp_options["user"] = self.settings.SMTP_USER
if self.settings.SMTP_PASSWORD: if self.settings.SMTP_PASSWORD:
smtp_options["password"] = self.settings.SMTP_PASSWORD smtp_options["password"] = self.settings.SMTP_PASSWORD
response = message.send(to=email_to, smtp=smtp_options) response: SMTPResponse = message.send(to=email_to, smtp=smtp_options)
logger.info(f"send email result: {response}") logger.info(f"send email result: {response}")
if not response.success:
logger.error(f"send email error: {response.error}")
return response.status_code in [250] return response.status_code in [250]