update
parent
199705b555
commit
c574b8ae6e
7
go.mod
7
go.mod
|
@ -9,6 +9,8 @@ require (
|
|||
github.com/rs/xid v1.3.0
|
||||
github.com/rs/zerolog v1.26.1
|
||||
github.com/spf13/viper v1.10.1
|
||||
github.com/vanng822/go-premailer v1.20.1
|
||||
github.com/yuin/goldmark v1.4.4
|
||||
golang.org/x/crypto v0.0.0-20211215165025-cf75a172585e
|
||||
gorm.io/driver/mysql v1.2.1
|
||||
gorm.io/driver/postgres v1.2.3
|
||||
|
@ -17,6 +19,8 @@ require (
|
|||
)
|
||||
|
||||
require (
|
||||
github.com/PuerkitoBio/goquery v1.5.1 // indirect
|
||||
github.com/andybalholm/cascadia v1.1.0 // indirect
|
||||
github.com/fsnotify/fsnotify v1.5.1 // indirect
|
||||
github.com/gin-contrib/sse v0.1.0 // indirect
|
||||
github.com/go-playground/locales v0.13.0 // indirect
|
||||
|
@ -24,6 +28,7 @@ require (
|
|||
github.com/go-playground/validator/v10 v10.4.1 // indirect
|
||||
github.com/go-sql-driver/mysql v1.6.0 // indirect
|
||||
github.com/golang/protobuf v1.5.2 // indirect
|
||||
github.com/gorilla/css v1.0.0 // indirect
|
||||
github.com/hashicorp/hcl v1.0.0 // indirect
|
||||
github.com/jackc/chunkreader/v2 v2.0.1 // indirect
|
||||
github.com/jackc/pgconn v1.10.1 // indirect
|
||||
|
@ -50,6 +55,8 @@ require (
|
|||
github.com/spf13/pflag v1.0.5 // indirect
|
||||
github.com/subosito/gotenv v1.2.0 // indirect
|
||||
github.com/ugorji/go/codec v1.1.7 // indirect
|
||||
github.com/vanng822/css v1.0.1 // indirect
|
||||
golang.org/x/net v0.0.0-20210813160813-60bc85c4be6d // indirect
|
||||
golang.org/x/sys v0.0.0-20211210111614-af8b64212486 // indirect
|
||||
golang.org/x/text v0.3.7 // indirect
|
||||
google.golang.org/protobuf v1.27.1 // indirect
|
||||
|
|
22
go.sum
22
go.sum
|
@ -1,6 +1,10 @@
|
|||
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
|
||||
github.com/Masterminds/semver/v3 v3.1.1 h1:hLg3sBzpNErnxhQtUy/mmLR2I9foDujNK030IGemrRc=
|
||||
github.com/Masterminds/semver/v3 v3.1.1/go.mod h1:VPu/7SZ7ePZ3QOrcuXROw5FAcLl4a0cBrbBpGY/8hQs=
|
||||
github.com/PuerkitoBio/goquery v1.5.1 h1:PSPBGne8NIUWw+/7vFBV+kG2J/5MOjbzc7154OaKCSE=
|
||||
github.com/PuerkitoBio/goquery v1.5.1/go.mod h1:GsLWisAFVj4WgDibEWF4pvYnkVQBpKBKeU+7zCJoLcc=
|
||||
github.com/andybalholm/cascadia v1.1.0 h1:BuuO6sSfQNFRu1LppgbD25Hr2vLYW25JvxHs5zzsLTo=
|
||||
github.com/andybalholm/cascadia v1.1.0/go.mod h1:GsXiBklL0woXo1j/WYWtSYYC4ouU9PqHO0sqidkEA4Y=
|
||||
github.com/cockroachdb/apd v1.1.0 h1:3LFP3629v+1aKXU5Q37mxmRxX/pIu1nijXydLShEq5I=
|
||||
github.com/cockroachdb/apd v1.1.0/go.mod h1:8Sl8LxpKi29FqWXR16WEFZRNSz3SoPzUzeMeY4+DwBQ=
|
||||
github.com/coreos/go-systemd v0.0.0-20190321100706-95778dfbb74e/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4=
|
||||
|
@ -10,6 +14,7 @@ github.com/creack/pty v1.1.7/go.mod h1:lj5s0c3V2DBrqTV7llrYr5NG6My20zk30Fl46Y7Do
|
|||
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
|
||||
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/eknkc/amber v0.0.0-20171010120322-cdade1c07385/go.mod h1:0vRUJqYpeSZifjYj7uP3BG/gKcuzL9xWVV/Y+cK33KM=
|
||||
github.com/fsnotify/fsnotify v1.5.1 h1:mZcQUHVQUQWoPXXtuf9yuEXKudkV2sx1E06UadKWpgI=
|
||||
github.com/fsnotify/fsnotify v1.5.1/go.mod h1:T3375wBYaZdLLcVNkcVbzGHY7f1l/uK5T5Ai1i3InKU=
|
||||
github.com/gin-contrib/sse v0.1.0 h1:Y/yl/+YNO8GZSjAhjMsSuLt29uWRFHdHYUb5lYOV9qE=
|
||||
|
@ -42,6 +47,8 @@ github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/
|
|||
github.com/google/go-cmp v0.5.6 h1:BKbKCqvP6I+rmFHt06ZmyQtvB8xAkWdhFyr0ZUNZcxQ=
|
||||
github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
||||
github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI=
|
||||
github.com/gorilla/css v1.0.0 h1:BQqNyPTi50JCFMTw/b67hByjMVXZRwGha6wxVGkeihY=
|
||||
github.com/gorilla/css v1.0.0/go.mod h1:Dn721qIggHpt4+EFCcTLTU/vk5ySda2ReITrtgBl60c=
|
||||
github.com/hashicorp/hcl v1.0.0 h1:0Anlzjpi4vEasTeNFn2mLJgTSwt0+6sfsiTG8qcWGx4=
|
||||
github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ=
|
||||
github.com/jackc/chunkreader v1.0.0/go.mod h1:RT6O25fNZIuasFJRyZ4R/Y2BbhasbmZXF9QQ7T3kePo=
|
||||
|
@ -176,6 +183,7 @@ github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXf
|
|||
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
|
||||
github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
|
||||
github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
|
||||
github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
|
||||
github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY=
|
||||
github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
|
||||
github.com/subosito/gotenv v1.2.0 h1:Slr1R9HxAlEKefgq5jn9U+DnETlIUa6HfgEzj0g5d7s=
|
||||
|
@ -183,7 +191,15 @@ github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69
|
|||
github.com/ugorji/go v1.1.7/go.mod h1:kZn38zHttfInRq0xu/PH0az30d+z6vm202qpg1oXVMw=
|
||||
github.com/ugorji/go/codec v1.1.7 h1:2SvQaVZ1ouYrrKKwoSk2pzd4A9evlKJb9oTL+OaLUSs=
|
||||
github.com/ugorji/go/codec v1.1.7/go.mod h1:Ax+UKWsSmolVDwsd+7N3ZtXu+yMGCf907BLYF3GoBXY=
|
||||
github.com/unrolled/render v1.0.3/go.mod h1:gN9T0NhL4Bfbwu8ann7Ry/TGHYfosul+J0obPf6NBdM=
|
||||
github.com/vanng822/css v1.0.1 h1:10yiXc4e8NI8ldU6mSrWmSWMuyWgPr9DZ63RSlsgDw8=
|
||||
github.com/vanng822/css v1.0.1/go.mod h1:tcnB1voG49QhCrwq1W0w5hhGasvOg+VQp9i9H1rCM1w=
|
||||
github.com/vanng822/go-premailer v1.20.1 h1:2LTSIULXxNV5IOB5BSD3dlfOG95cq8qqExtRZMImTGA=
|
||||
github.com/vanng822/go-premailer v1.20.1/go.mod h1:RAxbRFp6M/B171gsKu8dsyq+Y5NGsUUvYfg+WQWusbE=
|
||||
github.com/vanng822/r2router v0.0.0-20150523112421-1023140a4f30/go.mod h1:1BVq8p2jVr55Ost2PkZWDrG86PiJ/0lxqcXoAcGxvWU=
|
||||
github.com/yuin/goldmark v1.4.0/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
||||
github.com/yuin/goldmark v1.4.4 h1:zNWRjYUW32G9KirMXYHQHVNFkXvMI7LpgNW2AgYAoIs=
|
||||
github.com/yuin/goldmark v1.4.4/go.mod h1:rmuwmfZ0+bvzB24eSC//bk1R1Zp3hM0OXYv/G2LIilg=
|
||||
github.com/zenazn/goji v0.9.0/go.mod h1:7S9M489iMyHBNxwZnk9/EHS098H4/F6TATF2mIxtB1Q=
|
||||
go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE=
|
||||
go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE=
|
||||
|
@ -212,12 +228,17 @@ golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHl
|
|||
golang.org/x/mod v0.0.0-20190513183733-4bf6d317e70e/go.mod h1:mXi4GBBbnImb6dmsKGUJ2LatrhH/nqhxcFungHvyanc=
|
||||
golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg=
|
||||
golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/net v0.0.0-20180218175443-cbe0f9307d01/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
|
||||
golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
|
||||
golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
||||
golang.org/x/net v0.0.0-20190813141303-74dc4d7220e7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
||||
golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
||||
golang.org/x/net v0.0.0-20200904194848-62affa334b73/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA=
|
||||
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||
golang.org/x/net v0.0.0-20210805182204-aaa1db679c0d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||
golang.org/x/net v0.0.0-20210813160813-60bc85c4be6d h1:LO7XpTYMwTqxjLcGWPijK3vRXg1aWdlNOVOHRq45d7c=
|
||||
golang.org/x/net v0.0.0-20210813160813-60bc85c4be6d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
|
@ -230,6 +251,7 @@ golang.org/x/sys v0.0.0-20190813064441-fde4db37ae7a/go.mod h1:h1NjWce9XRLGQEsW7w
|
|||
golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20200116001909-b77594299b42/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
|
|
|
@ -0,0 +1,22 @@
|
|||
package messenger
|
||||
|
||||
type App struct {
|
||||
Name string
|
||||
Link string
|
||||
Logo string
|
||||
Copyright string
|
||||
}
|
||||
|
||||
type Base struct {
|
||||
App App
|
||||
Title string
|
||||
Intros []string
|
||||
Outros []string
|
||||
Markdown string
|
||||
|
||||
Greeting string
|
||||
Receiver string
|
||||
|
||||
Signature string
|
||||
Sender string
|
||||
}
|
|
@ -268,11 +268,11 @@
|
|||
<!-- Logo -->
|
||||
<tr>
|
||||
<td class="email-masthead">
|
||||
<a class="email-masthead_name" href="{{.Hermes.Product.Link}}" target="_blank">
|
||||
{{ if .Hermes.Product.Logo }}
|
||||
<img src="{{.Hermes.Product.Logo | url }}" class="email-logo" />
|
||||
<a class="email-masthead_name" href="{{.App.Link}}" target="_blank">
|
||||
{{ if .App.Logo }}
|
||||
<img src="{{.App.Logo }}" class="email-logo" />
|
||||
{{ else }}
|
||||
{{ .Hermes.Product.Name }}
|
||||
{{ .App.Name }}
|
||||
{{ end }}
|
||||
</a>
|
||||
</td>
|
||||
|
@ -284,172 +284,38 @@
|
|||
<!-- Body content -->
|
||||
<tr>
|
||||
<td class="content-cell">
|
||||
<h1>{{if .Email.Body.Title }}{{ .Email.Body.Title }}{{ else }}{{ .Email.Body.Greeting }} {{ .Email.Body.Name }},{{ end }}</h1>
|
||||
{{ with .Email.Body.Intros }}
|
||||
<h1>{{if .Greeting}}{{.Greeting}}{{else}}Hi{{end}} {{ .Receiver }},</h1>
|
||||
{{/* Intros */}}
|
||||
{{ with .Intros }}
|
||||
{{ if gt (len .) 0 }}
|
||||
{{ range $line := . }}
|
||||
<p>{{ $line }}</p>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ if (ne .Email.Body.FreeMarkdown "") }}
|
||||
{{ .Email.Body.FreeMarkdown.ToHTML }}
|
||||
|
||||
{{/* Main Body */}}
|
||||
{{ if (ne .Markdown "") }}
|
||||
{{ .Markdown | ToHTML }}
|
||||
{{ else }}
|
||||
{{ with .Email.Body.Dictionary }}
|
||||
{{ if gt (len .) 0 }}
|
||||
<dl class="body-dictionary">
|
||||
{{ range $entry := . }}
|
||||
<dt>{{ $entry.Key }}:</dt>
|
||||
<dd>{{ $entry.Value }}</dd>
|
||||
<p>No Body</p>
|
||||
{{ end }}
|
||||
</dl>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
<!-- Table -->
|
||||
{{ with .Email.Body.Table }}
|
||||
{{ $data := .Data }}
|
||||
{{ $columns := .Columns }}
|
||||
{{ if gt (len $data) 0 }}
|
||||
<table class="data-wrapper" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td colspan="2">
|
||||
<table class="data-table" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
{{ $col := index $data 0 }}
|
||||
{{ range $entry := $col }}
|
||||
<th
|
||||
{{ with $columns }}
|
||||
{{ $width := index .CustomWidth $entry.Key }}
|
||||
{{ with $width }}
|
||||
width="{{ . }}"
|
||||
{{ end }}
|
||||
{{ $align := index .CustomAlignment $entry.Key }}
|
||||
{{ with $align }}
|
||||
style="text-align:{{ . }}"
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
>
|
||||
<p>{{ $entry.Key }}</p>
|
||||
</th>
|
||||
{{ end }}
|
||||
</tr>
|
||||
{{ range $row := $data }}
|
||||
<tr>
|
||||
{{ range $cell := $row }}
|
||||
<td
|
||||
{{ with $columns }}
|
||||
{{ $align := index .CustomAlignment $cell.Key }}
|
||||
{{ with $align }}
|
||||
style="text-align:{{ . }}"
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
>
|
||||
{{ $cell.Value }}
|
||||
</td>
|
||||
{{ end }}
|
||||
</tr>
|
||||
{{ end }}
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
<!-- Action -->
|
||||
{{ with .Email.Body.Actions }}
|
||||
{{ if gt (len .) 0 }}
|
||||
{{ range $action := . }}
|
||||
<p>{{ $action.Instructions }}</p>
|
||||
{{ $length := len $action.Button.Text }}
|
||||
{{ $width := add (mul $length 9) 20 }}
|
||||
{{if (lt $width 200)}}{{$width = 200}}{{else if (gt $width 570)}}{{$width = 570}}{{else}}{{end}}
|
||||
{{safe "<!--[if mso]>" }}
|
||||
{{ if $action.Button.Text }}
|
||||
<div style="margin: 30px auto;v-text-anchor:middle;text-align:center">
|
||||
<v:roundrect xmlns:v="urn:schemas-microsoft-com:vml"
|
||||
xmlns:w="urn:schemas-microsoft-com:office:word"
|
||||
href="{{ $action.Button.Link }}"
|
||||
style="height:45px;v-text-anchor:middle;width:{{$width}}px;background-color:{{ if $action.Button.Color }}{{ $action.Button.Color }}{{ else }}#3869D4{{ end }};"
|
||||
arcsize="10%"
|
||||
{{ if $action.Button.Color }}strokecolor="{{ $action.Button.Color }}" fillcolor="{{ $action.Button.Color }}"{{ else }}strokecolor="#3869D4" fillcolor="#3869D4"{{ end }}
|
||||
>
|
||||
<w:anchorlock/>
|
||||
<center style="color: {{ if $action.Button.TextColor }}{{ $action.Button.TextColor }}{{else}}#FFFFFF{{ end }};font-size: 15px;text-align: center;font-family:sans-serif;font-weight:bold;">
|
||||
{{ $action.Button.Text }}
|
||||
</center>
|
||||
</v:roundrect>
|
||||
</div>
|
||||
{{ end }}
|
||||
{{ if $action.InviteCode }}
|
||||
<div style="margin-top:30px;margin-bottom:30px">
|
||||
<table class="body-action" align="center" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table align="center" cellpadding="0" cellspacing="0" style="padding:0;text-align:center">
|
||||
<tr>
|
||||
<td style="display:inline-block;border-radius:3px;font-family:Consolas, monaco, monospace;font-size:28px;text-align:center;letter-spacing:8px;color:#555;background-color:#eee;padding:20px">
|
||||
{{ $action.InviteCode }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
{{ end }}
|
||||
{{safe "<![endif]-->" }}
|
||||
{{safe "<!--[if !mso]><!-- -->"}}
|
||||
<table class="body-action" align="center" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<div>
|
||||
{{ if $action.Button.Text }}
|
||||
<a href="{{ $action.Button.Link }}" class="button" style="{{ with $action.Button.Color }}background-color: {{ . }};{{ end }} {{ with $action.Button.TextColor }}color: {{ . }};{{ end }} width: {{$width}}px;" target="_blank">
|
||||
{{ $action.Button.Text }}
|
||||
</a>
|
||||
{{end}}
|
||||
{{ if $action.InviteCode }}
|
||||
<span class="invite-code">{{ $action.InviteCode }}</span>
|
||||
{{end}}
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
{{safe "<![endif]-->" }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ with .Email.Body.Outros }}
|
||||
|
||||
{{/* Outros */}}
|
||||
{{ with .Outros }}
|
||||
{{ if gt (len .) 0 }}
|
||||
{{ range $line := . }}
|
||||
<p>{{ $line }}</p>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
|
||||
{{/* End Email */}}
|
||||
<p>
|
||||
{{.Email.Body.Signature}},
|
||||
{{.Signature}},
|
||||
<br />
|
||||
{{.Hermes.Product.Name}}
|
||||
{{ if .Sender }}{{.Sender}}{{else}}{{.App.Name}}{{end}}
|
||||
</p>
|
||||
{{ if (eq .Email.Body.FreeMarkdown "") }}
|
||||
{{ with .Email.Body.Actions }}
|
||||
<table class="body-sub">
|
||||
<tbody>
|
||||
{{ range $action := . }}
|
||||
{{if $action.Button.Text}}
|
||||
<tr>
|
||||
<td>
|
||||
<p class="sub">{{$.Hermes.Product.TroubleText | replace "{ACTION}" $action.Button.Text}}</p>
|
||||
<p class="sub"><a href="{{ $action.Button.Link }}">{{ $action.Button.Link }}</a></p>
|
||||
</td>
|
||||
</tr>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
</tbody>
|
||||
</table>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
@ -461,7 +327,7 @@
|
|||
<tr>
|
||||
<td class="content-cell">
|
||||
<p class="sub center">
|
||||
{{.Hermes.Product.Copyright}}
|
||||
{{.App.Copyright}}
|
||||
</p>
|
||||
</td>
|
||||
</tr>
|
||||
|
|
|
@ -0,0 +1,476 @@
|
|||
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml">
|
||||
<head>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
|
||||
<style type="text/css" rel="stylesheet" media="all">
|
||||
/* Base ------------------------------ */
|
||||
*:not(br):not(tr):not(html) {
|
||||
font-family: Arial, 'Helvetica Neue', Helvetica, sans-serif;
|
||||
-webkit-box-sizing: border-box;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
body {
|
||||
width: 100% !important;
|
||||
height: 100%;
|
||||
margin: 0;
|
||||
line-height: 1.4;
|
||||
background-color: #F2F4F6;
|
||||
color: #74787E;
|
||||
-webkit-text-size-adjust: none;
|
||||
}
|
||||
a {
|
||||
color: #3869D4;
|
||||
}
|
||||
/* Layout ------------------------------ */
|
||||
.email-wrapper {
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
background-color: #F2F4F6;
|
||||
}
|
||||
.email-content {
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
/* Masthead ----------------------- */
|
||||
.email-masthead {
|
||||
padding: 25px 0;
|
||||
text-align: center;
|
||||
}
|
||||
.email-masthead_logo {
|
||||
max-width: 400px;
|
||||
border: 0;
|
||||
}
|
||||
.email-masthead_name {
|
||||
font-size: 16px;
|
||||
font-weight: bold;
|
||||
color: #2F3133;
|
||||
text-decoration: none;
|
||||
text-shadow: 0 1px 0 white;
|
||||
}
|
||||
.email-logo {
|
||||
max-height: 50px;
|
||||
}
|
||||
/* Body ------------------------------ */
|
||||
.email-body {
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
border-top: 1px solid #EDEFF2;
|
||||
border-bottom: 1px solid #EDEFF2;
|
||||
background-color: #FFF;
|
||||
}
|
||||
.email-body_inner {
|
||||
width: 570px;
|
||||
margin: 0 auto;
|
||||
padding: 0;
|
||||
}
|
||||
.email-footer {
|
||||
width: 570px;
|
||||
margin: 0 auto;
|
||||
padding: 0;
|
||||
text-align: center;
|
||||
}
|
||||
.email-footer p {
|
||||
color: #AEAEAE;
|
||||
}
|
||||
.body-action {
|
||||
width: 100%;
|
||||
margin: 30px auto;
|
||||
padding: 0;
|
||||
text-align: center;
|
||||
}
|
||||
.body-dictionary {
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
margin: 20px auto 10px;
|
||||
padding: 0;
|
||||
}
|
||||
.body-dictionary dd {
|
||||
margin: 0 0 10px 0;
|
||||
}
|
||||
.body-dictionary dt {
|
||||
clear: both;
|
||||
color: #000;
|
||||
font-weight: bold;
|
||||
}
|
||||
.body-dictionary dd {
|
||||
margin-left: 0;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
.body-sub {
|
||||
margin-top: 25px;
|
||||
padding-top: 25px;
|
||||
border-top: 1px solid #EDEFF2;
|
||||
table-layout: fixed;
|
||||
}
|
||||
.body-sub a {
|
||||
word-break: break-all;
|
||||
}
|
||||
.content-cell {
|
||||
padding: 35px;
|
||||
}
|
||||
.align-right {
|
||||
text-align: right;
|
||||
}
|
||||
/* Type ------------------------------ */
|
||||
h1 {
|
||||
margin-top: 0;
|
||||
color: #2F3133;
|
||||
font-size: 19px;
|
||||
font-weight: bold;
|
||||
}
|
||||
h2 {
|
||||
margin-top: 0;
|
||||
color: #2F3133;
|
||||
font-size: 16px;
|
||||
font-weight: bold;
|
||||
}
|
||||
h3 {
|
||||
margin-top: 0;
|
||||
color: #2F3133;
|
||||
font-size: 14px;
|
||||
font-weight: bold;
|
||||
}
|
||||
blockquote {
|
||||
margin: 25px 0;
|
||||
padding-left: 10px;
|
||||
border-left: 10px solid #F0F2F4;
|
||||
}
|
||||
blockquote p {
|
||||
font-size: 1.1rem;
|
||||
color: #999;
|
||||
}
|
||||
blockquote cite {
|
||||
display: block;
|
||||
text-align: right;
|
||||
color: #666;
|
||||
font-size: 1.2rem;
|
||||
}
|
||||
cite {
|
||||
display: block;
|
||||
font-size: 0.925rem;
|
||||
}
|
||||
cite:before {
|
||||
content: "\2014 \0020";
|
||||
}
|
||||
p {
|
||||
margin-top: 0;
|
||||
color: #74787E;
|
||||
font-size: 16px;
|
||||
line-height: 1.5em;
|
||||
}
|
||||
p.sub {
|
||||
font-size: 12px;
|
||||
}
|
||||
p.center {
|
||||
text-align: center;
|
||||
}
|
||||
table {
|
||||
width: 100%;
|
||||
}
|
||||
th {
|
||||
padding: 0px 5px;
|
||||
padding-bottom: 8px;
|
||||
border-bottom: 1px solid #EDEFF2;
|
||||
}
|
||||
th p {
|
||||
margin: 0;
|
||||
color: #9BA2AB;
|
||||
font-size: 12px;
|
||||
}
|
||||
td {
|
||||
padding: 10px 5px;
|
||||
color: #74787E;
|
||||
font-size: 15px;
|
||||
line-height: 18px;
|
||||
}
|
||||
.content {
|
||||
align: center;
|
||||
padding: 0;
|
||||
}
|
||||
/* Data table ------------------------------ */
|
||||
.data-wrapper {
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
padding: 35px 0;
|
||||
}
|
||||
.data-table {
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
}
|
||||
.data-table th {
|
||||
text-align: left;
|
||||
padding: 0px 5px;
|
||||
padding-bottom: 8px;
|
||||
border-bottom: 1px solid #EDEFF2;
|
||||
}
|
||||
.data-table th p {
|
||||
margin: 0;
|
||||
color: #9BA2AB;
|
||||
font-size: 12px;
|
||||
}
|
||||
.data-table td {
|
||||
padding: 10px 5px;
|
||||
color: #74787E;
|
||||
font-size: 15px;
|
||||
line-height: 18px;
|
||||
}
|
||||
/* Invite Code ------------------------------ */
|
||||
.invite-code {
|
||||
display: inline-block;
|
||||
padding-top: 20px;
|
||||
padding-right: 36px;
|
||||
padding-bottom: 16px;
|
||||
padding-left: 36px;
|
||||
border-radius: 3px;
|
||||
font-family: Consolas, monaco, monospace;
|
||||
font-size: 28px;
|
||||
text-align: center;
|
||||
letter-spacing: 8px;
|
||||
color: #555;
|
||||
background-color: #eee;
|
||||
}
|
||||
/* Buttons ------------------------------ */
|
||||
.button {
|
||||
display: inline-block;
|
||||
background-color: #3869D4;
|
||||
border-radius: 3px;
|
||||
color: #ffffff !important;
|
||||
font-size: 15px;
|
||||
line-height: 45px;
|
||||
text-align: center;
|
||||
text-decoration: none;
|
||||
-webkit-text-size-adjust: none;
|
||||
mso-hide: all;
|
||||
}
|
||||
/*Media Queries ------------------------------ */
|
||||
@media only screen and (max-width: 600px) {
|
||||
.email-body_inner,
|
||||
.email-footer {
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
@media only screen and (max-width: 500px) {
|
||||
.button {
|
||||
width: 100% !important;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<table class="email-wrapper" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td class="content">
|
||||
<table class="email-content" width="100%" cellpadding="0" cellspacing="0">
|
||||
<!-- Logo -->
|
||||
<tr>
|
||||
<td class="email-masthead">
|
||||
<a class="email-masthead_name" href="{{.Hermes.Product.Link}}" target="_blank">
|
||||
{{ if .Hermes.Product.Logo }}
|
||||
<img src="{{.Hermes.Product.Logo | url }}" class="email-logo" />
|
||||
{{ else }}
|
||||
{{ .Hermes.Product.Name }}
|
||||
{{ end }}
|
||||
</a>
|
||||
</td>
|
||||
</tr>
|
||||
<!-- Email Body -->
|
||||
<tr>
|
||||
<td class="email-body" width="100%">
|
||||
<table class="email-body_inner" align="center" width="570" cellpadding="0" cellspacing="0">
|
||||
<!-- Body content -->
|
||||
<tr>
|
||||
<td class="content-cell">
|
||||
<h1>{{if .Email.Body.Title }}{{ .Email.Body.Title }}{{ else }}{{ .Email.Body.Greeting }} {{ .Email.Body.Name }},{{ end }}</h1>
|
||||
{{ with .Email.Body.Intros }}
|
||||
{{ if gt (len .) 0 }}
|
||||
{{ range $line := . }}
|
||||
<p>{{ $line }}</p>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ if (ne .Email.Body.FreeMarkdown "") }}
|
||||
{{ .Email.Body.FreeMarkdown.ToHTML }}
|
||||
{{ else }}
|
||||
{{ with .Email.Body.Dictionary }}
|
||||
{{ if gt (len .) 0 }}
|
||||
<dl class="body-dictionary">
|
||||
{{ range $entry := . }}
|
||||
<dt>{{ $entry.Key }}:</dt>
|
||||
<dd>{{ $entry.Value }}</dd>
|
||||
{{ end }}
|
||||
</dl>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
<!-- Table -->
|
||||
{{ with .Email.Body.Table }}
|
||||
{{ $data := .Data }}
|
||||
{{ $columns := .Columns }}
|
||||
{{ if gt (len $data) 0 }}
|
||||
<table class="data-wrapper" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td colspan="2">
|
||||
<table class="data-table" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
{{ $col := index $data 0 }}
|
||||
{{ range $entry := $col }}
|
||||
<th
|
||||
{{ with $columns }}
|
||||
{{ $width := index .CustomWidth $entry.Key }}
|
||||
{{ with $width }}
|
||||
width="{{ . }}"
|
||||
{{ end }}
|
||||
{{ $align := index .CustomAlignment $entry.Key }}
|
||||
{{ with $align }}
|
||||
style="text-align:{{ . }}"
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
>
|
||||
<p>{{ $entry.Key }}</p>
|
||||
</th>
|
||||
{{ end }}
|
||||
</tr>
|
||||
{{ range $row := $data }}
|
||||
<tr>
|
||||
{{ range $cell := $row }}
|
||||
<td
|
||||
{{ with $columns }}
|
||||
{{ $align := index .CustomAlignment $cell.Key }}
|
||||
{{ with $align }}
|
||||
style="text-align:{{ . }}"
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
>
|
||||
{{ $cell.Value }}
|
||||
</td>
|
||||
{{ end }}
|
||||
</tr>
|
||||
{{ end }}
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
<!-- Action -->
|
||||
{{ with .Email.Body.Actions }}
|
||||
{{ if gt (len .) 0 }}
|
||||
{{ range $action := . }}
|
||||
<p>{{ $action.Instructions }}</p>
|
||||
{{ $length := len $action.Button.Text }}
|
||||
{{ $width := add (mul $length 9) 20 }}
|
||||
{{if (lt $width 200)}}{{$width = 200}}{{else if (gt $width 570)}}{{$width = 570}}{{else}}{{end}}
|
||||
{{safe "<!--[if mso]>" }}
|
||||
{{ if $action.Button.Text }}
|
||||
<div style="margin: 30px auto;v-text-anchor:middle;text-align:center">
|
||||
<v:roundrect xmlns:v="urn:schemas-microsoft-com:vml"
|
||||
xmlns:w="urn:schemas-microsoft-com:office:word"
|
||||
href="{{ $action.Button.Link }}"
|
||||
style="height:45px;v-text-anchor:middle;width:{{$width}}px;background-color:{{ if $action.Button.Color }}{{ $action.Button.Color }}{{ else }}#3869D4{{ end }};"
|
||||
arcsize="10%"
|
||||
{{ if $action.Button.Color }}strokecolor="{{ $action.Button.Color }}" fillcolor="{{ $action.Button.Color }}"{{ else }}strokecolor="#3869D4" fillcolor="#3869D4"{{ end }}
|
||||
>
|
||||
<w:anchorlock/>
|
||||
<center style="color: {{ if $action.Button.TextColor }}{{ $action.Button.TextColor }}{{else}}#FFFFFF{{ end }};font-size: 15px;text-align: center;font-family:sans-serif;font-weight:bold;">
|
||||
{{ $action.Button.Text }}
|
||||
</center>
|
||||
</v:roundrect>
|
||||
</div>
|
||||
{{ end }}
|
||||
{{ if $action.InviteCode }}
|
||||
<div style="margin-top:30px;margin-bottom:30px">
|
||||
<table class="body-action" align="center" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<table align="center" cellpadding="0" cellspacing="0" style="padding:0;text-align:center">
|
||||
<tr>
|
||||
<td style="display:inline-block;border-radius:3px;font-family:Consolas, monaco, monospace;font-size:28px;text-align:center;letter-spacing:8px;color:#555;background-color:#eee;padding:20px">
|
||||
{{ $action.InviteCode }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
{{ end }}
|
||||
{{safe "<![endif]-->" }}
|
||||
{{safe "<!--[if !mso]><!-- -->"}}
|
||||
<table class="body-action" align="center" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td align="center">
|
||||
<div>
|
||||
{{ if $action.Button.Text }}
|
||||
<a href="{{ $action.Button.Link }}" class="button" style="{{ with $action.Button.Color }}background-color: {{ . }};{{ end }} {{ with $action.Button.TextColor }}color: {{ . }};{{ end }} width: {{$width}}px;" target="_blank">
|
||||
{{ $action.Button.Text }}
|
||||
</a>
|
||||
{{end}}
|
||||
{{ if $action.InviteCode }}
|
||||
<span class="invite-code">{{ $action.InviteCode }}</span>
|
||||
{{end}}
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
{{safe "<![endif]-->" }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ with .Email.Body.Outros }}
|
||||
{{ if gt (len .) 0 }}
|
||||
{{ range $line := . }}
|
||||
<p>{{ $line }}</p>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
<p>
|
||||
{{.Email.Body.Signature}},
|
||||
<br />
|
||||
{{.Hermes.Product.Name}}
|
||||
</p>
|
||||
{{ if (eq .Email.Body.FreeMarkdown "") }}
|
||||
{{ with .Email.Body.Actions }}
|
||||
<table class="body-sub">
|
||||
<tbody>
|
||||
{{ range $action := . }}
|
||||
{{if $action.Button.Text}}
|
||||
<tr>
|
||||
<td>
|
||||
<p class="sub">{{$.Hermes.Product.TroubleText | replace "{ACTION}" $action.Button.Text}}</p>
|
||||
<p class="sub"><a href="{{ $action.Button.Link }}">{{ $action.Button.Link }}</a></p>
|
||||
</td>
|
||||
</tr>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
</tbody>
|
||||
</table>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<table class="email-footer" align="center" width="570" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
<td class="content-cell">
|
||||
<p class="sub center">
|
||||
{{.Hermes.Product.Copyright}}
|
||||
</p>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,47 @@
|
|||
package messenger
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
_ "embed"
|
||||
"html/template"
|
||||
|
||||
"github.com/vanng822/go-premailer/premailer"
|
||||
"github.com/yuin/goldmark"
|
||||
"github.com/yuin/goldmark/extension"
|
||||
)
|
||||
|
||||
//go:embed base.gohtml
|
||||
var mailTmpl string
|
||||
|
||||
var engine *template.Template
|
||||
var app App
|
||||
|
||||
func init() {
|
||||
md := goldmark.New(
|
||||
goldmark.WithExtensions(extension.GFM),
|
||||
)
|
||||
engine = template.Must(template.New("email").Funcs(template.FuncMap{
|
||||
"ToHTML": func(mdtext string) (string, error) {
|
||||
var buf bytes.Buffer
|
||||
if err := md.Convert([]byte(mdtext), &buf); err != nil {
|
||||
return "", err
|
||||
}
|
||||
return buf.String(), nil
|
||||
},
|
||||
}).Parse(mailTmpl))
|
||||
}
|
||||
|
||||
func Parse(b *Base) (string, error) {
|
||||
b.App = app
|
||||
buf := &bytes.Buffer{}
|
||||
err := engine.Execute(buf, b)
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
pre, err := premailer.NewPremailerFromString(buf.String(), premailer.NewOptions())
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
html, err := pre.Transform()
|
||||
return html, err
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
package messenger
|
||||
|
||||
func init() {
|
||||
|
||||
// viper.SetDefault()
|
||||
}
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
package messenger
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"github.com/spf13/viper"
|
||||
"kumoly.io/kumoly/app/system"
|
||||
)
|
||||
|
||||
type Messenger struct {
|
||||
system.BaseService
|
||||
}
|
||||
|
||||
func (srv Messenger) GetName() string { return "messenger.Messenger" }
|
||||
|
||||
func (srv *Messenger) Init() error {
|
||||
app.Name = viper.GetString("name")
|
||||
app.Copyright = fmt.Sprintf("Copyright © %v %s. All rights reserved.",
|
||||
time.Now().Year(), viper.GetString("name"))
|
||||
app.Link = viper.GetString("server.url")
|
||||
return nil
|
||||
}
|
|
@ -0,0 +1,61 @@
|
|||
<h2>{{if .Email.Body.Title }}{{ .Email.Body.Title }}{{ else }}{{ .Email.Body.Greeting }} {{ .Email.Body.Name }},{{ end }}</h2>
|
||||
{{ with .Email.Body.Intros }}
|
||||
{{ range $line := . }}
|
||||
<p>{{ $line }}</p>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ if (ne .Email.Body.FreeMarkdown "") }}
|
||||
{{ .Email.Body.FreeMarkdown.ToHTML }}
|
||||
{{ else }}
|
||||
{{ with .Email.Body.Dictionary }}
|
||||
<ul>
|
||||
{{ range $entry := . }}
|
||||
<li>{{ $entry.Key }}: {{ $entry.Value }}</li>
|
||||
{{ end }}
|
||||
</ul>
|
||||
{{ end }}
|
||||
{{ with .Email.Body.Table }}
|
||||
{{ $data := .Data }}
|
||||
{{ $columns := .Columns }}
|
||||
{{ if gt (len $data) 0 }}
|
||||
<table class="data-table" width="100%" cellpadding="0" cellspacing="0">
|
||||
<tr>
|
||||
{{ $col := index $data 0 }}
|
||||
{{ range $entry := $col }}
|
||||
<th>{{ $entry.Key }} </th>
|
||||
{{ end }}
|
||||
</tr>
|
||||
{{ range $row := $data }}
|
||||
<tr>
|
||||
{{ range $cell := $row }}
|
||||
<td>
|
||||
{{ $cell.Value }}
|
||||
</td>
|
||||
{{ end }}
|
||||
</tr>
|
||||
{{ end }}
|
||||
</table>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ with .Email.Body.Actions }}
|
||||
{{ range $action := . }}
|
||||
<p>
|
||||
{{ $action.Instructions }}
|
||||
{{ if $action.InviteCode }}
|
||||
{{ $action.InviteCode }}
|
||||
{{ end }}
|
||||
{{ if $action.Button.Link }}
|
||||
{{ $action.Button.Link }}
|
||||
{{ end }}
|
||||
</p>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
{{ with .Email.Body.Outros }}
|
||||
{{ range $line := . }}
|
||||
<p>{{ $line }}<p>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
<p>{{.Email.Body.Signature}},<br>{{.Hermes.Product.Name}} - {{.Hermes.Product.Link}}</p>
|
||||
<p>{{.Hermes.Product.Copyright}}</p>
|
||||
`
|
|
@ -116,6 +116,12 @@ func (sys *System) Start() {
|
|||
}
|
||||
|
||||
l.Info().Msg("Starting...")
|
||||
if e := l.Trace(); e.Enabled() {
|
||||
config, err := ConfigShow("")
|
||||
if err == nil {
|
||||
e.Str("config", config).Msg("config")
|
||||
}
|
||||
}
|
||||
|
||||
sys.status = sys_main
|
||||
sys.main()
|
||||
|
|
Loading…
Reference in New Issue