Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Easy to understand example #252

Closed
julesbou opened this issue Jun 28, 2016 · 75 comments
Closed

Easy to understand example #252

julesbou opened this issue Jun 28, 2016 · 75 comments
Labels
status: help wanted requesting help from the community type: community enhancement feature request not on Twilio's roadmap

Comments

@julesbou
Copy link

julesbou commented Jun 28, 2016

Hello,

Would be great to provide an easy to understand example on your readme, something as simple as https://sendgrid.com/blog/migrating-app-sendgrids-template-engine/ for example, because tbh if I wanted to write 30 lines of javascript code to send a simple email I wouldn't be using sendgrid.

Your library is quite frustrating to use, even for an experienced developer.

Cheers,
and sorry for this angry rant

ps: this example is exactly what I'm looking for https://sendgrid.com/docs/Integrate/Code_Examples/v2_Mail/nodejs.html , so easy to use

@thinkingserious thinkingserious added type: community enhancement feature request not on Twilio's roadmap status: help wanted requesting help from the community labels Jun 28, 2016
@thinkingserious
Copy link
Contributor

Hello @julesbou,

Angry rants are fine with me, especially if they have solutions attached :)

Thank you for taking the time to let us know.

We are currently planning the improvements for the next iteration, so you had good timing!

If you have any other particular requests, please let us know either in this thread or please open additional issues.

Thanks!

@jsgandalf
Copy link

How do we use the helper class? All I wanna do is set the from name??

@jsgandalf
Copy link

Very helpful! This should be on the readme!!

@bcootner
Copy link

bcootner commented Jul 12, 2016

@jsgandalf @thinkingserious I too find the library quite frustrating to use. I am trying to send a template email. I found the examples here not very helpful. I am confused on how to set the "to" and "from" email addresses, and this code does not even send my email. I've been scratching my head for the past three days. Any help?

@thinkingserious
Copy link
Contributor

thinkingserious commented Jul 12, 2016

Thanks for the feedback @bcootner. Your request helps bump fixing this up the queue. This is an issue I'm itching to get done.

In the mean time, hopefully this example will help:

var sg = require('sendgrid').SendGrid(process.env.SENDGRID_API_KEY)

function helloTemplate(){
  var helper = require('sendgrid').mail

  from_email = new helper.Email("test@example.com")
  to_email = new helper.Email("test@example.com")
  subject = "Hello World from the SendGrid Node.js Library"
  content = new helper.Content("text/plain", "some text here")
  mail = new helper.Mail(from_email, subject, to_email, content)
  // The constructor above already creates our personalization object
  // -name- and -card- are substitutions in my template
  substitution = new helper.Substitution("-name-", "Example User")
  mail.personalizations[0].addSubstitution(substitution)
  substitution = new helper.Substitution("-card-", "Denver")
  mail.personalizations[0].addSubstitution(substitution)
  mail.setTemplateId("YOUR_TEMPLATE_ID")
  return mail.toJSON()
}

function send(toSend){
  //console.log(JSON.stringify(toSend, null, 2))
  //console.log(JSON.stringify(toSend))

  var sg = require('sendgrid').SendGrid(process.env.SENDGRID_API_KEY)

  var requestBody = toSend
  var emptyRequest = require('sendgrid-rest').request
  var requestPost = JSON.parse(JSON.stringify(emptyRequest))
  requestPost.method = 'POST'
  requestPost.path = '/v3/mail/send'
  requestPost.body = requestBody
  sg.API(requestPost, function (response) {
    console.log(response.statusCode)
    console.log(response.body)
    console.log(response.headers)
  })
}

send(helloTemplate())

Please reach out if you need additional help.

@bcootner
Copy link

bcootner commented Jul 12, 2016

@thinkingserious Thanks for you time and thoughtful response. I have the following code:

    var  sg = require('sendgrid').SendGrid("SG.**** .. ***6o");

    function welcomeTemplate() {
         console.log("template")
         var helper = require('sendgrid').mail
         from_email = new helper.Email("test@example.com")
         to_email = new helper.Email("myemailadress@gmail.com")
         subject = "Hello World from the SendGrid Node.js Library"
         content = new helper.Content("text/plain", "some text here")
         mail = new helper.Mail(from_email, subject, to_email, content)
         substitution = new helper.Substitution("-Name-", "bcootner")
         mail.personalizations[0].addSubstitution(substitution)
         mail.setTemplateId("5a****-*******-******-9")    //The ID of my Transactional Template
         return mail.toJSON()
}

function sendMail(toSend) {
     console.log("Send")
     var sg = require('sendgrid').SendGrid("SG.***....****o")
     var requestBody = toSend
     var emptyRequest = require('sendgrid-rest').request
     var requestPost = JSON.parse(JSON.stringify(emptyRequest))
     requestPost.method = 'POST'
     requestPost.path = '/v3/mail/send'
     requestPost.body = requestBody
     sg.API(requestPost, function (response) {
            console.log(response.statusCode)
            console.log(response.body)
            console.log(response.headers)
       })
}

And then I call this code with sendMail(welcomeTemplate()) but that doesn't work. The "template" and "send" appear in the logs but the statusCode, body or headers do not show up, no emails are being received and nothing shows up on my dashboard.

@thinkingserious
Copy link
Contributor

After requestPost.body = requestBody could you please do console.log(JSON.stringify(requestBody)) and let me know what you get.

@bcootner
Copy link

bcootner commented Jul 12, 2016

@thinkingserious After some debugging it seems like nothing gets printed to the log after the line var emptyRequest = require('sendgrid-rest').request. First "template" gets logged, then about 5 minutes later "send" gets printed (and if I uncomment the lines you commented in the send function those work fine). Is there something I'm missing for this require statement, I just did npm install sendgrid

@thinkingserious
Copy link
Contributor

thinkingserious commented Jul 12, 2016

Please try this:

A. Create a file called post.json with the following payload:

{"content":[{"type":"text","value":"Hello, World!"}],"from":{"email":"from_address@example.com"},"personalizations":[{"subject":"Hello, World!","to":[{"email":"john@example.com"}]}]}

B. Replace the example emails

C. Run the following command:

curl -X "POST" "https://api.sendgrid.com/v3/mail/send" \
        -H "Authorization: Bearer $SENDGRID_API_KEY"  \
        -H "Content-Type: application/json" \
        -d @post.json

D. Either replace $SENDGRID_API_KEY with your API KEY, or add your API Key to an environment variable called SENDGRID_API_KEY

@bcootner
Copy link

bcootner commented Jul 12, 2016

@thinkingserious I received that test email, I was also able to get the Hello Test working fine, it's just these templates don't want to work.

EDIT: So I replaced var emptyRequest = require('sendgrid-rest').request with var emptyRequest = sg.emptyRequest() and that sends the email, there's just not any formatting from the template design or any images.

@thinkingserious
Copy link
Contributor

@bcootner,

Unfortunately, I can't reproduce your error, so I'm trying to help step through where there could be a problem. Since you can send an email via curl, that means your API key is good. Perhaps the Template ID has a problem?

If you remove mail.setTemplateId("5a****-*******-******-9") does the email send?

@bcootner
Copy link

bcootner commented Jul 13, 2016

@thinkingserious So if I remove the setTemplateID it sends the test "Hello World from the SendGrid Node.js Library".

I'm not sure if you saw my edit, but by replacing var emptyRequest = require('sendgrid-rest').request with var emptyRequest = sg.emptyRequest() the text from my template does send, but there no formatting (no fonts, no images). I get the following print out now from the console.

2016-07-13T00:01:07.514157+00:00 app[web.1]:   date: 'Wed, 13 Jul 2016 00:01:07 GMT',
2016-07-13T00:01:07.514159+00:00 app[web.1]:   connection: 'close',
2016-07-13T00:01:07.514157+00:00 app[web.1]:   date: 'Wed, 13 Jul 2016 00:01:07 GMT',
2016-07-13T00:01:07.514158+00:00 app[web.1]:   'content-type': 'text/plain; charset=utf-8',
2016-07-13T00:01:07.502390+00:00 app[web.1]: 202
2016-07-13T00:01:07.502454+00:00 app[web.1]: 
2016-07-13T00:01:07.514155+00:00 app[web.1]: { server: 'nginx',
2016-07-13T00:01:07.514159+00:00 app[web.1]:   connection: 'close',
2016-07-13T00:01:07.514161+00:00 app[web.1]:   'x-frame-options': 'DENY' }

Something makes me think it's a problem with 'text/plain', but I'm not sure. Thanks again!

@ByEmke
Copy link

ByEmke commented Jul 13, 2016

Hey @bcootner, I have just experienced the same issue and been scratching my head for a few hours, but managed to solve it. It feels that there is too much unnecessary stuff needed before you can actually send the email, but here's my helper function to do that:

Params

  • from (e.g 'test@test.test')
  • to (e.g 'test@test.test')
  • subject (e.g 'test subject')
  • message (e.g 'test message')
  • template (template id which you want to use)
  • templateVariables (object, where key - variable in the email, value - value to replace it with) { ":name": "someName", ":email": "someEmail" }. Note that :email and :name is how I have set my variables in the email template, it can be -email- or whatever you have
  • success callback
  • error callback
    let sendTemplateMail =  (from, to, subject, message, template, templateVariables, successCallback, errorCallback) => {
        var sg = require('sendgrid').SendGrid(process.env.SENDGRID_API_KEY),
            helper = require('sendgrid').mail,
            content_text = new helper.Content("text/plain", message),
            content_html = new helper.Content("text/html", message),
            request = sg.emptyRequest(),
            email_to = new helper.Email(to),
            email_from = new helper.Email(from),
            mail = new helper.Mail(email_from, subject, email_to, content_text),
            personalization = new helper.Personalization();

        personalization.addTo(email_to);
        personalization.setSubject(subject);

        mail.setTemplateId(template);
        mail.addContent(content_html);

        for(var key in templateVariables) {
            if(templateVariables.hasOwnProperty(key)) {
                var substitution = new helper.Substitution(key, templateVariables[key]);
                personalization.addSubstitution(substitution);
            }
        }

        mail.addPersonalization(personalization);

        request.method = 'POST';
        request.path = '/v3/mail/send';
        request.body = mail.toJSON();

        sg.API(request, (json) => {
            if(json.statusCode >= 300) {
                errorCallback(json);
            } else {
                successCallback(json);
            }
        });
    }

The documentation indeed needs some refactoring, with basic, simple examples. Hope my function will help you out :)

@thinkingserious
Copy link
Contributor

@ByEmke thanks for your support! Could you please email us at dx@sendgrid.com with you T-shirt size and mailing address?

With regards to the documentation, a refactor is on it's way as well as for the mail helper itself. We've been collecting all of your feedback and are excited about the next iteration.

Also, a big confusion is that you still need set the content when using template. Fortunately, that will change very soon (days).

@bcootner I think you nailed it. You need content_html = new helper.Content("text/html", message). Fortunately, this requirement is going away in a few days, our team is currently changing this behavior so that when you specify a template, you will no longer need to set the content.

@bcootner
Copy link

@ByEmke @thinkingserious thanks for your help on this issue, I managed to get it to work with the following code last night:

 var sg = require('sendgrid').SendGrid("SendGrid API Key" or <environment variable>)

function sendEmail(tempID){
    var helper = require('sendgrid').mail;
    from_email = new helper.Email("frome-mail@example.com")
    to_email = new helper.Email("to-email@example.com")
    subject = "Dummy Subject"
    content = new helper.Content("text/html", "dummy content")
    mail = new helper.Mail(from_email, subject, to_email, content)

    substitution = new helper.Substitution("-name-", "User's Name")
    mail.personalizations[0].addSubstitution(substitution)
    mail.setTemplateId(tempID)
    var requestBody = mail.toJSON()
    var requestPost = JSON.parse(JSON.stringify(sg.emptyRequest()))
    requestPost.method = 'POST'
    requestPost.path = '/v3/mail/send'
    requestPost.body = requestBody
    sg.API(requestPost, function (response) {
       console.log(response.statusCode)
       console.log(response.body)
       console.log(response.headers)
  })
}

Thanks again!

@peterkuiper
Copy link
Contributor

I also feel that the docs are quite hard to follow, especially when using templates and some other features.

I prefer the request.body = {} syntax over the helper() syntax as this makes things more verbose and less easy to read (for me at least).

I spent quite some time going through the docs, testing changes, looking at your examples and trying again only to come here and find out that you do need to set content when using templates though the docs state otherwise. Argh. Stuff like this can drive you mad. Anyways kudos to @ByEmke for providing a working example.

@thinkingserious
Copy link
Contributor

@peterkuiper (or should I say Adam :))

Thanks for the feedback, we are very interested in how we can make the library docs better.

To be clear, are you referring to these? https://github.com/sendgrid/sendgrid-nodejs/blob/master/USAGE.md

With regard to the content issue (we heard all of you :)), this is just about fixed. We will deploying a release to the API that will not require the content to be set when using a template. We hope that change will make the template experience much better.

@peterkuiper
Copy link
Contributor

peterkuiper commented Jul 19, 2016

@thinkingserious I was checking out the docs on sendgrid.com (ie https://sendgrid.com/docs/API_Reference/Web_API_v3/Mail/index.html) while I should have gone straight to Github. I skimped through the README of this repo, checked out the examples and totally missed USAGE.md (my bad). The USAGE.md file should be the one that should be put on on sendgrid.com as it has my preferred format :) Still not sure about some best practices when using templates but I hope I can figure that out myself or find it in the docs.

@peterkuiper
Copy link
Contributor

peterkuiper commented Jul 19, 2016

I was browsing that file and just found a random example of something that I find confusing:

var request = sg.emptyRequest()
request.queryParams["start_time"] = '1'
request.queryParams["limit"] = '1'
request.queryParams["end_time"] = '1'
request.queryParams["offset"] = '1'
request.method = 'GET'
request.path = '/v3/suppression/blocks'
sg.API(request, function (response) {
    console.log(response.statusCode)
    console.log(response.body)
    console.log(response.headers)
  })

What types are start_time, limit, end_time and offset and what do these mean? Are there more queryParams? And why isn't it request.body?

There is a link to the User Guide (which does not help at all) while there should have been a link to the API docs which clears things up https://sendgrid.com/docs/API_Reference/Web_API_v3/blocks.html.

So you have to go back and forth trying to figure out where to find the information you need.

@thinkingserious
Copy link
Contributor

Excellent feedback @peterkuiper!

I'd like to swag you out as well. Please send us your T-shirt size and mailing address to dx@sendgrid.com.

We will update the USAGE.md docs to include descriptions of the query and response bodies.

Regarding templates, the plan there is to create a helper like we did for the mail endpoint, complete with examples of common use cases. Also, there is a fix coming where you will not have to specify the content when using templates. That is a big source of confusion.

@peterkuiper
Copy link
Contributor

peterkuiper commented Jul 20, 2016

@thinkingserious cool, thanks :) email sent!

While I am at it, I noticed something else which also refers to best practices (and is causing some confusion for my team). One of my teammates created templates for some features (ie verify email) and added verify-nl, verify-en etc. So every template was basically the same with the only difference being the text (different language). I have seen <%subject%> en <%body%> and couldn't find any reference to it (TL;DR from my part maybe) so I assume it is an internal substitution on your end which happens when using the API.

I'm curious what a "normal" practice might be:

  • Create a template for each feature in a different language and only do some minor substitutions (ie name)

It seems using this approach might cause a lot of work when you change parts of your template. Not sure if you would be able to create "template templates" (ie header/footer/whatever part). Also, the limit of 300 templates can easily be reached when you have a lot of different languages (this isn't an issue in our case).

  • Create a template for each feature and use <%body%> to set the body from your application and just have one "master" template (or use your on sub tag)

Hope the question makes sense :)

@thinkingserious
Copy link
Contributor

@peterkuiper,

I don't know, but I've put out some feelers. I'll respond with what I discover. Thanks!

@IonicaBizau
Copy link

@thinkingserious I ended up using version 2.0.0 which I really like how it's working:

var client = require("sendgrid")("key");

client.send({
  to: "foo@bar.com",
  from: "baz@bar.com",
  subject: "subject",
  text:  "hello"
  // Or using the html property:
  // html: "Hello <strong>World!</strong>!"
}, fn);

I'm looking to see how this would look like in version 3.x.x. I find the current examples really confusing.

@thinkingserious
Copy link
Contributor

Great feedback @IonicaBizau!

We will definitely be considering your thoughts for the next iteration.

@IonicaBizau
Copy link

@thinkingserious Great! Still, I'd like to know how this would look like in 3.x.x.

@thinkingserious
Copy link
Contributor

@adamreisnz
Copy link
Contributor

adamreisnz commented Aug 23, 2016

I don't use the Template helper, but I will share my approach to loading both HTML and text format templates and partials via a helper load method:

  /**
   * Load an email (both plain text and html)
   */
  load(email, data, req) {

    //Get filenames
    const PARTIAL_HTML = path.resolve('./app/components/' + email + '.html');
    const PARTIAL_TEXT = path.resolve('./app/components/' + email + '.txt');

    //Append some globals
    if (req) {
      Object.assign(data, {
        app: {
          title: req.app.locals.APP_TITLE,
          version: req.app.locals.APP_VERSION,
          url: req.app.locals.APP_BASE_URL,
        },
        date: {
          year: moment().format('YYYY'),
          date: moment().format('DD-MM-YYYY'),
        },
      });
    }

    //Return promise
    return Promise.all([
      Promise.all([
        readFile(TEMPLATE_TEXT, 'utf8'),
        readFile(PARTIAL_TEXT, 'utf8'),
      ]).spread((template, partial) => {
        return template.replace('{{partial}}', partial);
      }),
      Promise.all([
        readFile(TEMPLATE_HTML, 'utf8'),
        readFile(PARTIAL_HTML, 'utf8'),
      ]).spread((template, partial) => {
        return template.replace('{{partial}}', partial);
      }),
    ]).then(result => result.map(contents => replaceData(contents, data)));
  },

This can then be used as follows to obtain an object ready for use with Sendgrid:

  let email = mailer.load('user/emails/verify-email-address', data, req)
    .spread((text, html) => ({
      to: user.email,
      from: req.app.locals.EMAIL_IDENTITY_NOREPLY,
      subject: 'Verify your email address',
      text, html,
    }));

You could easily adapt the example to use something like Handlebars templating as well. In the above example the replaceData helper is a simple function that replaces handlebars-like tags with data provided.

@seanlindo
Copy link

seanlindo commented Aug 25, 2016

I'm not sure if this is relevant or not, but by NOT using the "mail helper" I saved myself an immeasurable amount of time. This is after getting so frustrated I downgraded to 2.0 on purpose. I'm just using a factory-type function to generate valid V3 JSON and am now very excited at the improvements in the V3 API (since I can actually use them now).

@adamreisnz
Copy link
Contributor

This is something that I struggled with at first as well. I think the
helpers could probably be made more efficient, and easier to use. I would
even argue that maybe they shouldn't be part of the core sendgrid module,
in order to separate concerns and allow people to opt in to use them.

I'll have another look at them and see if I can come up with some concrete
suggestions.

On Fri, Aug 26, 2016, 05:48 Sean Lindo notifications@github.com wrote:

I'm not sure if this by example or not, but by NOT using the "mail helper"
I saved myself an immeasurable amount of time. This is after getting so
frustrated I downgraded to 2.0 on purpose.


You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
#252 (comment),
or mute the thread
https://github.com/notifications/unsubscribe-auth/AAd8Qu5iRLFQwoKlRd2fP5oioT1uLqB6ks5qjdV2gaJpZM4JAiac
.

@thinkingserious
Copy link
Contributor

@seanlindo,

Thanks for taking the time to provide some feedback!

Here is an example of using this library without the Mail Helper: https://github.com/sendgrid/sendgrid-nodejs#without-mail-helper-class

The Mail Helper is a first version and we are dependent on feedback like yours to help us improve the next version. Do you mind sharing the specific issues you ran into so we can create tickets to fix them?

Also, I'm adding your vote to our backlog task to improve the Mail Helper to help move it up the queue. Thanks!

@adambuczynski,

I see that your awesomeness continues :)

I'm looking forward to your feedback, I know it will be great!

@thinkingserious
Copy link
Contributor

@julesbou,

We have started a USE_CASES.md file where we will provide examples for common use cases. The first was transaction templates :)

@adamreisnz
Copy link
Contributor

I'm looking forward to your feedback, I know it will be great!

👻

@seanlindo
Copy link

@thinkingserious Sure! Give me a day or so and I'll provide you a concrete example.

@thinkingserious
Copy link
Contributor

This is one of my favorite threads here :)

I think your feedback is going to be critical for the next iteration of this library, which will likely be a breaking change. If you have a moment, could you please take a look at our proposal? #290

Thanks!

@adamreisnz
Copy link
Contributor

adamreisnz commented Dec 9, 2016

@thinkingserious I finally came to understand what bothers me so much about all the Sendgrid helper classes introduced in v3... there's just too many of them and they make sending emails unnecessarily complicated :P

I didn't want to overhaul all of Sendgrid's code, so I decided to make a simple wrapper instead, sendgrid-mailer.

While Sendgrid's helper classes are useful behind the scenes, to create and validate email models, I don't think they should be forced upon us just to interact with the API. I find it makes writing Node apps more complicated than it should be, and the naming of the helpers can be quite confusing, e.g. Mail vs Email.

I think the basic example illustrates the problem well:

https://github.com/sendgrid/sendgrid-nodejs#with-mail-helper-class

This just seems way too convoluted for something as basic as "I want to send an email". It requires you to load 8 different dependencies and write 15 lines of code before you can send an email.

Not using the helper classes is arguably even worse though, as then you have to know the required structure of the email JSON request and populate it correctly yourself. One mistake will break the request easily.

So I abstracted all the helper classes logic away behind a simple, easy to use API helper, so that sending emails with Sendgrid becomes easy and fun again :)

The most basic example becomes:

//Load mailer and set API key (only needed once)
const mailer = require('sendgrid-mailer').config(API_KEY);
 
//Create email data 
const email = {
  to: 'a@example.org',
  from: 'Someone <b@example.org>',
  subject: 'Hello world',
  text: 'Hello plain world!',
  html: '<p>Hello HTML world!</p>',
};
 
//Send away 
mailer.send(email); //Returns promise 

The request is constructed behind the scenes and uses Sendgrid's helpers transparently.

It also supports sending multiple emails, exposes the Sendgrid object in case further customisation is needed, accepts Sendgrid Mail instances as well, and accepts a wide variety of formats for the to/from fields, e.g. Name <name@example.org> or an object with name/email properties. See the README for more details.

There's probably still room for improvement, but I wanted to share this solution here for people looking to use the Sendgrid API without being overwhelmed by it.

Hope it comes in handy for someone, and maybe it can provide some direction for the future of this library, in exposing a simpler API :)

cc @julesbou a bit late, but I hope you can still find a use for it.

@jamesdixon
Copy link

@adamreisnz seriously, thank you.

My background job that sends emails via sendgrid was using v4.0.7, which was already complicated enough. I upgraded to the latest version and sadly everything broke. I was so frustrated with how complex it was to send an email that I didn't even bother updating.

All that said, the simplicity of this is exactly what I was looking for. I'll give it a shot over the weekend.

Cheers!

@adamreisnz
Copy link
Contributor

@jamesdixon I was still stuck on v3.x.x and also didn't want to upgrade :)

Hopefully you will find it useful. Let me know how it works for you and if there's anything critical missing, thanks!

@thinkingserious
Copy link
Contributor

@adamreisnz,

This is AWESOME and thanks for sharing it with our community :)

tldr; our helper classes are not finished and you already beat us to where we are headed :)

We totally agree with your thoughts and this is the phase of the v3 library update we are currently working on across all 7 of our SDKs. Please see the Mail Helper Enhancement project here for more detail on the Node.js project.

Currently, we are finishing up the C# library. To get a concrete example of what we plan for this Node.js library, please see this. We are hoping to release that one within days.

So, I have a proposal:

Would you mind adding your solution into the Mail Helper here (similar to what we have done in C#)? I think your work would achieve a greater reach in that case. If not, no problem at all. Since you have posted your project under the MIT license I would hope you would forgive us if we borrowed from your good work a bit ;) And of course, we will make sure you get credit for your contributions.

If you decide to keep your work separate, could you please add a link here under the Community Libraries section?

Thanks for your amazing continued support. You rock!

@adamreisnz
Copy link
Contributor

@thinkingserious glad to hear you're thinking of heading the same way. The C# example looks better, but I think still somewhat convoluted for a JS implementation. Making everything classes is not necessarily always the best way to go in JS.

As for your proposal, since I'm still using the helper classes under the hood, I don't know how much of it would actually be useful to port into the official library. I would probably be more inclined to help with a major rewrite (e.g. v5) and start from fresh, taking input from users and the Node community and come up with an awesome API that is both easy to use yet flexible if needed.

But if in the mean time you want to borrow some of the code from my wrapper to use in the official library, by all means go for it :) I'll add the link to my wrapper in that page 🎉

@adamreisnz
Copy link
Contributor

I actually think that it might be a good idea to split the project into two packages, one lower level that includes the request logic for interacting with the API, and one higher level just for sending emails, similar to what I've created.

The lower level package could be used for people needing full access to the API, while the mailer package would be suitable for people just wanting to send emails. And of course under the hood, the mailer would use the API package.

@thinkingserious what are your thoughts on that?

@thinkingserious
Copy link
Contributor

@adamreisnz,

Thank you for the thoughtful feedback, as always.

I'm not sure if we need to split the project at this point. I think we can achieve similar results with the current helper model. That said, I'm open to exploring a new architecture in a future version and I would love to have you on board for that.

Hopefully some others in the community will weigh in.

I will think deeper on this and re-engage when it comes time to implement the updated Mail Helper.

Thanks again for your support and for adding the link to our docs!

@adamreisnz
Copy link
Contributor

It's a matter of separating concerns. You could include a helper/wrapper for easy mailing inside the main library, but in my opinion that's mixing two separate concerns to the likely detriment or needless complication of both. Keeping them separate will allow consumers to pick the library they need (or both), and would probably make development of both libraries easier because of the clearly defined boundaries.

I think it's the nature of Node and npm modules to have as much separation of concerns as possible, and have each package do a specific task (and be good at it!). It's something I've had to get used to as well when I first started with Node, but once I did, I liked the freedom and ability to develop clean, simple packages that it provides.

Look forward to hear some comments from the community.

@thinkingserious
Copy link
Contributor

Well, you are definitely persuasive with a solid argument :)

I really appreciate you taking the time to elaborate.

I was already looking forward to coming back to working on this library and now you've got me really excited to get back to working on this SDK with you and community.

@adamreisnz
Copy link
Contributor

Great, let me know when you're going to work on it :)
I'm on leave for 4 weeks so that means I'll finally have some spare time to do some work on open source projects as well 🌴

@thinkingserious
Copy link
Contributor

@adamreisnz,

Congrats!

@anymod
Copy link

anymod commented Dec 13, 2016

A much higher level "mailer package" is exactly what we'd want. Just need to send some emails.

With the last version it was dead simple, and now it's an unholy mess. "Basic" example currently has 8 vars defined, requiring special constructors. Huge step backward in terms of ease of use.

Should be as simple as

sendgrid.send({
  from: fromEmail,
  fromName: fromName,
  to: toEmail,
  subject: 'Hello'
  ...
})
.then(...)
.catch(...)
.finally(...)

Zero docs are needed, just an example we can copy paste and on our way. That's the primary value of SendGrid to our team, and unfortunately it is now missing.

@adamreisnz
Copy link
Contributor

@eeosk have a look at #252 (comment) 👍

@anymod
Copy link

anymod commented Dec 13, 2016

@adamreisnz Looks great; very obvious design decisions. I hope you are on the SendGrid payroll!

@transitive-bullshit
Copy link

@thinkingserious please seriously consider pointing the main docs to @adamreisnz project, as it simplifies everything significantly, and if I had known about it earlier today, it would've saved me hours of headache trying to use what imho is an overengineered, Java-inspired api in JS. Please give your users what they want, not what you think they want :-)

@transitive-bullshit
Copy link

Also, just to note that I wouldn't be surprised if other devs start ending up here more frequently now that the V2 API has been sunset, and new accounts will be forced to use the V3 API. Personally, the first thing I tried was using nodemailer (whose sendgrid transport still works w/ v2) which has made sense for dozens of projects in the past but took forever to get working this time around. If I had to guess given the popularity of nodemailer in the node community, I won't be the only one who ends up feeling this way in the coming months.

@adamreisnz
Copy link
Contributor

adamreisnz commented Mar 7, 2017

@fisch0920 thanks for your feedback, I'll be working together with @thinkingserious in the coming weeks to improve the Sendgrid API. Hopefully we'll come up with something that is easy to use but still flexible enough when needed.

@SendGridDX
Copy link
Collaborator

Hello Everyone,

I thought you might be interested in the re-design on the SendGrid Node.js Mail Helper: #378

Your feedback would be greatly appreciated!

With Best Regards,

Elmer

@thinkingserious
Copy link
Contributor

Please move to #378 for updates, thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
status: help wanted requesting help from the community type: community enhancement feature request not on Twilio's roadmap
Projects
None yet
Development

No branches or pull requests