Alan ve direktif sürümü belirleme stratejileri
Lütfen önce Şemayı alan sürümlemesi aracılığıyla geliştirme kılavuzunu okuyun; bu kılavuz Gato GraphQL'deki "field versioning" özelliğini açıklamaktadır.
Gato GraphQL, alanların ve direktiflerin versionConstraint argümanını almasına izin vererek kullanılacak alan/direktifin belirli sürümünü (yani uygulamasını) seçmeyi sağlar:
query GetPosts {
posts(versionConstraint: "^1.0") {
id
title(versionConstraint: ">=2.1")
excerpt @strUpperCase(versionConstraint: "~1.5.3")
}
}versionConstraint argümanını belirtmediğimizde ne olmalıdır? Örneğin, aşağıdaki queries içindeki surname alanı hangi sürüme çözümlenmeli?
query GetSurname {
account(id: 1) {
# Hangi sürüm kullanılmalı? 1.0.0? 2.0.0?
surname
}
}Burada iki endişemiz var:
- Hiçbiri sağlanmadığında kullanılacak varsayılan sürümü belirlemek
- İstemciyi aralarından seçim yapabileceği birden fazla sürüm olduğu konusunda bilgilendirmek
Bu endişeleri ele almadan önce, GraphQL'in queries çalıştırırken bağlamsal geri bildirim sağlama konusunda ne kadar iyi performans gösterdiğini öğrenmemiz gerekir.
Queries çalıştırırken bağlamsal geri bildirim sağlamak
GraphQL ile ilgili şu anda pek ideal olmayan bir durumu belirtmemiz gerekiyor: queries çalıştırırken iyi bağlamsal bilgi sunmuyor. Bu, deprecation'lar konusunda açıkça görülmektedir; deprecation verileri yalnızca Field ve Enum türleri üzerindeki isDeprecated ve deprecationReason alanları sorgulanarak introspection aracılığıyla gösterilmektedir:
{
__type(name: "Account") {
name
fields {
name
isDeprecated
deprecationReason
}
}
}Yanıt şöyle olacaktır:
{
"data": {
"__type": {
"name": "Account",
"fields": [
{
"name": "id",
"isDeprecated": false,
"deprecationReason": null
},
{
"name": "name",
"isDeprecated": false,
"deprecationReason": null
},
{
"name": "surname",
"isDeprecated": true,
"deprecationReason": "Use `personSurname`"
},
{
"name": "personSurname",
"isDeprecated": false,
"deprecationReason": null
}
]
}
}
}Ancak deprecated bir alanı içeren bir queries çalıştırıldığında…
query GetSurname {
account(id: 1) {
surname
}
}...deprecation bilgisi yanıtta görünmeyecektir:
{
"data": {
"account": {
"surname": "Owens"
}
}
}Bu, queries çalıştıran geliştiricinin şemanın güncellenip güncellenmediğini ve herhangi bir alanın deprecated olup olmadığını öğrenmek için aktif olarak introspection queries çalıştırması gerektiği anlamına gelir. Bu durum… ara sıra yaşanabilir mi? Büyük olasılıkla hiç yaşanmaz mı?
GraphQL API'sinin deprecated alanları içeren queries çalıştırırken deprecation bilgisi sağlaması, eski queries'lerin revize edilmesine yönelik büyük bir iyileştirme olurdu. Bu bilgi ideal olarak errors'dan sonra ve data'dan önce görünen yeni bir üst düzey deprecations girdisi altında verilebilir (spec'in yanıt formatı için önerisi izlenerek).
Bir deprecations üst düzey girdisi spec'in parçası olmadığından, Gato GraphQL'in "Proactive Feedback" özelliği, protokolü gerektiği gibi genişletmeye olanak tanıyan joker üst düzey extensions girdisini kullanarak queries yanıtında daha iyi geri bildirim desteği ekler:

Sürümleri uyarılar aracılığıyla duyurmak
GraphQL sunucusunun deprecation'ları sağlamak için extensions üst düzey girdisini kullanabildini az önce öğrendik. Bu aynı metodolojiden, geliştiriciye bir alanın sürümlendirildiğini bildirdiğimiz bir warnings girdisi eklemek için yararlanabiliriz. Bu bilgiyi her zaman sağlamıyoruz; yalnızca queries'in sürümlendirilmiş bir alanı içerdiği ve versionConstraint argümanının eksik olduğu durumlarda.
Bir alan için varsayılan sürümü tanımlamak
Uygulayabileceğimiz çeşitli yaklaşımlar vardır; bunlar arasında şunlar sayılabilir:
versionConstraint'i zorunlu kılmak- Belirli bir tarihe kadar varsayılan olarak eski sürümü kullanmak; o tarihte yeni sürüm varsayılan hale gelir
- Varsayılan olarak en son sürümü kullanmak ve queries geliştiricilerini hangi sürümü kullanacaklarını açıkça belirtmeye teşvik etmek
Bu stratejilerin her birini inceleyelim ve bu queries çalıştırıldığındaki yanıtlarına bakalım:
query GetSurname {
account(id: 1) {
surname
}
}1. versionConstraint'i zorunlu kılmak
Bu en açık olanıdır: alan argümanını zorunlu hale getirerek istemcinin sürüm kısıtlamasını belirtmemesini engellemek. Böylece sağlanmadığı her durumda queries bir hata döndürecektir.
Queries çalıştırıldığında şu yanıt alınır:
{
"errors": [
{
"message": "Argument 'versionConstraint' in field 'surname' cannot be empty"
}
],
"data": {
"account": {
"surname": null
}
}
}2. Yeni sürümün varsayılan hale geldiği belirli bir tarihe kadar eski sürümü varsayılan olarak kullanmak
Yeni sürümün varsayılan olacağı belirli bir tarihe kadar eski sürümü kullanmaya devam etmek. Bu geçiş süresinde, queries geliştiricilerinden o tarihten önce queries'deki yeni extensions.warnings girdisi aracılığıyla eski sürüme açıkça bir sürüm kısıtlaması eklemelerini istemek.
Queries çalıştırıldığında şu yanıt alınabilir:
{
"extensions": {
"warnings": [
{
"message": "Field 'surname' has a new version: '2.0.0'. This version will become the default one on January 1st. We advise you to use this new version already and test that it works fine; if you find any problem, please report the issue in https://github.com/mycompany/myproject/issues. To do the switch, please add the 'versionConstraint' field argument to your query (using Composer's semver constraint rules; see https://getcomposer.org/doc/articles/versions.md#writing-version-constraints): surname(versionConstraint:\"^2.0\"). If you are unable to switch to the new version, please make sure to explicitly point to the current version '1.0.0' before January 1st: surname(versionConstraint:\"^1.0\"). In case of doubt, please contact us at name@company.com.",
]
},
"data": {
"account": {
"surname": "Owens"
}
}
}3. En son sürümü kullanmak ve kullanıcıları hangi sürümü kullanacaklarını açıkça belirtmeye teşvik etmek
versionConstraint ayarlanmadığında alanın en son sürümünü kullanmak ve queries geliştiricilerini hangi sürümün kullanılması gerektiğini açıkça tanımlamaya teşvik etmek; yeni bir extensions.warnings girdisi aracılığıyla o alan için mevcut tüm sürümlerin listesini göstermek:
Queries çalıştırıldığında şu yanıt alınabilir:
{
"extensions": {
"warnings": [
{
"message": "Field 'surname' has more than 1 version. Please add the 'versionConstraint' field argument to your query to indicate which version to use (using Composer's semver constraint rules; see https://getcomposer.org/doc/articles/versions.md#writing-version-constraints). To use the latest version, use: surname(versionConstraint:\"^2.0\"). Available versions: '2.0.0', '1.0.0'.",
]
},
"data": {
"account": {
"surname": "Owens"
}
}
}Direktiflerin sürümlenmesi
Direktifleri sürümlemek için aynı stratejileri kullanabiliriz. Örneğin, sürüm kısıtlaması sağlanmadan queries çalıştırıldığında:
query {
post(by: { id: 1 }) {
title @strTitleCase
}
}Kullanılacak varsayılan bir sürüm varsayılabilir ve geliştiricinin queries'i revize etmesi için bir uyarı mesajı üretilebilir:
