Using the TFS 2010 API to subscribe to Workspace Events - c#

I'm trying to write some code that monitors the TFS workspace(s) on my local workstation but at the moment I'm having problems getting the events to fire.
For example if I map a new folder in my workspace I want to subscribe to the versionControl.UpdatedWorkspace event, and if I do a “get” I want to map to the versionControl.Getting event. The code below is a console application that I think should work, but when I do a get nothing happens. Does anyone know how to successfully subscribe to these events?
VS2010, TFS 2010, WinXP SP3
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Net;
using System.Text;
using Microsoft.TeamFoundation.Client;
using Microsoft.TeamFoundation.Framework.Client;
using Microsoft.TeamFoundation.Framework.Common;
using Microsoft.TeamFoundation.VersionControl.Client;
namespace TestEventHanling
{
class Program
{
static void Main(string[] args)
{
Uri serverUri = new Uri(#"http://TfsServer:8080/tfs/collection");
using (TfsTeamProjectCollection collection = new TfsTeamProjectCollection(serverUri, CredentialCache.DefaultCredentials))
{
VersionControlServer versionControl = (VersionControlServer)collection.GetService(typeof(VersionControlServer));
versionControl.UpdatedWorkspace += new WorkspaceEventHandler(OnUpdatedWorkspace);
versionControl.Getting += new GettingEventHandler(OnGetting);
Console.WriteLine("Press \'q\' to quit.");
while (Console.Read() != 'q') ;
}
}
internal static void OnUpdatedWorkspace(object sender, WorkspaceEventArgs e)
{
foreach (WorkingFolder wf in e.Workspace.Folders)
{
Console.WriteLine("Workspace updated {0}", wf.ServerItem);
}
}
internal static void OnGetting(Object sender, GettingEventArgs e)
{
Console.WriteLine("Getting: {0}, status: {1}", e.TargetLocalItem, e.Status);
}
}
}

My understanding are that these are events that are on your local instance of VersionControlServer. That is to say, they will fire when you act on that instance in your code.
For example, if, somewhere else in your code, you updated a workspace, then the UpdatedWorkspace handler would fire.
There's a smaller set of events that you can subscribe to server-side (check-in, builds, etc.), but I'm not sure that you can monitor what's happening on the server through the VersionControlServer class.

Related

Wireguard tunnel source to c#.Net: Service Run troubleshooting

I'm trying to make a simple console app client (starter.exe) on c# .NET Framework 4.6 to make a WireGuard protocol based connection using Wireguard source code.
What is done:
Downloaded wireguard source code from here: git://git.zx2c4.com/wireguard-windows
Successfuly built Tunnel.dll in ..\embeddable-dll-service\amd64\tunnel.dll via build.bat
Created a project in Visual Studio 2015.using the c# code from ..\embeddable-dll-service\csharp
Starting from here some strange thing are happenning:
if launching starter.exe \service <path to *.conf> I receive the
error
Service run error: The service process could not connect to the
service controller.
if launching starter.exe without parameters everything works fine until I remove the if{} block:
Unhandled Exception: System.ComponentModel.Win32Exception: The service
did not respond to the start or control request in a timely fashion
at WireGuardTunnel.Service.Add(String configFile) in
D:\Depository\BitBucket\WireGuard_Tunnel_Repository\WireGuardTunnel_proj\Launcher\Service.cs:line
69 at WireGuardTunnel.Program.Main(String[] args) in
D:\Depository\BitBucket\WireGuard_Tunnel_Repository\WireGuardTunnel_proj\Launcher\Program.cs:line
83
That means even if the code in if{} block is not executed it influencese somehow the application behaviour.
Next, as I want to make my app work with parameters I solved the
issue by removing return afer Service.Run and passing args[1] to Service.Add(args[1]). It works OK, but I have an extra log line (the first one due to Service.Run perpetual error described above) in the log:
Service run error: The service process could not connect to the
service controller. 235660: [TUN] [chicago4] Watching network
interfaces 245661: [TUN] [chicago4] Resolving DNS names
245661: [TUN] [chicago4] Creating Wintun interface 225660: [TUN]
[chicago4] Starting WireGuard/0.3.1 (Windows 6.1.7601; amd64)
So finally the questions:
Why Service.Run(confFile) does not work
Why Service.Run(confFile) influences the Service.Add(confFile)
Why if{} block is executed when I launch starte.exe with no parameters
The original Program.cs without modification:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net.Sockets;
using System.Diagnostics;
using System.Threading;
using System.Threading.Tasks;
using System.IO;
using System.Runtime.InteropServices;
namespace Tunnel
{
class Program
{
[DllImport("kernel32.dll")]
private static extern bool SetConsoleCtrlHandler(SetConsoleCtrlEventHandler handler, bool add);
private delegate bool SetConsoleCtrlEventHandler(UInt32 signal);
public static void Main(string[] args)
{
string baseDirectory = Path.GetDirectoryName(Process.GetCurrentProcess().MainModule.FileName);
string configFile = Path.Combine(baseDirectory, "demobox.conf");
string logFile = Path.Combine(baseDirectory, "log.bin");
if (args.Length == 2 && args[0] == "/service")
{
configFile = args[1];
Service.Run(configFile);
return;
}
try { File.Delete(logFile); } catch { }
Ringlogger log = new Ringlogger(logFile, "GUI");
var logPrintingThread = new Thread(() =>
{
var cursor = Ringlogger.CursorAll;
while (Thread.CurrentThread.IsAlive)
{
var lines = log.FollowFromCursor(ref cursor);
foreach (var line in lines)
Console.WriteLine(line);
Thread.Sleep(300);
}
});
logPrintingThread.Start();
SetConsoleCtrlHandler(delegate
{
Service.Remove(configFile);
Environment.Exit(0);
return true;
}, true);
try
{
Service.Add(configFile);
logPrintingThread.Join();
}
finally
{
Service.Remove(configFile);
}
}
}
}
Bit late to the party but I was having the exact same issue as above and discovered that in order to get everything working correctly you have to have Tunnel.Service.Run("path to config") defined on application initialization either in your main loop or your constructor then you can run Tunnel.Service.Add("path to config", true) which will create the service and start the VPN connection. It's also good practice to destroy the service on close using Tunnel.Service.Remove("path to config", true) as the service will continue to run and you will still be connected to your VPN until it is stopped manually.

Gracefully (and controlled) exit from .NET console application

I need to convert a C# windows service (.NET Framework 4.6.1) into a console application. So this application doesn't have a real interactive interface.
In the windows service application I have the OnStop() method to do the things I need before terminate... and exit.
Of course, I can create a file with a well-known name and in the console application periodically check for this file, but it seems to me an old style solution.
Is there a “best practice” to ask a console application to terminate gracefully having the time to complete the current processing?
So the solution I found has the following code
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApp1
{
class Program
{
private static bool keepRunning = true;
public static void Main(string[] args)
{
Console.WriteLine("Main started");
Console.CancelKeyPress += delegate (object sender, ConsoleCancelEventArgs e) {
e.Cancel = true;
keepRunning = false;
};
while (keepRunning)
{
Console.WriteLine("Doing really evil things...");
System.Threading.Thread.Sleep(3000);
}
Console.WriteLine("Exited gracefully");
}
}
}

XMPP connection hanging on "Resource Binding" process using xmedianet library

As a complete beginner in the field of instant messaging (using XMPP protocol), as well as windows phone 8.1 app development; I am trying to start off by using xmedianet library in order to connect to a server and communicate using XMPP protocol. After implementing the following example and tweaking it to my needs.
Here's the part of the code where I configure the connection parameters:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Navigation;
using Microsoft.Phone.Controls;
using Microsoft.Phone.Shell;
using WP8Xmpp.Resources;
using System.Net.XMPP;
using System.Net.Sockets;
using System.Threading;
namespace WP8Xmpp
{
public partial class MainPage : PhoneApplicationPage
{
private Boolean IsXmppSuccess { get; set; }
/// <summary>
/// Xmpp Client
/// </summary>
public XMPPClient ObjXmppClient { get; set; }
/// <summary>
/// XMPP Connection
/// </summary>
public XMPPConnection ObjXmppCon { get; set; }
// Constructor
public MainPage()
{
InitializeComponent();
}
private void btnLogin_Click(object sender, RoutedEventArgs e)
{
IsXmppValid();
}
private void IsXmppValid()
{
ObjXmppClient = new XMPPClient();
//initializing the xmpp client with credentials
ObjXmppClient.JID = "user#domain.com";
ObjXmppClient.JID.Resource = Guid.NewGuid().ToString();
ObjXmppClient.Password = "acc_password";
ObjXmppClient.Server = "server_uri";*/
ObjXmppClient.AutoReconnect = true;
ObjXmppClient.Port = 81; // I've already tried 5222 but 81 is the correct port in this server's case.
ObjXmppClient.RetrieveRoster = true;
ObjXmppClient.PresenceStatus = new PresenceStatus() { PresenceType = PresenceType.available, IsOnline = true };
ObjXmppClient.AutoAcceptPresenceSubscribe = true;
ObjXmppClient.AttemptReconnectOnBadPing = true;
ObjXmppCon = new XMPPConnection(ObjXmppClient);
ObjXmppCon.Connect();
ObjXmppClient.Connect();
//initializing the xmpp connection
ObjXmppCon.OnAsyncConnectFinished += ObjXmppCon_OnAsyncConnectFinished;
ObjXmppClient.OnStateChanged += new EventHandler(xMPPClient_OnStateChanged);
Thread.Sleep(2000);
} ...
When I launch this application using the WP 8.1 emulator and attempt a connection. Everything works fine until the Resource Binding step. I get the following output on the VS2013 console:
<--stream:features><ver xmlns="urn:xmpp:features:rosterver"/><compression xmlns="http://jabber.org/features/compress"><method>zlib</method></compression><bind xmlns="urn:ietf:params:xml:ns:xmpp-bind"/><session xmlns="urn:ietf:params:xml:ns:xmpp-session"/></stream:features>
Setting state to CanBind
Setting state to Binding
<--<
<--iq id="xxxxxxxx-xxxx-xxxx-xxxx-0f08b82b9f1f" to="user#domain/Resource" xmlns="jabber:client" type="result"><bind xmlns="urn:ietf:params:xml:ns:xmpp-bind"><jid>user#domain/Resource</jid></bind></iq>
Followed by nothingness except for a few "thread exit" messages and the program terminating after a few minutes.
I've been at it for days now.. I've tried all possible scenarios for the connection parameters, even tried fiddling with the library's code to no avail. Could anyone try to replicate this configuration with the same library to see if it's a problem on my side?
Note: connection to the server with the same account using another xmpp client works just fine.
Turned out the problem was that, for some reason, the "Bound" state was not firing even though the binding attempt returned a successful result. I've managed to "fix" this the ugly way by using Thread.sleep() and then changing the state manually to "bound" (note that the same trick is used to get to the "session" state). Here's a sample of my "patchwork" code:
void xMPPClient_OnStateChanged(object sender, EventArgs e)
{
switch (ObjXmppClient.XMPPState)
{
case XMPPState.Binding:
this.Dispatcher.BeginInvoke(() =>
{
Thread.Sleep(2000);
ObjXmppClient.XMPPState = System.Net.XMPP.XMPPState.Bound;
}
);
break;
case XMPPState.Sessioning:
this.Dispatcher.BeginInvoke(() =>
{
Thread.Sleep(2000);
ObjXmppClient.XMPPState = System.Net.XMPP.XMPPState.Session;
}
);
break; ...

pass telephone to default windows softphone while its running

I developed a softphone for windows, I know how to register it as default tell application by reading this question, but I don`t know how get arguments sent from a web application or another win application while my softphone is running.
The standard code to call tell app from web app is something like this:
window.open("tel: 05525825");
If you have registered your application for the scheme tel: and the Command is "yourapp.exe %1", then you can read them from the commandline arguments as explained in How to access command line parameters outside of Main in C#:
string arguments = Environment.GetCommandLineArgs();
string phoneNumber = arguments[1];
Of course you need to do some sanity checking before bluntly accessing and using the array element.
If you setup the protocol URL keys correctly your application will be run with the data in the command line (E.g. args[] in main())
To pass data to an already running instance of your application the easiest way is to use the StartupNextInstance event provided by VisualBasic.ApplicationServices and re-process new incomming command lines:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using Microsoft.VisualBasic.ApplicationServices;
namespace Foo
{
static class Program
{
[STAThread]
static void Main(string[] args)
{
var applicationBase = new ThisWindowsApplicationBase();
applicationBase.StartupNextInstance += (sender, e) => { applicationBase.HandleCommandLine(e.CommandLine); };
applicationBase.Run(args);
}
}
class ThisWindowsApplicationBase : WindowsFormsApplicationBase
{
internal ThisWindowsApplicationBase()
: base()
{
this.IsSingleInstance = true;
this.MainForm = new Form1();
this.HandleCommandLine(Environment.GetCommandLineArgs().Skip(1));
}
internal void HandleCommandLine(IEnumerable<string> commandLine)
{
this.MainForm.Text = "Processing: " + commandLine.FirstOrDefault();
}
}
}
Note this will not fire for the first run.

WPF C# application will freeze my whole computer ever 2-3 times I run it

I put a lot of information in this issue because I have no idea what will be relavent
Issue:
I am having an issue with a program I am working on where when running it, it will freeze my whole computer and return no error (I am completely incapable of doing anything CTRL+ALT+DEL doesn't even work). This program accepts a connection from a android client and atm the android client is not configured correctly so the connection is being rejected.
Question:
How can I stop my program from freezing my entire machine?
Conjecture:
I have a few theories as to what is going on but no idea how to fix them. I have read that this may have something to do with me running a single threaded process inside my async worker but I am not sure that the socket is a single threaded process. Also I am not entirely sure how I am supposed to deal with exceptions in a backgroundworker so I just let it fall back to the RunWorkerCompletedEventArgs then retrieve the error message from there.
What I have tried:
- I tried putting try catches every where then removing try catches nothing seems to be able to capture this error
- I checked my systems event log and nothing is showing up except my restarts after my computer freezes
- I have attempted to isolate the issue but it can literally happen at any point from the program starting till when I attempt to connect
Setup:
I am running the program out of visual studio 2012 professional on a windows 8 pro machine. The computer I am on has a i7-3770K 3.50GHz and 32GB of ram. The application that is attempting to make a connection to mine is a Android application and the credentials are incorrect when it is attempting to connect. Visual Studio is running off my main hard drive and building the project on another drive.
Closing:
With all that said would some one please be willing to help me? If you need any more information I will be happy to provide it, please ask.
Main Method:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.ComponentModel;
namespace Server
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class SourceServer : Window
{
private BackgroundWorker worker = new BackgroundWorker();
public SourceServer()
{
InitializeComponent();
StartListeningForConnections();
}
private void StartListeningForConnections()
{
worker.DoWork += new DoWorkEventHandler(worker_DoWork);
worker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(worker_RunWorkerCompleted);
worker.ProgressChanged += new ProgressChangedEventHandler(worker_ProgressChanged);
worker.WorkerReportsProgress = true;
if (worker.IsBusy != true)
{
worker.RunWorkerAsync();
}
}
private void worker_DoWork(object sender, DoWorkEventArgs e)
{
worker.ReportProgress(0, "Source server version 0.0.0.1ib started");
LoginServer oLoginServer = new LoginServer();
oLoginServer.StartListening(worker);
}
private void worker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
try
{
lvOutput.Items.Add(e.UserState.ToString());
}
catch (Exception exception)
{
lvOutput.Items.Add(exception.StackTrace);
}
}
private void worker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
if (e.Error != null)
{
System.IO.File.WriteAllText(Environment.CurrentDirectory + #"\log.txt", e.Error.StackTrace + " /n " + e.Error.Message);
}
else
{
MessageBox.Show("Error was null");
}
worker.Dispose();
}
}
}
SSL Socket Connection:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Threading;
using System.Net;
using System.Net.Sockets;
using System.Windows;
using System.Windows.Controls;
using System.ComponentModel;
using System.Net.Security;
using System.Security.Cryptography.X509Certificates;
using MySql.Data.MySqlClient;
using System.IO;
namespace Server
{
public class LoginServer
{
// Incoming data from the client.
public static string data = null;
public static X509Certificate serverCertificate = null;
public delegate void UpdateListView(ListView oOutput);
public void StartListening(BackgroundWorker worker)
{
// Data buffer for incoming data.
byte[] bytes = new Byte[1024];
// Establish the local endpoint for the socket.
IPHostEntry ipHostInfo = Dns.GetHostEntry(Dns.GetHostName());
IPAddress ipAddress = ipHostInfo.AddressList[1];
serverCertificate = X509Certificate.CreateFromCertFile(#"server.crt");
TcpListener oServer = new TcpListener(ipAddress, 12345);
// Bind the socket to the local endpoint and
// listen for incoming connections.
// Start listening for connections.
while (true)
{
Thread.Sleep(100);
worker.ReportProgress(0, "Waiting for connection....");
// Program is suspended while waiting for an incoming connection.
//Socket handler = listener.Accept();
oServer.Start();
TcpClient oClient = oServer.AcceptTcpClient();
Stream oStream = oClient.GetStream();
SslStream oSSLStream = new SslStream(oStream);
data = null;
// An incoming connection needs to be processed.
string sUsername = "place holder";
string sPassword = "place holder";
while (true)
{
bytes = new byte[1024];
int bytesRec = oSSLStream.Read(bytes, 0, bytes.Length);
data += Encoding.ASCII.GetString(bytes, 0, bytesRec);
string[] sCredentials = data.Split("|".ToCharArray()[0]);
sUsername = sCredentials[0];
sPassword = sCredentials[1];
if (data.IndexOf("<EOF>") > -1)
{
break;
}
}
// Show the data on the console.
worker.ReportProgress(0, "Connection Recieved : ");
worker.ReportProgress(0, "Username: " + sUsername);
worker.ReportProgress(0, "Password: " + sPassword);
worker.ReportProgress(0, "");
// Echo the data back to the client.
byte[] msg;
if (sUsername.Equals("test") && sPassword.Equals("test"))
{
msg = Encoding.ASCII.GetBytes("approved<EOF>\n");
worker.ReportProgress(0, "approved");
oSSLStream.Write(msg, 0, msg.Length);
}
else
{
msg = Encoding.ASCII.GetBytes("rejected<EOF>\n");
worker.ReportProgress(0, "rejected");
oSSLStream.Write(msg, 0, msg.Length);
}
}
}
public void VerifyUser()
{
}
}
}
While I don't see any reason for this to lock up your entire computer, I do see a couple of reasons for the application to potentially hang...
Your while loop inside of your SSL server will never break unless your client writes '<EOF>' to the stream; which you would have to force it to do. I would likely do something similar to this:
while(( bytesRec = oSSLStream.Read(bytes,0,bytes.Length)) > 0 )
{
// Compare input & break
}
-- The while loop you have now ( without a thread sleep ) will consume all of your systems resources waiting for ... something that may never occur.
In a related issue - I note that your 'DoWork' method launches the listener - but does not start a new thread for this listener. This means that the listener is running inside of your interface thread - which will cause the interface ( and potentially more... ) to hang until the process is completed - which as stated, may never happen.
... Ahem... This last paragraph may be incorrect - you are running an async worker, so I may be incorrect in my second assessment.
Cheers, hope this is helpful.
I've had some hanging problems on Windows 8 that I never saw on Windows 7 (with VS2012). As you experienced it worked fine the first time but only locked up Visual Studio (and not my whole machine) and I had to force quit.
The Visual Studio 2012 Update 4 (which focuses on bug fixes and compatibility) seemed to fix it, although I didn't scientifically test this.
Note: As of 9/1/13 this is only the RC2 version so please check for newer versions, and edit this answer when RTM happens.

Categories