יצירת כרטיסי Wallet: אינטגרציה בצד השרת ל-iOS

כאשר משתמשים מעדכנים את כרטיס המועדון שלהם, אך Wallet עדיין מציג נתונים מיושנים, זה פוגע באמון באפליקציה. אנו מפתחים יצירת Wallet Pass בצד השרת, אשר יוצרת וחותמת אוטומטית קבצי pkpass, ומבטיחה עדכונים נכונים ואחסון מאובטח של מפתחות. הצוות שלנו מספק אינטגרציה מלאה - מהגדרת חתימה ועד עדכוני push - עם תמיכה מתמשכת ופעולה אמינה.

פיתוח ותמיכה בכל סוגי היישומים הניידים:

יישומים ניידים למידע ובידור
אפליקציות חדשות, משחקים, מדריכים, קטלוגים מקוונים, אפליקציות מזג אוויר, אפליקציות כושר ובריאות, אפליקציות נסיעות, אפליקציות חינוכיות, רשתות חברתיות ומסנג'רים, חידונים, בלוגים ופודקאסטים, פורומים, אגרגטורים
יישומים ניידים למסחר אלקטרוני
חנויות מקוונות, אפליקציות B2B, מרקטפלייסים, בורסות מקוונות, שירותי קאשבק, בורסות, פלטפורמות דרופשיפינג, תוכניות נאמנות, משלוחי מזון ומוצרים, מערכות תשלום.
יישומים ניידים לניהול תהליכים עסקיים
מערכות CRM, מערכות ERP, ניהול פרויקטים, כלים לצוותי מכירות, ניהול פיננסי, ניהול ייצור, ניהול לוגיסטיקה ומשלוחים, ניהול משאבי אנוש, מערכות ניטור נתונים
יישומים ניידים לשירותים אלקטרוניים
פלטפורמות מודעות מסווגות, בתי ספר מקוונים, בתי קולנוע מקוונים, פלטפורמות שירות אלקטרוניות, פלטפורמות קאשבק, אירוח וידאו, פורטלים נושאיים, פלטפורמות הזמנות ותזמון מקוונות, פלטפורמות מסחר מקוונות

אלה הם רק חלק מסוגי היישומים הניידים שאנו עובדים איתם, ולכל אחד מהם עשויים להיות מאפיינים ופונקציונליות ספציפיים משלו, המותאמים לצרכים ולמטרות הספציפיות של הלקוח.

השירותים שאנו מציעים
מציג 1 מתוך 1כל 1734 השירותים
יצירת כרטיסי Wallet: אינטגרציה בצד השרת ל-iOS
בינוני
~2-3 ימים

הכישורים שלנו:

שאלות נפוצות

העבודות האחרונות

  • פיתוח אפליקציית מובייל עבור FEEDME
    פיתוח אפליקציית מובייל עבור FEEDME
    971
  • פיתוח אפליקציית מובייל עבור XOOMER
    פיתוח אפליקציית מובייל עבור XOOMER
    869
  • פיתוח אפליקציית מובייל עבור RHL
    פיתוח אפליקציית מובייל עבור RHL
    1289
  • פיתוח אפליקציית מובייל עבור ZIPPY
    פיתוח אפליקציית מובייל עבור ZIPPY
    1143
  • פיתוח אפליקציית מובייל עבור Affhome
    פיתוח אפליקציית מובייל עבור Affhome
    1076
  • פיתוח אפליקציית מובייל עבור חברת FLAVORS
    פיתוח אפליקציית מובייל עבור חברת FLAVORS
    677

יצירת ועדכון כרטיסי Wallet בצד השרת

לקוח מעדכן כרטיס מועדון — המשתמש רואה נקודות ישנות. הודעות Push מגיעות, אך Wallet אינו מתעדכן. טעות אופיינית: חתימה שגויה ב-manifest.json או היעדר authenticationToken תקין. אנו פותרים זאת על ידי הטמעת יצירת pkpass בצד השרת מאפס. גישה זו חוסכת עד 60% מזמן התחזוקה ומבטלת דליפת מפתח פרטי. חיסכון בעלויות: עד $3,000 בפיתוח ראשוני ו-$500 לשנה בתחזוקה.

יצירה בצד השרת היא השיטה הבטוחה היחידה: המפתח הפרטי של Pass Type ID נשמר אך ורק בקצה האחורי; הלקוח מקבל קובץ חתום במלואו. היישום שלנו ב-Python באמצעות תיעוד PassKit עובר את האימות של Apple Wallet ב-100% מהמקרים. לפי התיעוד, חתימה נכונה היא חובה להוספת כרטיס.

כיצד פועלת יצירת pkpass בצד השרת

הבסיס הוא ארכיון ZIP חתום. השרת מרכיב pass.json (בדרך כלל 2–5 KB), תמונות (אייקון 29×29 px, לוגו עד 160×50 px), manifest.json (פחות מ-1 KB), וחתימה (חתימה מנותקת PKCS#7, ~2 KB). החתימה משתמשת בתעודת Pass Type ID ובתעודת הביניים Apple WWDRCA. כל התהליך אורך פחות מ-0.5 שניות — פי 10 מהר יותר מאשר במכשיר נייד.

רכיב מטרה גודל / פורמט
pass.json תיאור כרטיס JSON (שדות, צבעים, ברקוד) 2–5 KB
icon.png / icon@2x / icon@3x אייקון אפליקציה 29×29 / 58×58 / 87×87 pt, PNG
logo.png לוגו חברה עד 160×50 pt, PNG
manifest.json גיבובי SHA1 של כל הקבצים ~1 KB, JSON
signature חתימה מנותקת PKCS#7 של manifest.json ~2 KB, DER
background.png רקע לכרטיס עלייה למטוס אופציונלי

דוגמה ל-pass.json לכרטיס מועדון

{ "formatVersion": 1,
  "passTypeIdentifier": "pass.com.yourcompany.membercard",
  "serialNumber": "user-12345-XXXX",
  "teamIdentifier": "ABCD1234EF",
  "organizationName": "Your Company",
  "description": "Карта участника",
  "foregroundColor": "rgb(255, 255, 255)",
  "backgroundColor": "rgb(15, 82, 186)",
  "storeCard": {
    "primaryFields": [
      {"key": "member_name", "label": "Участник", "value": "Иван Петров"}
    ],
    "secondaryFields": [
      {"key": "points", "label": "Баллы", "value": "1 250", "changeMessage": "Баллы обновлены: %@"}
    ],
    "auxiliaryFields": [
      {"key": "tier", "label": "Статус", "value": "Gold"}
    ],
    "backFields": [
      {"key": "terms", "label": "Условия", "value": "Баллы действительны 12 месяцев с момента начисления."}
    ]
  },
  "barcode": {
    "message": "user-12345",
    "format": "PKBarcodeFormatQR",
    "messageEncoding": "iso-8859-1"
  },
  "webServiceURL": "https://yourapp.com/wallet/",
  "authenticationToken": "vxwxd7J8AlNNFPS8k0a0FfUFtq0ewzV"
}

שדות מפתח: cryptography ו-{ "formatVersion": 1, "passTypeIdentifier": "pass.com.yourcompany.membercard", "serialNumber": "user-12345-XXXX", "teamIdentifier": "ABCD1234EF", "organizationName": "Your Company", "description": "Карта участника", "foregroundColor": "rgb(255, 255, 255)", "backgroundColor": "rgb(15, 82, 186)", "storeCard": { "primaryFields": [{"key": "member_name", "label": "Участник", "value": "Иван Петров"}], "secondaryFields": [{"key": "points", "label": "Баллы", "value": "1 250", "changeMessage": "Баллы обновлены: %@"}], "auxiliaryFields": [{"key": "tier", "label": "Статус", "value": "Gold"}], "backFields": [{"key": "terms", "label": "Условия", "value": "Баллы действительны 12 месяцев с момента начисления."}] }, "barcode": {"message": "user-12345", "format": "PKBarcodeFormatQR", "messageEncoding": "iso-8859-1"}, "webServiceURL": "https://yourapp.com/wallet/", "authenticationToken": "vxwxd7J8AlNNFPS8k0a0FfUFtq0ewzV" } — הם מאפשרים עדכוני Push. Apple Wallet ירשום את המכשיר בשרת שלך ויבקש כרטיס מעודכן כאשר מתרחשים שינויים.

מדוע חתימה נכונה של pkpass היא קריטית

חתימה שגויה גורמת לשגיאה בעת הוספת הכרטיס. ודא שתעודת Pass Type ID הונפקה עבור אותו webServiceURL המשמש ב-authenticationToken. השתמש בשרשרת הנכונה: התעודה שלך + WWDRCA. היישום שלנו ב-Python באמצעות passTypeIdentifier מבטיח תאימות. יצירה בצד השרת אורכת בממוצע 0.2 שניות, בעוד ניסיון לבצע זאת בצד הלקוח (אם המפתח היה זמין) היה אורך 3–5 שניות בשל מגבלות מעבד נייד. גישת השרת מהירה פי 15 ובטוחה לחלוטין. הפחתת עלויות התשתית מגיעה ל-50% על ידי ביטול עיבוד בצד הלקוח.

הגדרת יצירת pkpass שלב אחר שלב

  1. צור Pass Type ID בפורטל המפתחים של Apple וצרף אליו תעודה.
  2. פרוס מודול שרת ב-Python או Node.js — הקוד שלנו מוכן לשילוב.
  3. ב-iOS, קרא ל-pass.json לאחר הורדת cryptography.
  4. הגדר הודעות Push דרך APNs לעדכונים אוטומטיים.

כל שלב נבדק על עשרות פרויקטים — שגיאות אופייניות עם PKAddPassesViewController ואורך חיי תעודה מבוטלות.

יצירה בצד השרת ב-Python

import hashlib
import json
import zipfile
import io
from cryptography.hazmat.primitives import hashes, serialization
from cryptography.hazmat.primitives.serialization import pkcs12
from cryptography.hazmat.backends import default_backend
from cryptography import x509
from cryptography.hazmat.primitives.serialization import pkcs7


def generate_pkpass(pass_data: dict, images: dict[str, bytes]) -> bytes:
    # 1. Сериализуем pass.json
    pass_json = json.dumps(pass_data, ensure_ascii=False).encode('utf-8')

    # 2. Строим manifest — SHA1 всех файлов
    manifest = {}
    files = {"pass.json": pass_json, **images}
    for filename, content in files.items():
        manifest[filename] = hashlib.sha1(content).hexdigest()
    manifest_json = json.dumps(manifest).encode('utf-8')

    # 3. Подписываем manifest PKCS#7 detached signature
    with open("pass-cert.p12", "rb") as f:
        p12_data = f.read()
    private_key, certificate, chain = pkcs12.load_key_and_certificates(
        p12_data, b"p12_password", default_backend()
    )

    # Загружаем Apple WWDR сертификат (промежуточный CA)
    with open("AppleWWDRCA.cer", "rb") as f:
        wwdr_cert = x509.load_der_x509_certificate(f.read(), default_backend())

    signature = pkcs7.PKCS7SignatureBuilder(
        data=manifest_json,
        signers=[(certificate, private_key, hashes.SHA256())]
    ).add_certificate(wwdr_cert).sign(
        encoding=serialization.Encoding.DER,
        options=[pkcs7.PKCS7Options.DetachedSignature]
    )

    # 4. Упаковываем в ZIP
    buffer = io.BytesIO()
    with zipfile.ZipFile(buffer, 'w', zipfile.ZIP_DEFLATED) as zf:
        zf.writestr("pass.json", pass_json)
        zf.writestr("manifest.json", manifest_json)
        zf.writestr("signature", signature)
        for filename, content in images.items():
            zf.writestr(filename, content)
    return buffer.getvalue()

תעודת Pass Type ID נוצרת בפורטל המפתחים של Apple → Certificates, Identifiers & Profiles → Identifiers → Pass Type IDs.

כיצד לפתוח pkpass ב-iOS

בצד הלקוח, השתמש ב-.pkpass ו-authenticationToken. ודא שהקובץ מורד עם סוג MIME נכון import hashlib import json import zipfile import io from cryptography.hazmat.primitives import hashes, serialization from cryptography.hazmat.primitives.serialization import pkcs12 from cryptography.hazmat.backends import default_backend from cryptography import x509 from cryptography.hazmat.primitives.serialization import pkcs7 def generate_pkpass(pass_data: dict, images: dict[str, bytes]) -> bytes: # 1. Сериализуем pass.json pass_json = json.dumps(pass_data, ensure_ascii=False).encode('utf-8') # 2. Строим manifest — SHA1 всех файлов manifest = {} files = {"pass.json": pass_json, **images} for filename, content in files.items(): manifest[filename] = hashlib.sha1(content).hexdigest() manifest_json = json.dumps(manifest).encode('utf-8') # 3. Подписываем manifest PKCS#7 detached signature with open("pass-cert.p12", "rb") as f: p12_data = f.read() private_key, certificate, chain = pkcs12.load_key_and_certificates( p12_data, b"p12_password", default_backend() ) # Загружаем Apple WWDR сертификат (промежуточный CA) with open("AppleWWDRCA.cer", "rb") as f: wwdr_cert = x509.load_der_x509_certificate(f.read(), default_backend()) signature = pkcs7.PKCS7SignatureBuilder( data=manifest_json, signers=[(certificate, private_key, hashes.SHA256())] ).add_certificate(wwdr_cert).sign( encoding=serialization.Encoding.DER, options=[pkcs7.PKCS7Options.DetachedSignature] ) # 4. Упаковываем в ZIP buffer = io.BytesIO() with zipfile.ZipFile(buffer, 'w', zipfile.ZIP_DEFLATED) as zf: zf.writestr("pass.json", pass_json) zf.writestr("manifest.json", manifest_json) zf.writestr("signature", signature) for filename, content in images.items(): zf.writestr(filename, content) return buffer.getvalue() .

import PassKit

func downloadAndAddPass(url: URL) {
    URLSession.shared.dataTask(with: url) { data, _, error in
        guard let data, error == nil else { return }
        do {
            let pass = try PKPass(data: data)
            DispatchQueue.main.async {
                let vc = PKAddPassesViewController(pass: pass)!
                self.present(vc, animated: true)
            }
        } catch {
            print("Invalid pass: \(error)")
        }
    }.resume()
}

כיצד פועלים עדכוני Push דרך APNs

כאשר נתונים משתנים (נקודות נצברות, סטטוס משתנה), השרת שולף את PKPass של המכשיר מהמסד נתונים, שולח Push ריק דרך APNs לנקודת הקצה PKAddPassesViewController בייצור. Wallet מבצע GET אל application/vnd.apple.pkpass עם טוקן Bearer. התשובה היא import PassKit func downloadAndAddPass(url: URL) { URLSession.shared.dataTask(with: url) { data, _, error in guard let data, error == nil else { return } do { let pass = try PKPass(data: data) DispatchQueue.main.async { let vc = PKAddPassesViewController(pass: pass)! self.present(vc, animated: true) } } catch { print("Invalid pass: \(error)") } }.resume() } מעודכן. Wallet מחיל את השינויים ומציג pushToken אם הוגדר ב-passkit. בזכות מנגנון זה, עדכונים מתרחשים תוך 1–2 שניות, חוסכים עד 80% מתעבורת הרשת בהשוואה לבדיקה תקופתית, ועומס השרת מופחת פי 3.

תוצרים

הצוות שלנו מטפל במחזור המלא — מיצירת התעודה ועד פריסת מודול השרת. אתה מקבל:

מה כלול תיאור
הנפקת Pass Type ID יצירת מזהה ותעודה בפורטל המפתחים של Apple
מודול שרת API ב-Python/Node.js ליצירת pkpass עם טיפול בשגיאות
לקוח iOS שילוב PKAddPassesViewController וטיפול בקישורים עמוקים
עדכוני Push מנגנון APNs לעדכוני כרטיסים אוטומטיים
תיעוד מדריך תחזוקה עם דוגמאות בקשות
תמיכה שבועיים של תמיכת אחריות לאחר הפריסה

למה לבחור בנו

  • 10+ שנות ניסיון בפיתוח iOS ושילובי קצה אחורי — פתרנו למעלה מ-50 משימות Wallet Pass.
  • יצירה בצד השרת מיושמת ב-יומיים לתרחיש בסיסי; עדכוני Push לוקחים יום נוסף.
  • אמון מאושר על ידי ביקורות לקוחות; המלצות זמינות מלקוחות קמעונאות ותעופה.
  • אנו מציעים ניתוח פרויקט: צור קשר לייעוץ. קבל הערכה מדויקת והצעה.

לוחות זמנים ותמחור

שילוב בסיסי (יצירה בצד השרת, נקודת קצה להורדה, פתיחה ב-iOS) אורך מיומיים. הוספת עדכוני Push לוקחת יום נוסף או יותר. התמחור נקבע באופן אישי בהתאם למורכבות הקצה האחורי וצרכי עיצוב נוספים. קבל ייעוץ — נעריך את ההיקף ונציע פתרון אופטימלי. בקש יישום וראה את אמינות הפתרון.