جریان توسعه Google Wallet pass

Google Wallet API مجموعه ای از پیش تعریف شده از انواع پاس را ارائه می دهد که برای موارد استفاده خاص، مانند کارت هدیه، کارت پرواز، بلیط رویداد و موارد دیگر بهینه شده اند. همچنین یک نوع پاس عمومی وجود دارد که برای موارد استفاده در نظر گرفته شده است که در آن نوع پاس خاصی در دسترس نیست.

این مقاله قصد دارد شما را با مراحل اساسی مورد نیاز برای ایجاد و صدور مجوز با استفاده از Google Wallet API آشنا کند. راه‌های متعددی برای انجام برخی از مراحل زیر وجود دارد، اما در سطح بالا، همه انواع پاس‌ها با پیروی از یک جریان توسعه اولیه ایجاد می‌شوند.

برای بررسی دقیق ایجاد مجوز، به راهنمای وب، ایمیل، و پیامک یا برنامه‌های Android مراجعه کنید.

واسه چیه

یک کلاس Passes مجموعه‌ای از ویژگی‌ها را تعریف می‌کند که در چندین پاس مشترک هستند، شبیه به یک الگو. به عنوان مثال، اگر بلیت یک رویداد را صادر می‌کردید، کلاس پاس‌ها فیلدهایی را تعریف می‌کند که در همه بلیط‌ها یکسان هستند، مانند نام رویداد، تاریخ و زمان.

هر مجوزی که صادر می کنید باید به یک کلاس پاس ها ارجاع دهد. همچنین باید به هر کلاس Passes که ایجاد می کنید یک شناسه منحصر به فرد اختصاص دهید، که برای ارجاع به آن هنگام ایجاد مجوز استفاده می شود.

چگونه انجام می شود

یک کلاس پاس در قالب JSON تعریف شده است و می‌تواند با Google Wallet REST API، Android SDK یا در Google Wallet Business Console ایجاد شود.

نمایش نمونه پاس‌های کلاس

{
  "id": "ISSUER_ID.EVENT_CLASS_ID",
  "issuerName": "[TEST ONLY] Heraldic Event",
  "localizedIssuerName": {
    "defaultValue": {
      "language": "en-US",
      "value": "[TEST ONLY] Heraldic Event"
    }
  },
  "logo": {
    "sourceUri": {
      "uri": "https://images.unsplash.com/photo-1475721027785-f74eccf877e2?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&auto=format&fit=crop&w=660&h=660"
    },
    "contentDescription": {
      "defaultValue": {
        "language": "en-US",
        "value": "LOGO_IMAGE_DESCRIPTION"
      }
    }
  },
  "eventName": {
    "defaultValue": {
      "language": "en-US",
      "value": "Google Live"
    }
  },
  "venue": {
    "name": {
      "defaultValue": {
        "language": "en-US",
        "value": "Shoreline Amphitheater"
      }
    },
    "address": {
      "defaultValue": {
        "language": "en-US",
        "value": "ADDRESS_OF_THE_VENUE"
      }
    }
  },
  "dateTime": {
    "start": "2023-04-12T11:30"
  },
  "reviewStatus": "UNDER_REVIEW",
  "hexBackgroundColor": "#264750",
  "heroImage": {
    "sourceUri": {
      "uri": "https://images.unsplash.com/photo-1501281668745-f7f57925c3b4?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&auto=format&fit=crop&w=1032&h=336"
    },
    "contentDescription": {
      "defaultValue": {
        "language": "en-US",
        "value": "HERO_IMAGE_DESCRIPTION"
      }
    }
  }
}
    

واسه چیه

یک Object Passes خصوصیات یک پاس منحصر به فرد را تعریف می کند که برای یک کاربر خاص صادر می شود. به عنوان مثال، Object Passes برای بلیط رویداد، فیلدهایی را تعریف می کند که منحصر به یک بلیط خاص هستند، مانند شماره صندلی یا یک کد QR برای آن بلیط.

وقتی یک Object Passes ایجاد می‌شود، Google Wallet API یک مجوز جدید را ذخیره می‌کند و آن را با حساب صادرکننده شما مرتبط می‌کند. این پاس ذخیره شده ترکیبی از ویژگی های منحصر به فرد Passes Object و ویژگی های قالب مربوط به Passes Class است.

همچنین باید به هر Object Passes یک شناسه منحصر به فرد اختصاص دهید که برای ارجاع به آن هنگام صدور مجوز استفاده می شود.

چگونه انجام می شود

یک Object Passes فرمت JSON تعریف شده است و می تواند با Google Wallet REST API یا Android SDK ایجاد شود.

نمایش مثال Passes Object

{
  "id": "ISSUER_ID.OBJECT_ID",
  "classId": "ISSUER_ID.EVENT_CLASS_ID",
  "state": "ACTIVE",
  "seatInfo": {
    "seat": {
      "defaultValue": {
        "language": "en-us",
        "value": "5"
      }
    },
    "row": {
      "defaultValue": {
        "language": "en-us",
        "value": "G"
      }
    },
    "section": {
      "defaultValue": {
        "language": "en-us",
        "value": "40"
      }
    },
    "gate": {
      "defaultValue": {
        "language": "en-us",
        "value": "3A"
      }
    }
  },
  "barcode": {
    "type": "QR_CODE",
    "value": "BARCODE_VALUE",
    "alternateText": ""
  }
}
    

واسه چیه

برای صدور مجوز برای یک کاربر، یک کلاس پاس و شیء پاس باید در یک توکن وب JSON (JWT) کدگذاری شود. فرمت JWT یک استاندارد مشترک و باز برای ارائه دعاوی بین دو طرف است. در مورد صدور مجوز با Google Wallet API، از JWT ها برای ارسال ادعایی استفاده می شود که یک کاربر حق دسترسی به مجوز خاصی را دارد که با حساب صادر کننده شما مرتبط است.

هنگامی که یک JWT به API Google Wallet ارسال می‌شود، از داده‌های کدگذاری شده برای شناسایی یک مجوز خاص و صدور آن برای کاربر استفاده می‌شود. اگر مجوز قبلاً صادر شده باشد، این داده همچنین به Google Wallet API اجازه می‌دهد تشخیص دهد که مجوز تکراری است تا بیش از یک بار به Google Wallet کاربر اضافه نشود.

چگونه انجام می شود

JWT ها در قالب JSON بر اساس مشخصات JWT تعریف شده اند. برای تعریف JWT برای صدور مجوز با Google Wallet API، اطلاعات مجوزی را که می‌خواهید صادر کنید در ویژگی payload JWT ارائه می‌کنید.

نمونه JWT را نشان دهید

{
  "iss": "issuer@example.com",
  "aud": "google",
  "typ": "savetowallet",
  "iat": 1696877738,
  "origins": [
    "www.example.com"
  ],
  "payload": {
    "eventTicketObjects": [
      {
        "id": "ISSUER_ID.LOYALTY_OBJECT_SUFFIX"
      }
    ]
  }
}
    

واسه چیه

همه JWT‌هایی که برای صدور مجوز به Google Wallet API ارسال می‌شوند باید با اعتبارنامه‌هایی که قبلاً در Google Wallet Business Console ارائه کرده‌اید امضا شوند. امضا از اعتبارنامه‌های شما برای رمزگذاری JWT استفاده می‌کند تا پاس‌های شما ایمن بمانند، و به Google Wallet API اجازه می‌دهد تا تأیید کند که جزئیات مجوز رمزگذاری‌شده در آن معتبر هستند و با حساب صادرکننده شما مرتبط هستند.

چگونه انجام می شود

کتابخانه های سرویس گیرنده Google Wallet و Android SDK روش های راحتی را برای امضای JWT های شما ارائه می دهند. همچنین کتابخانه‌های متن‌باز متعددی وجود دارند که پیچیدگی امضای کد را برای انتخاب شما مدیریت می‌کنند.

برای کسانی که از Google Wallet REST API برای صدور مجوز استفاده می کنند، JWT با یک کلید حساب Google Cloud Service امضا می شود. برای کسانی که از Google Wallet Android SDK استفاده می کنند، SDK به طور خودکار امضای JWT را با اثر انگشت SHA-1 گواهی امضای برنامه شما انجام می دهد.

برای محافظت از اعتبارنامه‌های خود، JWT‌ها فقط باید در سرور شما یا با استفاده از Google Wallet Android SDK در برنامه شما امضا شوند.

نمونه امضای کد را نشان دهید

جاوا

  // Create the JWT as a HashMap object
  HashMap claims = new HashMap();
  claims.put("iss", ((ServiceAccountCredentials) credentials).getClientEmail());
  claims.put("aud", "google");
  claims.put("origins", Arrays.asList("www.example.com"));
  claims.put("typ", "savetowallet");

  // Create the Google Wallet payload and add to the JWT
  HashMap payload = new HashMap();
  payload.put("eventTicketObjects", Arrays.asList(newObject));
  claims.put("payload", payload);

  // Google Cloud service account credentials are used to sign the JWT
  Algorithm algorithm =
      Algorithm.RSA256(
          null, (RSAPrivateKey) ((ServiceAccountCredentials) credentials).getPrivateKey());
  String token = JWT.create().withPayload(claims).sign(algorithm);
        

Node.JS

  // Create the JWT claims
  let claims = {
    iss: this.credentials.client_email,
    aud: 'google',
    origins: ['www.example.com'],
    typ: 'savetowallet',
    payload: {
      eventTicketObjects: [newObject]
    },
  };

  // The service account credentials are used to sign the JWT
  let token = jwt.sign(claims, this.credentials.private_key, { algorithm: 'RS256' });
        

پایتون

  # Create the JWT claims
  claims = {
      'iss': self.credentials.service_account_email,
      'aud': 'google',
      'origins': ['www.example.com'],
      'typ': 'savetowallet',
      'payload': {
          # The listed classes and objects will be created
          'eventTicketObjects': [new_object]
      }
  }

  # The service account credentials are used to sign the JWT
  signer = crypt.RSASigner.from_service_account_file(self.key_file_path)
  token = jwt.encode(signer, claims).decode('utf-8')
        

واسه چیه

هنگامی که یک JWT امضا شده ایجاد کردید، آماده هستید تا پاس خود را برای یک کاربر Google Wallet صادر کنید! این کار با ارائه دکمه یا پیوند «افزودن به Google Wallet» به کاربر انجام می‌شود. هنگامی که کاربر روی دکمه یا لینک کلیک می کند، JWT امضا شده به API Google Wallet ارسال می شود، که سپس با استفاده از اطلاعات کاربری ذخیره شده شما، آن را رمزگشایی می کند. هنگامی که امضای JWT احراز هویت شد، مجوز برای کاربر صادر می شود تا در کیف پول Google خود ذخیره کند.

چگونه انجام می شود

برای ایجاد دکمه «افزودن به Google Wallet» برای یک برنامه Android، از Google Wallet Android SDK استفاده کنید که روش‌هایی را برای ایجاد دکمه ارائه می‌کند. برای همه پلتفرم‌های دیگر، از جمله وب، ایمیل، و پیام متنی، یک پیوند با قالب https://pay.google.com/gp/v/save/<signed_jwt> ایجاد کنید. در صورت امکان، بهتر است این پیوند را به عنوان دکمه «افزودن به Google Wallet» به کاربر تحویل دهید.

برای اطلاعات بیشتر در مورد استفاده از دکمه «افزودن به Google Wallet»، دستورالعمل‌های برند Google Wallet API را ببینید.

نمایش کد نمونه

  https://pay.google.com/gp/v/save/<signed_jwt>
        

Android SDK

  private lateinit var walletClient: PayClient
  private val addToGoogleWalletRequestCode = 1000
  private lateinit var addToGoogleWalletButton: View

  override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    walletClient = Pay.getClient(this)
    addToGoogleWalletButton.setOnClickListener {
      walletClient.savePasses(newObjectJson, this, addToGoogleWalletRequestCode)
    }
  }
        

هنگامی که کاربر شما مجوز صادر شده را ذخیره کرد، همراه با سایر مجوزهایی که ذخیره کرده است در برنامه Google Wallet او ظاهر می شود.

ایجاد اشیاء و کلاس های پاس در JWT

Passes Classes and Passes Objects ممکن است از قبل با استفاده از Google Wallet REST API یا Android SDK ایجاد شود. پس از ایجاد، از آنها برای صدور مجوز با ارجاع به شناسه آنها استفاده می شود.

همچنین، می‌توانید کلاس‌های پاس‌ها و اشیاء پاس‌ها را «در زمان مقرر» با جاسازی JSON آن‌ها مستقیماً در JWT ایجاد کنید که برای صدور مجوز به کاربر استفاده می‌شود. در این روش، Passes Classes و Passes Objects توسط Google Wallet API ایجاد می شود که JWT امضا شده با استفاده از دکمه یا پیوند «افزودن به Google Wallet» ارسال شود.

به عنوان مثال، شکل زیر یک JWT را با یک کلاس پاس جدید نشان می‌دهد و شیء عبور تعریف شده با استفاده از ویژگی‌های payload.eventTicketClasses و payload.eventTicketObjects . توجه داشته باشید که این ویژگی ها آرایه هستند، بنابراین می توانند یک یا چند کلاس پاس یا شیء عبور را بپذیرند. همچنین می‌توانید فقط یک شی Passes جدید را در JWT مشخص کنید که به یک کلاس پاس موجود با شناسه آن ارجاع می‌دهد.

نمونه JWT را نشان دهید

  {
    "iss": "issuer@example.com",
    "aud": "google",
    "typ": "savetowallet",
    "iat": 1696877738,
    "origins": [
      "www.example.com"
    ],
    "payload": {
      "eventTicketClasses": [{
        "id": "ISSUER_ID.EVENT_CLASS_ID",
        "issuerName": "[TEST ONLY] Heraldic Event",
        "localizedIssuerName": {
          "defaultValue": {
            "language": "en-US",
            "value": "[TEST ONLY] Heraldic Event"
          }
        },
        "logo": {
          "sourceUri": {
            "uri": "https://images.unsplash.com/photo-1475721027785-f74eccf877e2?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&auto=format&fit=crop&w=660&h=660"
          },
          "contentDescription": {
            "defaultValue": {
              "language": "en-US",
              "value": "LOGO_IMAGE_DESCRIPTION"
            }
          }
        },
        "eventName": {
          "defaultValue": {
            "language": "en-US",
            "value": "Google Live"
          }
        },
        "venue": {
          "name": {
            "defaultValue": {
              "language": "en-US",
              "value": "Shoreline Amphitheater"
            }
          },
          "address": {
            "defaultValue": {
              "language": "en-US",
              "value": "ADDRESS_OF_THE_VENUE"
            }
          }
        },
        "dateTime": {
          "start": "2023-04-12T11:30"
        },
        "reviewStatus": "UNDER_REVIEW",
        "hexBackgroundColor": "#264750",
        "heroImage": {
          "sourceUri": {
            "uri": "https://images.unsplash.com/photo-1501281668745-f7f57925c3b4?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&auto=format&fit=crop&w=1032&h=336"
          },
          "contentDescription": {
            "defaultValue": {
              "language": "en-US",
              "value": "HERO_IMAGE_DESCRIPTION"
            }
          }
        }
      }],
      "eventTicketObjects": [{
        "id": "ISSUER_ID.OBJECT_ID",
        "classId": "ISSUER_ID.EVENT_CLASS_ID",
        "state": "ACTIVE",
        "seatInfo": {
          "seat": {
            "defaultValue": {
              "language": "en-us",
              "value": "5"
            }
          },
          "row": {
            "defaultValue": {
              "language": "en-us",
              "value": "G"
            }
          },
          "section": {
            "defaultValue": {
              "language": "en-us",
              "value": "40"
            }
          },
          "gate": {
            "defaultValue": {
              "language": "en-us",
              "value": "3A"
            }
          }
        },
        "barcode": {
          "type": "QR_CODE",
          "value": "BARCODE_VALUE",
          "alternateText": ""
        }
      }]
    }
  }