Implementing a send invitation action
This commit is contained in:
parent
1e0c1a707d
commit
5893a2e665
|
@ -22,6 +22,7 @@ import { update } from '~/lib/update';
|
||||||
import { replicationDocument } from '~/lib/replication-document';
|
import { replicationDocument } from '~/lib/replication-document';
|
||||||
import { get } from '~/lib/get';
|
import { get } from '~/lib/get';
|
||||||
import { v4 as uuid } from 'uuid';
|
import { v4 as uuid } from 'uuid';
|
||||||
|
import { sendInvitation } from '~/routes/user/[id]';
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
values?: () => any;
|
values?: () => any;
|
||||||
|
@ -301,6 +302,15 @@ const User: Component<Props> = (props) => {
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const sendInvitationHandler = () => {
|
||||||
|
sendInvitation({
|
||||||
|
id: userId(data('username'), data('database')),
|
||||||
|
mail: data('mail'),
|
||||||
|
webInvitation: invitationLink(),
|
||||||
|
appInvitation: invitationLink('geo'),
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
console.log({
|
console.log({
|
||||||
caller: 'User ',
|
caller: 'User ',
|
||||||
props,
|
props,
|
||||||
|
@ -339,7 +349,8 @@ const User: Component<Props> = (props) => {
|
||||||
Invitations :
|
Invitations :
|
||||||
<A href={invitationLink()} target='_blank'>
|
<A href={invitationLink()} target='_blank'>
|
||||||
https
|
https
|
||||||
</A>,
|
</A>
|
||||||
|
,
|
||||||
<a href={invitationLink('geo')} target='_blank'>
|
<a href={invitationLink('geo')} target='_blank'>
|
||||||
geo
|
geo
|
||||||
</a>
|
</a>
|
||||||
|
@ -427,6 +438,12 @@ const User: Component<Props> = (props) => {
|
||||||
<Button.Root type='submit' disabled={!isDirty() || !isValid()}>
|
<Button.Root type='submit' disabled={!isDirty() || !isValid()}>
|
||||||
Save
|
Save
|
||||||
</Button.Root>
|
</Button.Root>
|
||||||
|
<Button.Root
|
||||||
|
disabled={isDirty() || !isValid()}
|
||||||
|
onclick={sendInvitationHandler}
|
||||||
|
>
|
||||||
|
Send invitation
|
||||||
|
</Button.Root>
|
||||||
<Button.Root onclick={deleteHandler}>Delete</Button.Root>
|
<Button.Root onclick={deleteHandler}>Delete</Button.Root>
|
||||||
</Match>
|
</Match>
|
||||||
<Match when={isNew()}>
|
<Match when={isNew()}>
|
||||||
|
|
|
@ -1,14 +1,19 @@
|
||||||
<!DOCTYPE html>
|
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta charset="utf-8">
|
<meta charset='utf-8' />
|
||||||
<meta http-equiv="x-ua-compatible" content="ie=edge">
|
<meta http-equiv='x-ua-compatible' content='ie=edge' />
|
||||||
<title>Validation</title>
|
<title>Validation</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<h2>Bienvenue {{id}}! </h2>
|
<h2>Bienvenue {{id}}! </h2>
|
||||||
<p>Le code de validation de votre configuration pour l'application Dyomedea est <code>{{code}}</code>.</p>
|
<p>Le code de validation de votre configuration pour l'application Dyomedea
|
||||||
|
est
|
||||||
|
<code>{{code}}</code>.</p>
|
||||||
<p>Ce code est valable pendant quinze minutes.</p>
|
<p>Ce code est valable pendant quinze minutes.</p>
|
||||||
<p>Eric</p>
|
<p>Eric</p>
|
||||||
</body>
|
<p>PS: vérifiez dans vos spams, notamment si vous utilisez gmail qui a
|
||||||
|
tendance à trouver que ce mail ressemble à du hameçonnage bien qu'il ne
|
||||||
|
contienne aucun lien.
|
||||||
|
</p>
|
||||||
|
</body>
|
||||||
</html>
|
</html>
|
|
@ -0,0 +1,34 @@
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta charset='utf-8' />
|
||||||
|
<meta http-equiv='x-ua-compatible' content='ie=edge' />
|
||||||
|
<title>Invitation</title>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<h2>Bienvenue {{id}}! </h2>
|
||||||
|
<p>Ce message est une invitation à
|
||||||
|
<a
|
||||||
|
href='https://dyomedea.app/2023/03/05/A-propos/#Configuration'
|
||||||
|
>configurer</a>
|
||||||
|
l'application
|
||||||
|
<a href='https://dyomedea.app'>Dyomedea</a>.</p>
|
||||||
|
<p>L'application peut être exécutée dans un navigateur sur n’importe quelle
|
||||||
|
plateforme (ordinateur, tablette, téléphone, …) ou sous la forme d’une
|
||||||
|
application Android.
|
||||||
|
</p>
|
||||||
|
<p>Pour configurer Dyomedea dans un navigateur, cliquez sur
|
||||||
|
<a href='{{webInvitation}}'>ce lien</a>.</p>
|
||||||
|
<p>Pour configurer l'application Android, commencez par télécharger et
|
||||||
|
installer l'application sur
|
||||||
|
<a href='https://dyomedea.app'>son site web</a>. A plusieurs reprises
|
||||||
|
Android essayera de vous dissuader mais je peux vous assurer que cette
|
||||||
|
application est moins dangereuse pour votre sécurité et votre vie privée
|
||||||
|
que les application Google !</p>
|
||||||
|
<p>Lorsque l'application sera installée, vous pourrez la configurer en
|
||||||
|
suivant
|
||||||
|
<a href='{{appInvitation}}'>ce lien</a>
|
||||||
|
sur votre téléphone.
|
||||||
|
</p>
|
||||||
|
<p>Eric</p>
|
||||||
|
</body>
|
||||||
|
</html>
|
|
@ -3,6 +3,49 @@ import User from '~/components/user';
|
||||||
import { createEffect, createSignal, Show } from 'solid-js';
|
import { createEffect, createSignal, Show } from 'solid-js';
|
||||||
import { adminCredentials, CheckCredentials } from '~/components/credentials';
|
import { adminCredentials, CheckCredentials } from '~/components/credentials';
|
||||||
import { get } from '~/lib/get';
|
import { get } from '~/lib/get';
|
||||||
|
import { createServerAction$ } from 'solid-start/server';
|
||||||
|
import { readConfig } from '~/server-only-lib/read-config';
|
||||||
|
import { createTransport } from 'nodemailer';
|
||||||
|
import { resolve } from 'path';
|
||||||
|
import hbs from 'nodemailer-express-handlebars';
|
||||||
|
|
||||||
|
export const [sendingInvitation, sendInvitation] = createServerAction$(
|
||||||
|
async (args: {
|
||||||
|
id: string;
|
||||||
|
mail: string;
|
||||||
|
webInvitation: string;
|
||||||
|
appInvitation: string;
|
||||||
|
}) => {
|
||||||
|
const { id, mail, webInvitation, appInvitation } = args;
|
||||||
|
const { credentials, mailer } = readConfig();
|
||||||
|
const transporter = createTransport(mailer);
|
||||||
|
|
||||||
|
const handlebarOptions = {
|
||||||
|
viewEngine: {
|
||||||
|
partialsDir: resolve('src/mail-template/'),
|
||||||
|
defaultLayout: false,
|
||||||
|
},
|
||||||
|
viewPath: resolve('src/mail-template/'),
|
||||||
|
};
|
||||||
|
transporter.use('compile', hbs(handlebarOptions));
|
||||||
|
|
||||||
|
const code = [...Array(6)].map((_) => (Math.random() * 10) | 0).join('');
|
||||||
|
|
||||||
|
const mailOptions = {
|
||||||
|
from: '"Dyomedea app" <app@dyomedea.com>', // sender address
|
||||||
|
to: mail, // list of receivers
|
||||||
|
subject: "Invitation à configurer l'application Dyomedea.",
|
||||||
|
template: 'invitation', // the name of the template file i.e email.handlebars
|
||||||
|
context: {
|
||||||
|
id,
|
||||||
|
webInvitation,
|
||||||
|
appInvitation,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
await transporter.sendMail(mailOptions);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
export default () => {
|
export default () => {
|
||||||
const { id } = useParams();
|
const { id } = useParams();
|
||||||
|
|
Loading…
Reference in New Issue