support PSM security

pull/25303/head
root 4 years ago
parent 73978ad047
commit a043be5d5c
  1. 47
      src/php/ext/grpc/channel_credentials.c
  2. 246
      src/php/tests/unit_tests/ChannelTest.php

@ -236,6 +236,47 @@ PHP_METHOD(ChannelCredentials, createInsecure) {
RETURN_NULL();
}
/**
* Create XDS channel credentials
* @param ChannelCredentials|null $fallback_creds The fallback credentials used
* if the channel target does not have the 'xds:///' scheme or if the xDS
* control plane does not provide information on how to fetch credentials
* dynamically.
* @return ChannelCredentials The xDS channel credentials object
*/
PHP_METHOD(ChannelCredentials, createXds) {
grpc_channel_credentials* xds_creds = NULL;
zval* fallback_creds = NULL;
if (zend_parse_parameters_ex(0, // ZEND_PARSE_PARAMS_QUIET,
ZEND_NUM_ARGS() TSRMLS_CC, "O!", &fallback_creds,
grpc_ce_channel_credentials) != SUCCESS) {
zend_throw_exception(spl_ce_InvalidArgumentException,
"createXds expects a fallback credentials",
1 TSRMLS_CC);
return;
}
char* fallback_creds_hash_str = "";
if (!fallback_creds) {
grpc_channel_credentials* insecure_creds =
grpc_insecure_credentials_create();
xds_creds = grpc_xds_credentials_create(insecure_creds);
} else {
wrapped_grpc_channel_credentials* wrapped_fallback_creds =
PHP_GRPC_GET_WRAPPED_OBJECT(wrapped_grpc_channel_credentials,
fallback_creds);
xds_creds = grpc_xds_credentials_create(wrapped_fallback_creds->wrapped);
fallback_creds_hash_str = wrapped_fallback_creds->hashstr;
}
// prefix "XDS:" as the hash of the xDS channel
char* hash_str = malloc(strlen(fallback_creds_hash_str) + strlen("XDS:") + 1);
strcpy(hash_str, "XDS:");
strcat(hash_str, fallback_creds_hash_str);
zval* xds_creds_obj = grpc_php_wrap_channel_credentials(
xds_creds, hash_str, false /* has_call_creds */ TSRMLS_CC);
RETURN_DESTROY_ZVAL(xds_creds_obj);
}
ZEND_BEGIN_ARG_INFO_EX(arginfo_setDefaultRootsPem, 0, 0, 1)
ZEND_ARG_INFO(0, pem_roots)
ZEND_END_ARG_INFO()
@ -263,6 +304,10 @@ ZEND_END_ARG_INFO()
ZEND_BEGIN_ARG_INFO_EX(arginfo_createInsecure, 0, 0, 0)
ZEND_END_ARG_INFO()
ZEND_BEGIN_ARG_INFO_EX(arginfo_createXds, 0, 0, 1)
ZEND_ARG_OBJ_INFO(0, fallback_creds, Grpc\\ChannelCredentials, 1)
ZEND_END_ARG_INFO()
static zend_function_entry channel_credentials_methods[] = {
PHP_ME(ChannelCredentials, setDefaultRootsPem, arginfo_setDefaultRootsPem,
ZEND_ACC_PUBLIC | ZEND_ACC_STATIC)
@ -278,6 +323,8 @@ static zend_function_entry channel_credentials_methods[] = {
ZEND_ACC_PUBLIC | ZEND_ACC_STATIC)
PHP_ME(ChannelCredentials, createInsecure, arginfo_createInsecure,
ZEND_ACC_PUBLIC | ZEND_ACC_STATIC)
PHP_ME(ChannelCredentials, createXds, arginfo_createXds,
ZEND_ACC_PUBLIC | ZEND_ACC_STATIC)
PHP_FE_END
};

@ -44,6 +44,21 @@ class ChannelTest extends \PHPUnit\Framework\TestCase
$this->assertNotNull($channel);
}
public function testCreateXdsWithSsl()
{
$xdsCreds = \Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
);
$this->assertNotNull($xdsCreds);
}
public function testCreateXdsWithInsecure() {
$xdsCreds = \Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createInsecure()
);
$this->assertNotNull($xdsCreds);
}
public function testGetConnectivityState()
{
$this->channel = new Grpc\Channel('localhost:50001',
@ -275,70 +290,90 @@ class ChannelTest extends \PHPUnit\Framework\TestCase
$this->channel2->close();
}
public function testPersistentChannelSameChannelCredentials()
{
$creds1 = Grpc\ChannelCredentials::createSsl();
$creds2 = Grpc\ChannelCredentials::createSsl();
$this->channel1 = new Grpc\Channel('localhost:50019',
["credentials" => $creds1,
"grpc_target_persist_bound" => 3,
]);
$this->channel2 = new Grpc\Channel('localhost:50019',
["credentials" => $creds2]);
// try to connect on channel1
$state = $this->channel1->getConnectivityState(true);
$this->waitUntilNotIdle($this->channel1);
$state = $this->channel1->getConnectivityState();
$this->assertConnecting($state);
$state = $this->channel2->getConnectivityState();
$this->assertConnecting($state);
$this->channel1->close();
$this->channel2->close();
}
public function testPersistentChannelDifferentChannelCredentials()
{
$creds1 = Grpc\ChannelCredentials::createSsl();
$creds2 = Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__).'/../data/ca.pem'));
$this->channel1 = new Grpc\Channel('localhost:50020',
["credentials" => $creds1,
"grpc_target_persist_bound" => 3,
]);
$this->channel2 = new Grpc\Channel('localhost:50020',
["credentials" => $creds2]);
// try to connect on channel1
$state = $this->channel1->getConnectivityState(true);
$this->waitUntilNotIdle($this->channel1);
$state = $this->channel1->getConnectivityState();
$this->assertConnecting($state);
$state = $this->channel2->getConnectivityState();
$this->assertEquals(GRPC\CHANNEL_IDLE, $state);
$this->channel1->close();
$this->channel2->close();
}
public function testPersistentChannelSameChannelCredentialsRootCerts()
{
$creds1 = Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__).'/../data/ca.pem'));
$creds2 = Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__).'/../data/ca.pem'));
$this->channel1 = new Grpc\Channel('localhost:50021',
["credentials" => $creds1,
"grpc_target_persist_bound" => 3,
]);
$this->channel2 = new Grpc\Channel('localhost:50021',
["credentials" => $creds2]);
public function persistentChannelSameChannelCredentialsProvider(): array
{
return [
[
Grpc\ChannelCredentials::createSsl(),
Grpc\ChannelCredentials::createSsl(),
50301,
],
[
Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__) . '/../data/ca.pem')
),
Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__) . '/../data/ca.pem')
),
50302,
],
[
Grpc\ChannelCredentials::createInSecure(),
Grpc\ChannelCredentials::createInSecure(),
50303,
],
[
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
),
50304,
],
[
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
),
50305,
],
[
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__) . '/../data/ca.pem')
)
),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__) . '/../data/ca.pem')
)
),
50306,
],
[
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createInSecure()
),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createInSecure()
),
50307,
],
];
}
/**
* @dataProvider persistentChannelSameChannelCredentialsProvider
*/
public function testPersistentChannelSameChannelCredentials(
$creds1,
$creds2,
$port
) {
$this->channel1 = new Grpc\Channel(
'localhost:' . $port,
[
"credentials" => $creds1,
"grpc_target_persist_bound" => 3,
]
);
$this->channel2 = new Grpc\Channel(
'localhost:' . $port,
["credentials" => $creds2]
);
// try to connect on channel1
$state = $this->channel1->getConnectivityState(true);
@ -353,17 +388,78 @@ class ChannelTest extends \PHPUnit\Framework\TestCase
$this->channel2->close();
}
public function testPersistentChannelDifferentSecureChannelCredentials()
{
$creds1 = Grpc\ChannelCredentials::createSsl();
$creds2 = Grpc\ChannelCredentials::createInsecure();
$this->channel1 = new Grpc\Channel('localhost:50022',
["credentials" => $creds1,
"grpc_target_persist_bound" => 3,
]);
$this->channel2 = new Grpc\Channel('localhost:50022',
["credentials" => $creds2]);
public function persistentChannelDifferentChannelCredentialsProvider(): array
{
return [
[
Grpc\ChannelCredentials::createSsl(),
Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__) . '/../data/ca.pem')
),
50351,
],
[
Grpc\ChannelCredentials::createSsl(),
Grpc\ChannelCredentials::createInsecure(),
50352,
],
[
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl(
file_get_contents(dirname(__FILE__) . '/../data/ca.pem')
)
),
50353,
],
[
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createInsecure()
),
50354,
],
[
\Grpc\ChannelCredentials::createInsecure(),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createInsecure()
),
50355,
],
[
\Grpc\ChannelCredentials::createSsl(),
\Grpc\ChannelCredentials::createXds(
\Grpc\ChannelCredentials::createSsl()
),
50356,
],
];
}
/**
* @dataProvider persistentChannelDifferentChannelCredentialsProvider
*/
public function testPersistentChannelDifferentChannelCredentials(
$creds1,
$creds2,
$port
) {
$this->channel1 = new Grpc\Channel(
'localhost:' . $port,
[
"credentials" => $creds1,
"grpc_target_persist_bound" => 3,
]
);
$this->channel2 = new Grpc\Channel(
'localhost:' . $port,
["credentials" => $creds2]
);
// try to connect on channel1
$state = $this->channel1->getConnectivityState(true);

Loading…
Cancel
Save