Passed
Push — master ( 96d02d...d08d15 )
by Songda
02:13 queued 10s
created

get_alipay_cert()   A

Complexity

Conditions 4
Paths 3

Size

Total Lines 15
Code Lines 10

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 10
c 0
b 0
f 0
dl 0
loc 15
rs 9.9332
cc 4
nc 3
nop 1
1
<?php
2
3
declare(strict_types=1);
4
5
use Yansongda\Pay\Contract\ConfigInterface;
6
use Yansongda\Pay\Exception\InvalidConfigException;
7
use Yansongda\Pay\Parser\NoHttpRequestParser;
8
use Yansongda\Pay\Pay;
9
use Yansongda\Pay\Rocket;
10
use Yansongda\Supports\Config;
11
use Yansongda\Supports\Str;
12
13
if (!function_exists('should_http_request')) {
14
    function should_http_request(Rocket $rocket): bool
15
    {
16
        return NoHttpRequestParser::class !== $rocket->getDirection() &&
17
            !in_array(NoHttpRequestParser::class, class_parents($rocket->getDirection()));
18
    }
19
}
20
21
if (!function_exists('get_alipay_config')) {
22
    /**
23
     * @throws \Yansongda\Pay\Exception\ContainerDependencyException
24
     * @throws \Yansongda\Pay\Exception\ContainerException
25
     * @throws \Yansongda\Pay\Exception\ServiceNotFoundException
26
     */
27
    function get_alipay_config(array $params): Config
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
28
    {
29
        $alipay = Pay::get(ConfigInterface::class)->get('alipay');
30
31
        $config = $params['_config'] ?? 'default';
32
33
        return new Config($alipay[$config] ?? []);
34
    }
35
}
36
37
if (!function_exists('get_public_crt_or_private_cert')) {
38
    /**
39
     * @return false|resource|string
40
     */
41
    function get_public_crt_or_private_cert(string $key)
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
42
    {
43
        if (Str::endsWith($key, '.crt')) {
44
            $key = file_get_contents($key);
45
        } elseif (Str::endsWith($key, '.pem')) {
46
            $key = openssl_pkey_get_private(
47
                Str::startsWith($key, 'file://') ? $key : 'file://'.$key
48
            );
49
        } else {
50
            $key = "-----BEGIN RSA PRIVATE KEY-----\n".
51
                wordwrap($key, 64, "\n", true).
52
                "\n-----END RSA PRIVATE KEY-----";
53
        }
54
55
        return $key;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $key also could return the type OpenSSLAsymmetricKey which is incompatible with the documented return type false|resource|string.
Loading history...
56
    }
57
}
58
59
if (!function_exists('verify_alipay_response')) {
60
    /**
61
     * @param string $sign base64decode 之后的
62
     *
63
     * @throws \Yansongda\Pay\Exception\ContainerDependencyException
64
     * @throws \Yansongda\Pay\Exception\ContainerException
65
     * @throws \Yansongda\Pay\Exception\InvalidConfigException
66
     * @throws \Yansongda\Pay\Exception\ServiceNotFoundException
67
     */
68
    function verify_alipay_response(array $params, string $contents, string $sign): bool
69
    {
70
        $public = get_alipay_config($params)->get('alipay_public_cert_path');
71
72
        if (is_null($public)) {
73
            throw new InvalidConfigException(InvalidConfigException::ALIPAY_CONFIG_ERROR, 'Missing Alipay Config -- [alipay_public_cert_path]');
74
        }
75
76
        return 1 === openssl_verify(
77
            $contents,
78
            $sign,
79
            get_public_crt_or_private_cert($public),
80
            OPENSSL_ALGO_SHA256);
81
    }
82
}
83
84
if (!function_exists('get_wechat_config')) {
85
    /**
86
     * @throws \Yansongda\Pay\Exception\ContainerDependencyException
87
     * @throws \Yansongda\Pay\Exception\ContainerException
88
     * @throws \Yansongda\Pay\Exception\ServiceNotFoundException
89
     */
90
    function get_wechat_config(array $params): Config
91
    {
92
        $wechat = Pay::get(ConfigInterface::class)->get('wechat');
93
94
        $config = $params['_config'] ?? 'default';
95
96
        return new Config($wechat[$config] ?? []);
97
    }
98
}
99