Marck
Marck

Reputation: 81

How to Forward Notifications with FileSystemWatcher and Incoming Webhook

I'm trying to make it so that whenever there are changes in the watch folder I get a notification by teams.

I did the monitoring code with FileSystemWatcher, but when it's time to notify Teams of the changes I don't get anything.

can you help me?

Below is the code I created so far:

 static async Task Main(string[] args)
        {
            var Path = args[0];

            using var watcher = new FileSystemWatcher(Path);
            watcher.NotifyFilter = NotifyFilters.Attributes
                                 | NotifyFilters.CreationTime
                                 | NotifyFilters.DirectoryName
                                 | NotifyFilters.FileName
                                 | NotifyFilters.LastAccess
                                 | NotifyFilters.LastWrite
                                 | NotifyFilters.Security
                                 | NotifyFilters.Size;

            watcher.Changed += OnChanged;
            watcher.Created += OnCreated;
            watcher.Deleted += OnDeleted;
            watcher.Renamed += OnRenamed;
            watcher.Error += OnError;

            using (var httpClient = new HttpClient())
            {
                using (var request = new HttpRequestMessage(new HttpMethod("POST"), "URL_Incoming Webhook"))
                {
                    request.Content = new StringContent("{'text':$Created}");
                    request.Content.Headers.ContentType = MediaTypeHeaderValue.Parse("application/json");

                    HttpResponseMessage response = await httpClient.SendAsync(request);
                }
            }

            watcher.Filter = "";
            watcher.IncludeSubdirectories = false;
            watcher.EnableRaisingEvents = true;

            Console.WriteLine("Press enter to exit.");
            Console.ReadLine();
        }

        private static void OnChanged(object sender, FileSystemEventArgs e)
        {
            if (e.ChangeType != WatcherChangeTypes.Changed)
            {
                return;
            }
            Console.WriteLine($"Changed: {e.FullPath}");
        }

        private static void OnCreated(object sender, FileSystemEventArgs e)
        {
            string value = $"Created: {e.FullPath}";
            Console.WriteLine(value);
        }

        private static void OnDeleted(object sender, FileSystemEventArgs e) =>
            Console.WriteLine($"Deleted: {e.FullPath}");

        private static void OnRenamed(object sender, RenamedEventArgs e)
        {
            Console.WriteLine($"Renamed:");
            Console.WriteLine($"    Old: {e.OldFullPath}");
            Console.WriteLine($"    New: {e.FullPath}");
        }

        private static void OnError(object sender, ErrorEventArgs e) =>
            PrintException(e.GetException());


        private static void PrintException(Exception? ex)
        {
            if (ex != null)
            {
                Console.WriteLine($"Message: {ex.Message}");
                Console.WriteLine("Stacktrace:");
                Console.WriteLine(ex.StackTrace);
                Console.WriteLine();
                PrintException(ex.InnerException);
            }
        }

I don't know if the best way to do this, but I'm open to suggestions, thanks.

Upvotes: 0

Views: 116

Answers (1)

CrossBound
CrossBound

Reputation: 146

NOTE there is some work you can do to make this code better, but for the sake of answering the asked question and not getting on a tangent I'll leave it as you have it (almost).

Possibly I'm missing something, but I don't see where you have anything setup to send a request to teams when your events get fired.

To start with, put your http request into a method

private static async Task sendRequestToTeams(string Text)
{
    try
    {
        using (var httpClient = new HttpClient())
        {
            using (var request = new HttpRequestMessage(new HttpMethod("POST"), "URL_Incoming Webhook"))
            {
                request.Content = new StringContent($"{{\"text\":\"{Text}\"}}");
                request.Content.Headers.ContentType = MediaTypeHeaderValue.Parse("application/json");

                HttpResponseMessage response = await httpClient.SendAsync(request);
            }
        }
    }
    catch (Exception error)
    {
        Console.WriteLine(error.ToString());
    }
}

Then you can call it on each of your events, like so:

private static void OnDeleted(object sender, FileSystemEventArgs e) 
{
    sendRequestToTeams($"Deleted: {e.FullPath}")
        .GetAwaiter().GetResult(); // allows you to call async from non async code
    Console.WriteLine($"Deleted: {e.FullPath}");
}

Upvotes: 1

Related Questions