#Transactional Email in #Javascript

November 23, 2017 Leave a comment

elastic-email

Transactional email differs from promotional / marketing email, in the sense that it is typically not sent it batches, but is sent in response to a user signing up to your website, or an event such as a low credit warning, or notification.

Normally, people think of email as a server side exercise, but you can also use Javascript to send email too – with the help of SMTPJS.com

Here’s a sample script using Elastic Email’s SMTP with SMTPJS –

Email.send(
“me@gmail.com”,
“you@gmail.com”,
“This is a subject”,
“this is the body”,
“smtp25.elasticemail.com”,
“username@gmail.com”,
“989accc0-cba1-4fbf-abf2-7bad4fc80526”,
function(data){ alert(data) }

);

It almost needs no explanation, it’s so simple!

Need an SMTP server:
If you don’t have access to an SMTP server, you can create one by opening an account at Elastic Email.com, then pressing Settings > SMTP/API, and using the SMTP configuration shown. Get SMTP Credentials

 

Advertisements
Categories: Uncategorized

Determine what version of #TLS your code is using.

November 23, 2017 Leave a comment

 

1_ibqd7KX_cmoaUmlidifNbA

If your code connects to a HTTPS web service, it’s possible that you are still not being fully secure. The thing is – HTTPS comes in a few different “Flavours”, or specifically TLS versions.

If you connect to a HTTPS service, but use an old TLS version, then you’re not being as secure as you could be.

However, if the HTTPS endpoint doesn’t complain about your TLS version, it’s often pretty hard to see exactly what TLS version you are using, and the last thing you want is to break open WireShark and try and pick apart the packets to see.

That’s where this handy API from Jeff Hodges comes in, at https://www.howsmyssl.com/a/check

If you make a call from C#, you may see a result like this

{
“given_cipher_suites”: [
“TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA”,
“TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA”,
“TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA”,
“TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA”,
“TLS_RSA_WITH_AES_256_CBC_SHA”,
“TLS_RSA_WITH_AES_128_CBC_SHA”,
“TLS_RSA_WITH_3DES_EDE_CBC_SHA”,
“TLS_RSA_WITH_RC4_128_SHA”,
“TLS_RSA_WITH_RC4_128_MD5”
],
“ephemeral_keys_supported”: true,
“session_ticket_supported”: true,
“tls_compression_supported”: false,
“unknown_cipher_suite_supported”: false,
“beast_vuln”: false,
“able_to_detect_n_minus_one_splitting”: true,
“insecure_cipher_suites”: {
“TLS_RSA_WITH_3DES_EDE_CBC_SHA”: [
“uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order”
],
“TLS_RSA_WITH_RC4_128_MD5”: [
“uses RC4 which has insecure biases in its output”
],
“TLS_RSA_WITH_RC4_128_SHA”: [
“uses RC4 which has insecure biases in its output”
]
},
“tls_version”: “TLS 1.0”,
“rating”: “Bad”
}

You can see, I get a “Bad” rating here, because I’m using TLS 1.0, and some obsolete cyphers.

I put in the following line to use TLS 1.2:

ServicePointManager.SecurityProtocol = (SecurityProtocolType)3072;

And received;

{
“given_cipher_suites”: [
“TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384”,
“TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256”,
“TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384”,
“TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256”,
“TLS_DHE_RSA_WITH_AES_256_GCM_SHA384”,
“TLS_DHE_RSA_WITH_AES_128_GCM_SHA256”,
“TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384”,
“TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256”,
“TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384”,
“TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256”,
“TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA”,
“TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA”,
“TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA”,
“TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA”,
“TLS_RSA_WITH_AES_256_GCM_SHA384”,
“TLS_RSA_WITH_AES_128_GCM_SHA256”,
“TLS_RSA_WITH_AES_256_CBC_SHA256”,
“TLS_RSA_WITH_AES_128_CBC_SHA256”,
“TLS_RSA_WITH_AES_256_CBC_SHA”,
“TLS_RSA_WITH_AES_128_CBC_SHA”,
“TLS_RSA_WITH_3DES_EDE_CBC_SHA”,
“TLS_RSA_WITH_RC4_128_SHA”,
“TLS_RSA_WITH_RC4_128_MD5”
],
“ephemeral_keys_supported”: true,
“session_ticket_supported”: true,
“tls_compression_supported”: false,
“unknown_cipher_suite_supported”: false,
“beast_vuln”: false,
“able_to_detect_n_minus_one_splitting”: false,
“insecure_cipher_suites”: {
“TLS_RSA_WITH_3DES_EDE_CBC_SHA”: [
“uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order”
],
“TLS_RSA_WITH_RC4_128_MD5”: [
“uses RC4 which has insecure biases in its output”
],
“TLS_RSA_WITH_RC4_128_SHA”: [
“uses RC4 which has insecure biases in its output”
]
},
“tls_version”: “TLS 1.2”,
“rating”: “Bad”
}

Still using some old Cyphers, but at least using TLS 1.2 now.

If you see the same API when called from Chome, you see:

 
“given_cipher_suites”: 
“TLS_GREASE_IS_THE_WORD_AA”,
“TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256”,
“TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256”,
“TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384”,
“TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384”,
“TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256”,
“TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256”,
“TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA”,
“TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA”,
“TLS_RSA_WITH_AES_128_GCM_SHA256”,
“TLS_RSA_WITH_AES_256_GCM_SHA384”,
“TLS_RSA_WITH_AES_128_CBC_SHA”,
“TLS_RSA_WITH_AES_256_CBC_SHA”,
“TLS_RSA_WITH_3DES_EDE_CBC_SHA”
],
“ephemeral_keys_supported”:true,
“session_ticket_supported”:true,
“tls_compression_supported”:false,
“unknown_cipher_suite_supported”:false,
“beast_vuln”:false,
“able_to_detect_n_minus_one_splitting”:false,
“insecure_cipher_suites”: 

},
“tls_version”:“TLS 1.2”,
“rating”:“Probably Okay”
}

Interestingly, you can also use this to see issues with Search Engine Spider bots, – look at the report from Yandex (Russian Search Engine)

Given Cipher Suites

The cipher suites your client said it supports, in the order it sent them, are:

  • TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384
  • TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384
  • TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384
  • TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384
  • TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA
  • TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA
  • TLS_DH_DSS_WITH_AES_256_GCM_SHA384
  • TLS_DHE_DSS_WITH_AES_256_GCM_SHA384
  • TLS_DH_RSA_WITH_AES_256_GCM_SHA384
  • TLS_DHE_RSA_WITH_AES_256_GCM_SHA384
  • TLS_DHE_RSA_WITH_AES_256_CBC_SHA256
  • TLS_DHE_DSS_WITH_AES_256_CBC_SHA256
  • TLS_DH_RSA_WITH_AES_256_CBC_SHA256
  • TLS_DH_DSS_WITH_AES_256_CBC_SHA256
  • TLS_DHE_RSA_WITH_AES_256_CBC_SHA
  • TLS_DHE_DSS_WITH_AES_256_CBC_SHA
  • TLS_DH_RSA_WITH_AES_256_CBC_SHA
  • TLS_DH_DSS_WITH_AES_256_CBC_SHA
  • TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA
  • TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA
  • TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA
  • TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA
  • TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384
  • TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384
  • TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384
  • TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384
  • TLS_ECDH_RSA_WITH_AES_256_CBC_SHA
  • TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA
  • TLS_RSA_WITH_AES_256_GCM_SHA384
  • TLS_RSA_WITH_AES_256_CBC_SHA256
  • TLS_RSA_WITH_AES_256_CBC_SHA
  • TLS_RSA_WITH_CAMELLIA_256_CBC_SHA
  • TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256
  • TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256
  • TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256
  • TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256
  • TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA
  • TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA
  • TLS_DH_DSS_WITH_AES_128_GCM_SHA256
  • TLS_DHE_DSS_WITH_AES_128_GCM_SHA256
  • TLS_DH_RSA_WITH_AES_128_GCM_SHA256
  • TLS_DHE_RSA_WITH_AES_128_GCM_SHA256
  • TLS_DHE_RSA_WITH_AES_128_CBC_SHA256
  • TLS_DHE_DSS_WITH_AES_128_CBC_SHA256
  • TLS_DH_RSA_WITH_AES_128_CBC_SHA256
  • TLS_DH_DSS_WITH_AES_128_CBC_SHA256
  • TLS_DHE_RSA_WITH_AES_128_CBC_SHA
  • TLS_DHE_DSS_WITH_AES_128_CBC_SHA
  • TLS_DH_RSA_WITH_AES_128_CBC_SHA
  • TLS_DH_DSS_WITH_AES_128_CBC_SHA
  • TLS_DHE_RSA_WITH_SEED_CBC_SHA
  • TLS_DHE_DSS_WITH_SEED_CBC_SHA
  • TLS_DH_RSA_WITH_SEED_CBC_SHA
  • TLS_DH_DSS_WITH_SEED_CBC_SHA
  • TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA
  • TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA
  • TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA
  • TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA
  • TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256
  • TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256
  • TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256
  • TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256
  • TLS_ECDH_RSA_WITH_AES_128_CBC_SHA
  • TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
  • TLS_RSA_WITH_AES_128_GCM_SHA256
  • TLS_RSA_WITH_AES_128_CBC_SHA256
  • TLS_RSA_WITH_AES_128_CBC_SHA
  • TLS_RSA_WITH_SEED_CBC_SHA
  • TLS_RSA_WITH_CAMELLIA_128_CBC_SHA
  • TLS_RSA_WITH_IDEA_CBC_SHA
  • TLS_ECDHE_RSA_WITH_RC4_128_SHA
  • TLS_ECDHE_ECDSA_WITH_RC4_128_SHA
  • TLS_ECDH_RSA_WITH_RC4_128_SHA
  • TLS_ECDH_ECDSA_WITH_RC4_128_SHA
  • TLS_RSA_WITH_RC4_128_SHA
  • TLS_RSA_WITH_RC4_128_MD5
  • TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA
  • TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA
  • TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA
  • TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA
  • TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA
  • TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA
  • TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA
  • TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA
  • TLS_RSA_WITH_3DES_EDE_CBC_SHA
  • TLS_EMPTY_RENEGOTIATION_INFO_SCSV
Categories: Uncategorized

π = 6.2831… ? Have we got it wrong?

November 22, 2017 Leave a comment

cooltext266929018210520

Recently reading a book by Steve mould “The Element In the Room”, he proposes that our definition of pi was a mistake, and instead it should have been double it’s value.

How can this be?, surely someone would have noticed. Well, it all comes down to definition. Pi is defined as the ratio between the diameter of a circle to the circumference. However, it could have just as easily be defined as the ratio of the radius of a circle divided by the diameter, and when that happens, many mathematical formulas become simplified.

Here’s a great video of Steve Mould arguing his case for Tau, or the double pi constant.

 

Categories: Uncategorized

Implementing a #HTTPS #Tunnel using c#

November 14, 2017 Leave a comment

rZl08

You very rarely have to work at TCP/IP level whenever writing network code in C#, and if you find yourself doing it, you’ve probably taken a very wrong turn. However, since information is sparse about the format of low level TCP requests, I’m writing this article.

This particular code snippet shows how to make a HTTPS tunnel via a proxy server in C#. It involves these steps:

  1. Send a CONNECT command instructing the proxy to connect to a remote server on a given port, i.e. 443 for SSL, and forward all subsequent traffic to this host and port.
  2. Read the response from the proxy, it should be a line saying “200 Tunnel Established”
  3. Pass the stream to a SSL stream object, and call AuthenticateAsClient
  4. Send HTTP data as normal.

Here’s some code to connect to ICanHazIP via SSL.

private static string TestIp(WebProxy proxy)
{
var tcp = new TcpClient(proxy.Address.Host, proxy.Address.Port);
var stream = tcp.GetStream();
var connect = Encoding.ASCII.GetBytes(“CONNECT http://www.icanhazip.com:443 HTTP/1.0\n\n”);
stream.Write(connect, 0, connect.Length);
var rawStream = new StreamReader(stream);
var strConnect = rawStream.ReadLine();
var ssl = new SslStream(stream);
ssl.AuthenticateAsClient(“www.icanhazip.com”);
var send = Encoding.ASCII.GetBytes(“GET / HTTP/1.0\r\n” +
“Host:www.icanhazip.com\r\n” +
“\r\n”);
ssl.Write(send, 0, send.Length);
var sr = new StreamReader(ssl);
var str = sr.ReadToEnd();
tcp.Close();
ssl.Close();
return str;
}

If you’re interested in low level socket programming in C#, check out by book:

Categories: Uncategorized

Access UK TV #EPG via #JSON

November 13, 2017 1 comment

iplayerfreesat02

If you are developing an app or website that allows people check television guides in the UK, then this API may help you out.

First, a list of 576 TV channels from the UK can be listed via this Rest API call;

http://tv.apixml.net/api.aspx?action=channels

Then, to get details of programs to be shown on this channel, then you can use the url;

http://tv.apixml.net/api.aspx?action=program&channelid=03c9f88a54910f471bb80c039e2a8fa1

Where channelId is obtained from the previous call. The schedule is always for the next 24 hours.

This API will be built into out TV UK app for iOS: https://itunes.apple.com/us/app/tv-uk/id464570844?mt=8

 

 

 

Categories: Uncategorized

Sending a base64 encoded file using #SMTP.js

November 10, 2017 Leave a comment

smtpjs

SMTPjs.com is a javascript library that allows you send email through Javascript. – You still need access to a outgoing mail (SMTP) server, but this makes life a little easier for your JS apps.

Today, we released v2.0.1 of the library, which has a few important fixes

  • The message body is no longer limited in size
  • There is now an optional callback parameter, that allows your code continue after the email is sent.
  • Attachments can be sent in base 64 format (dataURI) to the library.

Previous versions of the library will continue to be functional, but we recommend upgrading to the latest version.

Callback feature:

Depending on whether you use a stored token, or send your SMTP credentials with every request, then you use one of the two following blocks of code:

Email.send(“from@you.com”,
“to@them.com”,
“Subject”,
“Body”,
“smtp.server.com”,
“username”,
“password”,
function done(message) { alert(“sent”) }
);

or, when using stored credentials;

Email.send(“from@you.com”,
“to@them.com”,
“Subject”,
“Body”,
{
token: “your-token”,
callback:function done(message) { alert(“sent”) }
});

DataUri Attachments

Previously, in order to send an attachment with this script, then the file you needed to send needed to be already hosted online. This, may not be ideal, if you wanted your user to select a file from their device, or otherwise dynamically generate the file to be sent.

So, let’s imagine we want the user to select a file to be sent from their device, we add a form element as follows;

<input type=”file” id=”fileupload” onchange=”uploadFileToServer()” />

Then define the function uploadFileToServer as follows:

function uploadFileToServer() {
var file = event.srcElement.files[0];
console.log(file);
var reader = new FileReader();
reader.readAsBinaryString(file);
reader.onload = function () {
var datauri = “data:” + file.type + “;base64,” + btoa(reader.result);
Email.sendWithAttachment(“from@you.com”,
“to@them.com”,
“Subject”,
“Body”,
“smtp.server.com”,
“username”,
“password”,,
datauri,
function done(message) { alert(“Message sent OK”) }
);
};
reader.onerror = function() {
console.log(‘there are some problems’);
};
}

Categories: Uncategorized

#Translate any country name into any language in C#

November 10, 2017 Leave a comment

WordPress-Theme-Translation

If you have a multi-lingual app or website that needs to show a drop down list of country names, then it suddenly adds 195 words to your translation file, which is going to make your translation word count shoot up suddenly.

Surely, someone else has done this already?, yes, they have. The Unicode consortium have a public file that you can download that contains a list of countries, and lots of other information translated into many different languages; here; http://unicode.org/Public/cldr/1.7.0/core.zip

I extracted the two letter files ({language}.xml) from core/common/main, removed the dtd definition, and put it in to a folder named /data/localisation off the root of my website.

public static string Country(string code, string culture)
{
// Source: http://unicode.org/Public/cldr/1.7.0/core.zip
var locale = new CultureInfo(culture).TwoLetterISOLanguageName.ToLower();
var strLocalXmlFile = HttpContext.Current.Server.MapPath(“/data/Localisation/” + locale + “.xml”);
var xdoc = new XmlDocument();
xdoc.Load(strLocalXmlFile);
var xn = xdoc.SelectSingleNode(“//territory[@type='” + code + “‘]”);
return xn.InnerText;
}

Then you can call Country(“GB”,”sv-SE”) to get Storbritannien

Of course, there is many more things that you may want to translate, and nothing is better than a human translator, which I’d recommend OutsourceTranslation.com to find one.

Categories: Uncategorized