Gemini Code Assist ile geliştirme iş akışınızı güçlendirin

1. Giriş

e5b98fd4e417c877.png

Bu codelab'de, Gemini Code Assist'in yazılım geliştirme yaşam döngüsünün (SDLC) tasarım, derleme ve test ile dağıtım gibi temel aşamalarında size nasıl destek olabileceğini öğreneceksiniz. Tam bir uygulama tasarlayıp geliştirecek ve Google Cloud'da dağıtacağız.

Teknik bir etkinlikteki oturumlarda arama yapmak için bir API ve uygulama oluşturacağız. Her oturumda başlık, özet, süre, kategoriler ve bir veya daha fazla konuşmacı yer alır.

Yapacaklarınız

  • Sıfırdan OpenAPI spesifikasyonuna dayalı bir web uygulaması tasarlama, oluşturma, test etme ve dağıtma

Neler öğreneceksiniz?

  • OpenAPI Specification oluşturmak için Gemini Code Assist'i kullanma
  • OpenAPI spesifikasyonu için Python Flask uygulaması geliştirmek üzere Gemini Code Assist'in kod oluşturma özelliklerini kullanma
  • Python Flask uygulaması için web ön ucu oluşturmak üzere Gemini Code Assist'i kullanma
  • Uygulamayı Google Cloud Run'a dağıtma konusunda yardım almak için Gemini Code Assist'i kullanma
  • Uygulamayı oluşturup test ederken Kod Açıklaması ve Test Senaryosu Oluşturma gibi Gemini Code Assist özelliklerini kullanma

Gerekenler

  • Chrome web tarayıcısı
  • Gmail hesabı
  • Faturalandırmanın etkin olduğu bir Cloud projesi
  • Cloud projeniz için Gemini Code Assist'in etkinleştirilmesi

Bu laboratuvar, yeni başlayanlar da dahil olmak üzere her seviyeden geliştiriciye yöneliktir. Örnek uygulama Python dilinde olsa da neler olduğunu anlamak için Python programlamayı bilmeniz gerekmez. Bu oturumda, Gemini Code Assist'in özelliklerine aşina olmaya odaklanacağız.

2. Gemini Code Assist'i kurma

Bu bölümde, laboratuvarı kullanmaya başlamak için yapmanız gereken her şey açıklanmaktadır.

Cloud Shell IDE'de Gemini Code Assist'i etkinleştirme

Bu codelab'in geri kalanında, tamamen yönetilen bir Code OSS tabanlı geliştirme ortamı olan Cloud Shell IDE'yi kullanacağız. Cloud Shell IDE'de Code Assist'i etkinleştirip yapılandırmamız gerekiyor. Adımlar aşağıda verilmiştir:

  1. ide.cloud.google.com adresini ziyaret edin. IDE'nin görünmesi biraz zaman alabilir. Lütfen sabırlı olun ve varsayılan kurulum seçeneklerini kabul edin. IDE'yi ayarlamayla ilgili bazı talimatlar görürseniz lütfen varsayılan ayarlarla bu talimatları tamamlayın.
  2. Alt durum çubuğunda Cloud Code - Sign in (Cloud Code - Oturum aç) düğmesini tıklayın. Eklentiyi talimatlara uygun şekilde yetkilendirin. Durum çubuğunda "Cloud Code - no project" (Cloud Code - proje yok) ifadesini görürseniz bu ifadeyi ve ardından çalışmayı planladığınız projeler listesinden belirli bir Google Cloud projesini seçin.

6f5ce865fc7a3ef5.png

  1. Sağ alt köşedeki Code Assist düğmesini tıklayın ve doğru Google Cloud projesini son bir kez daha seçin. Cloud AI Companion API'yi etkinleştirmeniz istenirse lütfen etkinleştirin ve devam edin.
  2. Google Cloud projenizi seçtikten sonra, durum çubuğundaki Cloud Code durum mesajında projenizi görebildiğinizden ve sağ tarafta, durum çubuğunda Code Assist'in etkinleştirildiğinden emin olun (aşağıdaki resimde gösterildiği gibi).

709e6c8248ac7d88.png

Gemini Code Assist kullanıma hazır!

3. Firestore'u ayarlama

Cloud Firestore, uygulama verilerimiz için arka uç olarak kullanacağımız, tümüyle yönetilen bir sunucusuz belge veritabanıdır. Cloud Firestore'daki veriler, doküman koleksiyonları halinde yapılandırılır.

Varsayılan Firestore veritabanımızda sessions adlı bir koleksiyon oluşturmamız gerekiyor. Bu koleksiyonda, uygulamamızda kullanacağımız örnek veriler (dokümanlar) yer alır.

Cloud Shell IDE'nizden ana menü aracılığıyla Terminal'i açın (aşağıda gösterildiği gibi):

f1535e14c9beeec6.png

sessions adlı bir koleksiyon oluşturmamız gerekiyor. Bu bölümde örnek oturum dokümanlarının listesi yer alır. Her belgenin aşağıdaki özellikleri olacaktır:

  1. title: dize
  2. categories: dize dizisi
  3. speakers: dize dizisi
  4. duration: string
  5. summary: dize

Örnek verileri içeren bir dosyayı kendi projenizdeki bir pakete kopyalayarak bu koleksiyonu örnek verilerle dolduralım. Ardından, gcloud firestore import komutuyla koleksiyonu içe aktarabilirsiniz.

Firestore veritabanı başlatma

Cloud Console'da Firestore sayfasını ziyaret edin.

Projede daha önce bir Firestore veritabanı başlatmadıysanız default veritabanını oluşturun. Veritabanını oluştururken aşağıdaki değerleri kullanın:

  • Firestore modu: Native
  • Konum: Konum türü olarak Region simgesini seçin ve başvurunuza uygun bölgeyi belirleyin. Paket konumu için bir sonraki adımda bu konuma ihtiyacınız olacağından konumu not edin.
  • Veritabanını oluşturun.

504cabdb99a222a5.png

Şimdi aşağıdaki adımları uygulayarak sessions koleksiyonunu oluşturacağız:

  1. Aşağıda verilen gsutil komutuyla projenizde bir paket oluşturun. Aşağıdaki komutta <PROJECT_ID> değişkenini Google Cloud proje kimliğinizle değiştirin. <BUCKET_LOCATION> kısmını, varsayılan Firestore veritabanınızın Coğrafi Alanı'na karşılık gelen bir bölge adıyla (önceki adımda belirtildiği gibi) değiştirin. Bu ad US-WEST1, EUROPE-WEST1 veya ASIA-EAST1 olabilir :
gsutil mb -l <BUCKET-LOCATION> gs://<PROJECT_ID>-my-bucket
  1. Paket oluşturulduğuna göre, Firebase veritabanına aktarabilmemiz için hazırladığımız veritabanı dışa aktarma işlemini bu pakete kopyalamamız gerekir. Aşağıdaki komutu kullanın:
gsutil cp -r gs://sessions-master-database-bucket/2024-03-26T09:28:15_95256  gs://<PROJECT_ID>-my-bucket

İçe aktarılacak veriler olduğuna göre, oluşturduğumuz Firebase veritabanına (default) veri aktarma işleminin son adımına geçebiliriz.

  1. Aşağıdaki gcloud komutunu kullanın:
gcloud firestore import gs://<PROJECT_ID>-my-bucket/2024-03-26T09:28:15_95256

İçe aktarma işlemi birkaç saniye sürer. İşlem tamamlandığında https://console.cloud.google.com/firestore/databases adresini ziyaret ederek Firestore veritabanınızı ve koleksiyonunuzu doğrulayabilirsiniz. Aşağıda gösterildiği gibi default veritabanını ve sessions koleksiyonunu seçin:

d3e294d46ba29cd5.png

Böylece, uygulamamızda kullanacağımız Firestore koleksiyonunun oluşturulması tamamlanır.

4. Uygulama şablonunu oluşturma

Codelab'in geri kalanında kullanacağımız bir örnek uygulama (Python Flask uygulaması) oluşturacağız. Bu uygulama, teknik bir konferansta sunulan oturumlar arasında arama yapar.

Şu adımları uygulayın:

  1. Aşağıdaki durum çubuğunda Google Cloud proje adını tıklayın.

f151759c156c124e.png

  1. Bir seçenek listesi gösterilir. Aşağıdaki listeden Yeni Uygulama'yı tıklayın.

91ea9836f38b7f74.png

  1. Cloud Run uygulaması'nı seçin (bu, uygulamamızın çalışma zamanı olacaktır).
  2. Python (Flask): Cloud Run uygulama şablonunu seçin.
  3. Uygulamaya bir ad verin ve tercih ettiğiniz konuma kaydedin.
  4. Başvurunuzun oluşturulduğunu onaylayan bir bildirim gösterilir ve başvurunuzun yüklendiği yeni bir pencere açılır (aşağıda gösterildiği gibi). README.md dosyası açılır. Şimdilik bu görünümü kapatabilirsiniz.

aaa3725b17ce27cf.png

5. Gemini Code Assist ile etkileşim

Bu laboratuvar kapsamında, VS Code'daki Cloud Code uzantısının bir parçası olarak Cloud Shell IDE'de bulunan Gemini Code Assist Chat'i kullanacağız. Sol gezinme çubuğundaki Kod Asistanı düğmesini tıklayarak bu özelliği kullanabilirsiniz. Sol gezinme araç çubuğunda Code Assist simgesini a489f98a34898727.png bulun ve tıklayın.

Bu işlem, Cloud Shell IDE'de Code Assist sohbet bölmesini açar ve Code Assist ile sohbet edebilirsiniz.

14ad103efaa0ddaa.png

En üstteki çöp kutusu simgesine dikkat edin. Bu simge, Code Assist sohbet geçmişinin bağlamını sıfırlamanın yoludur. Bu sohbet etkileşiminin, IDE'de üzerinde çalıştığınız dosyalarla ilgili olduğunu da unutmayın.

6. API Tasarımı

İlk adımımız, tasarım aşamasında Gemini Code Assist'in yardımını almak olacak. Bu adımda, arama yapmak istediğimiz öğeler (bir etkinlikteki teknik oturumlar) için bir OpenAPI spesifikasyonu oluşturacağız.

Aşağıdaki istemi girin:

Generate an Open API spec that will allow me to retrieve all sessions, sessions by category, session by id. Each session has the following attributes: id, title, list of speakers, list of categories, summary and duration.

Bu işlem, çeşitli sorgu parametreleri aracılığıyla oturumlarda arama yapmak için bir OpenAPI spesifikasyonu oluşturmalıdır. Spesifikasyon örneği aşağıda verilmiştir:

openapi: 3.0.0
info:
 title: Sessions API
 description: This API allows you to retrieve all sessions, sessions by category, and session by id.
 version: 1.0.0
servers:
 - url: https://sessions.example.com
paths:
 /sessions:
   get:
     summary: Get all sessions
     operationId: getSessions
     responses:
       '200':
         description: OK
         content:
           application/json:
             schema:
               type: array
               items:
                 $ref: '#/components/schemas/Session'
 /sessions/{id}:
   get:
     summary: Get session by id
     operationId: getSessionById
     parameters:
       - name: id
         in: path
         required: true
         description: The id of the session
         schema:
           type: string
     responses:
       '200':
         description: OK
         content:
           application/json:
             schema:
               $ref: '#/components/schemas/Session'
 /sessions/categories/{category}:
   get:
     summary: Get sessions by category
     operationId: getSessionsByCategory
     parameters:
       - name: category
         in: path
         required: true
         description: The category of the sessions
         schema:
           type: string
     responses:
       '200':
         description: OK
         content:
           application/json:
             schema:
               type: array
               items:
                 $ref: '#/components/schemas/Session'
components:
 schemas:
   Session:
     type: object
     properties:
       id:
         type: string
         description: The id of the session
       title:
         type: string
         description: The title of the session
       speakers:
         type: array
         items:
           type: string
         description: The list of speakers for the session
       categories:
         type: array
         items:
           type: string
         description: The list of categories for the session
       summary:
         type: string
         description: The summary of the session
       duration:
         type: string
         description: The duration of the session

Spesifikasyonda şunların olduğunu fark edebilirsiniz:

  • Oturum türü için tanımlanmış bir şema.
  • Tanımlanmış birkaç API yolu:
  • /sessions
  • /sessions/{id}
  • /sessions/categories/{category}

Üst klasörde sessionsapi.yaml adlı bir dosya oluşturun ve "insert in current file option" (geçerli dosyaya ekle) seçeneğini (+ düğmesi) kullanarak Code Assist sohbet penceresindeki içeriği kopyalayın. Dosyayı Cloud Shell IDE'de açık tutun.

Bu noktada, Gemini Code Assist'in ilginç bir özelliğini, alıntı özelliğini inceleyebilirsiniz. Bu bilgiler, oluşturulan kod mevcut açık kaynak kodu gibi başka bir kaynaktan doğrudan uzun alıntılar yaptığında geliştiriciye gösterilir. Geliştiricinin ne yapacağına karar vermesi için kaynak ve lisans sunar.

Oluşturulan içerikten memnun olduğumuzu varsayarsak artık bu spesifikasyon belgesini kullanarak bunun için bir Python Flask uygulaması oluşturabiliriz.

7. Uygulamayı oluşturma

Şimdi Kod Asistanı'ndan uygulamayı oluşturmasını isteyeceğiz. sessionsapi.yaml dosyası açıkken aşağıdaki istemi girin.

Generate a Python Application using the Flask framework, based on the sessionsapi.yaml file. This application uses a local in memory list of sessions. Do not use any Flask extensions.

Bu, OpenAPI spesifikasyon dosyasında belirtilen işlevselliğe ve yollara dayalı Python Flask uygulaması için bir iskelet oluşturur.

Sağlanan Python Flask Uygulaması kodu aşağıdaki koda benzer olmalıdır:

from flask import Flask, jsonify, request

app = Flask(__name__)

sessions = [
    {
        "id": "1",
        "title": "Session 1",
        "speakers": ["Speaker 1", "Speaker 2"],
        "categories": ["Category 1", "Category 2"],
        "summary": "This is a summary of session 1.",
        "duration": "1 hour",
    },
    {
        "id": "2",
        "title": "Session 2",
        "speakers": ["Speaker 3", "Speaker 4"],
        "categories": ["Category 3", "Category 4"],
        "summary": "This is a summary of session 2.",
        "duration": "1 hour 30 minutes",
    },
]

@app.route('/sessions', methods=['GET'])
def get_sessions():
    return jsonify(sessions)

@app.route('/sessions/<id>', methods=['GET'])
def get_session_by_id(id):
    session = next((session for session in sessions if session['id'] == id), None)
    if session is None:
        return jsonify({}), 404
    return jsonify(session)

@app.route('/sessions/categories/<category>', methods=['GET'])
def get_sessions_by_category(category):
    sessions_by_category = [session for session in sessions if category in session['categories']]
    return jsonify(sessions_by_category)

if __name__ == '__main__':
    app.run()

Önceki adımda oluşturulan mevcut bir app.py dosyası olmalıdır. İçeriğini Code Assist tarafından oluşturulan kodla değiştirip dosyayı kaydetmeniz yeterlidir.

app.run() satırını 8080 bağlantı noktasını ve 0.0.0.0 ana makine adresini kullanacak şekilde değiştirmek ve yerel yürütme sırasında hata ayıklama modunda çalıştırmak istiyoruz.Bunu yapmanın bir yolu aşağıda verilmiştir. Öncelikle satırı vurgulayalım/seçelim:

app.run()

Ardından, Code Assist Chat arayüzünde istemi yazın: Explain this.

Bu satırda, söz konusu satırla ilgili ayrıntılı bir açıklama gösterilir. Aşağıda bu açıklamaya dair bir örnek verilmiştir:

58ec896a32a4fb68.png

Şimdi aşağıdaki istemi kullanın:

update the code to run the application on port 8080, host address 0.0.0.0, and in debug mode

Oluşturulan önerilen kod şu şekilde olmalıdır:

app.run(host='0.0.0.0', port=8080, debug=True)

app.py dosyasını bu snippet ile güncellemeyi unutmayın.

Uygulamayı yerel olarak çalıştırma

Şimdi, uygulamayı yerel olarak çalıştırarak uygulama şartlarını başlangıçtaki durumumuza göre doğrulayalım.

İlk adım, sanal ortama yüklenecek requirements.txt dosyasındaki Python paketi bağımlılıklarıyla sanal bir Python ortamı oluşturmaktır. Bunu yapmak için Cloud Shell IDE'de Komut Paleti'ne (Ctrl+Üst Karakter+P) gidin ve Create Python environment (Python ortamı oluştur) yazın. Sanal ortam (venv), Python 3.x yorumlayıcısı ve requirements.txt dosyasını seçmek için sonraki birkaç adımı uygulayın.

Ortam oluşturulduktan sonra yeni bir terminal penceresi (Ctrl+Üst Karakter+`) başlatın ve şu komutu verin:

python app.py

Aşağıda örnek bir yürütme gösterilmektedir:

(.venv) romin@cloudshell: $ python app.py 
 * Serving Flask app 'app'
 * Debug mode: on
WARNING: This is a development server. Do not use it in a production deployment. Use a production WSGI server instead.
 * Running on all addresses (0.0.0.0)
 * Running on http://127.0.0.1:8080
 * Running on http://10.88.0.3:8080
Press CTRL+C to quit
 * Restarting with stat
 * Debugger is active!
 * Debugger PIN: 132-247-368

API'yi artık aşağıdaki URL'lerde önizleyebilirsiniz. Geliştirme sunucunuzun 8080 numaralı bağlantı noktasında çalıştığını varsayıyoruz. Değilse lütfen uygun bağlantı noktası numarasıyla değiştirin.

  • https://<host-name>:8080/sessions
  • https://<host-name>:8080/sessions/{id}
  • https://<host-name>:8080/sessions/categories/{category}

app.py dosyasında bulunan JSON verilerini bu URL'leri kullanarak alabilmek için aşağıdaki adımları uygulayın:

Yeni bir terminal penceresi açıp aşağıdaki komutlardan herhangi birini deneyin:

curl -X GET http://127.0.0.1:8080/sessions
curl -X GET http://127.0.0.1:8080/sessions/<ID>
curl -X GET http://127.0.0.1:8080/sessions/categories/<CATEGORY_NAME> 

8. Kod Yeniden Düzenleme

app.py'nın sabit kodlanmış örnek JSON verilerini içermesi yerine, kodu ve verileri net bir şekilde ayırabilmek için bu verileri başka bir modüle ayırmak/çıkarmak isteyebiliriz. Haydi başlayalım.

app.py dosyasını açık tutun ve aşağıdaki istemi girin:

Can I improve this code and separate out the sessions data from this app.py file?

Bu işlem, nasıl yapacağınıza dair bazı öneriler sunar. Aldığımız ve sizin de benzer bir yanıt alacağınız örnek öneri aşağıda gösterilmiştir:

9b9c56cb527dac4c.png

Bunu uygulayalım ve verilerimizi Code Assist'in önerdiği gibi sessions.py dosyasına ayıralım.

sessions.py adlı yeni bir dosya oluşturun.

, içeriği, oluşturduğumuz verilere göre JSON listesi olan aşağıdaki öğe:

sessions = [
   {
       "id": "1",
       "title": "Session 1",
       "speakers": ["Speaker 1", "Speaker 2"],
       "categories": ["Category 1", "Category 2"],
       "summary": "This is a summary of session 1.",
       "duration": "1 hour",
   },
   {
       "id": "2",
       "title": "Session 2",
       "speakers": ["Speaker 3", "Speaker 4"],
       "categories": ["Category 3", "Category 4"],
       "summary": "This is a summary of session 2.",
       "duration": "1 hour 30 minutes",
   },
]

app.py dosyası artık çok daha basitleştirilmiş olup aşağıda gösterilmektedir:

from flask import Flask, jsonify, request
from sessions import sessions

app = Flask(__name__)

@app.route('/sessions', methods=['GET'])
def get_sessions():
   return jsonify(sessions.sessions)

@app.route('/sessions/<id>', methods=['GET'])
def get_session_by_id(id):
   session = next((session for session in sessions.sessions if session['id'] == id), None)
   if session is None:
       return jsonify({}), 404
   return jsonify(session)

@app.route('/sessions/categories/<category>', methods=['GET'])
def get_sessions_by_category(category):
   sessions_by_category = [session for session in sessions.sessions if category in session['categories']]
   return jsonify(sessions_by_category)

if __name__ == '__main__':
   app.run(host='0.0.0.0', port=8080, debug=True)

Uygulamayı yerel olarak çalıştırmaya ve API'yi bu yeniden düzenlenmiş değişikliklerle kullanmaya devam edebildiğinizden emin olun. Python geliştirme sunucusu muhtemelen hâlâ çalışıyordur. Bu nedenle, önceki adımdaki curl komutlarını hatırlamanız yeterlidir.

9. Firestore koleksiyonuyla entegrasyon

Bir sonraki adım, oturumlarımız için kullandığımız yerel bellek içi JSON listesinden uzaklaşmak ve uygulamamızı, bu kod laboratuvarının başında oluşturduğumuz Firestore veritabanındaki oturumlar koleksiyonuna bağlamaktır.

sessions.py dosyasını açık tutun ve aşağıdaki istemi girin:

Can you further refactor the sessions.py code to read from a Firestore database that has a collection named sessions. The collection has the same attributes as the session object that we have defined. Use the Python module google-cloud-firestore. 

Firestore koleksiyonundaki tüm oturumları okumak için aşağıdaki öneriyi aldık:

import google.cloud.firestore

# Create a Firestore client
db = google.cloud.firestore.Client()

# Get the sessions collection
sessions_collection = db.collection("sessions")

# Create a list of sessions
sessions = []

# Iterate over the documents and add them to the list
for doc in sessions_collection.stream():
   session = doc.to_dict()
   session["id"] = doc.id
   sessions.append(session)

Kodu sessions.py içine ekleyebilirsiniz.

Flask Development sunucusunu yerel olarak çalıştırıyorsanız uygulamanız, Python modülünün bulunamadığına dair bir hata mesajı göstererek kapanmış olabilir.

Örneğin, Code Assist'e requirements.txt dosyasına hangi Python modülünün eklenmesi gerektiğini sorabilirsiniz:

Which Python package needs to be installed to make the firestore code work?

Bu işlem, Python modülünün adını (ör. google-cloud-firestore) sağlar. Bu adı requirements.txt dosyasına ekleyin.

Python ortamını yeni eklenen modülle (google-cloud-firestore) yeniden oluşturmanız gerekir. Bunu yapmak için mevcut Terminal penceresinde aşağıdaki komutu verin:

pip install -r requirements.txt

Uygulamayı tekrar çalıştırın (python app.py ile yeniden başlatın) ve /sessions URL'sini ziyaret edin. Artık sessions koleksiyonuna eklediğimiz örnek dokümanları alabilirsiniz.

975d05e6518f1a6a.png

Belirli oturumları veya belirli bir kategoriye ait tüm oturumları almak için önceki adımlarda açıklandığı gibi diğer URI'leri sorgulayabilirsiniz.

10. Kod Açıklaması

Kod hakkında iyi bir anlayış kazanmak için Gemini Code Assist'in "Explain this" özelliğini kullanmanın tam zamanı. Dilediğiniz dosyaya gidebilir veya belirli kod snippet'lerini seçip Code Assist'e aşağıdaki istemi kullanarak soru sorabilirsiniz: Explain this.

Alıştırma olarak sessions.py dosyasını ziyaret edin, Firestore'a özgü kodu vurgulayın ve bu kodla ilgili açıklama alın. Bu özelliği yalnızca Python kodunda değil, projenizdeki diğer dosyalarda da kullanmayı deneyin.

11. Web uygulamasını oluşturma

API'yi oluşturup canlı bir Firestore koleksiyonuyla entegre ettiğimize göre şimdi uygulama için web tabanlı bir ön uç oluşturalım. Web ön uçumuz şu anda işlevselliğini minimum düzeyde tutacak, yani belirli bir kategoriye ait oturumları arayabilecek. Bunun için bir API yolumuz olduğunu (ör. /sessions/categories/{category}) ve web uygulamamızın bunu çağırması ve sonuçları alması gerektiğini unutmayın.

Hemen konuya girelim. Code Assist'e aşağıdaki istemi girin:

Generate a web application that allows me to search for sessions by category and uses the Flask application that we created. Please use basic HTML, CSS and JS. Embed all the Javascript and CSS code into a single HTML file only.

Bu işlem, JavaScript ve CSS'nin yerleştirildiği web uygulaması HTML'sini oluşturur. Ayrıca, kök URL'yi veya temel URL'yi ziyaret eden tüm kullanıcılara ana sayfanın sunulması için app.py dosyasına yeni bir rota eklemeniz de istenir. Bu bilgilerden bahsedilmiyorsa bilgi isteyin veya aşağıdaki snippet'i kullanın:

@app.route('/')
def index():
   return render_template('index.html')

Bu dosyayı index.html olarak kaydedebilirsiniz ancak bu dosyanın nereye (ör. hangi klasöre) kaydedilmesi gerektiğiyle ilgili bir sorunuz olabilir. Kod Asistanı'na ek sorular sorabiliriz.

Given that I am using the flask framework, where should I put the index.html file?

render_template çerçevesini kullandığı ve bu nedenle index.html dosyasının templates klasörüne yerleştirilmesi gerektiği konusunda net bilgiler verilmelidir. Bu codelab'in başında Flask şablonuna dayalı bir uygulama oluşturduğumuz için bu klasörü kullanabilirsiniz. Bu nedenle, mevcut bir index.html dosyası var ve içeriğini burada oluşturulan yeni dosya ile değiştirmeniz yeterli. Kod Asistanı, render_template öğesini app.py dosyanıza aktarmanız gerektiğini de belirtir.

Web uygulaması kodunu index.html dosyasına kaydedin ve bu dosyayı templates klasörüne yerleştirmeyi unutmayın.

Uygulamayı yerel olarak çalıştırma

Şimdi, uygulamayı yerel olarak çalıştırarak uygulama şartlarını başlangıçtaki durumumuza göre doğrulayalım.

Yerel Flask sunucusunun hâlâ çalıştığından ve herhangi bir hata göstermediğinden emin olun. Hata varsa bunları giderin ve sunucuyu başlatın.

Uygulama çalışmaya başladıktan sonra ana URL'sini ziyaret edin. Aşağıda gösterildiği gibi, sunulan index.html dosyası gösterilmelidir:

8ca586acc4536879.png

Verilerdeki kategorilerden birini giriş olarak sağlayın (ör. AI) ve Search düğmesini tıklayın. Bu metrik, AI kategorisiyle etiketlenen oturumları göstermelidir.

165faded790a6c.png

İsteğe bağlı bir alıştırma olarak, oturumların her biri için süre, kategoriler, konuşmacılar ve özet gibi ek meta veriler gösterilebilir.

12. Test Durumu Oluşturma

Oturum API'sini oluşturduk. Şimdi farklı API yolları için birim testi senaryoları oluşturmak üzere Gemini Code Assist'i kullanma zamanı.

app.py dosyasını açık tutun ve aşağıdaki istemi girin:

Generate unit test cases for app routes. Use unittest module.

Aşağıdaki yanıtı aldık:

import unittest
from app import app

class FlaskAppTestCase(unittest.TestCase):

    def test_index(self):
        tester = app.test_client()
        response = tester.get('/')
        self.assertEqual(response.status_code, 200)

    def test_get_sessions(self):
        tester = app.test_client()
        response = tester.get('/sessions')
        self.assertEqual(response.status_code, 200)

    def test_get_session_by_id(self):
        tester = app.test_client()
        response = tester.get('/sessions/1')
        self.assertEqual(response.status_code, 200)

    def test_get_sessions_by_category(self):
        tester = app.test_client()
        response = tester.get('/sessions/categories/category1')
        self.assertEqual(response.status_code, 200)

if __name__ == '__main__':
    unittest.main()

Yukarıdaki kodu içeren tests.py adlı bir dosya oluşturun.

Test Senaryosu Oluşturma ile İlgili Not

Yukarıdakinden farklı bir kod listesi görebilirsiniz. Bu durum, test senaryolarının çalıştırılmasında bazı sorunlara neden olabilir. Örneğin, bazı çalıştırmalarımızda aşağıdaki önemli kod parçalarının atlandığını gördük:

from app import app

Test senaryolarını çağıracağımız mevcut Flask uygulamasını içe aktarmak için yukarıdaki kod gereklidir.

if __name__ == '__main__':

`unittest.main()`

Test senaryolarını çalıştırmak için yukarıdaki kod gereklidir.

Çalışacağından emin olmak için her bir test senaryosuna bakmanızı, oluşturulan koddaki assertEqual ve diğer koşulları kontrol etmenizi öneririz. Veriler Firestore koleksiyonunda harici olduğundan bunlara erişilemeyebilir ve sonuç olarak bazı sahte veriler kullanılabilir. Bu nedenle testler başarısız olabilir. Bu nedenle, test durumlarınızı buna göre değiştirin veya hemen ihtiyacınız olmayabilecek bazı test durumlarını yorum satırı olarak işaretleyin.

Örnek olarak, test durumlarını aşağıdaki komutu kullanarak çalıştırdık (Yerel API uç noktalarına çağrı yapılacağından yerel geliştirme sunucusunu çalıştırdığınızdan emin olun):

python tests.py

Aşağıdaki özet sonucu elde edildi:

Ran 4 tests in 0.274s

FAILED (failures=2)

Oturum kimliği 3. testte doğru olmadığı ve category1 adlı bir kategori olmadığı için bu gerçekten doğrudur.

.

Bu nedenle, test senaryolarını buna göre ayarlayın ve test edin.

13. Test Odaklı Geliştirme

Şimdi de Test Odaklı Geliştirme (TDD) metodolojisini izleyerek oturum API'mize yeni bir arama yöntemi eklemeye bakalım. Bu metodolojide önce test senaryoları yazılır, ardından eksik uygulama nedeniyle testlerin başarısız olması sağlanır ve Gemini Code Assist kullanılarak eksik uygulama oluşturulur. Böylece testler başarılı olur.

tests.py dosyasına gidin (tests.py dosyasını tüm testlerin başarılı olacağı şekilde düzelttiğinizi varsayıyoruz). Kod Asistanı'na aşağıdaki istemi girin:

Generate a new test case to search for sessions by speaker

Bu sayede, tests.py dosyasına uygun şekilde eklediğimiz aşağıdaki test durumu uygulaması elde edildi.

  def test_get_sessions_by_speaker(self):
        tester = app.test_client()
        response = tester.get('/sessions/speakers/speaker1')
        self.assertEqual(response.status_code, 200)
        self.assertEqual(response.json, [sessions.sessions[0], sessions.sessions[1]])

Testleri çalıştırırsanız aşağıdaki hatayı görürsünüz:

$ python tests.py 
.F.
======================================================================
FAIL: test_get_sessions_by_speaker (__main__.FlaskAppTestCase)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/home/romin/hello-world-5/tests.py", line 21, in test_get_sessions_by_speaker
    self.assertEqual(response.status_code, 200)
AssertionError: 404 != 200

----------------------------------------------------------------------
Ran 3 tests in 0.010s

FAILED (failures=1)

Bunun nedeni, test durumunun (/sessions/speakers/) yolunu çağırması ve app.py içinde bu yolun uygulanmamış olmasıdır.

Code Assist'ten bir uygulama sağlamasını isteyelim. app.py dosyasına gidin ve Code Assist'e aşağıdaki istemi verin:

Add a new route to search for sessions by a specific speaker

Code Assist'in önerdiği aşağıdaki uygulamayı app.py dosyasına ekledik:

@app.route('/sessions/speakers/<speaker>', methods=['GET'])
def get_sessions_by_speaker(speaker):
    sessions_by_speaker = [session for session in sessions.sessions if speaker in session['speakers']]
    return jsonify(sessions_by_speaker)

tests.py dosyasını tekrar inceledik ve hızlı bir kontrol için test senaryomuzu aşağıdaki gibi değiştirdik:

   def test_get_sessions_by_speaker(self):
       tester = app.test_client()
       response = tester.get('/sessions/speakers/Romin Irani')
       self.assertEqual(response.status_code, 200)
       self.assertEqual(len(response.json), 1)

Test sorunsuz şekilde çalıştırıldı. Oluşturulan test senaryolarına bakmak, Firestore'da sahip olabileceğiniz verilere bağlı olarak bunları biraz değiştirmek ve Python birim testi senaryolarında uygun assert* yöntemlerine sahip olmak sizin için bir alıştırma olarak bırakılmıştır.

14. Google Cloud Run'a dağıtma

Geliştirme kalitemizden memnun olduğumuza göre son adımımız bu uygulamayı Google Cloud Run'a dağıtmak olacak. Ancak belki de her ihtimale karşı Code Assist'e bir şeyi unutup unutmadığımızı sormalıyız. app.py açıkken aşağıdaki istemi gönderin :

Is there something here I should change before I deploy to production?

Hata ayıklama işaretini kapatmayı unuttuğumuz için bu soruyu sormanız iyi oldu :

2f87ed3a811fb218.png

Belirtildiği gibi, hata ayıklamayı devre dışı bırakın ve uygulamayı doğrudan kaynaktan (önce container oluşturmaya gerek kalmadan) Cloud Run'a dağıtmak için kullanılabilecek gcloud komutuyla ilgili Gemini Code Assist'e sorun.

Aşağıdaki istemi girin:

I would like to deploy the application to Cloud Run directly from source. What is the gcloud command to do that?

Yukarıdaki istemin birkaç varyasyonunu deneyin. Denemeye çalıştığımız bir diğer yöntem ise şuydu:

I would like to deploy this application to Cloud Run. I don't want to build a container image locally but deploy directly from source to Cloud Run. What is the gcloud command for that?

İdeal olarak aşağıdaki gcloud komutunu almanız gerekir:

gcloud run deploy sessions --source .

Ayrıca şunları da alabilirsiniz:

gcloud run deploy <service-name> --source . \
—-platform managed \
—-allow-unauthenticated

Yukarıdaki komutu uygulamanın kök klasöründen çalıştırın. region istendiğinde us-central1'ı, unauthenticated invocations izni istendiğinde ise Y'ı seçin. Ayrıca Artifact Registry, Cloud Build ve Cloud Run gibi Google Cloud API'lerini etkinleştirmeniz ve Artifact Registry deposu oluşturma izni vermeniz de istenebilir. Lütfen izni verin.

Dağıtım işleminin tamamlanması yaklaşık 2 dakika sürer. Lütfen bekleyin.

Başarıyla dağıtıldıktan sonra Cloud Run hizmeti URL'sini görürsünüz. Herkese açık URL'yi ziyaret ettiğinizde aynı web uygulamasının başarıyla dağıtıldığını ve çalıştığını görmeniz gerekir.

c5322d0fd3e0f616.png

Tebrikler, çok iyi iş çıkardınız.

15. (İsteğe bağlı) Cloud Logging'i kullanma

Uygulama günlüklerinin Google Cloud hizmetlerinden birinde (Cloud Logging) merkezi olarak tutulmasını sağlayacak şekilde uygulamamıza günlük kaydı özelliğini ekleyebiliriz. Ardından, günlük girişlerini anlamak için Observability Gemini özelliğini de kullanabiliriz.

Bunu yapmak için öncelikle Google Cloud'dan mevcut bir Python Cloud Logging kitaplığını kullanmamız ve bu kitaplığı bilgilendirici, uyarı veya hata mesajlarını (günlüğe / önem düzeyine bağlı olarak) kaydetmek için kullanmamız gerekir.

Önce Code Assist'e bu soruyu sormayı deneyelim. Aşağıdaki istemi deneyin:

How do I use the google-cloud-logging package in Python?

Aşağıdaki gibi, konuyla ilgili bazı bilgiler içeren bir yanıt alırsınız:

2472e1ccaf8a217d.png

Kategoriye göre oturum arayan işleve günlük kaydı ifadeleri ekleyelim.

İlk olarak google-cloud-logging Python paketini requirements.txt dosyasına ekleyin.

Ardından, günlük kaydını uygulamak için kodu nasıl entegre ettiğimizi gösteren bir kod snippet'i geliyor:

...
from google.cloud import logging
...
app = Flask(__name__)

# Create a logger
logger = logging.Client().logger('my-log')

@app.route('/sessions/categories/<category>', methods=['GET'])
def get_sessions_by_category(category):
   logger.log_text(f"Fetching sessions with category {category}")
   sessions_by_category = [session for session in sessions.sessions if category in session['categories']]
   logger.log_text(f'Found {len(sessions_by_category)} sessions with category {category}')
   return jsonify(sessions_by_category)

# # Other App Routes

Önceki bölümde kullandığınız komutla hizmeti tekrar Cloud Run'a dağıtın. Dağıtım tamamlandıktan sonra /sessions/categories/<category> uç noktasına birkaç çağrı gönderin.

Cloud Console → Logs Explorer sayfasına gidin.

59e297577570695.png

...ve aşağıdaki şekilde gösterildiği gibi bu günlük kaydı ifadelerini filtreleyebilmeniz gerekir:

914f1fb6cac30a89.png

Günlük ifadelerinden herhangi birini tıklayıp genişletebilir ve ardından Explain this log entry simgesini tıklayabilirsiniz. Bu simge, günlük girişini açıklamak için Gemini'ı kullanır. Google Cloud için Gemini'ı etkinleştirmediyseniz Cloud AI Companion API'yi etkinleştirmeniz istenir. Lütfen talimatlara uygun şekilde devam edin.

Örnek bir yanıt aşağıda verilmiştir:

7fc9783910fa92cc.png

16. Tebrikler

Tebrikler, sıfırdan bir uygulama oluşturmayı başardınız ve tasarım, geliştirme, test ve dağıtım dahil olmak üzere SDLC'nin birçok yönünde Gemini Code Assist'i kullandınız.

Yapabilecekleriniz

Şu codelab'lere göz atın:

Referans belgeler