Communicating between client and server - javascript

If I were to build an app where a user could put javascript code on their website and, for example, it would track the number of impressions the site got, what would be the best way to send the information to my server?

XHR / XMLHttpRequest
The verb is probably best implemented as POST here.
MDN API link is the best I can give since it's a vague scenario:
https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest

Here is a small function to send an XMLHttpRequest:
function sendXMLRequest()
{
var xmlhttp = new XMLHttpRequest();
xmlhttp.open("GET","http://myserver.com", true);
xmlhttp.send();
}
(adapted from http://www.w3schools.com/ajax/ajax_xmlhttprequest_send.asp)
You would also have to find some way of calling this function when the site gets an 'impression' (or whatever event you want to track).

I would recommend using a web bug/pixel tracking. This makes a GET request to the server. This request wont be blocked by the same origin policy. The big analytics companies all use web bugs. Omniture and Google Analytics.
Basically you do a fake image request and put some extra tracking data on the call.
var webBug = new Image();
webBug.src = "http://yourserver.com/tracking/?visitorId=abc123&sessionId=123abc"
or just put the image into the html,
<img src="http://yourserver.com/tracking/?visitorId=abc123&sessionId=123abc"/>
http://en.wikipedia.org/wiki/Web_bug

Related

Chrome Extension OAUTH with Spotify API

I've been writing a chrome extension using the Spotify API and just got to the part where I need OAUTH to finish it up.
I've been looking at the spotify oath page (https://developer.spotify.com/web-api/authorization-guide/)
and it says you can just make a GET call and it'll take you to the page to log in, however when I implement it, it does nothing. I feel like I am missing some code but I am not sure what I am missing.
var xhr = new XMLHttpRequest();
xhr.onreadystatechange = function() {
if (xhr.readyState == 4) {
// Just alerting it to see what it came up with
alert(xhr.responseText);
}
}
xhr.open("GET", "https://accounts.spotify.com/authorize/?client_id=<clientID>&response_type=code&redirect_uri=https%3A%2F%2Fwww.google.com%2F", true);
xhr.send();
that is the code I have now (with client id filled in), and running it does nothing. (I specified http://www.google.com/ as my callback for now)
An XHR request will not, under any circumstance, open a page.
Running this code should return you the page contents, but you do nothing with it - certainly not properly display it for the user to interact with.
It seems like you need to read more on OAuth in general. That said:
Chrome extension API provides a specific tool for this: chrome.identity.launchWebAuthFlow(). It will take care of showing the auth page to the user and passing the token back to you. You need to use a specific "virtual" URL for it - see the chrome.identity documentation for more details. Also note that this API can't be used in a content script, you'll need to delegate this to the background page.

Importing events from MS Office 365 (PHP)

I have an intranet site for a small medical clinic, and on the front page I want to display upcoming events associated with the clinic-wide MS Office 365 email account.
I'm new to APIs, so some resources on how to get started would help.
The site is in PHP, but as I understand it, API functions can be done in JavaScript - either way is fine.
Once I can get an XML or JSON file from Microsoft, I'm pretty sure I can figure out how to format it for the site. The problem is just getting the info.
So far I have:
<script>
var req = new XMLHttpRequest();
req.open("GET", "https://outlook.office365.com/api/v1.0/users/{email address}/events", false);
req.send();
console.log(req.status);
console.log(req.StatusText);
</script>
The console logged:
"NetworkError: 401 Anonymous Request Disallowed
I've also tried the line req.open("GET", "https://outlook.office365.com/api/v1.0/users/me/events", false{or true}/ {username}, {password});, to which the console logged
NS_ERROR_DOM_BAD_URI: Access to restricted URI denied
Almost all the documentation I can find is directed toward individual users (employees of a company) interfacing with their 365 accounts through some web-based interface, so almost all of the urls have /me/ in them, indicating they have authenticated somehow. But I want my PHP or JavaScript script to automatically authenticate a single user and retrieve information. I imagine this requires hard-coding the user and password somewhere, but I've found no examples like that.
I'm obviously in way over my head, but can anyone offer any advice on how I can get this done? Or read more about how APIs work? Most of the documentation out there is directed at people who already have a certain level of knowledge, which I don't have, and don't really know how to get.
Thanks.
Missing part is authentication (OAuth) to connect from your app to O365..
Maybe this helps http://msdn.microsoft.com/library/bde5647a-fff1-4b51-b67b-2139de79ce4a%28Office.15%29.aspx
Yes, you do need to authenticate against the Office 365 APIs as indicated previously. To make calls against Office 365, you must register your app for OAuth against Azure AD.
I'd suggest looking at http://dev.office.com/getting-started/office365apis. It should guide you through setting up authentication and show you how to make the rest call.

What is the best/proper configuration? (javascript SOAP)

I need to retrieve data from a web service (via SOAP) during a nightly maintenance process on a LAMP server. This data then gets applied to a database. My research has returned many options and I think I have lost sight of the forest for the trees; partially because of the mix of client and server terms and perspectives of the articles I have read.
Initially I installed node.js and node-soap. I wrote a simple script to test functionality:
var soap = require('/usr/local/lib/node_modules/npm/node_modules/soap');
var url = "https://api.authorize.net/soap/v1/Service.asmx?WSDL";
soap.createClient(url, function(err, client)
{
if(typeof client == 'undefined')
{
console.log(err);
return;
}
console.log('created');
});
This uses a demo SOAP source and it works just fine. But when I use the actual URL I get a 5023 error:
[Error: Invalid WSDL URL: https://*****.*****.com:999/SeniorSystemsWS/DataExportService.asmx?WSDL
Code: 503
Response Body: <html><body><b>Http/1.1 Service Unavailable</b></body> </html>]
Accessing this URL from a browser returns a proper WSDL definition. I am told by the provider that the 503 is due to a same-origin policy violation. Next, I researched adding CORS to node.js. This triggered my stepping back and asking the question: Am I in the right forest? I'm not sure. So, I am looking for a command-line, SOAP capable, CORS app (or equivalent) configuration. I am a web developer primarily using PHP and Javascript, so Javascript is where I turned first, but that is not a requirement. Ideas? Or, is there a solution to the current script error (the best I think I have found is using jQuery in node.js which includes CORS)
Most likely, this error belongs to your website server.
Please go through this link, it might be helpful.
http://pcsupport.about.com/od/findbyerrormessage/a/503error.htm
Also you can open your wsdl in web browser, search for soap:address location tag under services. And figure out correct url, you are trying to invoke from your script. Directly access this url in browser and see what are you getting.
I think I have a better approach to the task. I found over the weekend that PHP has a full SOAP client. I wrote the same basic login script in PHP and it runs just fine. I get a valid authentication code in the response to loginExt (which is required in further requests), so it looks like things are working. I will comment here after verifying that I can actually use the web service.

Google OAuth WildCard Domains

I am using the google auth but keep getting an origin mismatch. The project I am working has sub domains that are generated by the user. So for example there can be:
john.example.com
henry.example.com
larry.example.com
In my app settings I have one of my origins being http://*.example.com but I get an origin mismatch. Is there a way to solve this? Btw my code looks like this:
gapi.auth.authorize({
client_id : 'xxxxx.apps.googleusercontent.com',
scope : ['https://www.googleapis.com/auth/plus.me',
state: 'http://henry.example.com',
'https://www.googleapis.com/auth/userinfo.email', 'https://www.googleapis.com/auth/userinfo.profile'],
immediate : false
}, function(result) {
if (result != null) {
gapi.client.load('oath2', 'v2', function() {
console.log(gapi.client);
gapi.client.oauth2.userinfo.get().execute(function(resp) {
console.log(resp);
});
});
}
});
Hooray for useful yet unnecessary workarounds (thanks for complicating yourself into a corner Google)....
I was using Google Drive using the javascript api to open up the file picker, retrieve the file info/url and then download it using curl to my server. Once I finally realized that all my wildcard domains would have to be registered, I about had a stroke.
What I do now is the following (this is my use case, cater it to yours as you need to)
On the page that you are on, create an onclick event to open up a new window in a specific domain (https://googledrive.example.com/oauth/index.php?unique_token={some unique token}).
On the new popup I did all my google drive authentication, had a button to click which opened the file picker, then retrieved at least the metadata that I needed from the file. Then I stored the token (primary key), access_token, downloadurl and filename in my database (MySQL).
Back on step one's page, I created a setTimeout() loop that would run an ajax call every second with that same unique_token to check when it had been entered in the database. Once it finds it, I kill the loop and then retrieve the contents and do with them as I will (in this case I uploaded them through a separate upload script that uses curl to fetch the file).
This is obviously not the best method for handling this, but it's better than entering each and every subdomain into googles cloud console. I bet you can probably do this with googles server side oauth libraries they use, but my use case was a little complicated and I was cranky cause I was frustrated at the past 4 days I've spent on a silly little integration with google.
Wildcard origins are not supported, same for redirect URIs.
The fact that you can register a wildcard origin is a bug.
You can use the state parameter, but be very careful with that, make sure you don't create an open redirector (an endpoint that can redirect to any arbitrary URL).

using xmlHTTPRequest for opening a secure application in a new window

We have a requirement where we want the ability to launch a new application (NewApp) from the base app (BaseApp). The login credentials for BaseApp and the NewApp are same since they use the same identity store.
BaseApp and NewApp are on different tech stacks, both being web applications. they are hosted on different servers.
NewApp provides basic Auth for web access.
How can I use java script to launch NewApp from links on my BaseApp. I want to be able to inject Basic Auth credentials.
I have tried using xmlHTTPRequest, but it appears to be geared more towards calling REST services and processing the fetched data rather than launching URLs.
using java script window.open(url) does not let me inject authorization header!
anything else I can explore ?
Additional Info:
The session cookie for BaseApp is not applicable for NewApp. When we first complete Basic Auth on the BaseApp, it generates a new Session Cookie which needs to be used.
Through xhr we are able to call the URL (with Basic Auth) for the NewApp. This returns a response with a session cookie.
The problem that I am unable to figure out is, how to render the response on a new window/tab on the browser.
The simplest solution is calling the new window with following url
http://<user>:<pass>#newapp
but this is not a good solution because you see credentials in plain text. You should better try one of the following solutions:
If you use a session cookie it's often possible to append it to the url like http://newapp?JSESSIONID=kjasbfkji877786sdf.
Either you can use the same Cookie from your base app (that should not be possible if the applications are on different machines)
Create XMLHttpRequest calling NewApp and authentication via BasicAuth. The response header should contain the required session cookie from the other server. Then you can call NewApp with the required cookie.
If you have no session cookie you could also try the second solution (XHR) because if a session is created it is also stored in the browser and the browser can manage session handling itself.
So in cases 1.2. and 2. you should do the following:
var XMLReq = new XMLHttpRequest();
XMLReq.open("GET", "url", asynchronous?, "user", "password");
XMLReq.send(null);
In case 1.2. you need to provide an additional handler for a succeeding call:
XMLReq.onload = function() {
window.open('http://NewApp?JSESSIONID='+XMLReq.getResponseHeader('Cookie'));
// note that 'JSESSIONID' depends on your backend implementation, this example is made for java backend
}
In case 2. it's simply
XMLReq.onload = function() {
window.open('http://NewApp');
}
The best solution would be OAuth or OpenID in this case but that depends on your usecase and your system environment and requires maybe a more complex backend implementation if there is currently no support for OAuth or OpenID.

Categories

Resources