قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب URL | خدمات أمازون ويب

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب URL | خدمات أمازون ويب

في العالم الرقمي اليوم، يفضل معظم المستهلكين العثور على إجابات لأسئلة خدمة العملاء الخاصة بهم بأنفسهم بدلاً من قضاء الوقت في التواصل مع الشركات و/أو مقدمي الخدمات. يستكشف منشور المدونة هذا حلاً مبتكرًا لبناء برنامج الدردشة الآلي للأسئلة والأجوبة أمازون ليكس يستخدم الأسئلة الشائعة الموجودة من موقع الويب الخاص بك. يمكن لهذه الأداة المدعمة بالذكاء الاصطناعي تقديم ردود سريعة ودقيقة على الاستفسارات الواقعية، مما يسمح للعميل بحل المشكلات الشائعة بسرعة وسهولة بشكل مستقل.

استيعاب عنوان URL واحد

لدى العديد من المؤسسات مجموعة منشورة من الإجابات للأسئلة الشائعة لعملائها متاحة على موقعها الإلكتروني. في هذه الحالة، نريد أن نقدم للعملاء برنامج chatbot يمكنه الإجابة على أسئلتهم من خلال الأسئلة الشائعة المنشورة لدينا. في تدوينة بعنوان قم بتحسين Amazon Lex من خلال ميزات الأسئلة الشائعة للمحادثة باستخدام LLMs، لقد أوضحنا كيف يمكنك استخدام مزيج من Amazon Lex وLlamaIndex لإنشاء روبوت محادثة مدعوم بمصادر المعرفة الحالية لديك، مثل مستندات PDF أو Word. لدعم الأسئلة الشائعة البسيطة، استنادًا إلى موقع ويب للأسئلة الشائعة، نحتاج إلى إنشاء عملية استيعاب يمكنها الزحف إلى موقع الويب وإنشاء عمليات تضمين يمكن استخدامها بواسطة LlamaIndex للإجابة على أسئلة العملاء. في هذه الحالة، سوف نبني على الروبوت الذي تم إنشاؤه في مشاركة المدونة السابقة، الذي يستعلم عن هذه التضمينات بنطق المستخدم ويعيد الإجابة من الأسئلة الشائعة لموقع الويب.

يوضح الرسم البياني التالي كيفية عمل عملية العرض وروبوت Amazon Lex معًا من أجل التوصل إلى الحل الذي نقدمه.

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب عنوان URL | أمازون ويب سيرفيسز PlatoBlockchain Data Intelligence. البحث العمودي. منظمة العفو الدولية.

في سير عمل الحل، يتم استيعاب موقع الويب الذي يحتوي على الأسئلة الشائعة عبر AWS لامدا. تقوم وظيفة Lambda هذه بالزحف إلى موقع الويب وتخزين النص الناتج في ملف خدمة تخزين أمازون البسيطة دلو (أمازون S3). تقوم مجموعة S3 بعد ذلك بتشغيل وظيفة Lambda التي تستخدم LlamaIndex لإنشاء عمليات التضمين المخزنة في Amazon S3. عندما يصل سؤال من المستخدم النهائي، مثل "ما هي سياسة الإرجاع الخاصة بك؟"، يستخدم روبوت Amazon Lex وظيفة Lambda الخاصة به للاستعلام عن التضمينات باستخدام نهج قائم على RAG مع LlamaIndex. لمزيد من المعلومات حول هذا النهج والمتطلبات المسبقة، راجع منشور المدونة، قم بتحسين Amazon Lex من خلال ميزات الأسئلة الشائعة للمحادثة باستخدام LLMs.

بعد اكتمال المتطلبات المسبقة من المدونة المذكورة أعلاه، فإن الخطوة الأولى هي استيعاب الأسئلة الشائعة في مستودع المستندات الذي يمكن توجيهه وفهرسته بواسطة LlamaIndex. يوضح الكود التالي كيفية تحقيق ذلك:

import logging
import sys
import requests
import html2text
from llama_index.readers.schema.base import Document
from llama_index import GPTVectorStoreIndex
from typing import List logging.basicConfig(stream=sys.stdout, level=logging.INFO)
logging.getLogger().addHandler(logging.StreamHandler(stream=sys.stdout)) class EZWebLoader: def __init__(self, default_header: str = None): self._html_to_text_parser = html2text() if default_header is None: self._default_header = {"User-agent":"Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/47.0.2526.80 Safari/537.36"} else: self._default_header = default_header def load_data(self, urls: List[str], headers: str = None) -> List[Document]: if headers is None: headers = self._default_header documents = [] for url in urls: response = requests.get(url, headers=headers).text response = self._html2text.html2text(response) documents.append(Document(response)) return documents url = "http://www.zappos.com/general-questions"
loader = EZWebLoader()
documents = loader.load_data([url])
index = GPTVectorStoreIndex.from_documents(documents)

في المثال السابق، نأخذ عنوان URL لموقع الأسئلة الشائعة المحدد مسبقًا من Zappos ونستوعبه باستخدام EZWebLoader فصل. في هذا الفصل، انتقلنا إلى عنوان URL وقمنا بتحميل جميع الأسئلة الموجودة في الصفحة في فهرس. يمكننا الآن طرح سؤال مثل "هل لدى Zappos بطاقات هدايا؟" واحصل على الإجابات مباشرة من الأسئلة الشائعة على الموقع. تُظهر لقطة الشاشة التالية وحدة اختبار روبوت Amazon Lex وهي تجيب على هذا السؤال من الأسئلة الشائعة.

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب عنوان URL | أمازون ويب سيرفيسز PlatoBlockchain Data Intelligence. البحث العمودي. منظمة العفو الدولية.

لقد تمكنا من تحقيق ذلك لأننا قمنا بالزحف إلى عنوان URL في الخطوة الأولى وقمنا بإنشاء عمليات تضمين يمكن أن يستخدمها LlamaIndex للبحث عن إجابة سؤالنا. تعرض وظيفة Lambda الخاصة بالروبوت الخاص بنا كيفية تشغيل هذا البحث عند إرجاع الهدف الاحتياطي:

import time
import json
import os
import logging
import boto3
from llama_index import StorageContext, load_index_from_storage logger = logging.getLogger()
logger.setLevel(logging.DEBUG) def download_docstore(): # Create an S3 client s3 = boto3.client('s3') # List all objects in the S3 bucket and download each one
try: bucket_name = 'faq-bot-storage-001' s3_response = s3.list_objects_v2(Bucket=bucket_name) if 'Contents' in s3_response: for item in s3_response['Contents']: file_name = item['Key'] logger.debug("Downloading to /tmp/" + file_name) s3.download_file(bucket_name, file_name, '/tmp/' + file_name) logger.debug('All files downloaded from S3 and written to local filesystem.') except Exception as e: logger.error(e)
raise e #download the doc store locally
download_docstore() storage_context = StorageContext.from_defaults(persist_dir="/tmp/")
# load index
index = load_index_from_storage(storage_context)
query_engine = index.as_query_engine() def lambda_handler(event, context): """
Route the incoming request based on intent.
The JSON body of the request is provided in the event slot. """ # By default, treat the user request as coming from the America/New_York time zone. os.environ['TZ'] = 'America/New_York' time.tzset() logger.debug("===== START LEX FULFILLMENT ====") logger.debug(event) slots = {} if "currentIntent" in event and "slots" in event["currentIntent"]: slots = event["currentIntent"]["slots"] intent = event["sessionState"]["intent"] dialogaction = {"type": "Delegate"} message = [] if str.lower(intent["name"]) == "fallbackintent": #execute query from the input given by the user response = str.strip(query_engine.query(event["inputTranscript"]).response) dialogaction["type"] = "Close" message.append({'content': f'{response}', 'contentType': 'PlainText'}) final_response = { "sessionState": { "dialogAction": dialogaction, "intent": intent }, "messages": message } logger.debug(json.dumps(final_response, indent=1)) logger.debug("===== END LEX FULFILLMENT ====") return final_response

يعمل هذا الحل بشكل جيد عندما تحتوي صفحة ويب واحدة على جميع الإجابات. ومع ذلك، فإن معظم مواقع الأسئلة الشائعة ليست مبنية على صفحة واحدة. على سبيل المثال، في مثال Zappos الخاص بنا، إذا طرحنا السؤال "هل لديك سياسة مطابقة الأسعار؟"، فسنحصل على إجابة أقل من مرضية، كما هو موضح في لقطة الشاشة التالية.

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب عنوان URL | أمازون ويب سيرفيسز PlatoBlockchain Data Intelligence. البحث العمودي. منظمة العفو الدولية.

في التفاعل السابق، لم تكن إجابة سياسة مطابقة الأسعار مفيدة لمستخدمينا. هذه الإجابة قصيرة لأن الأسئلة الشائعة المشار إليها هي رابط لصفحة معينة حول سياسة مطابقة الأسعار وكان زحف الويب الخاص بنا مخصصًا للصفحة الواحدة فقط. إن الحصول على إجابات أفضل يعني الزحف إلى هذه الروابط أيضًا. يوضح القسم التالي كيفية الحصول على إجابات للأسئلة التي تتطلب مستويين أو أكثر من عمق الصفحة.

الزحف على المستوى N

عندما نقوم بالزحف إلى صفحة ويب لمعرفة الأسئلة الشائعة، يمكن تضمين المعلومات التي نريدها في الصفحات المرتبطة. على سبيل المثال، في مثال Zappos الخاص بنا، نطرح السؤال "هل لديك سياسة مطابقة الأسعار؟" والجواب هو "نعم يرجى الزيارة لتعلم المزيد." إذا سأل شخص ما "ما هي سياسة مطابقة الأسعار الخاصة بك؟" ثم نريد أن نقدم إجابة كاملة مع السياسة. ويعني تحقيق ذلك أننا بحاجة إلى اجتياز الروابط للحصول على المعلومات الفعلية لمستخدمنا النهائي. أثناء عملية الاستيعاب، يمكننا استخدام أداة تحميل الويب الخاصة بنا للعثور على روابط الربط لصفحات HTML الأخرى ثم اجتيازها. يسمح لنا تغيير التعليمات البرمجية التالي في زاحف الويب الخاص بنا بالعثور على الروابط في الصفحات التي نزحف إليها. ويتضمن أيضًا بعض المنطق الإضافي لتجنب الزحف الدائري والسماح بالتصفية حسب البادئة.

import logging
import requests
import html2text
from llama_index.readers.schema.base import Document
from typing import List
import re def find_http_urls_in_parentheses(s: str, prefix: str = None): pattern = r'((https?://[^)]+))' urls = re.findall(pattern, s) matched = [] if prefix is not None: for url in urls: if str(url).startswith(prefix): matched.append(url) else: matched = urls return list(set(matched)) # remove duplicates by converting to set, then convert back to list class EZWebLoader: def __init__(self, default_header: str = None): self._html_to_text_parser = html2text if default_header is None: self._default_header = {"User-agent":"Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/47.0.2526.80 Safari/537.36"} else: self._default_header = default_header def load_data(self, urls: List[str], num_levels: int = 0, level_prefix: str = None, headers: str = None) -> List[Document]: logging.info(f"Number of urls: {len(urls)}.") if headers is None: headers = self._default_header documents = [] visited = {} for url in urls: q = [url] depth = num_levels for page in q: if page not in visited: #prevent cycles by checking to see if we already crawled a link logging.info(f"Crawling {page}") visited[page] = True #add entry to visited to prevent re-crawling pages response = requests.get(page, headers=headers).text response = self._html_to_text_parser.html2text(response) #reduce html to text documents.append(Document(response)) if depth > 0: #crawl linked pages ingest_urls = find_http_urls_in_parentheses(response, level_prefix) logging.info(f"Found {len(ingest_urls)} pages to crawl.") q.extend(ingest_urls) depth -= 1 #reduce the depth counter so we go only num_levels deep in our crawl else: logging.info(f"Skipping {page} as it has already been crawled") logging.info(f"Number of documents: {len(documents)}.") return documents url = "http://www.zappos.com/general-questions"
loader = EZWebLoader()
#crawl the site with 1 level depth and prefix of "/c/" for customer service root
documents = loader.load_data([url], num_levels=1, level_prefix="https://www.zappos.com/c/")
index = GPTVectorStoreIndex.from_documents(documents)

في التعليمة البرمجية السابقة، قدمنا ​​القدرة على الزحف إلى مستويات N بعمق، وأعطينا بادئة تسمح لنا بتقييد الزحف إلى الأشياء التي تبدأ بنمط عنوان URL معين فقط. في مثال Zappos الخاص بنا، جميع صفحات خدمة العملاء متجذرة منها zappos.com/c، لذلك قمنا بتضمين ذلك كبادئة لقصر عمليات الزحف لدينا على مجموعة فرعية أصغر وأكثر صلة. يوضح الكود كيف يمكننا استيعاب ما يصل إلى مستويين عميقين. يظل منطق Lambda الخاص بالروبوت الخاص بنا كما هو لأنه لم يتغير شيء باستثناء أن الزاحف يستوعب المزيد من المستندات.

لقد قمنا الآن بفهرسة جميع المستندات ويمكننا طرح سؤال أكثر تفصيلاً. في لقطة الشاشة التالية، يقدم الروبوت الخاص بنا الإجابة الصحيحة على السؤال "هل لديك سياسة مطابقة الأسعار؟"

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب عنوان URL | أمازون ويب سيرفيسز PlatoBlockchain Data Intelligence. البحث العمودي. منظمة العفو الدولية.

لدينا الآن إجابة كاملة على سؤالنا حول مطابقة الأسعار. فبدلاً من أن يُقال لنا ببساطة "نعم، راجع سياستنا"، فهو يقدم لنا تفاصيل من عملية الزحف من المستوى الثاني.

تنظيف

لتجنب تكبد نفقات مستقبلية، تابع حذف جميع الموارد التي تم نشرها كجزء من هذا التمرين. لقد قدمنا ​​برنامجًا نصيًا لإغلاق نقطة نهاية Sagemaker بأمان. تفاصيل الاستخدام موجودة في الملف README. بالإضافة إلى ذلك، لإزالة كافة الموارد الأخرى التي يمكنك تشغيلها cdk destroy في نفس الدليل مثل أوامر cdk الأخرى لإلغاء توفير جميع الموارد في المكدس الخاص بك.

وفي الختام

تتيح القدرة على استيعاب مجموعة من الأسئلة الشائعة في برنامج الدردشة الآلي لعملائك العثور على إجابات لأسئلتهم من خلال استعلامات واضحة ومباشرة باللغة الطبيعية. من خلال الجمع بين الدعم المدمج في Amazon Lex للتعامل الاحتياطي مع حل RAG مثل LlamaIndex، يمكننا توفير مسار سريع لعملائنا للحصول على إجابات مرضية ومنسقة ومعتمدة للأسئلة الشائعة. من خلال تطبيق الزحف على المستوى N في حلنا، يمكننا السماح بإجابات يمكن أن تمتد عبر روابط الأسئلة الشائعة المتعددة وتقديم إجابات أعمق لاستفسارات عملائنا. من خلال اتباع هذه الخطوات، يمكنك دمج إمكانات الأسئلة والأجوبة القوية القائمة على LLM واستيعاب عنوان URL الفعال في برنامج الدردشة الآلي Amazon Lex الخاص بك بسلاسة. وينتج عن ذلك تفاعلات أكثر دقة وشمولية ووعيًا بالسياق مع المستخدمين.


عن المؤلفين

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب عنوان URL | أمازون ويب سيرفيسز PlatoBlockchain Data Intelligence. البحث العمودي. منظمة العفو الدولية.ماكس هنكل والاس هو مهندس تطوير برمجيات في AWS Lex. إنه يستمتع بالعمل على الاستفادة من التكنولوجيا لتحقيق أقصى قدر من نجاح العملاء. خارج العمل ، إنه متحمس للطهي وقضاء الوقت مع الأصدقاء وحقائب الظهر.

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب عنوان URL | أمازون ويب سيرفيسز PlatoBlockchain Data Intelligence. البحث العمودي. منظمة العفو الدولية.سونغ فنغ هو عالم تطبيقي أقدم في مختبرات AWS AI ، متخصص في معالجة اللغة الطبيعية والذكاء الاصطناعي. يستكشف بحثها جوانب مختلفة من هذه المجالات بما في ذلك نمذجة الحوار المستند إلى المستندات ، والتفكير في الحوارات الموجهة نحو المهام ، وتوليد النص التفاعلي باستخدام البيانات متعددة الوسائط.

قم بتحسين Amazon Lex باستخدام LLMs وتحسين تجربة الأسئلة الشائعة باستخدام استيعاب عنوان URL | أمازون ويب سيرفيسز PlatoBlockchain Data Intelligence. البحث العمودي. منظمة العفو الدولية.جون بيكر هو SDE رئيسي في AWS حيث يعمل على معالجة اللغات الطبيعية ونماذج اللغات الكبيرة وغيرها من المشاريع ذات الصلة بالتعلم الآلي/الذكاء الاصطناعي. لقد عمل مع Amazon لأكثر من 9 سنوات وعمل عبر AWS وAlexa وAmazon.com. في أوقات فراغه، يستمتع جون بالتزلج والأنشطة الخارجية الأخرى في جميع أنحاء شمال غرب المحيط الهادئ.

الطابع الزمني:

اكثر من التعلم الآلي من AWS