Azure Static Web Apps Community: Criação de uma App (RAG) com App Spaces e Azure Static Web Apps

Azure Static Web Apps Community: Criação de uma App (RAG) com App Spaces e Azure Static Web Apps

This article is contributed. See the original author and article here.

thumb.jpg


 


No último encontro da Comunidade Azure Static Web Apps através do Canal do Youtube – Microsoft Azure Developers, foi demonstrado como se pode criar uma aplicação de Geração Aumentada por Recuperação (RAG) utilizando o Azure Static Web Apps e o App Spaces.


 


O evento foi conduzido pelo Dheeraj Bandaru, que é Product Manager do Azure Static Web Apps na Microsoft. Dheeraj contou com a participação do Skyler Hardle, que é Senior Manager do Apps Spaces na Microsoft.


 


Skyler, apresentou um guia prático sobre a integração entre esses serviços e a implementação de uma aplicação RAG (Retrieval Augmented Generation). A seguir, compartilharei com vocês o que foi abordado durante o evento, detalhando a arquitetura da aplicação e as etapas de desenvolvimento.


 


Mas, antes precisamos entender esse novo serviço e como ele pode ser útil para a criação de aplicações modernas.


Inclusive, se você deseja assistir ao evento na íntegra, poderá acessar o link abaixo:


 


 


 


O que é o App Spaces?


 


 


App Spaces é um serviço inteligente para desenvolvedores que reduz a complexidade de criar e gerenciar aplicações web. Ele ajuda a identificar os serviços corretos para suas aplicações no Azure e proporciona uma experiência de gerenciamento simplificada para o processo de desenvolvimento.


 


App Spaces também oferece os benefícios de implantar uma aplicação através dos serviços existentes do Azure, como Azure Container Apps e Azure Static Web Apps, com uma experiência focada no desenvolvimento e implantação de forma simplificada e rápida.


 


Resumindo….


 


app-spaces-definition.png


 


App Spaces é a maneira mais rápida de implantar e gerenciar suas cargas de trabalho de aplicativos inteligentes, sem ser um especialista em nuvem.


 


 


O que é Geraçaõ Aumentada por Recuperação (RAG)?


 


Geração Aumentada por Recuperação (RAG) é uma técnica que combina a recuperação de informações externas com a geração de respostas por modelos de linguagem (LLMs).


 


Essa abordagem permite enriquecer o contexto dos modelos de IA, proporcionando respostas mais precisas e relevantes. No caso do nosso aplicativo, utilizamos bancos de dados vetoriais para armazenar documentos e embeddings, permitindo uma recuperação eficiente e contextualizada de informações.


 


Primeiro, alguns conceitos básicos sobre RAG


 


Os grandes modelos de linguagem (LLMs) como o ChatGPT são treinados com dados públicos disponíveis na internet no momento do treinamento. Eles podem responder a perguntas relacionadas aos dados nos quais foram treinados. No entanto, esses dados públicos podem não ser suficientes para atender a todas as suas necessidades.


 


Você pode querer respostas baseadas em seus dados privados ou os dados públicos podem simplesmente estar desatualizados. A solução para esse problema é a Geração Aumentada por Recuperação (RAG), um padrão usado em IA que utiliza um LLM para gerar respostas com base em seus próprios dados.


 


Como o RAG Funciona?


 


RAG é um padrão que usa seus dados com um LLM para gerar respostas específicas aos seus dados. Quando um usuário faz uma pergunta, o armazenamento de dados é pesquisado com base na entrada do usuário. A pergunta do usuário é então combinada com os resultados correspondentes e enviada ao LLM usando um prompt (instruções explícitas para um modelo de IA ou aprendizado de máquina) para gerar a resposta desejada. Isso pode ser ilustrado da seguinte forma.


 


A imagem abaixo representa o fluxo de trabalho do RAG:


 


rag-workflow.png


 


Se você deseja saber mais sobre o RAG, recomendo a leitura do artigo Geração Aumentada por Recuperação (RAG).


 


 


Arquitetura do Aplicativo RAG com App Spaces


 


No evento, Skyler apresentou a arquitetura do aplicativo RAG que seria desenvolvido durante a apresentação. um frontend em React, um backend em FastAPI e um banco de dados vetorial. Esses componentes trabalham juntos para fornecer uma solução completa e integrada. Abaixo, detalho o funcionamento de cada um desses componentes.


 


A seguir, detalharei cada um desses componentes.


 


Frontend com React


 


O frontend do aplicativo é desenvolvido em React e faz chamadas a um backend FastAPI para buscar e armazenar embeddings em um banco de dados vetorial (Quadrant). A interface do usuário permite inserir perguntas e visualizar as respostas geradas pelo sistema.


 


Backend com FastAPI


 


O backend é responsável por duas funcionalidades principais:


 




  1. Gerar e armazenar embeddings: Utiliza a API de embeddings do OpenAI para gerar vetores a partir do texto fornecido e armazená-los no banco de dados vetorial.




  2. Recuperar e gerar respostas: Busca embeddings relevantes no banco de dados vetorial e utiliza o OpenAI GPT-4 para gerar respostas baseadas nesses embeddings.




 


app-running.png


 


Banco de Dados Vetorial


 


Para a aplicação foi utilizado o Quadrant, um banco de dados vetorial que permite armazenar e recuperar embeddings de forma eficiente. O Quadrant é uma solução escalável e de alto desempenho para aplicações que requerem a recuperação de informações relevantes com base em consultas feitas pelo usuário.


 


Implementação da Aplicação RAG


 


Configuração Inicial


 


Para começar, acesse o App Spaces no portal Azure e selecione a opção para criar um novo ‘space’ de aplicação. Você pode escolher um repositório do GitHub ou utilizar um dos templates fornecidos, como o RAG App. Configure as variáveis de ambiente necessárias, incluindo as chaves da API do OpenAI.


 


rag-app-spaces.png


 


Implantação do Frontend


 


O frontend da aplicação é uma aplicação React que pode ser implantado no Azure Static Web Apps. Para isso, basta configurar o repositório do GitHub e definir o diretório de saída da aplicação. O Azure Static Web Apps irá criar automaticamente um pipeline de CI/CD para implantar a aplicação.


 


aswa-app.png


 


Configuração e Implantação do Backend


 


O backend em FastAPI é implantado usando o Azure Container Apps no Azure. Ele manipula as requisições de geração e armazenamento de embeddings, bem como a recuperação e geração de respostas.


 


backend-app.png


 


Demonstração da Aplicação RAG


 




  • Inserindo e Armazenando Texto: O usuário insere um texto no frontend, que é enviado ao backend para gerar e armazenar embeddings no banco de dados vetorial.




 




  • Fazendo Perguntas e Recebendo Respostas: O usuário faz perguntas através do frontend, que são processadas pelo backend para buscar embeddings relevantes e gerar respostas utilizando o GPT-4 da OpenAI.




 


app-demo.png


 


Se desejar saber mais da aplicação desenvolvida no evento, poderá acessar o repositório do GitHub app-spaces-rag-app


 


Inclusive, Julia Muiruri, que é Developer Advocate na Microsoft, gravou um vídeo sobre a aplicação desenvolvida no evento. Você pode assistir o vídeo abaixo:


 


 


Gerenciamento e Extensibilidade


 


App Spaces facilita a adição de novos componentes a sua aplicação, como novos frontends ou integrações com outros serviços. A interface de gerenciamento permite visualizar logs, métricas e configurar variáveis de ambiente de forma intuitiva.


 


O mais interessante disso tudo é que independente da linguagem de programação no lado do Backend, você pode utilizar o App Spaces para gerenciar e implantar sua aplicação. Seja você um desenvolvedor Python, .NET, Node.js, Java, Go, etc., o App Spaces é uma excelente opção para gerenciar suas aplicações.


 


Se desejar ver outros exemplos de aplicações em diferentes linguagens de programação, poderá acessar o repositório do GitHub app-spaces-samples.


 


repo-spaces-repo.png


 


E, já recomendo em você começar agora a testar o App Spaces! Você pode começar a testar de forma totalmente gratuita. Acesse agora: AQUI ou clicando na imagem abaixo:


 


try-it-now.png


 


Conclusão


 


No encontro da comunidade Azure Static Web Apps, aprendemos a criar uma aplicação de Geração Aumentada por Recuperação (RAG) utilizando Azure Static Web Apps e App Spaces. Exploramos a arquitetura da aplicação, configuramos os componentes necessários e implementamos uma solução prática que enriquece o contexto dos modelos de IA, proporcionando respostas mais precisas e relevantes.


 


Lembrando que você poder rever o evento na íntegra, acessando o link abaixo:


 



 


Microsoft Reactor YouTube Channel


 


Você sabia que temos uma das maiores comunidades com temas diversos sobre tecnologia, nuvem e desenvolvimento de software? Não! Então, você precisa conhecer o Microsoft Reactor.


 



 


Além disso conta com inúmeros eventos online, presenciais, workshops, meetups e muito mais. Acesse o link da página oficial do Microsoft Reactor e inscreva-se no canal para ficar por dentro de tudo que acontece na comunidade.


 


reactor-page.png


 


Recursos Adicionais


 


Gostou do App Spaces? Quer saber mais sobre o serviço e como ele pode ajudar a simplificar o desenvolvimento de aplicações web? Ou melhor, quer aprender através de um tutorial prático como criar uma aplicação com App Spaces?


 


Deixarei abaixo alguns links que poderão te ajudar a explorar mais sobre o App Spaces e como ele pode ser útil para o desenvolvimento de aplicações modernas.


 



 


Espero que tenha gostado do artigo e que ele tenha sido útil para você. Se tiver alguma dúvida ou sugestão, não hesite em deixar um comentário abaixo.


 


Até a próxima! :cool:

What's New in Copilot for Sales – July 2024

What's New in Copilot for Sales – July 2024

This article is contributed. See the original author and article here.

Microsoft Copilot for Sales is reimagining sales. Integrated seamlessly into your daily tools across Microsoft 365 and Teams, Copilot for Sales harnesses the power of generative AI and customer data to keep sellers in their flow of work so they can spend more time with customers.


 


This month, we’re excited to bring capabilities to help sellers save time when collaborating with seamless sharing of key email info from Outlook to Teams, enable sellers to stay ahead of activities with meeting prep notes and recent emails, and enable sellers to receive suggested CRM updates in even more languages!  


 


As always, we invite you to get started, learn more, and stay connected! See you next month!


 


Capabilities highlighted below are included in the July release of Copilot for Sales. It may take time for specific capabilities to reach every tenant in each market.


 


In Outlook


 



Share key email information easily from Outlook to Teams


 


Today, sellers face challenges in efficiently sharing crucial customer information received via Outlook with their sales team members on Teams. Currently, they resort to manual copying and pasting of information, searching for the appropriate recipient, and then initiating a chat or posting in the right channel on Teams to share it.


 


With this release, we’re introducing seamless sharing to Teams in the seller’s flow of work in Outlook to help sales teams quickly start a Teams discussion with up-to-date and relevant information that can move a deal forward. Now, sellers can:



  • Share key email information with their colleagues in Teams

  • Add preamble text before sharing

  • Review and modify key email info before sharing

  • Share to any location in Teams ─ with a person, in a group chat, or in a Teams channel


Example of user flow for sharing key email info to Teams using Copilot for SalesExample of user flow for sharing key email info to Teams using Copilot for Sales


 


Find more details in our product documentation


 



Full language support in suggested CRM updates


 


Sellers are busy and today updating information crucial for their businesses directly in their CRM requires manual work. Bringing the ability to update their CRM to the flow of work for quick updates, sellers can save time and be more efficient.


 


This month, we’re excited to announce the rollout of additional language support for suggested CRM updates. Prior to this release, four languages were supported; this expansion enables Copilot for Sales to provide suggested updates in ten languages* for:


 



  • Monetary value changes (like budgets, revenue, fees etc.)

  • Timeline changes

  • Stage progression changes for an opportunity.


* Discover all the details at our supported languages page.


 


The fields a seller can update depend on their CRM permissions as well as which editable fields are enabled by the admins. Calculate fields, and all other scenarios will deep link to their CRM.


 


Screenshot of suggested CRM updates user interfaceScreenshot of suggested CRM updates user interface


 


In Teams


 



Stay ahead of activities with meeting prep notes and recent emails


 


Sellers and sales managers preparing for a meeting sift through vast amounts of data from a variety of sources, including their CRM, a time consuming and sometimes overwhelming activity. This can lead to information overload and potentially cause difficulty in prioritizing the most relevant details for their meeting.


We’re pleased to announce two new capabilities in our meeting prep to help both sellers and sales managers stay ahead of their most impactful activities! Starting with our July release:  



  • A meeting prep card will be sent about an hour* before a meeting instead of just as the meeting starts. (admin configuration settings coming soon!)

  • Recent emails in meeting prep now contain information about the last 2 emails sharing the same external contacts who are participating in the meeting.


*card will appear 45-75 minutes prior to meeting start time


 


Screenshot of meeting prep info card inside Teams.Screenshot of meeting prep info card inside Teams.


 



Get started


 


Ready to join us and other top-performing sales organizations worldwide? Reach out to your Microsoft sales team or visit our product web page.


 


Ready to install Copilot for Sales? Have a look at our deployment guide for Dynamics 365 Sales users or our deployment guide for Salesforce users.


 



Learn more


 


Ready for all the details? Check out the Copilot for Sales product documentation.


 


Ready for the latest tips…and more? Copilot for Sales Tip Time can serve as a foundation for your training of Copilot for Sales users, customers, or partners! This content includes use cases and demonstrates how each feature will benefit sellers, administrators, and sales managers. 


 


Looking for the latest adoption resources? Visit the Copilot for Sales Adoption Center and find the latest information about how to go from inspiration to adoption. 



Stay connected


 


Want to stay connected? Learn about the latest improvements before everyone else at https://aka.ms/salescopilotupdates. Join our community in the community discussion forum and we always welcome your feedback and ideas in our product feedback portal.


 

Integrating Azure Content Safety with API Management for Azure OpenAI Endpoints

Integrating Azure Content Safety with API Management for Azure OpenAI Endpoints

This article is contributed. See the original author and article here.

In today’s digital landscape, ensuring the safety and integrity of AI-generated content is paramount. Azure Content Safety, combined with Azure API Management, provides a robust solution for managing and securing Azure OpenAI endpoints. This blog will guide you through the integration process, focusing on text analysis and prompt shields.


 


content-filtering.gif


 


What is Azure Content Safety?


 


Azure AI Content Safety provides analysis for user and AI generated content. Currently available APIs include


 



  • Prompt Shields: scans user text and document text for input attacks on LLMs

  • Groundedness Detection: Verify if the response generated by the LLMs are grounded in the source provided

  • Protected material text detection: checks for existence of copyrighted material in the AI generated response

  • Analyze Text/Image: identifies and categorizes text severity against sexual content, hate, violence and self-harm 


 


Why Integrate Azure Content Safety?


 


Azure Content Safety offers advanced algorithms to detect and mitigate harmful content in both user prompts and AI-generated outputs. By integrating this with Azure API Management, you can:



  • Enhance Security: Protect your applications from harmful content.

  • Ensure Compliance: Adhere to regulatory standards and guidelines.

  • Improve User Experience: Provide a safer and more reliable service to your users.


 


Onboard Azure Content Safety API to Azure API Management


 


Like any other APIs, we can onboard Azure Content Safety API to Azure APIM by importing the latest OpenAPI specification. API management helps with enabling Managed Identity based authentication to the Content Safety API as well as communicate privately using Private Endpoints.


 


Onboard Azure OpenAI to Azure API Management


 


Onboarding AOAI to API Management comes with many benefits which are extensively discussed. I have a blog and github repo that talks about this in detail.


 


Integrate Content Safety with Azure OpenAI APIs in API Management


 


AI Gateway Labs is an amazing repository exploring various patterns through a series of labs. We have included 2 Content Safety scenarios as labs to demonstrate this integration.


 



 


The pattern behind this integration is to leverage the send-request policy in APIM to invoke the respective Content Safety API, and decide to forward the request to OpenAI, if it is safe.


 


The snippet below concatenates all the prompts in the incoming request to OpenAI and validates if there is any attack detected.


 


 

        <send-request mode="new" response-variable-name="safetyResponse">
            <set-url>@("https://" + context.Request.Headers.GetValueOrDefault("Host") + "/contentsafety/text:shieldPrompt?api-version=2024-02-15-preview")</set-url>
            <set-method>POST</set-method>
            <set-header name="Ocp-Apim-Subscription-Key" exists-action="override">
                <value>@(context.Variables.GetValueOrDefault<string>("SubscriptionKey"))</value>
            </set-header>
            <set-header name="Content-Type" exists-action="override">
                <value>application/json</value>
            </set-header>
            <set-body>@{
                string[] documents = new string[] {};
                string[] messages = context.Request.Body.As<JObject>(preserveContent: true)["messages"].Select(m => m.Value<string>("content")).ToArray();
                JObject obj = new JObject();		
                JProperty userProperty = new JProperty("userPrompt", string.Concat(messages));
                JProperty documentsProperty = new JProperty("documents", new JArray(documents));
                obj.Add(userProperty);
                obj.Add(documentsProperty);
                return obj.ToString();
            }</set-body>
        </send-request>
        <choose>
            <when condition="@(((IResponse)context.Variables["safetyResponse"]).StatusCode == 200)">
                <choose>
                    <when condition="@((bool)((IResponse)context.Variables["safetyResponse"]).Body.As<JObject>()["userPromptAnalysis"]["attackDetected"] == true)">
                        <!-- Return 400 if an attach is detected -->
                        <return-response>
                            <set-status code="400" reason="Bad Request" />
                            <set-body>@{ 
                        var errorResponse = new
                        {
                            error = new
                            {
                                message = "The prompt was identified as an attack by the Azure AI Content Safety service."
                            }
                        };                            
                        return JsonConvert.SerializeObject(errorResponse);
                    }</set-body>
                        </return-response>
                    </when>
                </choose>
            </when>
            <otherwise>
                <return-response>
                    <set-status code="500" reason="Internal Server Error" />
                </return-response>
            </otherwise>
        </choose>

 


 


The snippet below concatenates all the prompts in the incoming request to OpenAI and validates if it is within the allowed limits for hate, sexual, self harm and violence.


 


 

        <send-request mode="new" response-variable-name="safetyResponse">
            <set-url>@("https://" + context.Request.Headers.GetValueOrDefault("Host") + "/contentsafety/text:analyze?api-version=2023-10-01")</set-url>
            <set-method>POST</set-method>
            <set-header name="Ocp-Apim-Subscription-Key" exists-action="override">
                <value>@(context.Variables.GetValueOrDefault<string>("SubscriptionKey"))</value>
            </set-header>
            <set-header name="Content-Type" exists-action="override">
                <value>application/json</value>
            </set-header>
            <set-body>@{
            	string[] categories = new string[] {"Hate","Sexual","SelfHarm","Violence"};
				JObject obj = new JObject();
				JProperty textProperty = new JProperty("text", string.Concat(context.Request.Body.As<JObject>(preserveContent: true)["messages"].Select(m => m.Value<string>("content")).ToArray()));
				JProperty categoriesProperty = new JProperty("categories", new JArray(categories));
				JProperty outputTypeProperty = new JProperty("outputType", "EightSeverityLevels");
				obj.Add(textProperty);
				obj.Add(categoriesProperty);
				obj.Add(outputTypeProperty);
				return obj.ToString();
			}</set-body>
        </send-request>
        <choose>
            <when condition="@(((IResponse)context.Variables["safetyResponse"]).StatusCode == 200)">
                <set-variable name="thresholdExceededCategory" value="@{
                    var thresholdExceededCategory = "";

                    // Define the allowed threshold for each category
                    Dictionary<string, int> categoryThresholds = new Dictionary<string, int>()
                    {
                        { "Hate", 0 },
                        { "Sexual", 0 },
                        { "SelfHarm", 0 },
                        { "Violence", 0 }
                    };

                    foreach (var category in categoryThresholds)
                    {
                        var categoryAnalysis = ((JArray)((IResponse)context.Variables["safetyResponse"]).Body.As<JObject>(preserveContent: true)["categoriesAnalysis"]).FirstOrDefault(c => (string)c["category"] == category.Key);

                        if (categoryAnalysis != null && (int)categoryAnalysis["severity"] > category.Value)
                        {
                            // Threshold exceeded for the category
                            thresholdExceededCategory = category.Key;
                            break;
                        }
                    }
                    return thresholdExceededCategory;
                }" />
                <choose>
                    <when condition="@(context.Variables["thresholdExceededCategory"] != "")">
                        <return-response>
                            <set-status code="400" reason="Bad Request" />
                            <set-body>@{
                                var errorResponse = new
                                {
                                    error = new
                                    {
                                        message = "The content was filtered by the Azure AI Content Safety service for the category: " + (string)context.Variables["thresholdExceededCategory"]
                                    }
                                };
                                return JsonConvert.SerializeObject(errorResponse);
                            }</set-body>
                        </return-response>
                    </when>
                </choose>
            </when>
            <otherwise>
                <return-response>
                    <set-status code="500" reason="Internal Server Error" />
                </return-response>
            </otherwise>
        </choose>

 


 


Conclusion



Integrating Azure Content Safety with API Management for Azure OpenAI endpoints is a powerful way to enhance the security and reliability of your AI applications. By following these steps, you can ensure that your AI-generated content is safe, compliant, and user-friendly.


 


For more detailed information, refer to the Azure Content Safety documentation and the Azure API Management documentation.


 

Build intelligent MySQL applications using semantic search and generative AI

Build intelligent MySQL applications using semantic search and generative AI

This article is contributed. See the original author and article here.

Searching for content on a website uses keyword-based search, a method with its limitations. For example, searching for a ‘rain jacket for women’ on an e-commerce website returns all jackets for both men and women, as the search focuses on just the keyword ‘jacket’. The search simply isn’t contextual enough to provide the desired results.


 


Semantic search is a technique that allows users to search for information using natural language queries rather than specific keywords. With semantic search, the meaning and intent of users’ queries are inferred, and personalized relevant results are returned. Generative AI, on the other hand, is a type of artificial intelligence that can generate new content from existing data, such as text, images, or audio. You can use generative AI to produce summaries, captions, recommendations, or responses based on a user’s input and preferences.


 


This blog post discusses how to build intelligent MySQL applications with semantic search and generative AI response using Azure Open AI and Azure Database for MySQL with Azure AI search. As an example, we’ll use a Magento ecommerce app designed to sell jackets, and then build a “Product Recommender CoPilot” chat application that:



  • Recognizes the intent of a user’s natural language queries.

  • Generates custom responses to recommend suitable products using the product details and reviews data stored in Azure Database for MySQL.


 


Architecture


 


The simplest way to include the rich capabilities of semantic search and generative AI in your applications is to build a solution using the Retrieval Augmented Generation (RAG) architecture with Azure AI Search and Azure Open AI services.


 


What is a RAG architecture?


 


Retrieval Augmented Generation, or RAG, is an architecture that augments the natural language understanding and generation capabilities of LLMs like ChatGPT by adding an information retrieval system like Azure AI Search which works with your data stored in data sources like Azure Database for MySQL. In a typical RAG pattern:



  • A user submits a query or prompt in natural language.

  • The query is routed to Azure AI Search to find the relevant information.

  • Azure AI Search sends the top ranked semantic search results to a Large Language Model (LLM).

  • The LLM then processes the natural language query and uses reasoning capabilities to generate a response to the initial prompt.


 


Sample product recommender Copilot architecture


 


A sample RAG architecture for the AI solution we’ll show you how to build in this blog post appears in the following graphic:


Architecture.png



  1. Azure AI search pulls the content (in our case, the product details and reviews data) from a backend Azure Database for MySQL database by using an indexer that runs periodically.

  2. The product details and reviews data are further chunked and vectorized using Azure OpenAI’s text embedding model.

  3. Azure AI Search then persists this vectorized data in a vector search index.

  4. When a user uses the “Product Recommender CoPilot” chat application, the query is sent to an Azure OpenAI Chat Completion Service.

  5. Azure AI Search is now used as a data source to find the most relevant response using vector-search or hybrid search (vector + semantic search).

  6. The Azure OpenAI Chat Completion service then uses these search results to generate a custom response back to the user query.


In this post, we’ll walk you through how to set up the backend data sources, indexers, and models required to build this solution. It is a detailed guide to the sample Python code hosted in our GitHub repository in a Jupyter Notebook: azure-mysql/Azure_MySQL_AI_Search_Sample at master Azure/azure-mysql.


 


For a short demo of the entire process using a Magento ecommerce application, watch the following video!


 


 


Prerequisites


 


Before getting started, you need to ensure that the following prerequisites are in place.



  • An Azure account with an active subscription. If you don’t have one, create one for free here.

  • An Azure AI Search resource. If you don’t have one, you can create one via the Azure portal or the Azure CLI, as explained in the article here.

  • An Azure Open AI Services resource. If you don’t have one, you can create one via the Azure portal or the Azure CLI, as explained in the article here.

  • A MySQL database (in Azure Database for MySQL or any database provider) populated with product and reviews data obtained from your ecommerce application like Magento.



 


Process


 


Supporting semantic search in an e-commerce application that leverages Azure AI search and Azure Open AI Services in the backend requires completing the following:


 


I. Set up data source connection in Azure AI Search.


II. Set up automatic chunking, vectorization and indexing.


III. Use vector search from a sample application.


IV. Generate a GPT response to the user.


V. Test the solution in the Azure OpenAI Studio playground.


 


Azure AI search pulls the contents and reviews data from a backend MySQL flexible server by using an indexer that runs periodically. The reviewed data is further chunked and vectorized using Azure OpenAI’s text embedding model. In Azure AI search, the vectorized data then persists in a vector search index.


 


I. Set up data source connection in Azure AI Search


 


The data source definition specifies the data to index, credentials, and policies for identifying changes in the data. The data source is defined as an independent resource so that it can be used by multiple indexers. In this example, we’ll use a custom table with product details and review data which is stored in a database in Azure Database for MySQL.


 


In the Azure AI service, before creating a search Index, we’ll need to create a connection to your data source. We’ll import Azure AI classes like ‘SearchClient’, ‘SearchIndexerClient’, ‘SearchIndexerDataSourceConnection’ and their functions like “create_or_update_data_source_connection()” to setup the data source connection in Azure AI Search. We’ll also import several other models – the comprehensive list is shared in the following code sample.


 


Code: “1. Set up data source connection in Azure AI Search” in the Jupyter Notebook azure-mysql/Azure_MySQL_AI_Search_Sample at master Azure/azure-mysql


 


II. Set up automatic chunking, vectorization and indexing


 


We are now ready to create an Azure Database for MySQL indexer that periodically pulls the product details and reviews data from the database in Azure Database for MySQL, chunks and vectorizes the data and persists it in a vector search index.


 


To do this, we’ll first create an index which takes the product details and reviews data for each product, splits the combined text into chunks and embeds each chunk as a vector. For any incoming user query, we’ll search for the most relevant chunk using vector search and semantic search.


 


Create an Azure AI Search index


 


In Azure AI Search, a search index available to the search engine for indexing, full text search, vector search, hybrid search, and filtered queries. An index is defined by a schema and is saved to the search service.



  • We’ll first create an index object from the ‘SearchIndexClient’ class.

  • Then, we define the field mappings to correlate the fields in a MySQL database to the fields in the AI search Index. As the combined text is generally long, it needs to be chunked into smaller words. To do this, we’ll add an additional search field called “chunk”.

  • Next, we’ll decide the searches that the index will support. In this example, we’ll use ‘vector search’ along with ‘semantic re-ranking’. Here is how the two work together in our solution:

    • Vector search is first performed on all the entries in the search index.

    • Semantic search is sort of a neural network where the search can be performed only of limited number. The top 50 results obtained using vector search is sent to the neural network, which re-ranks these documents and provides the top matched result in the reduced context. Semantic search does a better optimization to find the best results. It also produces short-form captions and answers that are useful as LLM inputs for generation.



  • We’ll then define the vector search and semantic configurations:

    • Vector search configuration – You can choose different algorithms, such as HNSW or KNN, to perform the vector search. In this post, we’ll choose the most used algorithm – HNSW. We’ll configure the HNSW algorithm to use the ‘COSINE’ metric. Considering each vector as a point in the multi-dimensional space, the algorithm will not find the cosine distance between the points. Lower the distance, more similar the vectors.

    • Semantic configuration – Here, we’ll define the index field on which semantic re-ranking is performed.



  • Finally, we’ll create the search index using the above two configurations on the relevant MySQL DB table fields.


Code: “II. Set up automatic chunking, vectorization and indexing” -> “Create index” in the Jupyter Notebook azure-mysql/Azure_MySQL_AI_Search_Sample at master Azure/azure-mysql


 


Chunking


 


We’ll create a skillset using two pre-built “skills”:



  • The “Split Skill”, which takes the concatenated text and divides it into chunks.

  • The “Azure OpenAI Embedding Skill”, which takes the outputs of the Split Skill and vectorizes them individually.


We’ll then apply an Index Projector to make it so that our final index has one item for every chunk of text, rather than one item for every original row in the database.


 


Code: “II. Set up automatic chunking, vectorization and indexing” -> “Create skillset” in the Jupyter Notebook azure-mysql/Azure_MySQL_AI_Search_Sample at master Azure/azure-mysql


 


Create and run the MySQL Indexer


 


After you define the data source and create the index, you’re ready to create the indexer. The configuration of the Indexer requires the inputs, parameters, and properties that control run time behaviors.


 


To create an indexer, we’ll provide the name of the data source, index and skillset that we created in the previous steps. We’ll then run the indexer at periodic intervals.


 


Code: “II. Set up automatic chunking, vectorization and indexing” -> “Create indexer” in the Jupyter Notebook azure-mysql/Azure_MySQL_AI_Search_Sample at master Azure/azure-mysql


 


After the indexer is created, you can use the Azure portal to view the indexer under the Indexers blade in Azure AI Search. You can also run the indexer from the Azure portal or using Azure CLI. The runs can be configured to be ad hoc or scheduled:



  • Ad hoc – An indexer can be configured to run only once or on-demand. You can use APIs (like we used in the code sample), Azure portal or CLI to achieve this.

  • Scheduled – You can schedule and indexer to run at a certain time. Go to “Settings” section in the Azure portal view of the indexer, and choose hourly, one time, daily, or any other custom settings.


 


III. Use vector search from a sample application


 


With the Azure AI Search indexer ready and running, you can now use the vector search and semantic search capabilities from your application. To call the search function, provide the user query text, required query parameters like the number of nearest neighbors to return as top hits, and the columns or fields in the index to be considered. Also select query type “Semantic” to include both vector search and semantic search and provide the name of semantic search configuration object that you created in section II.


 


Code: “III. Use vector search from a sample application” in the Jupyter Notebook azure-mysql/Azure_MySQL_AI_Search_Sample at master Azure/azure-mysql


 


For a user query like “suggest me some rain jackets for women“, this single API call performs vector search and semantic re-ranking, and returns the top ranked results as shown in the following screenshot. You’ll also see the vector search score, semantic re-ranker score, and all the details of the recommended product.


 


Picture1.png


 


IV. Generate a GPT response to the user


 


To generate custom responses to the users, we need to simply make a call to the Azure OpenAI chat completion service. To trigger the completion, we first input some text as a “prompt”. The LLM in the service then generates the completion and attempts to match our context or pattern. An example prompt for this scenario could be: “You are an AI assistant that recommends products to people based on the product reviews data matching their query. Your answer should summarize the review text, include the product ID, include the parent id as review id, and mention the overall sentiment of the review.”


 


To generate the GPT response, we’ll use the Azure OpenAI’s chat.completions.create() API call and supply it with the user query, the Open AI model to be used, the Azure AI Search index as data source, and the prompt.


 


Code: “IV. Generate GPT Response to the user” in the Jupyter Notebook azure-mysql/Azure_MySQL_AI_Search_Sample at master Azure/azure-mysql


 


V. Test the solution in the Azure OpenAI Studio playground


 


Finally, it’s important to test the solution in Azure Open AI Studio, a user-friendly platform that allows developers to explore cutting-edge APIs and models and to build, test, deploy, and manage AI solutions for use in websites, applications, and other production environments.


 


For an end-to-end test of the AI solution in the Azure OpenAI Studio playground, perform the following steps:



  1. Go to Azure OpenAI studio, select your subscription and the Azure AI Search resource, and navigate to the “Chat playground”.

  2. In the section, in the Add your data tab, select Add a data source.

  3. In the pop-up window, select Azure AI Search as the data source.

  4. Fill in subscription details, and then choose the Azure AI Search service and Azure AI Search index created in the previous sections.

  5. Enable the Add vector search to this search resource option.

  6. Select the Azure OpenAI – text-embedding-ada-002 model and select Next.

  7. Select Hybrid + semantic search type.

  8. Review all the details and add the data source.

  9. In the Prompt tab under the Setup section, type your prompt message in the System message text box.
    You can use the sample prompt from the previous step or modify the prompt to add more details, such as product images, in the response.

  10. To test the solution, type a sample query in the chat box and watch your copilot generate a smart recommendation in response!


 


Test the solution in the Azure OpenAI Studio playground.png


 


Now, you’re all set to deploy this Product Recommender CoPilot AI solution to production!


 


Conclusion


 


If you’re running applications, such as content management systems (CMS), e-commerce applications, or gaming sites, with data hosted in Azure Database for MySQL, you can enhance your user experience by building generative AI search and chat applications using LLMs available in Azure OpenAI and vector storage and indexing provided by Azure AI Search. Unleash the power of your data hosted on MySQL with the simple and seamless AI integrations on Azure!


 


If you have any queries or suggestions for more AI-related content, please let us know by contacting us at AskAzureDBforMySQL@service.microsoft.com. We’re also open to collaborating with you on technical collateral! Check out our Contributors initiative at aka.ms/mysql-contributors to learn more.

Business Applications incentives updates for FY25

This article is contributed. See the original author and article here.

In FY25, we have made several changes to Microsoft Funded Engagements, formerly known as Partner Activities, to support deal acceleration and growth. These pre-defined engagements will help you align your go-to-market efforts with Microsoft and build expertise in enabling core use case scenarios. Read on to learn how to access these program investments NOW!


​Read more about the updates on the blog: https://aka.ms/bapafy25blog


Learn more about FY25 Funded Engagements in our webinar series: https://aka.ms/BAPAwebinars


Bookmark the Business Applications Funded Engagements page to stay updated with the latest resources, updates, and incentive announcements: https://aka.ms/BAFundedEngagements ​