From 31fe94f9e4b0c0a538a7c7bed3b333046c9f396b Mon Sep 17 00:00:00 2001 From: takline Date: Mon, 8 Jul 2024 19:46:31 +0000 Subject: [PATCH] fixing tests and docs --- README.md | 6 + config/config.py | 2 +- data/example_resume.yaml | 82 ---------- services/langchain_helpers.py | 7 +- services/resume_improver.py | 296 +++++++++++++++++++++++++--------- tests/README.md | 55 +------ tests/test_data/resume.pdf | Bin 0 -> 77653 bytes tests/test_pdf_generation.py | 2 +- tests/test_prompts.py | 28 +++- tests/test_services.py | 115 ++++++++++--- tests/test_utils.py | 16 +- 11 files changed, 375 insertions(+), 234 deletions(-) delete mode 100755 data/example_resume.yaml create mode 100644 tests/test_data/resume.pdf diff --git a/README.md b/README.md index 3b926c7..7d20314 100644 --- a/README.md +++ b/README.md @@ -77,6 +77,9 @@ ResumeGPT then creates a new resume YAML file in a new folder named after the jo Resume Example

+ + + ## Discussions Feel free to give feedback, ask questions, report a bug, or suggest improvements: @@ -85,3 +88,6 @@ Feel free to give feedback, ask questions, report a bug, or suggest improvements ## Contributors ⭐️ Please star, fork, explore, and contribute to ResumeGPT. There's a lot of work room for improvement so any contributions are appreciated. + + + diff --git a/config/config.py b/config/config.py index f7fc5dc..6b04cf5 100644 --- a/config/config.py +++ b/config/config.py @@ -7,7 +7,7 @@ logger = logging.getLogger(__name__) # Your resume filename here: -YOUR_RESUME_NAME = "example_resume.yaml" +YOUR_RESUME_NAME = "sample_resume.yaml" # Define project paths PROJECT_PATH = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) diff --git a/data/example_resume.yaml b/data/example_resume.yaml deleted file mode 100755 index 7b320fb..0000000 --- a/data/example_resume.yaml +++ /dev/null @@ -1,82 +0,0 @@ -editing: true -basic: - name: John Doe - address: - - Anytown, USA - contact: - email: johndoe@example.com - phone: 123-456-7890 - websites: - - text: LinkedIn - url: https://linkedin.com/johndoe - icon: linkedin - - text: GitHub - url: https://github.com/johndoe - icon: github - -summary: A Product Manager with over 10 years of experience in analytics, artificial intelligence, and product leadership. Demonstrated success in launching a new digital banking platform, increasing customer acquisition by 30%, and developing a strategic partnership with a leading fintech company, resulting in a 25% increase in market share. Skilled in Python, SQL, Azure, AWS, GCP, and AI/ML. Committed to driving transformative outcomes and scaling impact in a larger organization. - -education: - - school: State University - degrees: - - names: - - B.S. Economics and Political Science - - school: Another School - degrees: - - names: - - Masters - -experiences: - - company: Major Financial Institution - titles: - - name: Vice President - startdate: 2023 - enddate: 2024 - highlights: - - Led the development and launch of a new digital banking platform, increasing customer acquisition by 30% within the first six months. - - Implemented a customer feedback loop, resulting in a 20% improvement in customer satisfaction scores and a 15% reduction in churn rate. - - Spearheaded a cross-functional team to integrate blockchain technology into payment systems, reducing transaction times by 40% and enhancing security. - - - company: Consulting Firm - titles: - - name: Management Consultant - startdate: 2020 - enddate: 2022 - highlights: - - Designed and executed a digital transformation strategy for a major retail bank, leading to a 50% increase in online transactions and a 20% reduction in operational costs. - - Facilitated workshops with senior executives to align on strategic priorities, resulting in a unified roadmap and improved project execution. - - - company: Financial Services Company - titles: - - name: Product Manager - startdate: 2019 - enddate: 2020 - highlights: - - Launched a mobile app for personal finance management, achieving 100,000 downloads within the first three months and a 4.8-star rating on app stores. - - Collaborated with data scientists to develop predictive analytics models, enhancing customer targeting and increasing conversion rates by 25%. - - - company: Financial Services Company - titles: - - name: Data Scientist - startdate: 2018 - enddate: 2019 - highlights: - - Developed and deployed a recommendation engine for personalized financial advice, increasing user engagement by 35%. - - Conducted advanced data analysis to identify fraud patterns, reducing fraudulent transactions by 15% and saving the company $2 million annually. - -skills: - - category: Technical - skills: - - Python - - SQL - - Data Analysis - - API Integration - - Cloud Services - - category: Non-technical - skills: - - Communication - - Leadership - - Team Collaboration - - Strategic Planning - - Stakeholder Management - - Adaptability diff --git a/services/langchain_helpers.py b/services/langchain_helpers.py index 235725a..a1294df 100644 --- a/services/langchain_helpers.py +++ b/services/langchain_helpers.py @@ -2,14 +2,15 @@ from typing import List from dateutil import parser as dateparser from dateutil.relativedelta import relativedelta -from langchain.cache import InMemoryCache from langchain_openai import ChatOpenAI import langchain +from langchain_community.cache import InMemoryCache from .. import config # Set up LLM cache langchain.llm_cache = InMemoryCache() + def create_llm(**kwargs): """Create an LLM instance with specified parameters.""" chat_model = kwargs.pop("chat_model", ChatOpenAI) @@ -17,18 +18,21 @@ def create_llm(**kwargs): kwargs.setdefault("cache", False) return chat_model(**kwargs) + def format_list_as_string(lst: list, list_sep: str = "\n- ") -> str: """Format a list as a string with a specified separator.""" if isinstance(lst, list): return list_sep + list_sep.join(lst) return str(lst) + def format_prompt_inputs_as_strings(prompt_inputs: list[str], **kwargs): """Convert values to string for all keys in kwargs matching list in prompt inputs.""" return { k: format_list_as_string(v) for k, v in kwargs.items() if k in prompt_inputs } + def parse_date(date_str: str) -> datetime: """Given an arbitrary string, parse it to a date.""" default_date = datetime(datetime.today().year, 1, 1) @@ -39,6 +43,7 @@ def parse_date(date_str: str) -> datetime: config.logger.error(f"Date input `{date_str}` could not be parsed.") raise e + def datediff_years(start_date: str, end_date: str) -> float: """Get difference between arbitrarily formatted dates in fractional years to the floor month.""" datediff = relativedelta(parse_date(end_date), parse_date(start_date)) diff --git a/services/resume_improver.py b/services/resume_improver.py index 53d47ee..c86993d 100644 --- a/services/resume_improver.py +++ b/services/resume_improver.py @@ -25,7 +25,13 @@ class ResumeImprover(ExtractorLLM): def __init__(self, url, resume_location=None, llm_kwargs: dict = None): - """Initialize ResumeImprover with the job post URL and optional resume location.""" + """Initialize ResumeImprover with the job post URL and optional resume location. + + Args: + url (str): The URL of the job post. + resume_location (str, optional): The file path to the resume. Defaults to None. + llm_kwargs (dict, optional): Additional keyword arguments for the language model. Defaults to None. + """ super().__init__() self.job_post_html_data = None self.job_post_raw = None @@ -57,7 +63,11 @@ def __init__(self, url, resume_location=None, llm_kwargs: dict = None): self.summary = utils.get_dict_field(field="summary", data_dict=self.resume) def _extract_html_data(self): - """Extract text content from HTML, removing all HTML tags.""" + """Extract text content from HTML, removing all HTML tags. + + Raises: + Exception: If HTML data extraction fails. + """ try: soup = BeautifulSoup(self.job_post_html_data, "html.parser") self.job_post_raw = soup.get_text(separator=" ", strip=True) @@ -65,8 +75,17 @@ def _extract_html_data(self): config.logger.error(f"Failed to extract HTML data: {e}") raise - def _download_url(self): - """Download the content of the URL and return it as a string.""" + def _download_url(self, url=None): + """Download the content of the URL and return it as a string. + + Args: + url (str, optional): The URL to download. Defaults to None. + + Raises: + requests.RequestException: If the URL download fails. + """ + if url: + self.url = url try: response = requests.get(self.url, headers=config.REQUESTS_HEADERS) response.raise_for_status() @@ -75,8 +94,14 @@ def _download_url(self): config.logger.error(f"Failed to download URL {self.url}: {e}") raise - def download_and_parse_job_post(self): - """Download and parse the job post from the provided URL.""" + def download_and_parse_job_post(self, url=None): + """Download and parse the job post from the provided URL. + + Args: + url (str, optional): The URL of the job post. Defaults to None. + """ + if url: + self.url = url self._download_url() self._extract_html_data() self.job_post = JobPost(self.job_post_raw) @@ -103,8 +128,13 @@ def download_and_parse_job_post(self): self.parsed_job, filename=os.path.join(self.job_data_location, "job.yaml") ) - def create_draft_tailored_resume(self): - """Run a full review of the resume against the job post.""" + def create_draft_tailored_resume(self, auto_open=True, manual_review=True): + """Run a full review of the resume against the job post. + + Args: + auto_open (bool, optional): Whether to automatically open the generated resume. Defaults to True. + manual_review (bool, optional): Whether to wait for manual review. Defaults to True. + """ config.logger.info("Extracting matched skills...") self.skills = self.extract_matched_skills(verbose=False) @@ -124,38 +154,20 @@ def create_draft_tailored_resume(self): ) utils.write_yaml(resume_dict, filename=self.yaml_loc) self.resume_yaml = utils.read_yaml(filename=self.yaml_loc) - - subprocess.run(["cursor", "-r", self.yaml_loc]) - - while utils.read_yaml(filename=self.yaml_loc)["editing"]: - time.sleep(5) + if auto_open: + subprocess.run(config.OPEN_FILE_COMMAND.split(" ") + [self.yaml_loc]) + if manual_review: + while utils.read_yaml(filename=self.yaml_loc)["editing"]: + time.sleep(5) config.logger.info("Saving PDF") - self.create_pdf() - - def _launch_widget(self): - """Launch a widget for editing the resume.""" - self.text_area = widgets.Textarea( - value=self.resume_yaml, - disabled=False, - layout=widgets.Layout(width="80%", height="800px"), - ) - display(self.text_area) - self.button = widgets.Button(description="Submit") - self.button.on_click(self._on_button_clicked) - display(self.button) - - def _on_button_clicked(self, b): - """Handle the button click event to submit the edited resume.""" - self.resume_yaml = self.text_area.value - clear_output(wait=False) - time.sleep(1) - display(Markdown(self.resume_yaml)) - time.sleep(2) - clear_output(wait=True) - self.editing = False + self.create_pdf(auto_open=auto_open) def _section_highlighter_chain(self, **chain_kwargs) -> RunnableSequence: - """Create a chain for highlighting relevant resume sections.""" + """Create a chain for highlighting relevant resume sections. + + Returns: + RunnableSequence: The chain for highlighting resume sections. + """ prompt_msgs = Prompts.lookup["SECTION_HIGHLIGHTER"] prompt = ChatPromptTemplate(messages=prompt_msgs) @@ -163,7 +175,11 @@ def _section_highlighter_chain(self, **chain_kwargs) -> RunnableSequence: return prompt | llm | StrOutputParser() def _skills_matcher_chain(self, **chain_kwargs) -> RunnableSequence: - """Create a chain for matching skills from the resume to the job posting.""" + """Create a chain for matching skills from the resume to the job posting. + + Returns: + RunnableSequence: The chain for matching skills. + """ prompt_msgs = Prompts.lookup["SKILLS_MATCHER"] prompt = ChatPromptTemplate(messages=prompt_msgs) @@ -171,7 +187,11 @@ def _skills_matcher_chain(self, **chain_kwargs) -> RunnableSequence: return prompt | llm | StrOutputParser() def _summary_writer_chain(self, **chain_kwargs) -> RunnableSequence: - """Create a chain for writing a compelling resume summary.""" + """Create a chain for writing a compelling resume summary. + + Returns: + RunnableSequence: The chain for writing the resume summary. + """ prompt_msgs = Prompts.lookup["SUMMARY_WRITER"] prompt = ChatPromptTemplate(messages=prompt_msgs) @@ -179,7 +199,11 @@ def _summary_writer_chain(self, **chain_kwargs) -> RunnableSequence: return prompt | llm | StrOutputParser() def _improver_chain(self, **chain_kwargs) -> RunnableSequence: - """Create a chain for critiquing and improving the resume.""" + """Create a chain for critiquing and improving the resume. + + Returns: + RunnableSequence: The chain for critiquing and improving the resume. + """ prompt_msgs = Prompts.lookup["IMPROVER"] prompt = ChatPromptTemplate(messages=prompt_msgs) @@ -187,6 +211,14 @@ def _improver_chain(self, **chain_kwargs) -> RunnableSequence: return prompt | llm | StrOutputParser() def _get_degrees(self, resume: dict): + """Extract degrees from the resume. + + Args: + resume (dict): The resume data. + + Returns: + list: A list of degree names. + """ result = [] for degrees in utils.generator_key_in_nested_dict("degrees", resume): for degree in degrees: @@ -197,6 +229,14 @@ def _get_degrees(self, resume: dict): return result def _format_skills_for_prompt(self, skills: list) -> list: + """Format skills for inclusion in a prompt. + + Args: + skills (list): The list of skills. + + Returns: + list: A formatted list of skills. + """ result = [] for cat in skills: curr = "" @@ -209,6 +249,14 @@ def _format_skills_for_prompt(self, skills: list) -> list: return result def _get_cumulative_time_from_titles(self, titles) -> int: + """Calculate the cumulative time from job titles. + + Args: + titles (list): A list of job titles with start and end dates. + + Returns: + int: The cumulative time in years. + """ result = 0.0 for t in titles: if "startdate" in t and "enddate" in t: @@ -220,6 +268,11 @@ def _get_cumulative_time_from_titles(self, titles) -> int: return round(result) def _format_experiences_for_prompt(self) -> list: + """Format experiences for inclusion in a prompt. + + Returns: + list: A formatted list of experiences. + """ result = [] for exp in self.experiences: curr = "" @@ -233,14 +286,24 @@ def _format_experiences_for_prompt(self) -> list: return result def _combine_skills_in_category(self, l1: list[str], l2: list[str]): - """Combines l2 into l1 without lowercase duplicates""" + """Combine two lists of skills without duplicating lowercase entries. + + Args: + l1 (list[str]): The first list of skills. + l2 (list[str]): The second list of skills. + """ l1_lower = {i.lower() for i in l1} for i in l2: if i.lower() not in l1_lower: l1.append(i) def _combine_skill_lists(self, l1: list[dict], l2: list[dict]): - """Combine l2 skills list into l1 without duplicating lowercase category or skills""" + """Combine two lists of skill categories without duplicating lowercase entries. + + Args: + l1 (list[dict]): The first list of skill categories. + l2 (list[dict]): The second list of skill categories. + """ l1_categories_lowercase = {s["category"].lower(): i for i, s in enumerate(l1)} for s in l2: if s["category"].lower() in l1_categories_lowercase: @@ -252,9 +315,24 @@ def _combine_skill_lists(self, l1: list[dict], l2: list[dict]): l1.append(s) def _print_debug_message(self, chain_kwargs: dict, chain_output_unformatted: str): + """Print a debug message. + + Args: + chain_kwargs (dict): The keyword arguments for the chain. + chain_output_unformatted (str): The unformatted output from the chain. + """ message = "Final answer is missing from the chain output." def rewrite_section(self, section: list | str, **chain_kwargs) -> dict: + """Rewrite a section of the resume. + + Args: + section (list | str): The section to rewrite. + **chain_kwargs: Additional keyword arguments for the chain. + + Returns: + dict: The rewritten section. + """ chain = self._section_highlighter_chain(**chain_kwargs) chain_inputs = format_prompt_inputs_as_strings( @@ -282,6 +360,14 @@ def rewrite_section(self, section: list | str, **chain_kwargs) -> dict: return [s["highlight"] for s in section_revised] def rewrite_unedited_experiences(self, **chain_kwargs) -> dict: + """Rewrite unedited experiences in the resume. + + Args: + **chain_kwargs: Additional keyword arguments for the chain. + + Returns: + dict: The rewritten experiences. + """ result = [] for exp in self.experiences: exp = dict(exp) @@ -291,6 +377,14 @@ def rewrite_unedited_experiences(self, **chain_kwargs) -> dict: return result def extract_matched_skills(self, **chain_kwargs) -> dict: + """Extract matched skills from the resume and job post. + + Args: + **chain_kwargs: Additional keyword arguments for the chain. + + Returns: + dict: The extracted skills. + """ chain = self._skills_matcher_chain(**chain_kwargs) chain_inputs = format_prompt_inputs_as_strings( @@ -333,6 +427,14 @@ def extract_matched_skills(self, **chain_kwargs) -> dict: return result def write_summary(self, **chain_kwargs) -> dict: + """Write a summary for the resume. + + Args: + **chain_kwargs: Additional keyword arguments for the chain. + + Returns: + dict: The written summary. + """ chain = self._summary_writer_chain(**chain_kwargs) chain_inputs = format_prompt_inputs_as_strings( prompt_inputs=chain.input_schema().dict(), @@ -353,6 +455,14 @@ def write_summary(self, **chain_kwargs) -> dict: return summary["final_answer"] def suggest_improvements(self, **chain_kwargs) -> dict: + """Suggest improvements for the resume. + + Args: + **chain_kwargs: Additional keyword arguments for the chain. + + Returns: + dict: The suggested improvements. + """ chain = self._improver_chain(**chain_kwargs) chain_inputs = format_prompt_inputs_as_strings( prompt_inputs=chain.input_schema().dict(), @@ -374,6 +484,11 @@ def suggest_improvements(self, **chain_kwargs) -> dict: return improvements["final_answer"] def finalize(self) -> dict: + """Finalize the resume data. + + Returns: + dict: The finalized resume data. + """ return dict( basic=self.basic_info, summary=self.summary, @@ -382,47 +497,80 @@ def finalize(self) -> dict: skills=self.skills, ) - def create_pdf(self): + def create_pdf(self, auto_open=True): + """Create a PDF of the resume. + + Args: + auto_open (bool, optional): Whether to automatically open the generated PDF. Defaults to True. + + Returns: + str: The file path to the generated PDF. + """ parsed_yaml = utils.read_yaml(filename=self.yaml_loc) - result = { - "education": [ - {"degree": degree["names"][0], "university": edu["school"]} - for edu in sorted( - parsed_yaml["education"], - key=lambda x: "Wisconsin" not in x["school"], - ) - for degree in edu["degrees"] - ], - "objective": parsed_yaml["summary"], - "experience": [ + + def extract_education(education): + """Extract education details from the resume. + + Args: + education (list): The education data. + + Returns: + list: A list of dictionaries containing degree and university information. + """ + return [ + {"degree": degree, "university": edu["school"]} + for edu in education + for degree in edu["degrees"][0]["names"] + ] + + def extract_experience(experiences): + """Extract experience details from the resume. + + Args: + experiences (list): The experience data. + + Returns: + list: A list of dictionaries containing title, company, location, duration, and description. + """ + return [ { "title": title["name"], - "company": ( - "Capital One" - if "Capital One" in exp["company"] - else exp["company"] - ), - "location": "New York, NY", - "duration": ( - f"{'2012' if 'Capital One' in exp['company'] else title['startdate']}-{title['enddate']}" - if "enddate" in title - else "2024" - ), + "company": exp["company"], + "location": exp["location"], + "duration": f"{title['startdate']}-{title['enddate']}", "description": exp["highlights"], } - for exp in parsed_yaml["experiences"] + for exp in experiences for title in exp["titles"] - ], - "skills": [ - f"Technical: {', '.join(parsed_yaml['skills'][0]['skills'])}", - f"Soft Skills: {', '.join(parsed_yaml['skills'][1]['skills'])}", - ], + ] + + def extract_skills(skills): + """Extract skills details from the resume. + + Args: + skills (list): The skills data. + + Returns: + list: A list of formatted skills strings. + """ + return [ + f"{skill['category']}: {', '.join(skill['skills'])}" for skill in skills + ] + + result = { + "education": extract_education(parsed_yaml.get("education", [])), + "objective": parsed_yaml.get("summary", ""), + "experience": extract_experience(parsed_yaml.get("experiences", [])), + "skills": extract_skills(parsed_yaml.get("skills", [])), } + pdf_location = os.path.join( - self.job_data_location, config.CONFIG_INI["author"] + ".pdf" + self.job_data_location, f"{config.CONFIG_INI['author']}.pdf" ) pdf_generator = ResumePDFGenerator() pdf_generator.generate_resume(file_path=pdf_location, data=result) - open_file_commands = config.OPEN_FILE_COMMAND.split(" ") + [pdf_location] - subprocess.run(open_file_commands) + + if auto_open: + subprocess.run(config.OPEN_FILE_COMMAND.split(" ") + [pdf_location]) + return pdf_location diff --git a/tests/README.md b/tests/README.md index 689a083..c22772e 100644 --- a/tests/README.md +++ b/tests/README.md @@ -1,4 +1,4 @@ -# ResumeGPT - Tests +# ResumeGPT - Tests ResumeGPT tests are structured as follows: @@ -10,58 +10,17 @@ ResumeGPT tests are structured as follows: - `tests/test_models.py`: Contains tests for the `models` module. - `tests/test_utils.py`: Contains tests for the `utils` module. -## Tests Included in Each File - -### tests/test_config.py -- Tests for logger initialization. -- Tests for project paths. -- Tests for requests headers. -- Tests for model configuration. -- Tests for OpenAI API key. -- Tests for loading configuration from `config.ini`. - -### tests/test_services.py -- Tests for `ResumeImprover` class methods: - - `download_and_parse_job_post` - - `create_draft_tailored_resume` -- Tests for `langchain_helpers` functions: - - `create_llm` - - `format_list_as_string` - - `format_prompt_inputs_as_strings` - - `parse_date` - - `datediff_years` - -### tests/test_pdf_generation.py -- Tests for `ResumePDFGenerator` class methods: - - `generate_resume` - -### tests/test_prompts.py -- Tests for `Prompts` class methods: - - `initialize` - - `load_prompts` - - `load_descriptions` - -### tests/test_models.py -- Tests for `JobDescription` model fields. -- Tests for `JobSkills` model fields. -- Tests for `ResumeSectionHighlight` model fields. -- Tests for `ResumeSkills` model fields. - -### tests/test_utils.py -- Tests for `yaml_handler` functions: - - `read_yaml` - - `write_yaml` - - `dict_to_yaml_string` -- Tests for `file_handler` functions: - - `read_jobfile` - - `generator_key_in_nested_dict` - - `get_dict_field` ## Running the Tests To run the tests, use the following command: -``` +```python pytest ``` +Or: + +```python +pytest tests/test_services.py +``` \ No newline at end of file diff --git a/tests/test_data/resume.pdf b/tests/test_data/resume.pdf new file mode 100644 index 0000000000000000000000000000000000000000..7853a42bf4b35093441e9ad51d9c6c3df9a17457 GIT binary patch literal 77653 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 z ze7Q`AM;@O=g!r^#b4UuUp1`0G2Nknk|gBkuJR=?Dgswyaq z5`Y3#k*;^JUCEX_&_|e_Gfc0rK{#5(L1+x^vqMyp3T;aWuKLj1N2gsP<>M6CBD!;% z7zEdMIGoFML}YYbu!3z-@C+DHFfhHxJ{c{DKtU(iF-WE13O`JB&ZX(2R7o2yBApza zQ)EUP0;U{p&Q(_Tg@Y`VrNZqie{;DOwX}zin{j$Nz9wh_lbb?v<_#+Ulh0RL9&U&i z!GnIwV$F)0Fdp{M*-6k+V6;pbTaGB9r*PXEg}JpLPOD9aMfu9!9j+IyUTAmj+)ALA zuJL-)nQ8XBzTP{-4Q{#p!RiuzqzG;$ZzAwZm3*FzON80#;Jp0?{Bqd~En2+$<7K6r zzP&z)eph$kTjUZjJx_CRKC@J$3*5lD!4|ruF!VYimB$5{`-@T+*K}6uAQiPL=5vJ&uQWd6dkYYBtOgB9%PRIGMzU@3 z=E+%}S9jVz-?MCAAcL~zaN3ykGT1If70PzX((M~7EC+YGDKptN8x1;_&lGyKd;FeW ztK|(x%BG(F~P8b&OADu^}5*Ze@AZk#~<_x9CBhA7ws~NHYa1V1$@RSRp0{b_NG=pc*nTN^Sdoj$XHOekXxV+y5A{)& z1ISDM4o`+tLkA)M6Ca4pzdj3v5I^8jh;lc4rmm0c#qO9pn;K#eZ-3Fg~Q8$gr3(9FwA1vU2MWKKmN}w9*HVbhJ(*)s;m5De7JmxLVCK1zBnif^6 zqBOj4+K-ATdsyw(P)1!f|oRQk1yCJhd}% zo3)#=>gTOe)OIu3GvvRQZQxp$u@-wUjcl@WY&IrhE+eO2He5bDBtB)7ijnh&% z@=FL(Di^J4UUyU^vc)Q|)OHtLsjj=+$<`{nK2wJ5IP$wS%`jD=<(G>PA2_j)2hekp zinW51_$}wUO@TFmA}r8R@MJ9G76}%Oo-|2W8an!et$Pp2m#gV#O=~hEQ4W%**k1QJ z1JZi+kzow}GWF_`WIfQDBn;(FzqQK$kg0Z)nEr`QaI|h-sOI9G$`XP1*_b&*l9yR( z)xB4m!$toS*!f2C1@uD9!;HUD2;#O(gy-N+I19xLqhBcl4jxp|qpOPk32Dk5anD_~ zcGSWJian!WeZLARWU7uq9Fv2SH}6cH#fZ{)h;IOk=nyTW6Z3ag6@?9$wIWYQ`5VeI zU1&0e(<}Et=;$?C1`#;JnprD4MLlIQ`cB0XjrQBcg*eMb8tCn4XIJ3W=iCD<6y!ZN z7e7=>=7XB5&e#gY-|#*f?R}I+;;}>aWP5z=YvWz7+ z92^8R(E##jJ!4?B?D>wh#%Zi~(VK^)NSz5g^SvoH&M2luI`f@5PK~Bhs|rmd*fuf8 zC&oVwj+igH1Vf1LQkUxmtUAx<Njd}FqFe#y{~QNiaa5kA5u zj7vZ7OwD~EUV3PcG#_@WAoZ7^a$}&z+{vce#F9M@H&#N&u$X8o+!e*q!gJJbzJ?I? z6MWh;MzaCbssh!wAnI`KL(tXuW0n!VcK*S{vSCVkJXnDB$JaQ&^G%6PN!BAl_s3R) zeH`k~4Aw52T%VXo8@EbxKmU&M)sjpV4nJV;>7xw+@Xk`eO}5kDb310&>!f!Z+>je^ z(ByKw_H^)v#xU1jA~N56mNEz*g(*{Gszeiiu$gg;J2&{0hXL~IR3%e<5yb6^C?jkg z{g3|_CaLu^q4UlBG=M~@4FXhy;owbHzgajGE>OB-9>i}vfna(DWY;z`vIGh?aO*MM z5=^2fuew|k=10;`a2SVt#G9OaEM%yMo`e=OxR8`IQaes4sXA6$NG6k9#gm;z9oCcDk*+zB^(IoK_tvlP2gJ(oM2(tyG@OpQsWk+l3l%v`_3@c-zU7c9q z9o7*F>|qkvT@m=b)mR_OgQgOa#hK1w;syWsE*ypaxS?9;??;Lf$}q(z1;D;{afmUU z1l|1G1hVHZx}Eyy>1;t#bmL_g~P&f%l9-7oU_g6D^ zkTMb?2D#)q!#UoQwA>Gk4moIxfAPxJP>_{vE=I8Q3SCvCigM5$Ke%mdPFp4~M5m|; zThAg_@&a~=U6YtiH;Qzp^4Jpc+*ap(@mG2``??kcg03S5y|Z@MiLS-U*z^pWKSQL< zn1|1cEhfAt#;T^CP{&ZxQ`W9|9ocz@>Duj`UH{Wq#N1Eo5O!FT4ph(auh?BoecJfl z<7TqVtHH1Ahr+r+H}K0GuhXT)g(Y9hizUT;_059PJ&^Q=>EY5qXhbsjVra&yOa5q$ zA~DJMb%I6u;07ukVaxW|1=_3+zY;d^nUgkrgl!IMV&6g1gEiHG8uY*5iP8$e;X(^J zD5uI!mI@KQo%hCcdQAVA#p32JpdH!X1cRAE_yr=#Ba@2JRR)kc=U0D_-^IF?j5`7*Rg9a=D5l#8#l1n zrY}#)zde+8F5$gP!xN`3*{q(50^7`=k_W|fB63t)YmGc%Y8ikR`1ZkeSs-@qU(2xU z6UiG{ghvek^2zS5^}&! z@XY|F-h=EpbKc<{s)OW16$4LaZN4!rbWDQDn+tw|)kB%k(;}EAwivO&Q#f+Qi@@Wq z9W+8mq`uMmA$L6_bWp~dS7j|(d%~0i)qrjOsfjk8?MPVz zjQ(SuwI$JJPJztny`X?Ac%qCh%1)ek)T%|x$?B^69%`~RpxUvh5gIFlQ0NCUKk6ln|fm~=#2j1m`GByckR|TI0&%7=3 zHGO;{#)!YiRg##=Izf3qI3o6xi5cWFwzfT%wN5a%{nR&$^VllsxYu7g`F4As9EEn0Ad1ORMt}2c!q%L!$ zku05Is$S~@OYWu_5J4Z;a9zdX#4774Cim&M8{ON>Pwn&^?P9NmV%K*-)4i@M(8gIw zpWj^Stuk4!ox;DBWXm7nZNHgu*Y9SbU&Mk*0_-qCs&=7Dr_*rdG1j8vpvUq2?uXY@ z*3Iv&@Uf$#4&FmY;s!U3W9v^EJMLFF%qtau_7uw4OduK#qUM?F@?IBG+l7IOZ5%m) z=$l97V>8d%%U?xozE-PIgm_oYa@2`wak$TWwi&}5y;OMe+g5ozw(uAe8S;%l&PsvU7?y@1=R9)Z9* z4#T$R-QO@*;vYcp3e|O@k}EyOI1toSE}d~LEb?S03(uA0CLTcxUVYoRQ`;Vl?xA~r zbTtmPEaTinp()mgFuqDG9eHaWm1IhPZx=) z5}9AXFVf9sg)wptIWwlUX33sirSew=t^7SaJ3CxfPL3%fZnQaTOIs;oH#+=+M3(O_ z`xT0$3|RuLEs>$)ylEttAy$ zvt#)18E$}`GZ~fn&MGoG-U}Khi z(sTKUu)|lDc8T$GyS2i8?Ups0!pDgrhm&F0ye&3jdh&$#gxn20oFU?8j#-6e!wod;cbFTck>;CTz zCR?s{e_`0QGDTi{gN?Xx$%6u`I(oE(1W38^rInIiG8D&lTJ4-N|E+0URY_Snx2#;5 z!CLw)am=z7qWnq@Nz^yHOh@V?7*DCK8!xHtCs}>L*?jrtzgaj)oyQw{{qrym}kS(NeGvS(Gfx{aJ{sY#R%Ef_)dW28VpR}5a zbZw^5=Vu|Z>?>SNpHpR{kiBhf`a8V{p*k|fEPI@bcvSqhQqOJrK05HFQSus(*?aT6 zyPON>W9zPW`m5-R5jL52Y=;vM(;B1_-Ir{--kTAB6^87TRGhZ*Z3_T0H_54Wo-v*6 zDYa13fBZ)&H3g=M5@OzRoC@ETS7Ic?Xg#65lq$i@D+4Jko=Rka8@zgm$Of`O+ziPX z8kB)25VX#MX08?d7NCJNgn}{J3pF>^6UJh$RM>}m}>T`Ss;7LljeU8zZs05&av}Y zOxL-D;WcK;|BeH0F!&p9f*Ecs|BCZ6%joL1K-DF^!nihi=Q9{zVwG0#!)38ws*_5j zBWDs?kUu!DI(L`ZGJ?}pMdM0;9x;OdEK-PW6`?P{>xfa!%kzF@M8q&axiY^^IQ0Ln zezW%-#>>$CY{Khss4n4WWAWJ!ltiAs^ZR_fy4~!4d!my&6ZmCggBei zW&`|##DI4UrG;t}wKEP=5*+JNd;x(2cy8!C3VE*d1H{c|uhf+|Lj_yun5asuXe30r zI7YHyq$bJ#c9#Tk?Wzu0F>!*tSu{{143Z4I=f!caV@F%*UYZd3*!Llmoq~|A0f4cl zQ&euPtJa<*y#a>kHL%Rtr&LdT3yZi{;#e_U6e|OjnM+(X1E{YQQ~C=2-C}wiL$B|; zc#y?oJ=DWSeo*6ZYxif_76`0oUDOxPnRA8EeV;pI=(1#Gmk?}-moTpbF(zO6cfXIM z&@HF$#@RI4cKi{kF_K0x61?H`v`Yy@kT@)Oj}du6ZKYdikfqqDe5UnyWW8R#{SU`% zDpOY=pBYZuH+9}lB^{KynI3W?$WnN-*TYuRbHUDH&$)<4ZIu?wxPO0R6-%zL@Y2PBKm`P$s4OUO18uV zywoQIZH+9nNS{JASKUp}I2( zk^7ba+K4QSsUl;-YyZX z+hiWOF4p~|_c1A-ryZVDysenR`|1~X9<^^IFJOnd<~chp%e>*>#d-e6*Qr^RN8u8^ zvYOQ0?(6F3dNH?u?=)eg;mVz(=#3ktZt06!gs>%hvORY9<8tp#=@Qi}KX!wqIT|%- zx5m2ozEWFix@A+Gfn*_^X&US3E<90)_%1la%MyJ~RTYy|jLMA1YF_4WiJsgs{^G2P z5ZofN#Y-4%+3bOgvw8K};77#sXN#ibX7CL{V77fz<1J4Q_AX9~G;{_pf+}5dHqWI) z$zGkJ7Ic9a0psKdFFJ<9!nL}Vg6h8mXI@S#Z<_>)L}lqFk&oHzi1g$Z1PNPWTS3nr z-~$dKpr=i&L&`%Wo!%pqunA3p6xAAnxxDm1?;0?)y4V<;Ahm>+1%T>~cCaYqeKCk* zUX7Ldz_7b|=Cr&IIET1&D;;P4S~t3L$g*7!{VeIM6e)V6roi;RcgI5cq65OeoY1Bj zI%qwol=WfnIhj7MjbjRMYe+nK5ur2K4>hO(vy-ZN!bkD69u2j!*2QXw=7K9wgAzBP zm1RQ-?CaSxrma{&UrhmaG%)4G{nyoz0GKrqp@2awVPX(=va`oIRmMbT%F3g0%sigc z$Fd#nE>DWl?&QSVla@9F3T|b5@OH+H3Rj7oV8|OIo7GtNd~X!WVDfFy*yELXnhSzC z)75X?>nGYclUd+4=zQw=6p$K`x>LRz5+k+@#Tq#9YX7k`$>AGDXSO&|C}P)3L^jMg zQeS8|C@RmWuE19Tcx5;wNMywP3JfD>#8Clw8!h{M7K%3FE{kt)w{$1kV)Q=+`=-o& z1cTlfc5|WCk?B;H*FpgM0CM~$^a6L*9IEico2Wnmqho9mj_}J8V1ShhFY=O6wmK&= zu))w&9m_CxF?4%HRn+yjST6^{Ts_@q95aCed0KtABNHwG9$x&DZ*$JpfE6lj4bYf$ z(P3wYX3c>QQhvrA+=>e$lJ4JWqN|?BF8DwDmHWii^QPZTHFMa!EXHXJ^rn6zRJ^dm;sVY`y*$ zfB^pHXPHm*SG|w-HiD0b(VO0k0Hqa^z;w&ZWq4FEjWp7Yz!OSFT{>rFgZb&C_M>$q z0n#MOudwJcpmBt=xM?)BtY*^^0jFlt?Vme*+K?Lol@HVEG@P!h%Lcu+l2%UYOXA=3 zOkE!P(b-3ns`HAjuVObeE$|;(c?h>wRQA;~B{<1aRh@RjX*k_u#=cGS>s`u$ex7q9 zdk`kL;xP+xWLBw3HDi{|y_oerfuWv+a95)NbiD94TT61(o+zLETSSa|p0hZSeKtV_!}L+ zUzg?^xL#>OjqxcLrx6!q(A|pWqd9qMr7TN!lrF&qtx29QvMjsPCBx%G%VB?qUlaU! z{IljPYy&KjaMC+HYbLH+1Tr|_d{jy(hXRKGW!R?b^uU-`xG$kf-V#Iq*_ACvuB-3` zm||robz!S8v8o8(w256gH6bx`1`YGpDj)81{kaU~=nZ*m2y%Aey ztFv@|^JIg}m8u!o>l%!$t87p_)MGOW|I~lw_uo6OvfLl8q6kWxG4_y*+37V(Lh)67$)+;V@xJ{xp?k`(gYSNPOK%3X7 zF%J%2-5YnT8VlxNMcLHZk*FEu#y6_;S4?%@nb8cEPOll&gDgsXXrIyFO9>9QTPz*Z zV=To%wX8!uzp6n932V#a_BfHMTbMgMg<2eY7D+8)vj^X53q2EF0uJ&FyS;WVD` z(q$6l6E9&VF~lf16?+AjI1oWV{qeV0spfQR7MAx8W4m-6t?jAQ7Wr|=^oj8TI~nKH zrhECJIw`UbqD8T^gr;XL#;V##T~kZY^YKcWdJHI0eC}dpkini?fy|Wf=KqMRVeq@{ zA`1=!0-Ih)maDVF=?;bl(Z-9M5!ilRS=Fn{5OCts%ff4!S$GEwD(-jcu^QCvX9n)` z0x^OwSWe66<4r==;)kuu+S2*zTe&4@YU)XqECt~k%4v(r4U~KBLT~`x-m^?0 z;uG21AaaTBEKowZTct=5m$lWBFQmtx5UbbaQt4M2*3oT>_J&y86UX9UhOy+xnm#Fu z1!ER7k*HXv&6tfS&pJXpTj2my>Xe8wtAXR+c6^jU2Nr|tX(#6%NGk;Cs!~DFvx|7w ziy3uNh58K+X%sz9+`M9nok-b}A0D5u+FxF%4{9fM zK5XNtEnH3CS*MDCAzUkvj%iAeuj4H?{mA2)xE;=onMX=S3#6*7>5^}rADkB)dtjFF z=;Taws?88o7A)tM@N2196rbjyS7e*5%ERade3-SUkc4L41XV_rd6j&(W_ELi83XoYDNv0+YW)e0mImrp+@rpP1_O9wv*Xs`G+_ve-Qd`ev$ZHxN%kgVpo z&Q?ycR!1}da7Rk*VPfYuSGaI&dk>elw39Bw?wy)k&`+;4beUw&e!q2ulk>%t5}IU# z`j%!~Crn~NTAo>8UHBBlxqw`Xp>Yr)#cdM}ZoZH9rwhW-1j)A}e99&?tII^Z>Tlw1 zTqa&p)Zi)FAX2v|$G?x&7}Cn;&ULXf-_K)*SDs@9%^S&3d$xEAS@ z_R5l6?_qX}kts53Ygm1Q5g{H=nUTY2?M}_gIehr=n~H!GkT(Gx-_%RP1_^u90wHmm zplYrmt$?C-K(J>AN<^L3QQQD@_qQ3o?o0XujQxOWguITg)DR2J_*oeR`Jf(bgelpZJ|&0TN&ni46!lKIt;&um-TXIYpaE z0q0#3%UoeY>;@0c<0GmM&mzz|1ZFtl1Lk8(&qUhV()C7356#FuF{f*%U!R1-+TU0m zKtu&h^&79z>?B5i9!9p}cO}?C^!`#Zoc1P#0M(uo`hYsR96l(9)V41{? zpE!~@Mt+Hb30-4fg*h#>S2&XC6_G`iomUvjxhY zc80!sPtK;;UZbh0^le6u5FKdv2!=S~x51I&UGieQ=BNPLUUG`V|+uO)H1;rf34)%n7 z%5UcHpBqemve8w^+YSO>US% zhR+l?h0Q$%E<7$uXc}~0Mf3=d?WQci19E8u<3+FSHFdNX^U9n~dp1i}NE20ayT}U{|TUHzysvcBhv{ zbbvHmhEHxB|H>dL+3m#Tf^$ziO;cOTf?&%HimE2k6kMvf?ziB;sR@RFH^_K_w zm_IxeH8b(+Zz@v2&kluu2xu$^=RG&8lOv@ygZJ?QLDRIczBb6`y4=N&&BgRLGBK}g z8YZ{23YEaEzLs;?x0r=9KZD8-#O~Djlicr(!h2|d7m=%_db4HeV#czgHgejIp3-MKWlJ72vd6Gi}kS;)!CN5@Wm9|qn zAmR*zn)pL@M~R}8+e72tJaR!kN5ODfTR^y$vo51k>-GNAVFzOiyf*RrUZ{q(Fr;Oa zTl$n_Y4}p{B8C#f!~R;f;v5!RZWv~x-_l{SUlfDUruTG;aMR~ubBXY@1y@BTMH99! zvvNX?{`q9yt9sU!y+htMWxUp|`*HH^H?O~!dN#YfOZy1<#J0F6O~Q|3^E@`QGpLO~Cr7b5ZH=)wsn-+7 zPXGXIEh4iBA)DrUV0M|BYX9(R@lkMBu?zV9Q?ajVi0L%SA<<-msv~}X?vQ}fv>BPC zWKy~!er$>Y$VlJItSCROf`@iHh(DGCT()V7H287dX{mc9)dNmOz$jUVrex5KBISFi zcS4_s^9{6infDWZ{Er{)I$V2pgqZL&0UX-~0{bE0c$t(9hK!Wt_oCnil(fM9Hq05d z$!5uRq;n~o;*0m0e{m4M9Q`VZ(GU@u6gg{)WtcwvQ_Q=i3^6b-5zb zSvyTHhkY`oHnMuA?=@w$SET|aw@6H09GrWm!^5bThI}}N+e;s7-Rz<5w4}b?-{^R1 zPHW5UDSyk@GqT}5yVW+2VwhO^N`x+xP1~dgCByvs3#4~#2(byhj+Yn@(`M?&_!PsAIfgptg_gU&nAL`4fW~1Z z446>LBBXQC%2;@FtzsWTU!TLxH&H=@?31UvQ$R>dh09CLX{t3B(f(fZ&2i4Jd47*u zK3|e8;>urq0#6>$b0SL3=sD=ws2D)5CWUuB-*-|8>;JycmK3mWxax_g8-yafp_ z3vT3DPq(F`*Ew7X+7zrFw<5!_I>nlp3P<5VAFj4s%-GboRpS$YtLI0DXNoXI>4SAa z-y6WVZjfpyfdTw2uCjL|V^x|2;y&rD5!om|XfdCZo|cc8k_-d=zRdo!$oXLtPis#i zpzqZ~_BuoqzIlexyVBI>ZZQRI`BWP8h+_t}BP{AWNj$r{il1e{;KrQ?Y`Eoje_cg; zRfGG2cHC?A?8Xk%QLhZIqmeK`B@KWV|FEtZ+f?e95w1;4QHmqYG1~E2EtPb#w){kGKBc+6pkg?)o zF1f2*)BcG@7})ncBKQkzn3*mElW~)?x4q(hah##Y+gnk^X(OA^&QUk9CFe%7XQbF3O*vR_LhW8S( z)?|1mzw<)1oYr~RK+{yFmWF@`12w1#_@hG+qNnG_*28w>Bu2OMiMn~zV%BpA+3ObU zC8}t?T1YLMhNSi7FO|dRQCd2i{)XVD+DLIre_xP@t)AZlvbmC*Bjenf{73rkJp`LA z`|RQVJ8|p$f(1UB2b1_`L-1+AglujY0C=#Vl(R5l1BsKWEE$2OX3^B+HmOC&oWqJ8 z+h1EbQS9PH&j&v=B}{B|5|x5(U75-E6sXxu)5ld_R_3Z;O!q6YiF5{%$^s2ZT17^&1h_b8!I&!0Z4&v_ULiH5ef2q&F;1V`isQn?5Mo6Q0WWuoktOO=q-)HQG4dEj4c0GOev~ z0>rCU%~Upt*)?{K|E`{_x1P=8#ZtM7w{4xXZ~H-1EgGwCenEK59RFQA86Rzl|Fc(Q zZwy~-?y7T<=UAuSNg4gsCaTQD;P~c5@bJo=b_zzuw3y{{1?@R0tFJALAiH=xM4Xf* zM<8P}{e96!P>SqyYC2bc&cF(pIVFyKNv?mUz|IXZclDfC!-2T;g?NXmv2w;ai2m2t zIBC#iRhq0Pw6~SK3X+Pu_4)|uOHOGypviaQFs7KUkaKaJB2A`jEYOo5yXkI`AyC)J z-b(+`Xz}-1Is3`#$5tQXy!NLw{XQX9u2DD&o=*@IG_T@w0;)jH>@93TnC)@T^Q~Dk zt7lN&^FCj*{ZFC>5CM5R{V$MFRg+EYvzm0|c0XGhH7Uv|Z?L3bZG9(8bYF~f5g-q_ z%>q;LV>gUSoA{GB{e+P#21OJvF?_F{Bz^{mt7FKsJPh0P_4y}#&JsndTS*%IYBgLv z2YcF^{oJ#w|yS_9B*2vzP#&-C&Ou@RE_i3$myaoYtizSnw3~_`VD^E4k`r z0YZP6+M&v#VTc52kO9V8-I`3ked{uNbxWbqgB4RigKwkqw_!Jaxy{DXK7yAEx#F-E2Qo(_x=p+c)$<#Lfm?xL9yCcx-`!7QWDVm z(2N}4hxNe+2Z(HL266KL;^8ixYvI*<&`6S;)`xfXX{$#7UZ(mz& zduN-;Lv;&Og50`XszdaVm;>RpMzt1Oq`1DfD!zZ!A=iidR#rbG`EPesuCYd0MM;fSx>Q(C% zmCGfbd#F7?RdR2v!3C8r7$plXZ%8weaH(!ztTXR>6B9qJO;}ygY5baZm};Wa&{#fD zZhGAlp|Nc{%!Xk36QGMAI^o#rYjOSDn0oOs3(BHa_vr89QZ7 znNM>t0rs$NG@t}zNAoUf(y1F}+i35OI|*rvKW9#*=mUgBozwk)@%9!#aWz}NH%@SO zch_Nt!2<-B;O;uOyK9gj2@u>hIKd@oNO1SyZUKTj-{g7EdCq(4yH)o+Rrg+MSM9ZX z_x|_l)ob?%)4x4FbnwsuYehoJZ0B)$LrlAOgL_6`&4GF5XY-+s?{H8bA^)D0iqx!^ zo1|z)#&h7^J6aYrhLuvjFa2Bc3Y;Wwg*2v4r^e+kfpNdH47G%+di`oS15y*u?PyP{J(&+O;kY!1?I%m4`1!2$e!zgyda0 zwL&(ndLgNV2?wLwm108`yv)V#(OV8pg;|ho&dIH3XtCbl36`$p7pG~20ql3_N#E6t zt$Tv`>g##&1Zvpz{lnYRz9Mr-dc0F9VABph$geBw`1NaS+V^YavwPV~gW?%4_G*uV zl9>Xpn>{FCGi~2lMKmG(xc}4m*oYO`(D(U|4qD{}!!iY=(Pj2yEfB~j^}!LIpI;mt zwBl-L-uT}T=dI@i+C4NCH>E{)*u7dG3e~Dnbu8D<80M$~3|=X#t5~k58~^M;ivP%c zfYEGl=Ij^5NuTd+-fe}Iv5nt+^N3~ae4#-xY&N#uyyVX)@O{a9ZDL3Ar&a@N3I|&= zhA4P}Xx@~a|2|mj>}1nn2I1lLo$%B*8Y6hr5NCGlSr@Vkt~156c)hNgxt_k2y?1`U z?RF3i&)rkvtc2EYOuJ8AlhZdQa6^p@r>4kdr3)oXb+puj+WI{7+!#Y6+(3Yo!q;(@ zv0f-W=~Jrp+t_-rzc;@8ZZBFz10&&!jSOj=tIX9f5I26Wq>jc@&ta!G;cH}1)&Imh z=)tM}+5v`fxMF)ZO_LbQ2}G|w%%G7;XR^tyKi^z}$1Rv{r5gkAcCdVZjdeoR0T~Wf zOW)T6To(6ql5&{LtT*dFAz><{wGC$82rti()^(rToF@sS7e2q~8dwe|RXt}({`MmT z=iv8m$$0lAKYXS{)PCo4Y&+gM=Jb#QM0o?(9+m}M)iMseZ055VIOhZR2qNc#pmLg3 zRjN4OWy&O=$);V>_RJDwtz_3*MiM`nyJirV`{Hv8ok_AeW8HB=s%Mv|A(o9wVcD$AEBP##;Zc*W&n!-z} znwyo9OxSzit`7Pj^@#eYZb8(0eY$P&o7|+KSB$RT1Q3kZWMS(QYB0b2Y8`Q<@;Nme zPIA-WW%`+5EzcE_oE^V~$0T3ck)lk`nLDSdCr65R+##LF!G;i5TxcJsmUnni~nJ>}8o&@WL?g7GD_<5E>)-tWfi^U<;pov9PR~^lcq7 zJQu7e`F>E%vdu}dx>L+lKEZLVHGn=&tm&|OmvFIy*L4B8X3O~F{wSfFLtM>wS}#O{ z3O{v+L6b_G?cT|d;klg_ry*|v$)SKa)q^;_s#zybnfGd$!&a|~3xsg=o?;dW@YdZ3V zH;#VR`}@Cr_X{zC!K^v55;cXxf`N-;tJ6}uTCVg57ZveB7iW^8mrc-?%8-R3rp3=s zv$mt3VS8Sfd2Y<_O+ki&^Y~OWdl{Q_XyZT!gLN3GIdAD|uQyq%wV!qm-VS;w(~LN) zAx6dX#;J}zMlPsYkS4`+8wr{#fKPWuzm)tm78EO|`tcKOM)Dm2=DUIoxx>ER57w-| zv01|Lb(GjLh85J@V4ErAix*S|xplvaEajvg{b&y_F0Tl_sMT-)Uz9QZMrc5BMbMiK zQG4nQv3|)Q+#UbO%GNrPE?;$texYge`rx$T_-UvbIPYMORzCB)I5psEb3#Q%f`iVz zd=o$4-q`l;gc1w1BbYj8-(f1O#ePUjAt%!$YS}=aN{_dKf|j#-TddGlD7i<`67*{w z{wBc8+NgSp1?c;(hXUv(A6KxGm4I1Jj%4Y1q0|nL#PGyKsC08O+PGWf0f7$xnK(Nz%Q%7a>J;yZ?vi$ zAFkS3fxB-*TWG-!D4vIe7m5-I9(+u)dDza@Sq<5Vtz%CRKvMW*B8T$+CU_{@V8f=WHsE^{s@7gn|ng=cd}Y&?M{kG=73r>kl1{BbkQ%AU8eVxVt7 zx7eiL14TY}T5{U;IZGBWnXZ2E*}^vx@-&e&936TZCM%VG=!ox^Jo=(glO@ZfWza$| zAlmWm;DEyLZR34rZ)85_TTn`EKmQmdN|V(z$gZt!w#(fj0^%1I>mgR_JJun-axP<$ zf+90Z^)$P~mGm%g9@Mhg(AFaJ+;mCF%*G@dS$3Iq8^qr_OdTZu?0L{-KNbW6aPR!? z>T7u6yGINFwuOtvktc$BpP7d0a^H1O6)KdmO|&{IiLZJ%&#IGJlw9XYB~$$>^`b)^ z+FNgLm!a!>uN8=6F{@P>op*yMnAuc(@;GhhJTFX%0!?i@?5sx3J=r;pgRm zkPH`+9lS&ynYz>2Nd;8Gt;pW3`@&3)&=)zq;g^p|oX42=WezXu=kKvR4YHFe;58Z?Rp8awW_GWgXGgegOhUkzyO}R@(Ar00YQ6%1X zL$q5~RqRUDqS#o%^JDxAI(U80sIZGEye82guA2H_BvBo$?`0IZ+^8;C-7*?$pN@q-!cRGTQP>%+4QFl1Y!SMdu>z^Jn z($u>GTmeaAcWtXA{dBzQMDvVGgT^LITV`8^=mCa~zT^Jw#XsbA`SpyOitX3FBrN8- zxr3`+$vq#(7I&5pACr#+y}ms)SjX{iXJ1qNo`1l)jSXRg8%L_abjfGy%{g=X5MRb} z4`C;K(D1i;jLX=_$enep`U*5vFvzi&H%b!zD5&C<^4djzf=)JuGBOr!k|CPWwAgvQ zKMKdyjwRPwH1TypZ_O>0siwqx!Z~vi3bqKF8AU)bcNlv^6}}bCvKFcWbw@e=r-GaP z3wcwLm`SHky{_A^ZP&ESlvQS;dZ=tF@9$h#DvLx1hvZEOmT11#@TN}jO0m5E zpfRU~svh+rs2acIgLj z&U~e*AxhX!qOfySi4rCq*i+4~-WpIB9b@}`ZASRPIPe+Ac9jKsXqyE`9(}N*>^78>zv&Bvi>am)TSdWA|$1gZ^ZClHbx7Vr2Fod>C3hQCe1*le11;fNv1&h|tEPRdUgOhrh;}EhHhd{mC-p93A`) zO@Yoh&WYEI_EA6l8Sl2=rS)|lk}Huuz4@;YK~L>GoCj~^&m)vkhI-`zT(4>3C!|tT zGjJgmsA^uE!4-<5nR!g=5)Ya3znI1(u0~J8ro#lOosehd4AOZpAezykO{tJ7Oj`x< zlU{2(w(*<*MthdYhF2RJC?#&;26YK9H621&u?5dtFrD>BID4qDF{nZ*jNup%TgH?M z#)7f|9>#*rTA}W5Cu5*@Y{YW!EZ@mkmZn&FE@-Voq^uTAZ}L;JJ#`iXAeJ}cxu+el zb;mcCemQFwkI%3CF3hYuZ*GLPwx%!2mg{2dmjfU8>IG(gJ}l_&oq5?kSCrnbqx1$w zU&__}=)UKw&xP4a{5txJIAqBIsWaXhN|0drx#!1f_*>x1alm*9Z(#eA+;y4Ce4eqX z-ipCJL0u5awOi2s0Al+UbqddZN8RuFCBQ3nGz|BYU$$`~MAv*2OSXF+*U~+hGhU6_ zrU@iWtv#Y4Z6XqVfphK;E5S=0BFNWSL)R?o$D*|ovz{wsvzf9-{3)v+%PKtD!>pH` zY6g4uKxQ{P^|??WTI_gbWrFeto0|NtBZ0G@H;b7_fPLWyQ@@h@`00cuiw7aUj2B@i zPb#N4_VN^m+%f7=g%jWS7s2ugW4-4+JNMeFF@FBF-zWVCzbVc!ACH!?a^@v}q^vn0 zE+}#nJt|N595z<3X+B>20WG?Wi@UN}=5z%uly>5$U-qnnt5}76N(`r+x(XNUx2rvM z27{k+9^MLFcKLE*isH3iLlywRYuN~XHNEi>WVahWK83e7F>lp98o#eImFels(o3pJ z!ijNWuPdZ12}G2#KYm-!u( z$q)ol7DcgoR&js{v#Bkw1(Ic){NWc<{=5rQrDB(QQ}v^eVA72v$a)7Zx`Jq!wnRtI zt~gyGtN&{hRbyKWa z9kQgMih6F9<{`;3H$`A*Q?wZ=kEhpNLjM~_4y}NzX{1w7t}tXUW1{iWT<~H0M+NK) zaT5=n^%UG>@~x@F>REjIkNWl%ka$T-2`0ngXDw5@k2X;m+o@q6wZVM$#VjTMPZ z#Uo6lBYJbj#a+8zY$EDZx2`S+|xg#s&$arb3?ql!;g!8`aFSpBEk5*1jgl#h~; z-CoyKk^2w}mc(8U5Nv%$iVD<>#{CB|| zU%yilbdjPUYJB!9<+DPeD~>o_f}Q2-EfF8?eEoZ{QZbwS)r*b9iv`zl_Q2IJ5LZMw zwCEj?=cDfAr08f}ze`$898Wc9@2!?qWa;Q#VM@B>qlqOZLnrcD2z<*8hiCwNC(=WY z=ox{0AWCO<|9Fq}y80Q)EwMj>D1u+r2=OMozb{pXwIw~CU*&uEO+z-iRBz-Cj8(XH z)omqzU-%A8Blwz7?QYI9UT>6+SDv91>xk%^K4;|Kgu-EtxzdBB-AU^xXW#`)O8A6O zneILlvL*jl!cnpMJ@6)IEmRF558YqaDQijW;RqKX805+gp@eqpDBo7rIh~oJpo_gj z`l2w_J!jf6mQfvHk9tN;D9YCm=0bt%($4TLlu9*7^ZECU>!i-W7F2_1-->R6bysH+ z9TctL9f&VUxiKmyEKyi&x0*%^wgJqi;ENugbpyNZSDWM$=!9YQ;&@;*cDT4aSat-Q zT9~wM7{Q6|bZT^siWga0givaj!yb~?upW7YGcY8#Ay^vlC?m+4CX{JtyTS6@WEwgL zOt|&k2PTZz;sVU@#d!!LF#RTiX-FlZwA_e_ND(Hu%rJO8HYRYySl?l}h|!c0OM{cd zMTy~+zuafPd5^>ts%k<{466*&*TbEN>>2_Sk1Q#U3C6StW9LR7M?=yNxQG^CC$8WU z8kErw_<=36L5n3!jb{-YVgj>|H6<=KK~xl?ahVuO8UL-{A`#&phF=x|g_`nPhz@ob zC;{fHOC8ZZiZ2Y2GaM$^zQyxQ=oaGW6dnS5BM>dt(a6`i|!vl=i3-KSFcj z@}?yPl(P_znvh>8!*eJzu>j2t?^nXFnnIDg3HbuVG8`qRZ}JcPdPGbBf=dYOwKyx# z^<&Qb8J%d$CsIAC7#*9`6rw$}%2QiV zq~;0+Nby^7q#V1y9;vzlMGfD5oDa2A*|2p^Nf8Wd!JX9(Ve8%@p0Z?ag?@7vyrX4{ zQismKg_s%~Ta~Q)O-f51v2I2_UD5zjJi@?Pt5$-oP?;>h>Ax(5#V{`Q!L5U1JMiYs zc;`2X@toU(92u4b70MF(*vx}EW-^wlWWu49U;yG))-d?OM)HLp`GMmW;XLfVK(MrmSN^pwWXH+xevz& zLOfad%?rhT6$(>^Yz@t=&e?Z7NLdKdVR${v+_>*yn1VMxWl{{A zQe)AF(N7?^h||i};x3AHQDSYrW{-lE30~EL`?+YeDu2#4l$y-NoU1Nc=r7-X!?{B- z^fS4cxt+yHZ8gu(JNuk;hh``&xhff%S)ZAIV#t_kSgVbMZ3V(mhqoHsultJD1eUu8 zft&J(8`HZ-$C(w3sIH92vMyWuYUPuuwZfzyN*ZiTk2^PpBBGQDY8pCf54{QuW9W4E zJ%;s%|NP{Z>!{nLa5ovL*n< z#1_PvC45howziivePciz7v+M(87Q95@+s4A6uyM5pPm1y#I%~%YcgW>XmoVfbGrXI zBNhty3>2?#opLXk2q^8_UOqlowK6aZQ7w!1)xh(E(D7M68^!(n?4oS6)v<&=Dpw4$ z3HySobKuEQ6%-=5)hImbVU^DsSy)cYiXI~rY9OMtgP!q`b|%JSQm;<>EY@{~>pt98 z6?ZpQv)91I$h{gYlg6PXZ5>O{%l_M)RZN|ks2|d*!tfp= zn?;KslT;Y7`Ch{DqYAaMd)zr#`1o|h)gls*3AnMoj>^o%8FP*VTw5HEJ4Ya&Q0*HC z2fN)EF9%5lrDk>t{N`9m>ZA=&@>TGC+x!&9CYrUJb&SpgWD>ae*dZsBbWMNdOkbts z+NRwy-=e=UIWkYG>GO~v0D|JhIX3*PLFkqh!18z&9hf^+UmGUM7}Rl z_6Zn}kGo)2V{HhAYWVuw5XrIPnEXFyu% zQKcr}U4WUX$fI9Z%gYVSbEEN7`K|zY5R5<4A}^Hv`tKB2(0`-Aio2QrAu;m+*4k$L36U@iYPtC&%5a8s676|}(IiVNu{Q)WeAxT3i%a**ECOP`a}_^w3<~(c1nmsHqf56jFfqxOU|A4un zopOWnr~mHP|8WEA!~b#3zXku_i}Uh=IJx=xc&P!rKu!=C0HWptfI0d2K~O^g%*o9M z68Kkt`FRC6xw!!X)co9hoWMUUa$W#{6CeOhO{nJp9v)60FM#h~#@`Bm8@xb%PB0HI zkQx9@JRWFm=*_^-$^A!)4=N4<^8^3Y-2aWRKvC+PV1BRw_1^~6^S|BuUl<^02mjQE zy2!}~fVv0b2674j`Kf^*ZcgA|;ek5ND*%lX^xIKrT_|Oq56sWWF97%x6h0uB6B-{r z=t+J~UT*%sDuICle9(@AI6>SzAZh?~vfu{tK^6I+HzTwKK3-lf* z{(EfxF8F6|{2eg>H#am2(59i&7ql?|)IDhbc>hF$2O2qO!2WXiA7wyp04KB@nkpbp zKJGt`Lc7ZIr}p2M@$x|vk{bx5<^=-(5mtTyX!p3GCI37H=7Gxm$<=?;hDI7F0G&Yp zmipTOK&ALVU}(Eg{{{ZctpI4uLHq*$tuh}!06N?90jc?+t^5_cKM?^6KpTS2P=C&X z0K9(`_@PqV0#F42=bu4?CKmUfR{weY&j|gU#eeYnsL&UaKXd0FaQ{E&(ElwoAH@G} z+;E4#q4~K`Xg($sns3)bJXI8e?wfyr2L6(TYNk6dM(worwL{TWj};2dkEe%1^Npd< ze2k~h=`U%RzXH5$J)df`+qO1*Y}VkfDiWr`Zz5EIUjP2f?KMnt$`E?q( zV%nq!yvX(O7FOaKZLhev+VH)Y5mS76SbThF_*D|<{Ww1PbO9FicyI&*V;6l_?Ar|k zACIgan-;xBA5Ztzl!Ly$H>?+4BidZ*YZ8jjY{~@nne*#&5FS|(G#}~m+rJ2~4JY{T zna)42DyCW!`Bc>_%np|q+g2@=UzZmiCTIqg-avk9S`86oI8{8~^bR z>mL3&Pi*}^+`W9E;mm|-hdcV^0oyn}o!oxV0Y4s#%vMU(HV+h_lli~nhs^8!Es=zF4n;_~@;dBA-Cmi9$oQT)mKQ^bsBe_Sq4i`)d{lFAi6G+9*+ ze`H_$v@OZ|iR13u`a^dxg>#EJH8wRpx!eFEio)woOX?nrudN^}xw#Mvx1Jy`yx#Bh z^o!wrq)*10H}AhAFRqNgReMWexT1clfBMz;RMP_u3d@J3c*Cyu#hYHee&^6|TIB)_ z%sA(ey_~O`??D~@bG^2v-SO>NEArdU1nhcz8l!fXA0<^mPe*x_G^TJgaemXE$Ur$+ zFE(H<%GVI3yIC^E`IjIReZu@-#$gXY0}O&lYecm`_@T*)=9AXvNX@!t?4_QbC#r=n z0V~`4)9pvtOLw~9m%gf``O~QLO4xkEqkQsZP^*We|I>t!N+$+QVZe{;6+bJHeavu7 zQRT7Ig+|jK$3MG5{HXkK9BU-mnbse05@sIh{5kx?jFlI)Cn?a?=)Qjgp!e0G-yoPh zCrb7_$=;EWqafjE_z!$mq1*uU?xlNU=W`{x9m}oCc4AC-B5P0$g{O)ZOGzTAi5 zz~AiVt+CR-<_AI%`DYkN7H=5oX;IQYAnJa=So{Dl@Byv$1G3KttUFbhdjbhld~sEL zNtfi;a>){w%yC1ih~;lcG$P7XG0LSp$|!+((lg;1s%W-S4iHLP8QnZz(Zko-WoRCS zlnpRf1)?(vgaxpCQH1&Z5EN30J_rJb)bNCB16*7I4|IiKgjT*w18LOr5!dqjN9m@0C`eje-FaZM&O!|$25_&e*{7O`o1&4=q2cT%{EgId>6sNVp4Ds zV*VnQ)%ad+xH+k`bM>w`vu?|}!DuD;VT{4!bek%R;9{B;Fg0a|F_MsfJ??FF4bP}B zRF6?KvW((`_jS{7tk#ZblL1m$1QT z&_k}04XmE^Y=Do4{?lkFwmNK$B5|!Md7w4Bp@ZmG*xJz~#=dj|6~${RbZeA*x<_QCu6gx+$=KP<(`9Lp@i)Y2Mbp?j^aP zc%1=q*l6}Os33_KZuo=6Z`JSjY!y`R{2CF3DY?XVdGu&o73{=VU%2ndW!H%|lJewT zjYB)K9^gh(=Yl#Hu2J-!dGAs0S>N}o^J&ZOWH8aZ;NO!DTu<*)O#se>Qn^M459;^H z+_y_6Ox+PEq<)ytzs*a6WX!#Mb<-{vE1#ianah$GFC+?0V2SWSpdHI3C&m>RSPiXf{%wHwMx{!;tCle;S3g+uzUBx82!p2F! zDvmw(z=|K*hK;WF?u%0&Hu4!_i7+tPk57*bC#F|s7kR`|9dhUAmZp|x7F2RSS2Dl- zZaygsUT=^u7|fftoe7P3M}k^-ej+>m#+g-=r@x=>>sNvz^7QbS!H+S~pQ$yj43@1} z!Qz>ST#o5spUAju(v$ReV>s%F?Ij%uc6v@^oe%A`>A`W@m~j%%tJMQK&WFOISX078 zrHJtO5;QHe3%@$r*uW7?p)2Yl^M(Oseg$YJUOJ_}-n%dy;=2 z^i%{Werey~9vMeEZ&bIh^mBch`ItX>!ugh&Px?rO>Fa!Qxto064XPt!fV3AfR%))O z`*=gtoO03C5#14!cARoulJg`@)5Ao*P-)Sn2I~|srR}#^*6Z`g&*!q*HyVO){Q6*n zM>ygBAKzrpCW7ep{kI=axvJAOY&Cd(ci{};;>L3K+(}T1ujRdaZOr`U-u1>Evnrx@ zrYB#umHdsJh>Qwn5@n_t<3Rd!1fa=sd!(l~eRBuz12#$d3ChlCTSc}y@;nmT5NyCb zQJ5H*D$8sO&u-pOX=)JT9j&1uucLxYsjFe)pb~3?Csp;(>xV%UYBNBHDa4%>Z;{6` z&V2wQk5=}($;ANk*Eg;9LrVgPNCmF58YS(qmuw3GkOGAh>Q-$F$R&PxcEFai;e=bV z4!L;|mHM?ZakBSK{^S)|DI8wTRd+5~SYghDh9mkqS?qg9V!A?noKiKX?)iv){;7)K zCIvkrQoNyvG(qr?_W}>Eo(j%!NP?^kSr)cw3*^Ilh>X57zMo1yiGS===r(5?7XE^c zHJ3pDM+G52k^H*E#|y8vZPoj4KT2j8ZgBGp7MSk*M8DX%+D+wa)cQ$k%OP{MvDCP$ zwEj$a7{q2z=89ySu>kv_l`as=a?bELlj%uGPm*LwD1;V%!1z%2>P*FPkU2ljMCpgu zhOEWL#E`1s5^5^@*E0HCr;iHi%m}4uh$VR5wM@TQ(AhY+@^;MXZaz*2L`?Tc9uD+= zklfzI*@b}3&*I&q!_H;Ak6_4<R6cOjIGG^qJX%}$lDXCyqpI2NZxd=mOW6=E6Bptey zAd}#COqq@4{m<0QUV6icdTMg0;%d}hq>-T+O*dIXA^NY!T^m9_%`2I|Ihu(Od_SiI zaLv{!GtY}pI&y7@f9$3fs6mPnU-3kqPudXR_PolE=Akthz?4J@@z;Ve{&{@pidBsZ#@s{*$vH|{kPin|1Q8t=BdlX3^=X+GEF#qI&gVYo z7RZiJ*@POOQmCH6w;w1vhxLmv(HyRvNRh&TU+zBSQ`|?p2%WVy9+RKF82NH*$w()8 zswXfUzWcy%ij4vfZV-3y<$ah6G$BC1PmIQbZ9eb6)Po~@={UHL&qeOQcLgI0G;T$a zLyS?OAWtSaz6t1OZ`OJ5yjR8`#xVN*{JkSuXWNxG*b}=GZ8#<#x~aAzuA@jQ(FXqT zA`O%~^t2XrJlWzx#h=5;dZ`AFSfgdnc}(pUPlP#EKJx{i5|+A86ndj14u#Z-XSKAz)V#2;r2CFB7ctTN1N?q`b$SBM%ik8&-o#MnQ?v<*oMyY}i9r z!9ryEf+7zZ+mR}RZ>4;~6*0qkKJ4LhgGhzkZTe?44`N)eiW`yi0`?P^oOjSHI%Xox zmi1j`zR9%Kx{9L>M@!>aADBl?u#dH|1Bh@nKlkK3{dm zD=t4i_wA}I6;At1b&GIjk4b$`68EYnOP9I(8qw*!iS`X~BDEe^9H82%*HZM|(cDop z8nb@UMopk$F0qf~i>>qXSnOf><}pRY*m@Al_W3N)d^GJPgWv<~gP@a?`MLxDp1(q5 z>iE&a)sXM(kl;qS@xw6vi~MbzC#FoQz$bC4`rX}KMd|V?g7NtoW;v|`&v1s7Bsb|# zm#veyth=-u;D~yyF<2p8i<7!K8V06BvNM%%N*navszDLPSa}C*N3K5B$s^}mDFV*n zF2nC-D879^ln9Yf)N>j3R_PTbXXE)9ae(5wnw$VS*kvT}W=|Q1IiiZ>wxtXtArg?FGD?Q?0`&PkKilLZqlD0; zXrG)VA;HbJZkhKVM|tY(A44i+#5&n2jD3&1y$53|hN{F%jj-W4{kqHR!polsveSdL z?B+fb8&SFISGW#m41ec8JsCO4A}+hx2xn2j+1H=nt<${Ln7^?+_MQ+!pr8 zWc+Rh%w}T<(sFp;pc$#JhUr%x@LTWGZ@$qZxzaYb*0LJWolA{|QTn4# z)^s1acFNKWgmg(ptlW-&@%6rPjmi9+WgCC?=FPZ~>g&GHK^su}`%pc#b=`tA7R3Ug?$02$li88utRz`NC8WF7t2UP41w&LxE2h@Fav@YbFSzgWv7 z@Xozi^@v_fM{hGKyzMVrM;v2w9Ecsykuu)d)k$A2Q5b#Lm=6>ayIwlFOL?hGbr&vF zyC4g?oHjmLzKhL$^2Xa&(JCg`5nXu|aL;kc5^npJ=Hi$tL84}4Ix%DW5`2(J0!x$| z3>c_Nc}T1NASAaCRjVYtIb2h_FGjYGQJ*=J#mBNH zbJ6K}F?;CC8``2UEqRky>I@mmG@`@%F=hM7I6_%-qJEH(;T65bz(hv7(2g@SAtO76 zDW$Frkp8}Lb`Z2_8J3bFKIf-=>IJU-z2X%|j34)GkpIl&o7>kzyk?oJCWR|kzgzc+ z%!nhcc$M}&OYx1yyb;|ST$K7<)sfhzJwOYqZu*7oN2h4)FkjvCvL z+7vK3BhJ1?(`yIApJ=**Be=>c9UMIE|c^!&a3{?dli$X8FqpY*i3$j zAeADIKD0I&m%x)UB5Wb?-CTAedk?!#pp5!6EsYN&^&8$4E0(S$bg^57qKez6a53zJ z2hER}t9yX@puV4ZHG}rgFt!r-`s`Jvf)_`di3ZRDh58whrCY$`>}NTbDF(~On( zFbCfcE@SeF!G{AKoS(KY|PL`Lw=pYSpA1@c6wHR8rBT zNU@A{kUW{>NLH!mIV#*9^c=ZbVtMgV8N+RVI!Hvgb@M35Z!^DZ@-lr;rbd5mU(a zgZ>#Q>v}60>&FvVCfEbp#BD(tyr^8tAp|>wS?OH>Lh35h6>q=u*|jQ4+L(kj5Xg>( zS(+h72f@Q@<&-s6u*$sQHv5S9zPm#hE9VtG^~?ePv^9!?8eCD zY<6{l;9~X4VA^g8%?+XB^@CUhuTFp*sW_q z{Ju(nxoLMmiML8eja?(!7FlhPwNd^$(xwvL&#mZjyoY*?-|SsM0YlXA0(&pEsuJw7 zVkApIJUYQ$NGn)UGs?p8lO{3=NXoRV%<&V4oS=migIZvRnmX|l-d6t95@w1cml z&KHz02O%LY)dp=|JsqQxqk__9#;zRuFRW+T&jkLZyc3F4yLx6RV51Pc9dJhXBskv3 zWjTyaL#jUuyxZ*}6#vtCIcAGCk|zEfJhah(tR7(b=}I$V1%*UN)!fq(Th15v``AfU zC4Q+j*S7zJ1pTHAI?gSO6ywL}H}tzjw{UbJGChM!F=2ASQB*SD-lCNXRI?_XX-vWH zPSL2&L`F7#s|VnHu3#{t7=gEVWk)cJ<+!SwF($XpAZEduVBq)zpHZ`*>KGg*BGt+_!aegi{Z4)8F~p`yw7=uxy{kA=_m*MKd7)e2HjxUWp)2oB zslPSEgtud)1Yv=CBTnC>t&KJe2-?99EcbQbxX%p>NEYBQkq(fPTYnxCq^YQsmf{k> z|6wj@a{YY|wt_x5H++fy!}}r^m(lA#&nh9Mf?be-xmNvff%D-)WPB#n?s`tuQd$JF zRCNrlHHi@iONU(d=5*9COL%dlR=JvWkw`j1DSOh)v$FwZr$n>f?3~Orm z=-JLTx;Y$cg^w-B?2IU}(-9SKTvN&n7+AF@rvE9L7XCYRcFx$X7D6wa2psxw zubv_^<`Je&vI-YB596y{TaaO#sTs?-P2wc+8zJmEq&1b6>p1gpJN?09*wiN6_I^dq zwVyF$dVYHRO26v3zfR^uB>o=auS)PwbtiN1gX>EIdk}jqDEWD%e+_7yWLcMSk7#{)GU4jA)gzF zfcneCw@=7FaDnswmh%%ow03Z(+&1E)j~_LwjI^hR;v;Uj$GHM_(Y%aT%JD{bgMXfY z&Kc`%Hk960qiQrdc34~7na^JpAvIIpn~nGEHECE9*3>u|{v@D7;_tqIyCu5$l8dA- z8Y2AegGa_0&TgXIhwAL*Fui(`#UZ=7wlyab>1C4K>Wf_P9s)l{_oHJ@(skjMm%pV#`YRZ9K*l zt>wOt=o=Ca)2g2~c;%k`T(-zoj<08lsM;{i!AJr* zkKGl#DZJ)M8X&Jq!?%b0&+Hr9ubT1V5 z5HUtMj6Ke4+ua}2&t9)}9M#l5%qCERbh)LwksRta?~T6ZRSB3Dni}%@#IDP{?^Lx+ zvQrH6Se%)1TACtFt?- zAIm7Qf9ykJKe^wgc+i^DD;TY_aMMVZ&~*4}dGKrg7r7lDVueJZG#wKp!ha>^gU0x6 z2?vl(wAo2~Wg$mj%;h5f+x3CaJwq%#w%daJlwFn9*1mS&#bBEd)m^Xk>GH&v+vgyG z>?8S6DkD++ePddw47_9RGkc3`_!Gw34}E!GMZHj^dc-Hgit*F6cwKB`#ig|eCYU2L zx6Nqp_$JEn+r*gt&L5>gf*^=AFwDxbPCNl&2 zb}b*5zx3a>Y(tP*A&l@?g;?;}T8!Sw%0FUEwX}>H^VGlE_X>u;BHO$Ur65H^FeAih z4%p?Nuhmodb`+alOG>qYUL7u`vkP*4_+9h6d2dlf8gs!YO#fnSo|uo^>2jf!POvb; zvd6I1%SvqH)Eaw}dqF8MSz2k|Prxg9Aq&>b4Jk^Mikc@MrcMZcTG5j8plN5lBW~d{ zD6=|?kCQ2GSZ>R8ss(BW<$Q)+6bQ&l6aTH(zh9+k(4*I1Qm!dM)ff|?Av78#(1+JH zEhxRG{8-$k7o}`IisMoiPh8tOwb`(yxErtt0BbuxMD7Dl&tZe z5L_bp(Z1(E>c~}(h`Y=Y{rYZ-44EyJ6T)kE^sbo)3{W{8O_0$e8h`v^*}#$LbPmD{ zTg}OOqAT5dDkG^9Ih3lhK}=}~MJ?)LDtmp8Db7%p_wkvK_)&WM8#h`Zm{ZJ*WW%W2 zvW!x5W2ldmJJM<_n+bX3n``%RBY-bb&vvWKKE{zF`lG64&jE>%!)Vpwn%A`08bA2_ zEWy#S&B`)CX0-m>0nZ%!YOD9%*CVo{`IVsA^^<(Tq&&?!CaKazh!TUaLf84pUZ?j) zt7el)`VWXpW|fI5BX9JHkdbKZOD6w#g7qfr;9Cc>Uh5m!+;r2qrPK>c$ps1TAJEMV zv7Ez-dT|rMmxBv?Rosz;qB%5Pe}kmC7vP9U!T%cw432+}av1=`ZN2kJe~SvqVmk{z zo=)bCQ0axc;dnWu${p#FB%!`;Y!>Br?{IvW_7e8G?VfJWNSEol-q3!xlW+8UrSyR&U@siCV;pXv| zU9kEi2%--9 zg+FPJcJ>*LBdZbyuXcy4hX4vi2r>DsmyBV;KFH{02~G){A)Y=tN49~fr`39fKlu3g zKPsxOjHWL$bSe~T91<_l_s1}M3oc(}>2d96YOS@MFO}8|d#>GHVK_V-UF^|EPj@T+ zP8)Na%h1=VGBkcVJMHT5e>~bdJ?*lTY}OyHYPw}V^tSY$%y)7SbG~ol%*9&6j)zOM z1riVV#0s6D30-ZCKmN{_5lhQ(mr*<6R`U+mhjVj6QiA?seJjccR<0(vNPFQ;O>H#P ze!G4pSRfeM6~A6XcYE~eS+Ib?-J;q#FDp)3Y~UU925fTJ#en#uBUpS2&v{H0M9#p2 zGi@UhsF`p@G(JSFu~+}?N>nCTbHP!$Wm~6)T$6R9WAjjlXP84(UsBm?qC7_cRe)$i zv=Mmh9#Ls)m3U6Ky&No7n{71O0A2H%xc6L@n0XhhN^p)E=$*_op2#kc?!oRUyl3(O zjz*384QjY-2sR5gEw1j=SdOR--4Rz`vH^8{8K!wEPM8eZ)7%2|VGcGY&&;EfI0FICt*8eUoiW$Z2J5eY-q*0NLlXvEbz;z_j-XO*NOz?b{fLCqD1hDd3- z2Crv3xs;`$6y6@=tP{B{p@-;DC6T2?qg;Vqsu?wn8#((Ew~wZ3pM-GFzSG{67S1U2 zEy)!aT&!(UBGE8a4o5}M(R71gw}8jejCQwQOdb)Ghf6`zECj(p-+g=)D23bcrnuq_ zhuhu=hSUz|hb|XDH_m9?yNtVq0#FY~XyfR=v!j_fmHt|qsKhv5l4z$s(8#hq7V(An zfOsk`(qS50rKkdSYvT4~08B{@51^TTnjFb;DT=Y^kXM|J&`OYkzZk8L7z@0Wird!w zE}ar7P=XFyFu(gt=$C=eJ;qtMe8h^RTc`f48DTDUeFgh_+{G9Z zOKr4x13o9!B+B`ZIHk8`Q?_>9JFj$S6gxl7F8XU_u9cggqdC*)8J@HX>JWI?o{3Vf z<+~woR#!15NQp5OWQsypPB9TKGZ8fJ^vT3rz5OJ0byBp~i+U{=l&(-(cWW=T;*ZCb z@3Vhhh>|o|-fg2~-(IyH+j;qOzhQBi_n_B;$R)a9F03 zU4tN4itvsI#$(Nhh`bjXSQk+Cv<#ohx(0%N+iHXFkgn)uVNxZ)M`~MlhUkAS&tuc= zRa=vROk15glocUre4X!k(hWA4OY)t?WGMT!-q$J8O}>q$CoI!|5@2Tt(|jse=k7Oe zse0nc3bP-%AKh@zx8}1wDH`g=g}K0`=$CRaUy+6}N%I~uFxJ!^4*K$=6s~sG<(}sO zO~*kl8;lcpsf~-#sG>infy+4C!U3z6K{j*cmiqD;)#i?R-%pPb@fEiH9ld*Pkq8|F ztS}Zjmd@C&-E1mKFPBhCt%tt$qNV8>|8-s%@pbpS@;$`+Zp!Q6{ERQN`M8eT+0$8u zs`Hw;&6%&2YlP>u1ukT<-1WLjj_10^!7|C`Zc=aae!LBxw&Ng3rcHK}xB0dcJ@oAJ z^Hm!`fNp}&B7RiqS0QCsLMqWy<*=m^U^x&5XC@Jyu^W=hpQQHQN4a1IETuKCk(7(3t=qFG~4^@I*_Q?VqDBqI#u z|JeMJ($OF~R5k*17qs%amHuoI4v|a~tgt);#0^7ZgcUj8v5KNN#lCA3V_Jb>o;sMq zz>hl+>()P~mX*0e1oVpvS`GB=T>%$lE1TU>oh)Upu9V^Hs%-_eecW~GN|kn$+iKa) zluqzFP->mpgOjLGwAGI5b-s>t@m?Li1hT*1w&aA^tSU?|V6tftjbX3qwtGwucTDPa zoD_KYDs)orh&hIRb}ayL%8}c9{a!HlO*IG`#wOD76&ofh61-VVV9O}1A4O54m4lcn zoCTeJ;Z;SWJf~QqTUoq4k?2v1+<6y3caRL#?!d#cE3eFQ7dL^PLmi69LX8z1tVXr` zD|zJnvMz`>46O}!G4@Og;z7QsR_yIOMrG)%PNkmSdR<4K8GueZf3ptfLN6)8rOFC* zLKU~bE9T@~XcrGs58p}c~ zwb*?u%-sj{(?kat%O%MVnRIq&5u}dSScw;{+D!7%^gQOt7w4A(3`}YCA5ww!8(JH^jwS|#+3BkoT0qeT`csz4#dnKkc5Auo9$L;m>dgES6KVMjH5Em|-q_@w?)?gDB zalD>d&#f1|UxsAS*Z$T7{;x)T7vZEf@`Gi}f!$XpSuA?j69tvy8wvY263%bQUaKc6h-(d@i8mAiVtQ?X+GJfP2QC zzBD8T>#O}ZJIXysH7aha(ZfY|@70^VQwgb^Yo;}UPI^p>IbahvxXy7zuzE47)4Ud{ zGaHsY1FzscA%rk8ER{)D^b0c@A~>U6<9>QC$dx-fR zVssyLHz1adMgBSVRiWej6}^f)7(X<@A;lRQYq2cHE)X#F z$uiaQx5iNJw)g;=VW`B`Lrj~|GD4ff$kszPw>2AL4kB$r#-NNY#`Vmt@~D8z-~pwI z%TUSHJ0!g&+dpKl5u`{f35LsSJ1Q{_ha9AyNpI0Y`%ir^Tpg%zB32x=-y>h?-8yKG z5eH=2LFD$cX5om6OPY1cdY!HI8j`B%V`4bGyi3>5*{+OI5)4dDx*d((;#Vgk7&O|3 z`fEUoA?e={8w9h7`EKL_@%S5VhIMmmKGNi>pthZ+md4F%%Pi&bvG0q=`ly1^>`GL# zl++w{d#z52tLV$VrK%R>rd@plx)tfwAUf&6|uq^4WA0=Q9rgI`gzL|K5SRBMDB?53P1O=$PN?k zU_DY_Y43^7A!k_p%u?+(8owtz9x*i(ccUXbqYWF{OT%_qOw@&ZWMMp)sa#{zPMRqi=&35wvLr*d4$TI9dm3Uh z^K=X2cNV^!DFW|FO$5!zi4pW)aFtjJBnuz4V_kV+|s};fUOzsqZ|E1x2)DmZquiNAl09W zxybV3{~!o4$r$#P9*WI=!)?MauBy∈=wZWsqY^BfZBLrTow&IgAeM6SN>Fz9)HS z^da_Qk03V{;9MX7T_q|8RQfy=?$yrgb~twUv?P^sMYuiHwjAl&=B*iFhvp*~e>(-A z=5l>_*`!7BG!Ps%bj^MPW~GDuRaLOr1baF}^8%(EZf{0~&f)~l#e`cfyHh+Hz_J+o z)E*_h=R}l}aa?${X)l)WE&0m=G1E>S+CZa~LM|w67^oTLm>KPC1ea+d&PU*JKUd+M zBd(ZJb7iHy_cF`U>=NA3Bm|9LV@*DsgwL9;*Z_S;OFq|`@O8v#t%0AfrvFNztYz3CK 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 XK*-<=za<$CheYduR8=hData Infrastructure Engineer | OpenAI | OpenAI", + self.resume_improver.job_post_html_data, + "HTML title not found in job post data", + ) + self.assertIn( + "Data Infrastructure Engineer", + self.resume_improver.job_post_raw, + "Job title not found in raw job post data", + ) + + # Check parsed job data + self.assertIsNotNone(self.resume_improver.parsed_job, "Parsed job data is None") + self.assertIsInstance( + self.resume_improver.parsed_job, dict, "Parsed job data is not a dictionary" + ) + + # Check specific fields in parsed job data + self.assertIsNotNone( + self.resume_improver.parsed_job.get("job_summary"), "Job summary is None" + ) + self.assertGreater( + len(self.resume_improver.parsed_job.get("qualifications", [])), + 0, + "Qualifications list is empty", + ) + self.assertGreater( + len(self.resume_improver.parsed_job.get("duties", [])), + 0, + "Duties list is empty", + ) + self.assertGreater( + len(self.resume_improver.parsed_job.get("ats_keywords", [])), + 0, + "ATS keywords list is empty", + ) + + # Check specific values in parsed job data + self.assertNotEqual( + self.resume_improver.parsed_job.get("is_fully_remote"), + True, + "Job is incorrectly marked as fully remote", + ) + self.assertIn( + "$200K – $385K", + self.resume_improver.parsed_job.get("salary", ""), + "Expected salary range not found", + ) + self.assertIn( + "data infrastructure engineer", + self.resume_improver.parsed_job.get("job_title", "").lower(), + "Expected job title not found", + ) + self.assertIn( + "openai", + self.resume_improver.parsed_job.get("company", "").lower(), + "Expected company name not found", + ) + self.assertIn( + "python", + ", ".join(self.resume_improver.parsed_job.get("ats_keywords", [])).lower(), + "Expected ATS keyword 'python' not found", + ) + self.assertIn( + "4+ years in data infrastructure engineering", + ", ".join( + self.resume_improver.parsed_job.get("qualifications", []) + ).lower(), + "Expected qualification not found", + ) + self.assertIn( + "design, build, and maintain data infrastructure systems", + ", ".join(self.resume_improver.parsed_job.get("duties", [])).lower(), + "Expected duty not found", + ) def test_create_draft_tailored_resume(self): - self.resume_improver.create_draft_tailored_resume() + self.resume_improver.create_draft_tailored_resume( + auto_open=False, manual_review=False + ) self.assertTrue(self.resume_improver.yaml_loc.endswith("resume.yaml")) + class TestLangchainHelpers(unittest.TestCase): def test_create_llm(self): llm = create_llm() self.assertIsNotNone(llm) - def test_format_list_as_string(self): - result = format_list_as_string(["item1", "item2"]) - self.assertEqual(result, "\n- item1\n- item2") - - def test_format_prompt_inputs_as_strings(self): - result = format_prompt_inputs_as_strings(["key1", "key2"], key1="value1", key2="value2") - self.assertEqual(result, {"key1": "value1", "key2": "value2"}) - - def test_parse_date(self): - date = parse_date("2023-01-01") - self.assertEqual(date.year, 2023) - - def test_datediff_years(self): - diff = datediff_years("2020-01-01", "2023-01-01") - self.assertEqual(diff, 3.0) if __name__ == "__main__": unittest.main() diff --git a/tests/test_utils.py b/tests/test_utils.py index 3edd2e2..122d7e5 100644 --- a/tests/test_utils.py +++ b/tests/test_utils.py @@ -6,17 +6,25 @@ get_dict_field, ) import os +from ..config import config class TestYamlHandler(unittest.TestCase): def test_read_yaml(self): - data = read_yaml(filename="data/sample_resume.yaml") + data = read_yaml(filename=os.path.join(config.DATA_PATH, "sample_resume.yaml")) self.assertIsInstance(data, dict) def test_write_yaml(self): data = {"key": "value"} - write_yaml(data, filename="data/test_output.yaml") - self.assertTrue(os.path.exists("data/test_output.yaml")) + write_yaml( + data, + filename=os.path.join(config.DATA_PATH, "tests_example/test_output.yaml"), + ) + self.assertTrue( + os.path.exists( + os.path.join(config.DATA_PATH, "tests_example/test_output.yaml") + ) + ) def test_dict_to_yaml_string(self): data = {"key": "value"} @@ -26,7 +34,7 @@ def test_dict_to_yaml_string(self): class TestFileHandler(unittest.TestCase): def test_read_jobfile(self): - content = read_jobfile("data/sample_job_posting.txt") + content = read_jobfile(os.path.join(config.DATA_PATH, "tests_example/job.yaml")) self.assertIsInstance(content, str) def test_generator_key_in_nested_dict(self):