You're Invited:Meet the Socket Team at RSAC and BSidesSF 2026, March 23–26.RSVP
Socket
Book a DemoSign in
Socket

ms-mailer-templates

Package Overview
Dependencies
Maintainers
1
Versions
96
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

ms-mailer-templates - npm Package Compare versions

Comparing version
2.4.1
to
3.0.1
+688
build/css/ink.css
/**********************************************
* Ink v1.0.5 - Copyright 2013 ZURB Inc *
**********************************************/
/* Client-specific Styles & Reset */
#outlook a {
padding:0;
}
body{
width:100% !important;
min-width: 100%;
-webkit-text-size-adjust:100%;
-ms-text-size-adjust:100%;
margin:0;
padding:0;
}
.ExternalClass {
width:100%;
}
.ExternalClass,
.ExternalClass p,
.ExternalClass span,
.ExternalClass font,
.ExternalClass td,
.ExternalClass div {
line-height: 100%;
}
#backgroundTable {
margin:0;
padding:0;
width:100% !important;
line-height: 100% !important;
}
img {
outline:none;
text-decoration:none;
-ms-interpolation-mode: bicubic;
width: auto;
max-width: 100%;
float: left;
clear: both;
display: block;
}
center {
width: 100%;
min-width: 580px;
}
a img {
border: none;
}
p {
margin: 0 0 0 10px;
}
table {
border-spacing: 0;
border-collapse: collapse;
}
td {
word-break: break-word;
-webkit-hyphens: auto;
-moz-hyphens: auto;
hyphens: auto;
border-collapse: collapse !important;
}
table, tr, td {
padding: 0;
vertical-align: top;
text-align: left;
}
hr {
color: #d9d9d9;
background-color: #d9d9d9;
height: 1px;
border: none;
}
/* Responsive Grid */
table.body {
height: 100%;
width: 100%;
}
table.container {
width: 580px;
margin: 0 auto;
text-align: inherit;
}
table.row {
padding: 0px;
width: 100%;
position: relative;
}
table.container table.row {
display: block;
}
td.wrapper {
padding: 10px 20px 0px 0px;
position: relative;
}
table.columns,
table.column {
margin: 0 auto;
}
table.columns td,
table.column td {
padding: 0px 0px 10px;
}
table.columns td.sub-columns,
table.column td.sub-columns,
table.columns td.sub-column,
table.column td.sub-column {
padding-right: 10px;
}
td.sub-column, td.sub-columns {
min-width: 0px;
}
table.row td.last,
table.container td.last {
padding-right: 0px;
}
table.one { width: 30px; }
table.two { width: 80px; }
table.three { width: 130px; }
table.four { width: 180px; }
table.five { width: 230px; }
table.six { width: 280px; }
table.seven { width: 330px; }
table.eight { width: 380px; }
table.nine { width: 430px; }
table.ten { width: 480px; }
table.eleven { width: 530px; }
table.twelve { width: 580px; }
table.one center { min-width: 30px; }
table.two center { min-width: 80px; }
table.three center { min-width: 130px; }
table.four center { min-width: 180px; }
table.five center { min-width: 230px; }
table.six center { min-width: 280px; }
table.seven center { min-width: 330px; }
table.eight center { min-width: 380px; }
table.nine center { min-width: 430px; }
table.ten center { min-width: 480px; }
table.eleven center { min-width: 530px; }
table.twelve center { min-width: 580px; }
table.one .panel center { min-width: 10px; }
table.two .panel center { min-width: 60px; }
table.three .panel center { min-width: 110px; }
table.four .panel center { min-width: 160px; }
table.five .panel center { min-width: 210px; }
table.six .panel center { min-width: 260px; }
table.seven .panel center { min-width: 310px; }
table.eight .panel center { min-width: 360px; }
table.nine .panel center { min-width: 410px; }
table.ten .panel center { min-width: 460px; }
table.eleven .panel center { min-width: 510px; }
table.twelve .panel center { min-width: 560px; }
.body .columns td.one,
.body .column td.one { width: 8.333333%; }
.body .columns td.two,
.body .column td.two { width: 16.666666%; }
.body .columns td.three,
.body .column td.three { width: 25%; }
.body .columns td.four,
.body .column td.four { width: 33.333333%; }
.body .columns td.five,
.body .column td.five { width: 41.666666%; }
.body .columns td.six,
.body .column td.six { width: 50%; }
.body .columns td.seven,
.body .column td.seven { width: 58.333333%; }
.body .columns td.eight,
.body .column td.eight { width: 66.666666%; }
.body .columns td.nine,
.body .column td.nine { width: 75%; }
.body .columns td.ten,
.body .column td.ten { width: 83.333333%; }
.body .columns td.eleven,
.body .column td.eleven { width: 91.666666%; }
.body .columns td.twelve,
.body .column td.twelve { width: 100%; }
td.offset-by-one { padding-left: 50px; }
td.offset-by-two { padding-left: 100px; }
td.offset-by-three { padding-left: 150px; }
td.offset-by-four { padding-left: 200px; }
td.offset-by-five { padding-left: 250px; }
td.offset-by-six { padding-left: 300px; }
td.offset-by-seven { padding-left: 350px; }
td.offset-by-eight { padding-left: 400px; }
td.offset-by-nine { padding-left: 450px; }
td.offset-by-ten { padding-left: 500px; }
td.offset-by-eleven { padding-left: 550px; }
td.expander {
visibility: hidden;
width: 0px;
padding: 0 !important;
}
table.columns .text-pad,
table.column .text-pad {
padding-left: 10px;
padding-right: 10px;
}
table.columns .left-text-pad,
table.columns .text-pad-left,
table.column .left-text-pad,
table.column .text-pad-left {
padding-left: 10px;
}
table.columns .right-text-pad,
table.columns .text-pad-right,
table.column .right-text-pad,
table.column .text-pad-right {
padding-right: 10px;
}
/* Block Grid */
.block-grid {
width: 100%;
max-width: 580px;
}
.block-grid td {
display: inline-block;
padding:10px;
}
.two-up td {
width:270px;
}
.three-up td {
width:173px;
}
.four-up td {
width:125px;
}
.five-up td {
width:96px;
}
.six-up td {
width:76px;
}
.seven-up td {
width:62px;
}
.eight-up td {
width:52px;
}
/* Alignment & Visibility Classes */
table.center, td.center {
text-align: center;
}
h1.center,
h2.center,
h3.center,
h4.center,
h5.center,
h6.center {
text-align: center;
}
span.center {
display: block;
width: 100%;
text-align: center;
}
img.center {
margin: 0 auto;
float: none;
}
.show-for-small,
.hide-for-desktop {
display: none;
}
/* Typography */
body, table.body, h1, h2, h3, h4, h5, h6, p, td {
color: #222222;
font-family: "Helvetica", "Arial", sans-serif;
font-weight: normal;
padding:0;
margin: 0;
text-align: left;
line-height: 1.3;
}
h1, h2, h3, h4, h5, h6 {
word-break: normal;
}
h1 {font-size: 40px;}
h2 {font-size: 36px;}
h3 {font-size: 32px;}
h4 {font-size: 28px;}
h5 {font-size: 24px;}
h6 {font-size: 20px;}
body, table.body, p, td {font-size: 14px;line-height:19px;}
p.lead, p.lede, p.leed {
font-size: 18px;
line-height:21px;
}
p {
margin-bottom: 10px;
}
small {
font-size: 10px;
}
a {
color: #2ba6cb;
text-decoration: none;
}
a:hover {
color: #2795b6 !important;
}
a:active {
color: #2795b6 !important;
}
a:visited {
color: #2ba6cb !important;
}
h1 a,
h2 a,
h3 a,
h4 a,
h5 a,
h6 a {
color: #2ba6cb;
}
h1 a:active,
h2 a:active,
h3 a:active,
h4 a:active,
h5 a:active,
h6 a:active {
color: #2ba6cb !important;
}
h1 a:visited,
h2 a:visited,
h3 a:visited,
h4 a:visited,
h5 a:visited,
h6 a:visited {
color: #2ba6cb !important;
}
/* Panels */
.panel {
background: #f2f2f2;
border: 1px solid #d9d9d9;
padding: 10px !important;
}
.sub-grid table {
width: 100%;
}
.sub-grid td.sub-columns {
padding-bottom: 0;
}
/* Buttons */
table.button,
table.tiny-button,
table.small-button,
table.medium-button,
table.large-button {
width: 100%;
overflow: hidden;
}
table.button td,
table.tiny-button td,
table.small-button td,
table.medium-button td,
table.large-button td {
display: block;
width: auto !important;
text-align: center;
background: #2ba6cb;
border: 1px solid #2284a1;
color: #ffffff;
padding: 8px 0;
}
table.tiny-button td {
padding: 5px 0 4px;
}
table.small-button td {
padding: 8px 0 7px;
}
table.medium-button td {
padding: 12px 0 10px;
}
table.large-button td {
padding: 21px 0 18px;
}
table.button td a,
table.tiny-button td a,
table.small-button td a,
table.medium-button td a,
table.large-button td a {
font-weight: bold;
text-decoration: none;
font-family: Helvetica, Arial, sans-serif;
color: #ffffff;
font-size: 16px;
}
table.tiny-button td a {
font-size: 12px;
font-weight: normal;
}
table.small-button td a {
font-size: 16px;
}
table.medium-button td a {
font-size: 20px;
}
table.large-button td a {
font-size: 24px;
}
table.button:hover td,
table.button:visited td,
table.button:active td {
background: #2795b6 !important;
}
table.button:hover td a,
table.button:visited td a,
table.button:active td a {
color: #fff !important;
}
table.button:hover td,
table.tiny-button:hover td,
table.small-button:hover td,
table.medium-button:hover td,
table.large-button:hover td {
background: #2795b6 !important;
}
table.button:hover td a,
table.button:active td a,
table.button td a:visited,
table.tiny-button:hover td a,
table.tiny-button:active td a,
table.tiny-button td a:visited,
table.small-button:hover td a,
table.small-button:active td a,
table.small-button td a:visited,
table.medium-button:hover td a,
table.medium-button:active td a,
table.medium-button td a:visited,
table.large-button:hover td a,
table.large-button:active td a,
table.large-button td a:visited {
color: #ffffff !important;
}
table.secondary td {
background: #e9e9e9;
border-color: #d0d0d0;
color: #555;
}
table.secondary td a {
color: #555;
}
table.secondary:hover td {
background: #d0d0d0 !important;
color: #555;
}
table.secondary:hover td a,
table.secondary td a:visited,
table.secondary:active td a {
color: #555 !important;
}
table.success td {
background: #5da423;
border-color: #457a1a;
}
table.success:hover td {
background: #457a1a !important;
}
table.alert td {
background: #c60f13;
border-color: #970b0e;
}
table.alert:hover td {
background: #970b0e !important;
}
table.radius td {
-webkit-border-radius: 3px;
-moz-border-radius: 3px;
border-radius: 3px;
}
table.round td {
-webkit-border-radius: 500px;
-moz-border-radius: 500px;
border-radius: 500px;
}
/* Outlook First */
body.outlook p {
display: inline !important;
}
/* Media Queries */
@media only screen and (max-width: 600px) {
table[class="body"] img {
width: auto !important;
height: auto !important;
}
table[class="body"] center {
min-width: 0 !important;
}
table[class="body"] .container {
width: 95% !important;
}
table[class="body"] .row {
width: 100% !important;
display: block !important;
}
table[class="body"] .wrapper {
display: block !important;
padding-right: 0 !important;
}
table[class="body"] .columns,
table[class="body"] .column {
table-layout: fixed !important;
float: none !important;
width: 100% !important;
padding-right: 0px !important;
padding-left: 0px !important;
display: block !important;
}
table[class="body"] .wrapper.first .columns,
table[class="body"] .wrapper.first .column {
display: table !important;
}
table[class="body"] table.columns td,
table[class="body"] table.column td {
width: 100% !important;
}
table[class="body"] .columns td.one,
table[class="body"] .column td.one { width: 8.333333% !important; }
table[class="body"] .columns td.two,
table[class="body"] .column td.two { width: 16.666666% !important; }
table[class="body"] .columns td.three,
table[class="body"] .column td.three { width: 25% !important; }
table[class="body"] .columns td.four,
table[class="body"] .column td.four { width: 33.333333% !important; }
table[class="body"] .columns td.five,
table[class="body"] .column td.five { width: 41.666666% !important; }
table[class="body"] .columns td.six,
table[class="body"] .column td.six { width: 50% !important; }
table[class="body"] .columns td.seven,
table[class="body"] .column td.seven { width: 58.333333% !important; }
table[class="body"] .columns td.eight,
table[class="body"] .column td.eight { width: 66.666666% !important; }
table[class="body"] .columns td.nine,
table[class="body"] .column td.nine { width: 75% !important; }
table[class="body"] .columns td.ten,
table[class="body"] .column td.ten { width: 83.333333% !important; }
table[class="body"] .columns td.eleven,
table[class="body"] .column td.eleven { width: 91.666666% !important; }
table[class="body"] .columns td.twelve,
table[class="body"] .column td.twelve { width: 100% !important; }
table[class="body"] td.offset-by-one,
table[class="body"] td.offset-by-two,
table[class="body"] td.offset-by-three,
table[class="body"] td.offset-by-four,
table[class="body"] td.offset-by-five,
table[class="body"] td.offset-by-six,
table[class="body"] td.offset-by-seven,
table[class="body"] td.offset-by-eight,
table[class="body"] td.offset-by-nine,
table[class="body"] td.offset-by-ten,
table[class="body"] td.offset-by-eleven {
padding-left: 0 !important;
}
table[class="body"] table.columns td.expander {
width: 1px !important;
}
table[class="body"] .right-text-pad,
table[class="body"] .text-pad-right {
padding-left: 10px !important;
}
table[class="body"] .left-text-pad,
table[class="body"] .text-pad-left {
padding-right: 10px !important;
}
table[class="body"] .hide-for-small,
table[class="body"] .show-for-desktop {
display: none !important;
}
table[class="body"] .show-for-small,
table[class="body"] .hide-for-desktop {
display: inherit !important;
}
}
/* -------------------------------------
GLOBAL
A very basic CSS reset
------------------------------------- */
* {
margin: 0;
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
box-sizing: border-box;
font-size: 14px;
}
img {
max-width: 100%;
}
body {
-webkit-font-smoothing: antialiased;
-webkit-text-size-adjust: none;
width: 100% !important;
height: 100%;
line-height: 1.6em;
/* 1.6em * 14px = 22.4px, use px to get airier line-height also in Thunderbird, and Yahoo!, Outlook.com, AOL webmail clients */
/*line-height: 22px;*/
}
/* Let's make sure all tables have defaults */
table td {
vertical-align: top;
}
/* -------------------------------------
BODY & CONTAINER
------------------------------------- */
body {
background-color: #f6f6f6;
}
.body-wrap {
background-color: #f6f6f6;
width: 100%;
}
.container {
display: block !important;
max-width: 600px !important;
margin: 0 auto !important;
/* makes it centered */
clear: both !important;
}
.container-max {
max-width: 1400px !important;
}
.content {
max-width: 600px;
margin: 0 auto;
display: block;
padding: 20px;
}
.content-max {
max-width: 1400px;
}
/* -------------------------------------
HEADER, FOOTER, MAIN
------------------------------------- */
.main {
background-color: #fff;
border: 1px solid #e9e9e9;
border-radius: 3px;
}
.content-wrap {
padding: 20px;
}
.content-block {
padding: 0 0 20px;
}
.header {
width: 100%;
margin-bottom: 20px;
}
.footer {
width: 100%;
clear: both;
color: #999;
padding: 20px;
}
.footer p, .footer a, .footer td {
color: #999;
font-size: 12px;
}
/* -------------------------------------
TYPOGRAPHY
------------------------------------- */
h1, h2, h3 {
font-family: "Helvetica Neue", Helvetica, Arial, "Lucida Grande", sans-serif;
color: #000;
margin: 40px 0 0;
line-height: 1.2em;
font-weight: 400;
}
h1 {
font-size: 32px;
font-weight: 500;
/* 1.2em * 32px = 38.4px, use px to get airier line-height also in Thunderbird, and Yahoo!, Outlook.com, AOL webmail clients */
/*line-height: 38px;*/
}
h2 {
font-size: 24px;
/* 1.2em * 24px = 28.8px, use px to get airier line-height also in Thunderbird, and Yahoo!, Outlook.com, AOL webmail clients */
/*line-height: 29px;*/
}
h3 {
font-size: 18px;
/* 1.2em * 18px = 21.6px, use px to get airier line-height also in Thunderbird, and Yahoo!, Outlook.com, AOL webmail clients */
/*line-height: 22px;*/
}
h4 {
font-size: 14px;
font-weight: 600;
}
p, ul, ol {
margin-bottom: 10px;
font-weight: normal;
}
p li, ul li, ol li {
margin-left: 5px;
list-style-position: inside;
}
/* -------------------------------------
LINKS & BUTTONS
------------------------------------- */
a {
color: #191919;
text-decoration: underline;
}
a:hover {
color: #484848;
}
.block {
display: block;
}
.btn-primary {
text-decoration: none;
color: #FFF;
background-color: #191919;
border: solid #191919;
border-width: 10px 20px;
line-height: 2em;
/* 2em * 14px = 28px, use px to get airier line-height also in Thunderbird, and Yahoo!, Outlook.com, AOL webmail clients */
/*line-height: 28px;*/
font-weight: bold;
text-align: center;
cursor: pointer;
display: inline-block;
border-radius: 5px;
text-transform: capitalize;
}
.btn-primary:hover {
background-color: #484848;
border-color: #484848;
}
/* -------------------------------------
OTHER STYLES THAT MIGHT BE USEFUL
------------------------------------- */
.last {
margin-bottom: 0;
}
.first {
margin-top: 0;
}
.aligncenter {
text-align: center;
}
.alignright {
text-align: right;
}
.alignleft {
text-align: left;
}
.clear {
clear: both;
}
/* -------------------------------------
ALERTS
Change the class depending on warning email, good email or bad email
------------------------------------- */
.alert {
font-size: 16px;
color: #fff;
font-weight: 500;
padding: 20px;
text-align: center;
border-radius: 3px 3px 0 0;
}
.alert a {
color: #fff;
text-decoration: none;
font-weight: 500;
font-size: 16px;
}
.alert.alert-warning {
background-color: #FF9F00;
}
.alert.alert-bad {
background-color: #D0021B;
}
.alert.alert-good {
background-color: #68B90F;
}
/* -------------------------------------
INVOICE
Styles for the billing table
------------------------------------- */
.invoice {
margin: 40px auto;
text-align: left;
width: 80%;
}
.invoice td {
padding: 5px 0;
}
.invoice .invoice-items {
width: 100%;
}
.invoice .invoice-items td {
border-top: #eee 1px solid;
}
.invoice .invoice-items .total td {
border-top: 2px solid #333;
border-bottom: 2px solid #333;
font-weight: 700;
}
/* --------------------------------------
Airdrop Crap
----------------------------------------- */
.airdrop {
width: 100%;
table-layout: fixed;
}
.airdrop .fixed-size {
width: 80px;
min-width: 80px;
}
.airdrop .fixed-size.fixed-size-small {
width: 60px;
min-width: 60px;
}
.airdrop .floating {
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
}
/* -------------------------------------
RESPONSIVE AND MOBILE FRIENDLY STYLES
------------------------------------- */
@media only screen and (max-width: 640px) {
body {
padding: 0 !important;
}
h1, h2, h3, h4 {
font-weight: 800 !important;
margin: 20px 0 5px !important;
}
h1 {
font-size: 22px !important;
}
h2 {
font-size: 18px !important;
}
h3 {
font-size: 16px !important;
}
.container {
padding: 0 !important;
width: 100% !important;
}
.content {
padding: 0 !important;
}
.content-wrap {
padding: 10px !important;
}
.invoice {
width: 100% !important;
}
}
.header-padding {
padding-top: 40px;
padding-bottom: 40px;
}
.section-padding {
padding-top: 40px;
}
p {
font-size: 16px;
color: rgb(0, 0, 0);
}
.rfx-button {
background-color: rgb(74, 144, 226);
display: inline-block;
color: rgb(255, 255, 255);
text-transform: uppercase;
padding: 10px 20px;
text-align: center;
border-radius: 3px;
overflow: hidden;
}
.rfx-button:active, .rfx-button:focus, .rfx-button:hover, .rfx-button:visited {
color: rgb(255, 255, 255) !important;
}
.rfx-button:hover {
background-color: rgb(39, 75, 135);
}
address {
font-style: normal;
}
.social {
text-align: right;
height: 100%;
}
.social > a {
display: inline-block;
border-radius: 6px;
overflow: hidden;
}
.social > a > img {
border-radius: 6px;
width: 32px !important;
height: 32px !important;
}
.model-preview {
max-width: 458px;
}
@media only screen and (max-width: 600px) {
table[class="container"] .block-grid td {
width: 100% !important;
padding-right: 0;
padding-left: 0;
}
}
* {
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
}
body {
-webkit-font-smoothing: antialiased;
-webkit-text-size-adjust: none;
}
.sl-body {
background: #F6F4F5;
margin-top: 0;
}
.sl-main {
margin: 0 auto;
background: #fff;
padding-top: 10px;
}
.main {
margin: 0 auto;
}
.logo-container {
text-align: center;
}
.sl-logo {
width: 230px;
margin-bottom: 12px;
}
.container {
margin: 0 auto;
background-color: white;
border-radius: 10px;
width: 100%;
max-width: 586px;
padding: 0 57px;
}
.sl-button {
background-color: #3c8bfb;
text-decoration: none;
max-width: 250px;
width: 100%;
padding: 17px 30px;
color: white;
font-size: 14px;
font-weight: bold;
display: inline-block;
}
.sl-button-row {
height: 51px;
margin-top: 32px !important;
margin-bottom: 38px !important;
text-align: center;
}
.sl-link {
text-decoration: none;
color: #1d7bff;
}
.sl-text {
font-weight: 400 !important;
font-size: 14px !important;
line-height: 18px !important;
margin-bottom: 20px !important;
}
.sl-text_top {
margin-top: 38px !important;
margin-bottom: 20px;
}
.sl-text_bottom {
margin-bottom: 42px !important;
}
.sl-text-common {
font-weight: 400 !important;
font-size: 14px !important;
}
h1 {
font-size: 20px !important;
font-weight: bold !important;
padding: 0 !important;
margin: 49px 0 30px 0 !important;
}
h2 {
font-size: 14px !important;
font-weight: bold !important;
padding: 0;
margin: 0;
margin-bottom: 40px !important;
}
td {
vertical-align: inherit !important;
}
h1, .centered {
margin-top: 10px !important;
margin-bottom: 10px !important;
text-align: center;
}
const i18next = require('i18next');
const { join } = require('path');
const { readdirSync, lstatSync } = require('fs');
const fsBackend = require('i18next-fs-backend');
const i18nPath = join(__dirname, '../i18n');
const SUPPORTED_NAMESPACES = [
'emails', // default
];
module.exports = (function initI18n() {
const i18n = i18next.createInstance();
i18n
.use(fsBackend)
.init({
initImmediate: false,
fallbackLng: 'en',
nsSeparator: ':|',
keySeparator: false,
ns: SUPPORTED_NAMESPACES,
defaultNS: 'emails',
preload: readdirSync(i18nPath).filter((fileName) => lstatSync(join(i18nPath, fileName)).isDirectory()),
backend: {
loadPath: join(__dirname, '../i18n/{{lng}}/{{ns}}.json'),
},
});
return i18n;
}());
/**
* This is a small helper, which allows you
* to pickup email templates from a build folder
* and then render it into HTML with a passed context
*/
// init, it's sync, done once on startup
const Promise = require('bluebird');
const Errors = require('common-errors');
const hbs = require('handlebars');
const fs = require('fs');
const path = require('path');
const i18n = require('./i18n');
const templateDirectory = path.resolve(__dirname, '../build/templates');
const ext = '.html';
// read templates
const templates = {};
fs.readdirSync(templateDirectory)
.filter((filename) => path.extname(filename) === ext)
.forEach((filename) => {
templates[path.basename(filename, ext)] = hbs.compile(fs.readFileSync(`${templateDirectory}/${filename}`, 'utf-8'));
});
// public API
function renderEmailTemplate(templateName, context, opts = {}) {
const template = templates[templateName];
if (!template) {
return Promise.reject(new Errors.NotFoundError(templateName));
}
if (!context || typeof context !== 'object') {
return Promise.reject(new Errors.TypeError('context must be an object'));
}
return Promise.try(function tryRendering() {
const fixedT = i18n.getFixedT(context.lng);
return template(context, {
...opts,
helpers: {
...opts.helpers,
t(key, attributes) {
return new hbs.SafeString(fixedT(key, attributes.hash));
},
},
});
});
}
renderEmailTemplate.translate = i18n.t.bind(i18n);
module.exports = renderEmailTemplate;
+24
-25
{
"name": "ms-mailer-templates",
"description": "Templates for mailer microservice",
"version": "2.4.1",
"main": "./lib/index.js",
"version": "3.0.1",
"main": "./src/index.js",
"scripts": {
"prepublishOnly": "yarn compile && babel ./src -d ./lib",
"test": "yarn lint && yarn compile && NODE_ENV=test mocha",
"prepublishOnly": "pnpm compile",
"test": "pnpm lint && pnpm compile && NODE_ENV=test mocha",
"lint": "eslint ./src",

@@ -13,3 +13,3 @@ "compile": "gulp production",

"semantic-release": "semantic-release",
"i18n:parse": "yarn i18next"
"i18n:parse": "pnpm i18next"
},

@@ -30,20 +30,14 @@ "repository": {

"handlebars": "^4.7.6",
"i18next": "^19.8.7",
"i18next-fs-backend": "^1.0.8"
"i18next": "^23.7.17",
"i18next-fs-backend": "^2.3.1"
},
"devDependencies": {
"@babel/cli": "^7.12.7",
"@babel/core": "^7.12.7",
"@babel/plugin-proposal-class-properties": "^7.12.1",
"@babel/plugin-transform-strict-mode": "^7.12.1",
"@babel/preset-env": "^7.12.7",
"babel-eslint": "^10.1.0",
"chai": "^4.1.2",
"datauri": "^3.0.0",
"datauri": "^4.1.0",
"del": "^6.0.0",
"eslint": "7.14.0",
"eslint-config-makeomatic": "^5.0.3",
"eslint": "8.56.0",
"eslint-config-makeomatic": "^6.0.0",
"eslint-plugin-import": "^2.22.1",
"eslint-plugin-mocha": "^8.0.0",
"eslint-plugin-unicorn": "^23.0.0",
"eslint-plugin-mocha": "^10.2.0",
"eslint-plugin-unicorn": "^50.0.1",
"gulp": "^4.0.2",

@@ -53,12 +47,17 @@ "gulp-cli": "^2.3.0",

"gulp-htmlmin": "^5.0.1",
"gulp-imagemin": "^7.1.0",
"gulp-imagemin": "^9.0.0",
"gulp-inline-css": "^4.0.0",
"gulp-inline-source": "^4.0.0",
"gulp-preprocess": "^3.0.3",
"i18next-parser": "^3.6.0",
"gulp-preprocess": "^4.0.2",
"i18next-parser": "^8.12.0",
"imagemin-pngcrush": "^7.0.0",
"locize-cli": "^7.6.12",
"mocha": "^8.2.1",
"semantic-release": "^17.3.0"
}
"locize-cli": "^8.0.0",
"mocha": "^10.2.0",
"semantic-release": "^23.0.0"
},
"files": [
"build/",
"i18n",
"src/*.js"
]
}
{
"plugins": [
"@babel/plugin-transform-spread",
"@babel/plugin-transform-destructuring",
"@babel/plugin-transform-strict-mode",
"@babel/plugin-transform-parameters",
"@babel/plugin-transform-shorthand-properties",
"@babel/plugin-proposal-object-rest-spread",
"@babel/plugin-proposal-class-properties"
]
}
# http://editorconfig.org
root = true
[*]
indent_style = space
indent_size = 2
end_of_line = lf
charset = utf-8
trim_trailing_whitespace = true
insert_final_newline = true
[*.md]
trim_trailing_whitespace = false

Sorry, the diff of this file is not supported yet

{
"extends": "makeomatic",
"parser": "babel-eslint",
"plugins": [
"mocha"
],
"env": {
"mocha": true
},
"rules": {
"prefer-arrow-callback": 0,
"max-len": [2, 150]
}
}
{
"branches": [
{ "name": "master" },
{ "name": "develop", "prerelease": "rc" }
],
"analyzeCommits": {
"preset": "angular",
"releaseRules": [
{ "type": "docs", "release": "patch" },
{ "type": "refactor", "release": "patch" },
{ "type": "style", "release": "patch" },
{ "type": "minor", "release": "minor" },
{ "type": "patch", "release": "patch" },
{ "type": "major", "release": "major" },
{ "type": "breaking", "release": "major" }
]
}
}
const {
dest, src, series, parallel, watch,
} = require('gulp');
const inlinesource = require('gulp-inline-source');
const inlineCss = require('gulp-inline-css');
const connect = require('gulp-connect');
const imagemin = require('gulp-imagemin');
const pngcrush = require('imagemin-pngcrush');
const del = require('del');
const preprocess = require('gulp-preprocess');
const htmlmin = require('gulp-htmlmin');
const Datauri = require('datauri');
const paths = {
styles: 'styles/*.css',
images: 'images/*',
dist: 'build/',
preview: 'preview/',
tmp: 'tmp/',
templates: 'src/templates/**.html',
filesToMove: 'src/css/**.css',
};
// data uri part
function toBase64(path, env) {
return env === 'production' ? new Datauri(`${__dirname}/path`).content : path;
}
// clean
exports.clean = del.bind(null, [paths.dist, paths.preview]);
// dev server
exports.connect = function previewServer() {
connect.server({
livereload: true,
root: 'build',
});
return watch([paths.filesToMove, paths.templates], exports.defaultTask);
};
// move css
exports.css = series(exports.clean, function moveStyles() {
return src(paths.filesToMove)
.pipe(dest(`${paths.dist}css`))
.pipe(dest(`${paths.preview}css`));
});
// minify images
exports.imagemin = series(exports.clean, function minifyImages() {
return src(paths.images)
.pipe(imagemin({
use: [pngcrush()],
}))
.pipe(dest(`${paths.preview}images`));
});
// preview templates
exports.templates = series(exports.clean, function buildTemplates() {
return src(paths.templates)
.pipe(preprocess({ context: { NODE_ENV: 'development', toBase64 }, extension: '.html' }))
.pipe(inlinesource({ swallowErrors: false }))
.pipe(dest(`${paths.preview}templates`))
.pipe(connect.reload());
});
// production templates
exports.templatesProduction = series(
parallel(exports.clean, exports.css),
function buildProdTemplates() {
return src(paths.templates)
.pipe(preprocess({ context: { NODE_ENV: 'production', toBase64 }, extension: '.html' }))
.pipe(inlinesource({
swallowErrors: false,
rootpath: `${__dirname}/src`,
}))
.pipe(inlineCss({
removeLinkTags: false,
preserveMediaQueries: true,
}))
.pipe(htmlmin({ removeComments: true, collapseWhitespace: true, minifyCSS: true }))
.pipe(dest(`${paths.dist}templates`));
}
);
// reload connect
exports.reload = function reloadConnect() {
return src(paths.templates)
.pipe(connect.reload());
};
exports.production = parallel(exports.templatesProduction, exports.css, exports.imagemin);
exports.defaultTask = parallel(exports.templates, exports.templatesProduction, exports.imagemin, exports.css);
exports.watch = parallel(exports.defaultTask, exports.connect);
module.exports = {
lexers: {
html: [{
lexer: 'HandlebarsLexer',
functions: ['t'],
}],
},
locales: ['en'],
output: './i18n-parsed/$LOCALE/$NAMESPACE.json',
defaultNamespace: 'emails',
useKeysAsDefaultValue: true,
keySeparator: false,
namespaceSeparator: ':|',
createOldCatalogs: false,
sort: true,
input: ['src/templates/**/*.html'],
};
"use strict";
const i18next = require('i18next');
const _require = require('path'),
join = _require.join;
const _require2 = require('fs'),
readdirSync = _require2.readdirSync,
lstatSync = _require2.lstatSync;
const fsBackend = require('i18next-fs-backend');
const i18nPath = join(__dirname, '../i18n');
const SUPPORTED_NAMESPACES = ['emails' // default
];
module.exports = function initI18n() {
const i18n = i18next.createInstance();
i18n.use(fsBackend).init({
initImmediate: false,
fallbackLng: 'en',
nsSeparator: ':|',
keySeparator: false,
ns: SUPPORTED_NAMESPACES,
defaultNS: 'emails',
preload: readdirSync(i18nPath).filter(fileName => lstatSync(join(i18nPath, fileName)).isDirectory()),
backend: {
loadPath: join(__dirname, '../i18n/{{lng}}/{{ns}}.json')
}
});
return i18n;
}();
"use strict";
function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { _defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
/**
* This is a small helper, which allows you
* to pickup email templates from a build folder
* and then render it into HTML with a passed context
*/
// init, it's sync, done once on startup
const Promise = require('bluebird');
const Errors = require('common-errors');
const hbs = require('handlebars');
const fs = require('fs');
const path = require('path');
const i18n = require('./i18n');
const templateDirectory = path.resolve(__dirname, '../build/templates');
const ext = '.html'; // read templates
const templates = {};
fs.readdirSync(templateDirectory).filter(filename => path.extname(filename) === ext).forEach(filename => {
templates[path.basename(filename, ext)] = hbs.compile(fs.readFileSync(`${templateDirectory}/${filename}`, 'utf-8'));
}); // public API
function renderEmailTemplate(templateName, context) {
let opts = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
const template = templates[templateName];
if (!template) {
return Promise.reject(new Errors.NotFoundError(templateName));
}
if (!context || typeof context !== 'object') {
return Promise.reject(new Errors.TypeError('context must be an object'));
}
return Promise.try(function tryRendering() {
const fixedT = i18n.getFixedT(context.lng);
return template(context, _objectSpread(_objectSpread({}, opts), {}, {
helpers: _objectSpread(_objectSpread({}, opts.helpers), {}, {
t: function (key, attributes) {
return new hbs.SafeString(fixedT(key, attributes.hash));
}
})
}));
});
}
renderEmailTemplate.translate = i18n.t.bind(i18n);
module.exports = renderEmailTemplate;