<commit_before>﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using HtmlAgilityPack;
using System.Text.RegularExpressions;
using System.Globalization;

namespace Facebook_Messenger_Export
{
    class Thread
    {
        public List<Message> Messages { get; } // is this the best data structure?
        public List<Person> Participants { get; }
        public int UID { get; }

        /// <summary>
        /// Default contstructor
        /// </summary>
        /// <param name="participants">The list of participants (parsed elsewhere)</param>
        public Thread(List<Person> participants)
        {
            Messages = new List<Message>();
            Participants = participants;
        }

        public Thread(HtmlDocument thread, int id)
        {
            UID = id;



            HtmlNode body = thread.DocumentNode.FirstChild.ChildNodes.Where(w => w.Name == "body").ToList()[0];
            List<HtmlNode> nodes = body.ChildNodes.Where(w => w.Name != "#text").ToList(); // eliminates whitespace text nodes

            Participants = CreateListOfParticipants(body.FirstChild.InnerText); 

            
            for (int i= 0; i< (nodes.Count)/2; i++){
                AddMessage(nodes[i].ChildNodes[1], nodes[i + 1]);
            }

        }

        /// <summary>
        /// Helper method to construct Participants object
        /// </summary>
        /// <param name="text">Plain text from Facebook</param>
        /// <returns>List of Person objects for each ID</returns>
        private List<Person> CreateListOfParticipants(string text)
        {
            string[] ids = Regex.Split(text, ", ");
            //DateTime time = new DateTime();
           // time.   
            List<Person> rtn = new List<Person>();
            foreach(string s in ids)
            {
                rtn.Add(new Person(s.Trim()));
            }
            return rtn;
        }


        /// <summary>
        /// Creates a Message object from the two HTML tags necessary to do so
        /// See the README for an explanation so you know what I'm talking about
        /// </summary>
        /// <param name="messageHeader">The tag with class message_header</param>
        /// <param name="pStuff">Stuff in the p (the actual message)</param>
        /// <returns>A nice message object with the information</returns>
        private void AddMessage(HtmlNode messageHeader, HtmlNode paragraphTag)
        {
            HtmlNodeCollection attributes = messageHeader.ChildNodes;

            // first tag
            string facebookEmail = attributes[0].InnerText;

            // process time (second tag)
            string rawTime = attributes[1].InnerText;
            Moment time = new Moment(rawTime.Remove(rawTime.Length - 4, 4), rawTime.Remove(0, rawTime.Length - 3));

            Message message = new Message(paragraphTag.InnerText,time,facebookEmail.Remove(facebookEmail.Length-13,13),UID);
            Messages.Add(message);                           
        }
        

       
    }
}
<commit_msg>Completed single thread parser<commit_after>﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using HtmlAgilityPack;
using System.Text.RegularExpressions;
using System.Globalization;

namespace Facebook_Messenger_Export
{
    class Thread
    {
        public List<Message> Messages { get; } // is this the best data structure?
        public List<Person> Participants { get; }
        public int UID { get; }

        /// <summary>
        /// Default contstructor
        /// </summary>
        /// <param name="participants">The list of participants (parsed elsewhere)</param>
        public Thread(List<Person> participants)
        {
            Messages = new List<Message>();
            Participants = participants;
        }

        public Thread(HtmlDocument thread, int id)
        {
            UID = id;



            HtmlNode body = thread.DocumentNode.FirstChild.ChildNodes.Where(w => w.Name == "body").ToList()[0];
            List<HtmlNode> nodes = body.ChildNodes.Where(w => w.Name != "#text").ToList(); // eliminates whitespace text nodes

            Participants = CreateListOfParticipants(body.FirstChild.InnerText);

            Messages = new List<Message>();
            for (int i= 0; i< nodes.Count; i+=2){
                AddMessage(nodes[i].ChildNodes[1], nodes[i + 1]);
            }

        }

        /// <summary>
        /// Helper method to construct Participants object
        /// </summary>
        /// <param name="text">Plain text from Facebook</param>
        /// <returns>List of Person objects for each ID</returns>
        private List<Person> CreateListOfParticipants(string text)
        {
            string[] ids = Regex.Split(text, ", ");
            //DateTime time = new DateTime();
           // time.   
            List<Person> rtn = new List<Person>();
            foreach(string s in ids)
            {
                rtn.Add(new Person(s.Trim()));
            }
            return rtn;
        }


        /// <summary>
        /// Creates a Message object from the two HTML tags necessary to do so
        /// See the README for an explanation so you know what I'm talking about
        /// </summary>
        /// <param name="messageHeader">The tag with class message_header</param>
        /// <param name="pStuff">Stuff in the p (the actual message)</param>
        /// <returns>A nice message object with the information</returns>
        private void AddMessage(HtmlNode messageHeader, HtmlNode paragraphTag)
        {
            HtmlNodeCollection attributes = messageHeader.ChildNodes;

            // first tag
            string facebookEmail = attributes[0].InnerText;

            // process time (second tag)
            string rawTime = attributes[1].InnerText;
            Moment time = new Moment(rawTime.Remove(rawTime.Length - 4, 4), rawTime.Remove(0, rawTime.Length - 3));

            Message message = new Message(paragraphTag.InnerText,time,facebookEmail.Remove(facebookEmail.Length-13,13),UID);
            Messages.Add(message);                           
        }
        

       
    }
}

{'fraction_non_alphanumeric': 0.11319244316362471, 'fraction_numerical': 0.004803073967339097, 'mean_word_length': 1.9676959619952494, 'pattern_counts': {'":': 0, '<': 58, '<?xml version=': 0, '>': 60, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 4, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3499784', 'n_tokens_mistral': 1652, 'n_tokens_neox': 1565, 'n_words': 442}