James O'Neill's Blog

February 11, 2011

Elop and Ballmer : it’s the Ecosystem . Does everyone get it now ?

Filed under: Uncategorized — jamesone111 @ 6:07 pm

As the dust starts to settle after the announcement of the partnership between Microsoft and Nokia, the question has come from more than one quarter “what about the other handset vendors ?” 
There are 4 of them today. HTC has 4 phones out (the HD7, Mozart Trophy and Surround) with a 5th, the “Pro” due imminently; it makes more than a dozen Android devices. LG has one phone the Optimus 7 with a pro version in the pipeline, and according to Wikipedia makes 8 Android devices.  Samsung has the Omnia 7 and (if Wikipedia is to be believed) makes 9 Android devices. Dell is the last of the first wave Windows phone 7 manufacturers and it too has an Android device. Nokia is the first phone maker to go with Windows 7 who didn’t also go with Android. The initial “gang of four” can’t accuse Microsoft of infidelity when they had not been exclusive themselves,one must expect Microsoft to sell operating systems to all comers. The four also know that once they were eight: Garmin-Asus, HP, Toshiba and Sony-Ericsson were with them at launch. HP’s plans changed and the other three went quiet. Some drop out, some join, and so the world turns. I suspect their first thought is that if the decline in Nokia’s share comes to a halt, there will be less easy business to pick up.

You can watch the Stephen Elop and Steve Ballmer’s press conference here . Elop’s opening remarks echoed something from his burning platform memo: “The game has changed from a battle of devices to a war of ecosystems.”  Ecosystem was the word of the day*, I stopped counting the number of times it was used. It’s not about Nokia’s Windows Phone 7 device against, Dell’s, against HTCs against LG’s against Samsung’s. It’s about Microsoft’s ecosystem – with phones by Dell,HTC, LG, Nokia Samsung, and whoever else, against Google’s ecosystem with phones by Dell, HTC, LG, Samsung, Motorola, Sony-Ericsson, Old Uncle Tom Cobley and all, against the Apple and Blackberry ecosystems.

About 25:15 into the press conference someone asked Steve Ballmer about the other handset makers. He replies “The overall development of critical mass in Windows phone 7,  from other manufacturers, from the chipset community, is important to both of us – despite the fact that obviously Nokia wants to sell all the Windows phones it can”. Elop chimes in “This is an important thing for people to think about: Our number one priority is the success of the Windows Phone Ecosystem, in which Nokia is participating, so it is to our benefit to get that critical mass and virtuous cycle going which includes work done by  some of our handset competitors. We will encourage that, that’s a good thing. ”. We can’t prosper unless the ecosystem prospers. 

The next question Elop gets is “Why Microsoft not Android ?”  and his answer is interesting “What we assessed was 3 options…  internal: MeeGo Symbian and so-forth … the concerns about whether we could quickly enough develop a third ecosystem without the help of a partner like Microsoft … made that option concerning, absolutely concerning.” (Lovely way of putting it) “We explored the opportunity with the Google ecosystem … our fundamental belief is that we would have difficulties differentiating within that ecosystem – if we tipped over into the Android ecosystem, and there was a sense that was the dominant ecosystem at that point the commoditisation risk was very high, prices, profits everything being pushed down value being moved out to Google essentially. ”.

That begs a bunch of follow-up questions. “You don’t think you can build an ecosystem with MeeGo but HP think they can with WebOs  do you think they should be more … concerned ?”. “Is the Android handset market in a dash to the bottom or are you saying Nokia joining that market would have made it so ?”  “How will Nokia differentiate when Microsoft has worked to give consistent experience over all the Windows Phone 7 devices?”  “Why won’t  value will get moved out to Microsoft ? (Isn’t that the danger if you succeed and Microsoft’s becomes the dominant ecosystem ?)”
The financial question did get asked, and half answered, Nokia will pay Royalties on the OS, Microsoft will buy services from Nokia to strengthen the ecosystem. Who knows if Google would have offered them the  same ? Connections have little way to add value, the opportunities for the handset makers are reducing. Pushing stuff to the handsets is where the opportunity is today. I haven’t made a lot of purchases since I got my HTC trophy, but Microsoft take 30% of software sales from marketplace and if the margin Music is the same they’ve made £10 out of me in 3 months, that’s £80 over the two year life of a phone. I never had much idea what a Microsoft charged to put its software on a phone, (you can buy Windows 7 home Premium from a PC builder for £62 + VAT so Windows Mobile 6.x / Windows Phone 7 netting more than £80 doesn’t seem plausible). A year ago Microsoft made zero once a phone had been sold, now the revenue is reaching the point  where a token license fee is feasible – I can’t see Microsoft letting go completely.  And of course the biggest ecosystem by unit volume is an OS given away to sell advertising. You can see Nokia wanting to be in an ecosystem where it is not just as a handset maker.

 

* I nearly used “It’s the ecosystem stupid”, or “Our priorities are ecosystem, ecosystem, ecosystem” for a title.

Why IE9 might cause some unnecessary installations

Filed under: Internet Explorer — jamesone111 @ 1:22 pm

Have a look at this picture and tell me what the user Needs to do (apart from getting a life an not watching the Downfallen Meme on YouTube that is).

image

It’s pretty clear what they need to do … How about this one which I got this morning.

image

 

I have had various different versions of Silverlight on this machine, developer bits and so on. It seems the site wants a different one

image

I decided this was a beta issue, removed Silverlight, re-installed and yes, you’ve guessed, wound up with exactly the same version number showing under Control Panel / Programs and the same message on the web page.

Eventually I spotted this

image

That blue symbol means filtering is on – ActiveX filtering to be exact, and that means no Silverlight or flash. That’s a good thing. Until you forget. Which I did, and plenty of other people will too. I like that the notification is discreet. I certainly don’t want something trying to get my attention to say it has saved me from a distracting piece of flash. So web pages need to start saying something different.

February 10, 2011

IE9 and getting to grips with privacy

Filed under: Uncategorized — jamesone111 @ 10:04 pm

I wrote a post a few weeks ago entitled “One small step for IE9, one giant leap for privacy”. With the arrival of IE9 release candidate things have changed a little bit: the only words I can repeat from my initial reaction are STUPID and BROKEN but whilst things are not quite as I would have liked they are nowhere near as bad I first feared

First the bad….

  1. You can no longer import /export   block /allow lists. Previously you could export the list which IE built up, hand edit the XML and re-import it. This was tedious to do and only  worked at very small scale.
  2. The XML format announced by  Dean Hachamovitch Corporate Vice President, Internet Explorer in December   – which was the self same format used in import and export  appears to have been abandoned. The new format is a a text file, but doesn’t use the de-facto standard (adblocker for firefox).
  3. Microsoft was previously accused – by the Wall Street Journal no less of sabotaging the protection offered by in private filtering. When people take a good look at the Lists Microsoft is promoting  there may be fresh accusations that they are poor filleted things.
  4. The auto-blocking is a bit heavy handed – on my system it blocked on WordPress’s stylesheets. I can find the offending block and make it an allow, but most users won’t be able to and will turn their own personal block lists off.

Let’s expand on that third point.  I can’t see any sense in changing from the XML format to a text file but not allowing people to import the lists used by the ad-blocker add-on for Firefox.  If you want to believe in a conspiracy, then Microsoft is too cosy with advertisers. Microsoft’s page actually has an entry from Easy List described thus: “EasyPrivacy Tracking Protection List is based on the popular EasyPrivacy subscription for Adblock Plus and is managed by the well-known EasyList project“. Quite true and there’s   2,581 lines of it. But main EasyList which blocks 10,000 plus sites is not available (though it shouldn’t take long to convert it)

So the good.

  1. It only takes a couple of minutes with PowerShell to get the XML files into the new text format. Since my old list blocked or allowed whole domains , and used the same text as a description as it had in the “block regex” or “allow regex”, I just needed to see if a row was a block or an allow, and prefix the domain name with “+d” or “-d”  converting  “\.” to “.” in the description as I went.
    $x=[xml](get-content C:\users\Public\Documents\export.xml | %{$_ -replace "item","rssItem" })
    $x.rss.channel.rssItem | where {$_.blockregex}  | % {"-d " + $_.description -replace "\\\.","."} | clip

    $x.rss.channel.rssItem | where {$_.allowregex}  | % {"+d " + $_.description -replace "\\\.","."}  |clip
    The first line reads the XML and the second and third place the text in the clipboard and I can paste it into notepad with a file which starts
    msFilterList
    : Expires=5

    The first line is obvious and the second is the number of days to wait between updates. Simples. I could have done it all in PowerShell without bothering with notepad/

  2. It’s pretty easy to put an “Add my TPL” link on a page  it goes
    <a href="javascript:window.external.msAddTrackingProtectionList ('http://server.MyDomain.com/myFileText, 'Description’')">Add TPL</a>
    I couldn’t get this to work with File:// urls, or skydrive and wordpress filters out that kind of link. Grrr
  3. Active X blocking.  Read “flash blocking”. This is new for RC. Regular readers will know I hate flash which wants to pull my attention away from the content I’m trying to read. No active-X means No flash. But sometimes you need flash turning it on and off is a pain. Now you get this 
    image
    I’ve circled the the “content blocked” icon on the address bar. Click it and you can turn off what you want – and it seems to apply to that site only , but on all future visits – though you can turn it back on.
    image

February 9, 2011

On outsiders and burning platforms.

Filed under: Uncategorized — jamesone111 @ 6:06 pm

 

The only impression Stephen Elop left on me in his time at Microsoft was that his speech at Tech-ed  in Berlin on the 20th Anniversary of the fall of the wall had been seen as boring. What is already being called  his “Burning platform” memo  pretty much kills off any reputation for dullness. Wake up calls to companies rarely get openings of this drama:
There is a pertinent story about a man who was working on an oil platform in the North Sea. He woke up one night from a loud explosion …  He could stand on the platform, and inevitably be consumed by the burning flames. Or, he could plunge 30 meters in to the freezing waters. The man was standing upon a “burning platform,” and he needed to make a choice.  ….  We too, are standing on a “burning platform” ”

Engadget says Elop is “neither Finnish, nor raised in the Nokia system” and  I’ve had a couple of conversations recently about incomers to companies.  You’d expect Microsoft to end up full of “Microsoft people”,  Ford to be full of “Ford people” and Nokia full of “Nokia people”. If you can get past people’s tendency to hire in their own image and companies being most attractive to people like the ones they already have – even then people adopt the ways of a community they belong to – which could be business, academic, government, even monastic. It was someone writing about the Atkins diet who introduced me to an idea from Thomas Kuhn’s “The structure of scientific revolutions”: new ideas must come from outside the community (Atkins was a cardiologist, not a dietician); precisely because being part of the community means buying into its ideas. People raised inside a system don’t change it: change comes from outside.

The people who appointed Elop would have known that.  It’s likely that Elop had reached the conclusion “If we jump we may drown, if we don’t we will burn” before he took the job, and would have shared it. Now he’s told a wider audience there is no other choice “we have multiple points of scorching heat that are fuelling a blazing fire around us.”

He says the iPhone has 61% of the $300+ smartphone market and Nokia “still don’t have a product that is close to their experience.”  He says  “Android came on the scene just over 2 years ago, and this week they took our leadership position in smartphone volumes. Unbelievable”.  And at the low end of the market “Chinese OEMs are cranking out a device much faster than … ‘the time that it takes us to polish a PowerPoint presentation’.”  
The problems aren’t just external Nokia is “not even fighting with the right weapons.”  he says:  “We thought MeeGo would be a platform for winning high-end smartphones. However, at this rate, by the end of 2011, we might have only one MeeGo product in the market.”  We thought, past tense? If you don’t think it will be that platform then what do you do with it?  He says Symbian “has proven to be non-competitive … and also creating a disadvantage when we seek to take advantage of new hardware platforms.”  Symbian, like Windows Mobile 6.x was designed for pre-iPhone market they’re cold-war products in a Post Berlin-Wall world. 

And it’s to metaphors of warfare that Elop turns to explain the jump Nokia is expected to announce on Feb 11th. “The battle of devices has now become a war of ecosystems, where ecosystems include not only the hardware and software of the device, but developers, applications, ecommerce, advertising, search, social applications, location-based services, unified communications and many other things. Our competitors aren’t taking our market share with devices; they are taking our market share with an entire ecosystem. This means we’re going to have to decide how we either build, catalyse or join an ecosystem.”

Putting the building option to one side, which ecosystem will they catalyse or join? The language seems to rule out selecting more than one. It’s probably safe to assume that Apple aren’t looking to license their OS, ditto RIM. Palm’s new WebOS doesn’t have much of an ecosystem. A Google VP appeared to rule out Android by tweeting#feb11 “Two turkeys do not make an Eagle”.’  The date appears to suggest Nokia and someone else.  And I seem to have crossed everyone but Microsoft off the list.

Microsoft Published Steve Ballmer’s mail from September 9th last year announcing Elop was off.  Maybe “I… look forward to continuing to work with him in his new role at Nokia.” is just what you say as CEO when one of your people becomes CEO somewhere else? But if on Friday, 155 days later, Steve and Stephen make a joint announcement someone is bound to ask if 155 days is long enough to do much more than polish a two-CEO PowerPoint presentation.

February 7, 2011

How to read Excel files in PowerShell.

Filed under: Uncategorized — jamesone111 @ 2:44 pm

I picked up a post of Lee Holmes’ entitled Does Your Hard Work Advance the Ecosystem; which  joins a discussion that started with what Lee terms a “fairly chewy piece” on the Lync PowerShell blog. That was about reading stuff from the cells of an Excel spreadsheet to set up users. Over here Jason basically says “very clever and all that, but wouldn’t you just convert to .CSV ?”  Lee’s piece is worth reading in full, but the key points are

  1. Some people will do things the hard way.  A few lines of PowerShell can replace hundreds in something like C#. [Side note: I’ve been working in C# recently and I know this only too well]. The experience of some hard-core programmers stops them imagining an easy way.
  2. There isn’t anything built into PowerShell to read XLS / XLSx files, so showing people how Excel can be used does move things forward. And PowerShell is about automating: starting a process by manually loading files into Excel and converting isn’t ideal.
  3. It is easy to write up and share what you did for a specific case. But a generic is better –providing an “Import-XLS” command is more useful than CreateLyncUsersFromXLS.PS1

I have to agree with both Jason and Lee – one probably would load the file in the Excel, and that isn’t the ideal. I’ve been manipulating the Office object model on and off since the early 1990’s so I really get Jason’s point that there is more to learn there than makes sense for an admin to pick up to get round the problem of people not saving in .CSV format when asked.

So here, for any admin confronted with that problem is ConvertFrom-XLx – it accepts a path to a file, or a file object from the pipeline ,  (so dir *.xlsx | convertFrom-XLx will work). It checks that the file exists, and ends with .XL<something> – that’s the little regular expression used with the -match and -replace operators. The -replace puts .CSV into the save name and the file is then opened, saved as CSV (that’s type 6 in a SaveAs operation), and closed (false says don’t stop to ask the user anything on closing)
Finally if a –PassThru parameter is specified the CSV file can be read in and passed to the next step in a pipeline.  

function ConvertFrom-XLx {
  param ([parameter(             Mandatory=$true,
                         ValueFromPipeline=$true,
           ValueFromPipelineByPropertyName=$true)]
         [string]$path ,
         [switch]$PassThru
        )

  begin { $objExcel = New-Object -ComObject Excel.Application }
Process { if ((test-path $path) -and ( $path -match ".xl\w*$")) {
                  
 $path = (resolve-path -Path $path).path
                $savePath = $path -replace ".xl\w*$",".csv"
              $objworkbook=$objExcel.Workbooks.Open( $path)
            
 $objworkbook.SaveAs($savePath,6) # 6 is the code for .CSV
              $objworkbook.Close($false)
              if ($PassThru) {Import-Csv -Path $savePath }
         
}
        
 else {Write-Host "$path : not found"}
        }
   end  { $objExcel.Quit() }
}

February 3, 2011

How to get files from a Windows Phone 7 App to a PC

Filed under: Uncategorized — jamesone111 @ 12:31 pm

In my review of Windows phone 7 I said that a lot of things I wanted to see changed in future could be summarized as “make it easier to get stuff on and off the phone”. If you are a user of phones I’m afraid this article won’t be of any more than academic interest, but if you write apps for the phone it is something you may want to know, especially if your background does not include Windows Communication Framework (WCF).

An earlier previous post  had said my new Windows 7 phone was Not a “Storage device” – that the Zune software syncs music, pictures and video [only]  without exposing the file system.  The memory card is non removable, and there is no API for developers to upload to Windows live. If you start writing for the phone you quickly find there is an “E-Mail compose task”, but if you does not let you add files from your app as attachments. If you have a small amount of text to send you can can put it in the body of the message. I found that the following code works …

EmailComposeTask ect = new EmailComposeTask();
ect.Subject = "Data from  Windows phone";
using (StreamReader sr = new StreamReader(
               appStorage.OpenFile("myFile.Txt", System.IO.FileMode.Open)))
{
  ect.Body = sr.ReadToEnd();
  ect.Body = ect.Body.Substring(0, 30000);
  }
  ect.Show();

But it’s unsuitable for anything but text and worse, if you want to send more than 32 KB it will crash

image

.NET experts might say “just look at System.Net.Mail”, but the compact framework on the phone doesn’t support the mail parts of System.Net, or the sockets parts (in case you harbour visions of connecting to Port 25 and hand cranking through SMTP – an old party piece of mine), it doesn’t even support ftp. If your app wants to get data in or out it must be over http… 

There are 3rd party storage services on the internet, but very few of them publish an API (Microsoft don’t publish the API for SkyDrive, and most of the other free storage providers follow suit.) As far as can I can find, no one yet has implemented something which can be simply added to an app to give “upload file” functionality. (No sooner will I push the publish button on this post than someone will of). Coding for the that APIs I was able to find would add a lot of complexity but it was also in the back of my mind that, I don’t want people who use my app to be required to sign up with a new storage provider. More to the point I want the data on my PC, not in the cloud so maybe if I could code something to do that … Everything I read said “use WCF” but assumed  pre-existing knowledge beyond mine. what I had.  So this is a crash guide to WCF for one purpose – moving files – and if you are new to WCF you only need to know that:

  • It allows clients to call methods/functions/procedures – “operations” on a server (PC), your work goes into writing the operations, not hooking them up to the network.
  • It works over HTTP so the phone can be a client
  • Access to the sever is via the SOAP protocol, which allows Visual Studio to add “proxy classes” which handle accessing the remote operations, so essentially you say “Make a connection”, “call this”, “call that” without worrying that what you are calling is remote. 

I am going to implement a very simple service, in the simplest possible way. It is going to be a Windows Command Line program, modelled on an example found on MSDN. To set itself up to listen on a particular port it needs to be run as administrator (you can read more about why, and how to avoid this requirement but it is beyond the scope of this post). This means to start debugging it Visual Studio needs to be run as Administrator, and the finished program needs to be Run As Administrator.

The service takes ONE kind of request that contains a file name and text which is to be written to the end of the file (if the file doesn’t already exist, it will be created). That’s it, the following are left as exercises for the reader

  • Any kind of security or authentication. If you leave the server part running and someone accesses it, they can add or change files on your computer.
  • Any handling of “state”,  beyond rudimentary flow control.
  • Handling non-text files.

If you are trying to do this yourself, it can be done in VB (see the MSDN example) but here is a step by step tutorial in C#

  • Start by creating a new project in Visual Studio, use a Windows Console Application  project
  • Add a reference to System.ServiceModel.
  • You should have one file open (program.cs), add to the using statements,
      using System.ServiceModel;
      using System.ServiceModel.Description;
  • as the first lines in your namespace add
    [ServiceContract]
    public interface Itransfer {
             [OperationContract]
            string NewOrAppendString(string fileName, string content);     

    }
  • This defines the service interface clients will be able to connect to and the operations it can perform.
    You can see there is one service and one operation, named NewOrAppendString, which takes two arguments – strings named filename and content, and returns a string as a result.
  • Next add a class which will implement Itransfer. The method(s) just defined must have matching one(s) in this class, like so:
    public class Transfer : Itransfer
        { public string NewOrAppendString(string fileName, string content)
            { try
                { using (var file = System.IO.File.Open(
                      Environment.GetFolderPath(Environment.SpecialFolder.Desktop) +
                       @"\" + fileName, System.IO.FileMode.Append))
                    {using (var sw = new System.IO.StreamWriter(file))
                       {sw.WriteLine(content); }
                    }
                   return "OK";
                }
                catch { return "failed"; }
           }
    }
  • That’s the service defined, notice the file is being saved to the desktop; obviously the program could be more polished. The same applies to the following which will start the service. Visual studio should have give the Program class a main procedure so inside  static void Main(string[] args) we can insert.
    string endpoint      = "http://localhost:31365/Transfer/Service";
    Uri baseAddress      = new Uri(endpoint);
    ServiceHost Selfhost = new ServiceHost(typeof(Transfer), baseAddress);           
    try  {
               Console.WriteLine("Attempting to start listening on " + endpoint);
               Selfhost.AddServiceEndpoint( typeof(Itransfer),
                                            new BasicHttpBinding(), "Transfer");
               ServiceMetadataBehavior smb = new ServiceMetadataBehavior();
               smb.HttpGetEnabled          = true;
               Selfhost.Description.Behaviors.Add(smb);
               Selfhost.Open();
               Console.WriteLine("Press <ENTER> to terminate service.");
               Console.ReadLine();
               Selfhost.Close();
            }
    catch (CommunicationException ce) {
               Console.WriteLine("An Exception occurrred : {0}", ce.Message);
               Selfhost.Abort();
    }

  • This is not hard to decipher, the MetaDataBehavior is set to tell the service to publish its description – without that Visual studio can’t get create the proxy class. I’m using a fixed port and in a polished program we’d let the user specify it, we’d display the IP address to connect to and so on. A “production” version might be more sophisticated in a lot of ways, and obviously you can offer more operations: Want to remotely control a program ? Send a query to a database ? If you can write a method for it, it should be possible (though you should read about the need to serialize data types). Powerful stuff.  
  • The next step is to start the program. Copy the end point to the clipboard and paste it into the address box in Internet explorer . You should get the metadata description page, which tells you a little about the service. Try replacing localhost with the IP address of your computer and test that, then try that URL in IE on your phone / phone emulator.
  • You will probably find that Windows firewall blocks the connection from a phone, but allows it from the emulator (or anything else running on the same PC). If this happens start the Windows Firewall management console, click “Incoming rules” (top left), and then “New Rule” (top right).   Specify “port” in the wizard on the next page select TCP “and enter the port number (31365 in my example code),  select “allow the connection” on the next page, and select all the networks on the one after that and on the last page give the rule a name like “phone transfer”. Unless you can get the page in IE the rest will not work so don’t underestimate the importance of this step.
  • Now you can add a service reference to  project in Visual studio, if you are trying to copy Click for a larger versionmy steps here the simplest way is to create a new phone application. In solution explorer, right click and add a new Service reference. Paste the URL into the address box and press GO. In a moment you should get a message “1 service(s) found”.

    The one service we have is named “transfer” and if you expand that you’ll see that it implements Itransfer which has an operation named NewOrAppendString. You can rename the Namespace. at the bottom I changed mine to “Transfer”

  • With the service reference in place it is possible to define a variable as a member of the phone apps’s main page 
    Transfer.ItransferClient client;
  • Then I use it in some code attached to a button in my phone app
    string addrText = http://192.168.1.100:31365/Transfer/Service/Transfer"; 
    client = new Transfer.ItransferClient("BasicHttpBinding_Itransfer", addrText );
    client.NewOrAppendStringCompleted +=
                 new  EventHandler< Transfer.NewOrAppendStringCompletedEventArgs >
                        (client_NewOrAppendStringCompleted);
    client.CloseCompleted +=
                 new EventHandler<System.ComponentModel.AsyncCompletedEventArgs>
                        (client_CloseCompleted);
    String mytext = "here is some text" + Environment.NewLine ; client.NewOrAppendStringAsync("Test.txt", mytext );
    client.CloseAsync;
  • I’m changing the address of the service from “localhost” to my machine’s IP address, and normally we’d have a mechanism for this information to be put into the program. The name that’s used in the next line is a bit hard to discover , it is the address specified when the service reference was added ( http://192.168.1.100:31365/Transfer/Service/ ), with service name (Transfer) appended to the end. If you look back at the console program you can see where that name is specified.  BasicHttpBinding was specified for the end point in that program too, and the end point name is the binding name joined to the interface name with an underscore.
  • Client has a method to call NewOrAppendString asynchronously. It will then raise an event to say the call has completed (the same applies to closing the client connection), so we add a couple of procedures to handle these events, for now they can use MessageBox.Show to say they have been called.
  • At this point it is necessary to break the app. Stop the service, then run the app and click the button and you will get an error in the code generated by adding the service reference.
    public string EndNewOrAppendString(System.IAsyncResult result) {   
        object[] _args = new object[0];
        string _result = ((string)(base.EndInvoke("NewOrAppendString", _args, result)));
        return _result;}
  • The simplest thing is to wrap a try , catch round this so that a failure does not cause the program to die (rather charmingly the phone tidies up after a crash so you don’t see the error, the program just goes away). We can look at the result in the event handler and see if we had an error. 
    public string EndNewOrAppendString(System.IAsyncResult result) {
        object[] _args = new object[0];
        string _result = "";
        try { _result = ((string)   <etc as above> ;}
        catch { }
        return _result;
    }
  • Now if you run the app again the call will come back without crashing and you can look for success and assume failure if you don’t explicitly get success.. So now you can start the command line program and try again. If all is well a file should appear on your desktop .
  • This is all grand, but you’ll find when you want to send files that there is a limit to how big the request can be: I send my data when it exceeds 4000 bytes to remain inside this limit. You can also out for yourself (by modifying this code to send the numbers from 1 to 1000 as separate requests) there  is no guarantee that requests will be processed in the order they are sent.  My solution is to only send the next block of a file when I have had the OK returned from the current one.  I define a string , transferFileName, and a stream reader, transferFileReader at the Page level in the phone app along with transferClient then I have the following code for my button
    private void btnSend_Click(object sender, RoutedEventArgs e){
        transferFileName    = filesList.SelectedItem.ToString();
        transferFileReader  = new StreamReader(appStorage.OpenFile(transferFileName ,
                                                       System.IO.FileMode.Open));
        string myText        = transferFileReader.ReadLine();
        string addrText      ="http://192.168.1.100:31365/Transfer/Service/Transfer";
       transferClient          = new Transfer.ItransferClient("BasicHttpBinding_Itransfer",
                                                       addrText);
       client.NewOrAppendStringCompleted +=
                 new  EventHandler< Transfer.NewOrAppendStringCompletedEventArgs >
                        (client_NewOrAppendStringCompleted);
       client.CloseCompleted +=
                 new EventHandler<System.ComponentModel.AsyncCompletedEventArgs>
                        (client_CloseCompleted);
        transferClient.NewOrAppendStringAsync(transferFileName , myText);
    }
  • This is much the same as before except I’m reading from a file and the name for the destination and reader object are accessible to other methods. Astute readers will also have spotted that I only send one line of the file. That’s it. Nothing can happen until the completed event fires and its method gets called, which looks like this :
    void client_NewOrAppendStringCompleted(object sender,
                                         NewOrAppendStringCompletedEventArgs e)
    {
        if (e.Result.ToUpper() == "OK")
            {  string myText = "";
                while ((myText.Length < 4000) && (!transferFileReader.EndOfStream))
                    { myText += transferFileReader.ReadLine() + Environment.NewLine;}
                if (myText != "")
                   { transferClient.NewOrAppendStringAsync(transferFileName, myText); }
            }
        if ((transferFileReader.EndOfStream) | (e.Result.ToUpper() != "OK"))
            {  transferClient.CloseAsync(); }
        if (e.Result.ToUpper() != "OK")
            { var foo = MessageBox.Show("An error occurred in the transfer"); }
    }

    void client_CloseCompleted(object sender,
           System.ComponentModel.AsyncCompletedEventArgs e)
    {  transferFileReader.Close(); }

  • So if the result is “OK” we read from the file until we have 4K of data or hit the end of the file. We send the text if there is any (we’ll immediately hit the end of file if we got the OK back from the very last block in the file, and we want to avoid an infinite loop). We client if we got to the end, or hit an error. And if we hit an error we say so, and when the client closes, we close the file. Even with a couple of extra bits for specifying the port and server name it comes out at only about 60 lines of C# It takes me 50-something lines to handle input of server name and port and persist them between settings. 

Eventually I’ll write a nicer and more versatile version, but as I’ve been at pains to point out, my purpose is to show how this stuff works anyone going through the same thing can learn from what I went through.

Create a free website or blog at WordPress.com.