产生CloudFront的签名URL时性能下降 [英] Slow performance when generating CloudFront Signed URLs

查看:606
本文介绍了产生CloudFront的签名URL时性能下降的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我下面这个样本来创建签名的CloudFront的使用PHP的网址
http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/CreateURL_PHP.html

I'm following this sample to create Signed URLs on CloudFront using PHP http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/CreateURL_PHP.html

和我所拥有的一切工作正常,并生成签署的网址为RTMP分布和HTTP分布。

And I have everything working fine and generating the Signed URLs for both RTMP Distributions and HTTP Distributions.

不过,我注意到,生成登录URL需要相当长一段时间,我不知道在生产中与成千上万的请求使用时可能会产生什么影响。

However I noticed that generating the Sign URL takes quite some time and I wonder what impact could have when used in production with thousands of requests.

我做了一些测试,它似乎是很长一段时间正在是由于PHP的OpenSSL的功能。

I did some tests and it seems that the long time is taking is due to the php-openssl functions.

下面是code:

<?php

class Cloudfront {

    const KEYPAIRID = 'MYKEYPAIRID';
    const PVTKEYFILE = '/home/keys/myprivatekey.pem';

    public function rsa_sha1_sign($policy) {
        $signature = "";

        // load the private key
        $fp = fopen(self::PVTKEYFILE, "r");
        $priv_key = fread($fp, 8192);
        fclose($fp);
        $pkeyid = openssl_get_privatekey($priv_key);

        // compute signature
        openssl_sign($policy, $signature, $pkeyid);

        // free the key from memory
        openssl_free_key($pkeyid);

        return $signature;
    }

    public function simulated_rsa_sha1_sign($policy) {
        // create a simulated signature
        $signature = "©3•{š(|i~'{µÜr…6—\L¶…ÙiÃÔh@ç÷S„Aóö¯‡d‰‹{¦ºx­òrd)Xcª
            Áh‚°Bgþ èòëÿô Š#CßFe  ÓÒ>v1    R€¥#–þ*¸çGÀýƒ Ј¾F<t)eV7¿ø_ŒQÎiXXU s˜¦Ij:ý
            ÒR ‹ÚQ§ Çm8à  ºâ*+äÇjƒãýO  4 ~ Uöeóy˜¢93_0iy §âE– a÷f¥y¿ÈãÏ`‹ _ì`ß ½õ  ‹*
            ÁM‘çõD  jrüB •d˜¥  èp Òü¿Ö NŒ«éoI X  €v=RÌlŠ¤ /Á û9Yš¾î";

        // load the private key file although is not actually used
        $fp = fopen(self::PVTKEYFILE, "r");
        $priv_key = fread($fp, 8192);
        fclose($fp);

        return $signature;
    }

    public function url_safe_base64_encode($value) {
        $encoded = base64_encode($value);
        // replace unsafe characters +, = and / with the safe characters -, _ and ~
        return str_replace(
                array('+', '=', '/'), array('-', '_', '~'), $encoded);
    }

    public function create_stream_name($stream, $signature, $expires) {
        $result = $stream;
        // if the stream already contains query parameters, attach the new query parameters to the end
        // otherwise, add the query parameters
        $separator = strpos($stream, '?') == FALSE ? '?' : '&';
        $result .= $separator . "Expires=" . $expires . "&Key-Pair-Id=" . self::KEYPAIRID . "&Signature=" . $signature;
        // new lines would break us, so remove them
        return str_replace('\n', '', $result);
    }

    public function get_signed_stream_name($video_path, $expires) {
        // this policy is well known by CloudFront, but you still need to sign it, since it contains your parameters
        $canned_policy = '{"Statement":[{"Resource":"' . $video_path . '","Condition":{"DateLessThan":{"AWS:EpochTime":' . $expires . '}}}]}';
        // sign the original policy, not the encoded version
        $signature = $this->rsa_sha1_sign($canned_policy);
        // make the signature safe to be included in a url
        $encoded_signature = $this->url_safe_base64_encode($signature);

        // combine the above into a stream name
        $stream_name = $this->create_stream_name($video_path, $encoded_signature, $expires);

        return $stream_name;
    }

}

这基本上是相同的样本是CloudFront的对他们的文档。然后,我创建了一个控制器是我打的电话,以get_signed_stream_name()生成签署的网址。我决定做一个while循环,看看需要多长时间来创建500签署的网址。

That's basically the same sample that CloudFront have on their docs. Then I created a controller were I make the calls to get_signed_stream_name() to generate the signed urls. I decided to do a while loop to see how long it takes to create 500 signed urls.

public function signedurl() {
        // Script start
        $start = microtime(true);

        $this->load->helper('cloudfront');
        $this->cloudfront = new Cloudfront();

        $i = 1;
        while ($i <= 500) {
            $expires = time() + rand(300, 900);
            $http_video_path = 'http://mydistribution.cloudfront.net/myvideo.mp4';
            $signed_http_url = $this->cloudfront->get_signed_stream_name($http_video_path, $expires);

            echo '<strong>HTTP Signed URL:</strong> <br />' . $signed_http_url;
            echo '<br /><br />';

            $i++;
        }

        // Script end
        $time_taken = microtime(true) - $start;
        echo $time_taken;
    }

生成500签署的网址在while循环用了大约11秒我的本地机器上。然后,我决定改变,如:

Generating 500 signed urls in that while loop took around 11 seconds on my local machine. Then I decided to change the like:

$signature = $this->rsa_sha1_sign($canned_policy);

$signature = $this->simulated_rsa_sha1_sign($canned_policy);

要看看发生了什么,如果一切都只是调用PHP的OpenSSL的功能openssl_get_privatekey(),openssl_sign(),openssl_free_key()运行。

To see what happened if everything was run except invoking the php-openssl functions openssl_get_privatekey(), openssl_sign(), openssl_free_key().

我跑了相同的脚本与500 while循环,并花了0.090秒。所以基本上PHP的OpenSSL的功能,使脚本慢了很多。这是不是我应该担心,这是正常的,因为我产生这些签署的网址,它需要相当大的处理能力?

I ran the same script with the 500 while loop and it took 0.090 seconds. So basically the php-openssl functions make the script a lot slower. Is this something I should be worried, it is normal since I'm generating these signed urls and it takes considerable processing power?

我做了多次尝试,并在这里都花了为每个3采样时间。

I did several tries and here are sample time it took for 3 of each.

Real code using OpenSSL functions generating 500 signed url calls:
11.135037899
11.6025328636
11.0253090858

500 URLs simulated without using the OpenSSL functions:
0.0828909873962
0.0903220176697
0.0916609764099

另外,我想知道我怎么可以创建在分发的任何文件工作的签名。通配符我可以生成可用于所有在该文件夹或分布下的文件的签名。我读了某个地方,这是可能的,但不知道如何使用高于样本。也许我可以为每个请求,而不是在请求返回的每个文件就会少密集创建一个单一的签名。

Also, I would like to know how I could create a signature that work for any file in the distribution. A wildcard that I could generate a signature that can be used for all the files under that folder or distribution. I read someplace that it was possible, but not sure how using those samples above. Maybe if I can create a single signature for each request instead of for each file returned in the request would be less intensive.

谢谢!

推荐答案

我观察与使用 RSA 模块来计算的宝途(AWS的的Python SDK)相同的性能问题签名。我认为问题简单地归结为一个事实,即RSA计算是在这种背景下缓慢。我想/希望的解决之道在于调整设置或处理私人内容的工作流程。

I observe the same performance issue with Boto (AWS's Python SDK) which uses rsa module to compute the signature. I think the problem simply comes down to the fact that RSA computation is slow in this context. I think/hope the solution lies in adjusting the setup or the workflow of dealing with private content.

这篇关于产生CloudFront的签名URL时性能下降的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆