|
|
|
|
@ -474,14 +474,94 @@ When you start with the UI can you can prototype all of the interactions, figure |
|
|
|
|
aim for only what you need. Keep doing this and you'll slowly build a nice data model with less |
|
|
|
|
cruft for the application you're creating. |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
## Additional Features |
|
|
|
|
|
|
|
|
|
### Sending Emails |
|
|
|
|
## Sending Emails |
|
|
|
|
|
|
|
|
|
Coming soon... |
|
|
|
|
> __WARNING__: The email sending feature is currently very simple. Don't think you can send 200 |
|
|
|
|
> million spam messages with it. |
|
|
|
|
|
|
|
|
|
The email system uses a [Redis]() queue to schedule messages, and an email router to actually |
|
|
|
|
deliver them. The idea is that you don't want to wait for email crafting and delivery in your web |
|
|
|
|
application most of the time. Ideally what you want to do is: |
|
|
|
|
|
|
|
|
|
1. In an `api.go` you receive a form or action from the user that needs an email. Say a password |
|
|
|
|
reset. |
|
|
|
|
2. You use the `common/email` module to craft a simple message and send it to the queue. Your |
|
|
|
|
message at this stage is usually a very simple `struct` with the information your email router |
|
|
|
|
needs to build the email. |
|
|
|
|
3. In your `api.go` file _immediately return rather than wait for email delivery._ |
|
|
|
|
4. Your email router then sits there and processes the email requests. When a new message comes in |
|
|
|
|
it takes the data, queries your database, configures the templates, and finally sends it to the |
|
|
|
|
email server. |
|
|
|
|
|
|
|
|
|
Since email is asynchronous there's no point in your web application waiting around for all of #4 to |
|
|
|
|
be done. Just toss out a message on a queue and move on. |
|
|
|
|
|
|
|
|
|
### Running the `mailer` |
|
|
|
|
|
|
|
|
|
There's a simple router implemented in `tools/cmd/mailer` that you can run to get going. You can |
|
|
|
|
use this to send simple emails but you should probably write a new one that handles your more |
|
|
|
|
sophisticated emails like password resets and receipts. |
|
|
|
|
|
|
|
|
|
You can run it from the command line with: |
|
|
|
|
|
|
|
|
|
```shell |
|
|
|
|
./bin/mailer |
|
|
|
|
``` |
|
|
|
|
|
|
|
|
|
It will require that you install `redis` for it to work. |
|
|
|
|
|
|
|
|
|
### Testing Your Email Locally |
|
|
|
|
|
|
|
|
|
Running an email server locally is kind of a pain, and setting up everything so you can view sent |
|
|
|
|
emails is even harder. That's way the awesome and fabulous [MailHog](https://github.com/mailhog/MailHog) exists. |
|
|
|
|
|
|
|
|
|
You can install it easily (it's written in Go) and then run it: |
|
|
|
|
|
|
|
|
|
```shell |
|
|
|
|
MailHog |
|
|
|
|
``` |
|
|
|
|
|
|
|
|
|
By default it opens an SMTP port on `1025` and a web server at 127.0.0.1:8025. If you point your |
|
|
|
|
browser at 127.0.0.:8025 you'll get a fake email inbox. This inbox will show you both the HTML and |
|
|
|
|
TEXT versions of your email, plus other useful things. |
|
|
|
|
|
|
|
|
|
### How To Send |
|
|
|
|
|
|
|
|
|
### Receiving Payments |
|
|
|
|
Here's an example of sending an email from a form submission in `features/email/api.go`. |
|
|
|
|
|
|
|
|
|
```go |
|
|
|
|
package features_email |
|
|
|
|
|
|
|
|
|
import ( |
|
|
|
|
email "MY/webapp/common/email" |
|
|
|
|
"github.com/gofiber/fiber/v2" |
|
|
|
|
) |
|
|
|
|
|
|
|
|
|
func PostApiEmailSend(c *fiber.Ctx) error { |
|
|
|
|
go email.OneShotSend(email.EmailMessage{ |
|
|
|
|
To: c.FormValue("To"), |
|
|
|
|
From: c.FormValue("From"), |
|
|
|
|
Subject: c.FormValue("Subject"), |
|
|
|
|
Template: c.FormValue("Template"), |
|
|
|
|
}) |
|
|
|
|
|
|
|
|
|
return c.Redirect("/email/") |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func SetupApi(app *fiber.App) { |
|
|
|
|
app.Post("/api/email/send", PostApiEmailSend) |
|
|
|
|
} |
|
|
|
|
``` |
|
|
|
|
|
|
|
|
|
### Email Templates |
|
|
|
|
|
|
|
|
|
The templates use the same default `text/template` engine that the rest of the system uses, but you |
|
|
|
|
should use Markdown to write them. This automatically gives you both a nice text format (Markdown |
|
|
|
|
already is like an email) and an HTML output. Look at `emails/signup.md` for a simple example. |
|
|
|
|
|
|
|
|
|
## Receiving Payments |
|
|
|
|
|
|
|
|
|
Coming soon... |
|
|
|
|
|
|
|
|
|
@ -489,6 +569,15 @@ Coming soon... |
|
|
|
|
|
|
|
|
|
Here's some questions I get when people see this. |
|
|
|
|
|
|
|
|
|
### What if My Email Templates Need HTML? |
|
|
|
|
|
|
|
|
|
You should be able to work with the code in `common/email` to make it do what you want. I don't |
|
|
|
|
think it's specifically looking for any extension, but I haven't tested it. Try just dropping the |
|
|
|
|
`.html` you want into the `emails/` directory and sending it. |
|
|
|
|
|
|
|
|
|
You should also know that really complex HTML usually get filtered, so it's best to keep it simple |
|
|
|
|
HTML and Markdown will help you stick to that. |
|
|
|
|
|
|
|
|
|
### Isn't Fiber Banned?! |
|
|
|
|
|
|
|
|
|
First off, nobody has the right to "ban" a project. If you're hanging out in the Go discord and |
|
|
|
|
|