python - 在 Python 中验证 Windows 8 应用内购买收据签名

标签 python xml windows-8 in-app-purchase xmlsec

我正在尝试使用 pyxmlsec 验证 Windows 8 收据 XML 签名。

我的收据 (receipt.xml) 如下所示:

<?xml version="1.0"?><Receipt Version="1.0" ReceiptDate="2012-08-30T23:10:05Z" CertificateId="b809e47cd0110a4db043b3f73e83acd917fe1336" ReceiptDeviceId="4e362949-acc3-fe3a-e71b-89893eb4f528"><AppReceipt Id="8ffa256d-eca8-712a-7cf8-cbf5522df24b" AppId="55428GreenlakeApps.CurrentAppSimulatorEventTest_z7q3q7z11crfr" PurchaseDate="2012-06-04T23:07:24Z" LicenseType="Full" /><ProductReceipt Id="6bbf4366-6fb2-8be8-7947-92fd5f683530" ProductId="Product1" PurchaseDate="2012-08-30T23:08:52Z" ExpirationDate="2012-09-02T23:08:49Z" ProductType="Durable" AppId="55428GreenlakeApps.CurrentAppSimulatorEventTest_z7q3q7z11crfr" /><Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo><CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" /><SignatureMethod Algorithm="http://www.w3.org/2001/04/xmldsig-more#rsa-sha256" /><Reference URI=""><Transforms><Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature" /></Transforms><DigestMethod Algorithm="http://www.w3.org/2001/04/xmlenc#sha256" /><DigestValue>cdiU06eD8X/w1aGCHeaGCG9w/kWZ8I099rw4mmPpvdU=</DigestValue></Reference></SignedInfo><SignatureValue>SjRIxS/2r2P6ZdgaR9bwUSa6ZItYYFpKLJZrnAa3zkMylbiWjh9oZGGng2p6/gtBHC2dSTZlLbqnysJjl7mQp/A3wKaIkzjyRXv3kxoVaSV0pkqiPt04cIfFTP0JZkE5QD/vYxiWjeyGp1dThEM2RV811sRWvmEs/hHhVxb32e8xCLtpALYx3a9lW51zRJJN0eNdPAvNoiCJlnogAoTToUQLHs72I1dECnSbeNPXiG7klpy5boKKMCZfnVXXkneWvVFtAA1h2sB7ll40LEHO4oYN6VzD+uKd76QOgGmsu9iGVyRvvmMtahvtL1/pxoxsTRedhKq6zrzCfT8qfh3C1w==</SignatureValue></Signature></Receipt>

这是我的证书 (cert):

-----BEGIN CERTIFICATE-----
MIIDyTCCArGgAwIBAgIQNP+YKvSo8IVArhlhpgc/xjANBgkqhkiG9w0BAQsFADCB
jjELMAkGA1UEBhMCVVMxEzARBgNVBAgMCldhc2hpbmd0b24xEDAOBgNVBAcMB1Jl
ZG1vbmQxHjAcBgNVBAoMFU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjEWMBQGA1UECwwN
V2luZG93cyBTdG9yZTEgMB4GA1UEAwwXV2luZG93cyBTdG9yZSBMaWNlbnNpbmcw
HhcNMTExMTE3MjMwNTAyWhcNMzYxMTEwMjMxMzQ0WjCBjjELMAkGA1UEBhMCVVMx
EzARBgNVBAgMCldhc2hpbmd0b24xEDAOBgNVBAcMB1JlZG1vbmQxHjAcBgNVBAoM
FU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjEWMBQGA1UECwwNV2luZG93cyBTdG9yZTEg
MB4GA1UEAwwXV2luZG93cyBTdG9yZSBMaWNlbnNpbmcwggEiMA0GCSqGSIb3DQEB
AQUAA4IBDwAwggEKAoIBAQCcr4/vgqZFtzMqy3jO0XHjBUNx6j7ZTXEnNpLl2VSe
zVQA9KK2RlvroXKhYMUUdJpw+txm1mqi/W7D9QOYTq1e83GLhWC9IRh/OSmSYt0e
kgVLB+icyRH3dtpYcJ5sspU2huPf4I/Nc06OuXlMsD9MU4Ug9IBD2HSDBEquhGRo
xV64YuEH4645oB14LlEay0+JZlkKZ/mVhx/sdzSBfrda1X/Ckc7SOgnTSM3d/DnO
5DKwV2WYn+7i/rBqe4/op6IqQMrPpHyem9Sny+i0xiUMA+1IwkX0hs0gvHM6zDww
TMDiTapbCy9LnmMx65oMq56hhsQydLEmquq8lVYUDEzLAgMBAAGjITAfMB0GA1Ud
DgQWBBREzrOBz7zw+HWskxonOXAPMa6+NzANBgkqhkiG9w0BAQsFAAOCAQEAeVtN
4c6muxO6yfht9SaxEfleUBIjGfe0ewLBp00Ix7b7ldJ/lUQcA6y+Drrl7vjmkHQK
OU3uZiFbCxTvgTcoz9o+1rzR/WPXmqH5bqu6ua/UrobGKavAScqqI/G6o56Xmx/y
oErWN0VapN370crKJvNWxh3yw8DCl+W0EcVRiWX5lFsMBNBbVpK4Whp+VhkSJilu
iRpe1B35Q8EqOz/4RQkOpVI0dREnuSYkBy/h2ggCtiQ5yfvH5zCdcfhFednYDevS
axmt3W5WuHz8zglkg+OQ3qpXaXySRlrmLdxEmWu2MOiZbQkU2ZjBSQmvFAOy0dd6
P1YLS4+Eyh5drQJc0Q==
-----END CERTIFICATE-----

当我使用 xmlsec1 控制台程序时,它确实有效(感谢我的 previous question ):

$ xmlsec1 --verify --pubkey-cert-pem cert receipt.xml
OK
SignedInfo References (ok/all): 1/1
Manifests References (ok/all): 0/0

现在我尝试使用 pyxmlsec 包(及其 docs )执行相同的操作:

In [1]: import xmlsec; xmlsec.init(); xmlsec.cryptoInit(); xmlsec.cryptoAppInit(None)
Out[1]: 0

In [2]: mngr = xmlsec.KeysMngr(); xmlsec.cryptoAppDefaultKeysMngrInit(mngr)
Out[2]: 0

In [3]: mngr.certLoad('cert', xmlsec.KeyDataFormatCertPem , xmlsec.KeyDataTypePublic)
Out[3]: 0

In [4]: dsig_ctx = xmlsec.DSigCtx(mngr)

In [5]: import libxml2; f = libxml2.parseFile('receipt.xml'); node = xmlsec.findNode(f.getRootElement(), xmlsec.NodeSignature, xmlsec.DSigNs)

In [6]: dsig_ctx.verify(node)
func=xmlSecKeysMngrGetKey:file=keys.c:line=1370:obj=unknown:subj=xmlSecKeysMngrFindKey:error=1:xmlsec library function failed: 
func=xmlSecDSigCtxProcessKeyInfoNode:file=xmldsig.c:line=871:obj=unknown:subj=unknown:error=45:key is not found: 
func=xmlSecDSigCtxProcessSignatureNode:file=xmldsig.c:line=565:obj=unknown:subj=xmlSecDSigCtxProcessKeyInfoNode:error=1:xmlsec library function failed: 
func=xmlSecDSigCtxVerify:file=xmldsig.c:line=366:obj=unknown:subj=xmlSecDSigCtxSigantureProcessNode:error=1:xmlsec library function failed: 
Out[6]: -1

我在这里做错了什么?如何解决?或者有没有更好的 python 包来完成这个任务?

最佳答案

这是在没有外部文件的情况下验证收据的方法:


import xmlsec
from lxml import etree
from M2Crypto import X509
import StringIO<p></p>

<p>def validate_win_signature(receipt, cert):
    xml = etree.fromstring(receipt)
    xmlsec.tree.add_ids(xml, ["ID"])
    signature_node = xmlsec.tree.find_node(xml, xmlsec.Node.SIGNATURE)
    assert signature_node is not None
    assert signature_node.tag.endswith(xmlsec.Node.SIGNATURE)
    ctx = xmlsec.SignatureContext()
    certx509 = X509.load_cert_string(cert)
    pubkey = certx509.get_pubkey().get_rsa().as_pem(cipher=None)
    keystream = StringIO.StringIO(pubkey)
    key = xmlsec.Key.from_memory(keystream, xmlsec.KeyFormat.PEM)
    ctx.key = key
    ctx.verify(signature_node)
</p>

关于python - 在 Python 中验证 Windows 8 应用内购买收据签名,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23337858/

相关文章:

c# - 内购成功后正确步骤

python - 如何设置默认的python库路径

xml - 使用 xslt 更新 XML 文件

windows - 关联 App Store 应用程序和桌面应用程序的方法

xml - 如何覆盖父/扩展元素内的 Xsd 元素

安卓.view.InflateException : Error inflating class fragment on Startup (no error in onCreate? )

要使用的 HTMl5/CSS3 框架将适用于 Windows 8 手机和 Windows 8 平板电脑以及 iPad 和网络浏览器?

python - 在语料库 Python 中查找损坏的文件

python - 为什么 tempfile 和 os.chdir() 会抛出 RecursionError?

python - Python/C API 中 Python 胶囊的安全和防御编码视角