diff --git a/composer.json b/composer.json index 541d95b..743f867 100644 --- a/composer.json +++ b/composer.json @@ -18,7 +18,8 @@ "require": { "php": ">=7.0", "anam/phantommagick": "~2.0", - "anam/phantomjs-linux-x86-binary": "~2.1.1" + "anam/phantomjs-linux-x86-binary": "~2.1.1", + "overtrue/laravel-filesystem-qiniu": "^1.0" }, "require-dev": { "phpunit/phpunit": "~6.0", diff --git a/config/config.php b/config/config.php index c1c9a5a..6118d3f 100644 --- a/config/config.php +++ b/config/config.php @@ -10,8 +10,25 @@ */ return [ + 'default' => [ + 'storage' => env('DEFAULT_POSTER_STORAGE', 'qiniu'), + ], //图片存储位置 'disks' => [ + 'qiniu' => [ + 'driver' => 'qiniu', + //七牛云access_key + 'access_key' => env('QINIU_ACCESS_KEY', ''), + //七牛云secret_key + 'secret_key' => env('QINIU_SECRET_KEY', ''), + //七牛云文件上传空间 + 'bucket' => env('QINIU_BUCKET', ''), + //七牛云cdn域名 + 'domain' => env('QINIU_DOMAIN', ''), + //与cdn域名保持一致 + 'url' => env('QINIU_DOMAIN', ''), + 'root' => storage_path('app/public/qiniu'), + ], 'MiniProgramShare' => [ 'driver' => 'local', 'root' => storage_path('app/public/share'), @@ -27,6 +44,6 @@ 'quality' => 9, //是否压缩图片 'compress' => true, - //是否删除废弃图片文件 - 'delete'=>true, + //是否删除废弃图片文件 + 'delete' => true, ]; diff --git a/src/MiniProgramShareImg.php b/src/MiniProgramShareImg.php index 17643c5..ac2b2c1 100644 --- a/src/MiniProgramShareImg.php +++ b/src/MiniProgramShareImg.php @@ -17,133 +17,139 @@ class MiniProgramShareImg { - public static $conv = null; - - public static function init() - { - if (is_null(self::$conv) || !self::$conv instanceof Converter) { - self::$conv = new Converter(); - } - - return self::$conv; - } - - /** - * 生成海报. - * - * @param $url - * - * @return array|bool - */ - public static function generateShareImage($url) - { - if (!$url) { - return false; - } - - $options = [ - 'dimension' => config('ibrand.miniprogram-poster.width', '575px'), - 'zoomfactor' => config('ibrand.miniprogram-poster.zoomfactor', 1.5), - 'quality' => config('ibrand.miniprogram-poster.quality', 100), - ]; - - $saveName = date('Ymd').'/'.md5(uniqid()).'.png'; - $file = config('ibrand.miniprogram-poster.disks.MiniProgramShare.root').'/'.$saveName; - - $converter = self::init(); - - $converter->source($url)->toPng($options)->save($file); - - if (config('ibrand.miniprogram-poster.compress', true)) { - self::compress($file); - } - - return [ - 'url' => Storage::disk('MiniProgramShare')->url($saveName), - 'path' => $saveName, - ]; - } - - /** - * 压缩图片. - * - * @param $file - */ - public static function compress($file) - { - list($width, $height, $type) = getimagesize($file); - $new_width = $width * 1; - $new_height = $height * 1; - - $resource = imagecreatetruecolor($new_width, $new_height); - $image = imagecreatefrompng($file); - imagecopyresampled($resource, $image, 0, 0, 0, 0, $new_width, $new_height, $width, $height); - imagepng($resource, $file, config('ibrand.miniprogram-poster.quality', 9)); - imagedestroy($resource); - } - - /** - * 绑定关系. - * - * @param Model $model - * @param array $path - * - * @return Poster - */ - public static function attach(Model $model, array $path) - { - $poster = new Poster(['content' => $path]); - $model->posters()->save($poster); - - return $poster; - } - - /** - * 关系是否存在. - * - * @param \Illuminate\Database\Eloquent\Model $model - * - * @return mixed - */ - public static function exists(Model $model) - { - $poster = Poster::where('posterable_id', $model->id)->where('posterable_type', get_class($model))->first(); - if ($poster) { - return $poster; - } - - return false; - } - - /** - * 生成海报. - * - * @param \Illuminate\Database\Eloquent\Model $model - * @param $url - * @param bool $rebuild - * - * @return array|bool - */ - public static function run(Model $model, $url, $rebuild = false) - { - $poster = self::exists($model); - - $path = []; - - if (!$poster || $rebuild) { - $path = self::generateShareImage($url); - self::attach($model, $path); - } - - if ($poster && $rebuild) { - $old = $poster->content; - if (config('ibrand.miniprogram-poster.delete', true) && !empty($old) && isset($old['path']) && Storage::disk('MiniProgramShare')->exists($old['path'])) { - Storage::disk('MiniProgramShare')->delete($old['path']); - } - $poster->content = $path; - $poster->save(); - } - - return $path; - } + public static $conv = null; + + public static function init() + { + if (is_null(self::$conv) || !self::$conv instanceof Converter) { + self::$conv = new Converter(); + } + + return self::$conv; + } + + /** + * 生成海报. + * + * @param $url + * + * @return array|bool + */ + public static function generateShareImage($url) + { + if (!$url) { + return false; + } + + $options = [ + 'dimension' => config('ibrand.miniprogram-poster.width', '575px'), + 'zoomfactor' => config('ibrand.miniprogram-poster.zoomfactor', 1.5), + 'quality' => config('ibrand.miniprogram-poster.quality', 100), + ]; + + $saveName = date('Ymd') . '/' . md5(uniqid()) . '.png'; + $storage = config('ibrand.miniprogram-poster.default.storage'); + $file = config('ibrand.miniprogram-poster.disks.' . $storage . '.root') . '/' . $saveName; + + $converter = self::init(); + + $converter->source($url)->toPng($options)->save($file); + + if (config('ibrand.miniprogram-poster.compress', true)) { + self::compress($file); + } + + if ('qiniu' == $storage) { + Storage::disk($storage)->put($saveName, file_get_contents($file)); + } + + return [ + 'url' => Storage::disk($storage)->url($saveName), + 'path' => $saveName, + ]; + } + + /** + * 压缩图片. + * + * @param $file + */ + public static function compress($file) + { + list($width, $height, $type) = getimagesize($file); + $new_width = $width * 1; + $new_height = $height * 1; + + $resource = imagecreatetruecolor($new_width, $new_height); + $image = imagecreatefrompng($file); + imagecopyresampled($resource, $image, 0, 0, 0, 0, $new_width, $new_height, $width, $height); + imagepng($resource, $file, config('ibrand.miniprogram-poster.quality', 9)); + imagedestroy($resource); + } + + /** + * 绑定关系. + * + * @param Model $model + * @param array $path + * + * @return Poster + */ + public static function attach(Model $model, array $path) + { + $poster = new Poster(['content' => $path]); + $model->posters()->save($poster); + + return $poster; + } + + /** + * 关系是否存在. + * + * @param \Illuminate\Database\Eloquent\Model $model + * + * @return mixed + */ + public static function exists(Model $model) + { + $poster = Poster::where('posterable_id', $model->id)->where('posterable_type', get_class($model))->first(); + if ($poster) { + return $poster; + } + + return false; + } + + /** + * 生成海报. + * + * @param \Illuminate\Database\Eloquent\Model $model + * @param $url + * @param bool $rebuild + * + * @return array|bool + */ + public static function run(Model $model, $url, $rebuild = false) + { + $poster = self::exists($model); + + $path = []; + + if (!$poster || $rebuild) { + $path = self::generateShareImage($url); + self::attach($model, $path); + } + + if ($poster && $rebuild) { + $old = $poster->content; + $storage = config('ibrand.miniprogram-poster.default.storage'); + if (config('ibrand.miniprogram-poster.delete', true) && !empty($old) && isset($old['path']) && Storage::disk($storage)->exists($old['path'])) { + Storage::disk($storage)->delete($old['path']); + } + $poster->content = $path; + $poster->save(); + } + + return $path; + } } diff --git a/src/PhantoMmagickServiceProvider.php b/src/PhantoMmagickServiceProvider.php index 8fe5484..e4bee26 100644 --- a/src/PhantoMmagickServiceProvider.php +++ b/src/PhantoMmagickServiceProvider.php @@ -15,28 +15,30 @@ class PhantoMmagickServiceProvider extends ServiceProvider { - public function boot() - { - if ($this->app->runningInConsole()) { - $this->publishes([__DIR__.'/../config/config.php' => config_path('ibrand/miniprogram-poster.php')], 'config'); - - if (!class_exists('CreatePosterTables')) { - $timestamp = date('Y_m_d_His', time()); - $this->publishes([ - __DIR__.'/../migrations/create_poster_tables.php.stub' => database_path('migrations/'.$timestamp.'_create_poster_tables.php'), - ], 'migrations'); - } - } - } - - public function register() - { - $this->mergeConfigFrom( - __DIR__.'/../config/config.php', 'ibrand.miniprogram-poster' - ); - - $filesystems = $this->app['config']->get('filesystems.disks', []); - - $this->app['config']->set('filesystems.disks', array_merge(config('ibrand.miniprogram-poster.disks'), $filesystems)); - } + public function boot() + { + if ($this->app->runningInConsole()) { + $this->publishes([__DIR__ . '/../config/config.php' => config_path('ibrand/miniprogram-poster.php')], 'config'); + + if (!class_exists('CreatePosterTables')) { + $timestamp = date('Y_m_d_His', time()); + $this->publishes([ + __DIR__ . '/../migrations/create_poster_tables.php.stub' => database_path('migrations/' . $timestamp . '_create_poster_tables.php'), + ], 'migrations'); + } + } + } + + public function register() + { + $this->mergeConfigFrom( + __DIR__ . '/../config/config.php', 'ibrand.miniprogram-poster' + ); + + $filesystems = $this->app['config']->get('filesystems.disks', []); + + $this->app['config']->set('filesystems.disks', array_merge(config('ibrand.miniprogram-poster.disks'), $filesystems)); + + $this->app->register(\Overtrue\LaravelFilesystem\Qiniu\QiniuStorageServiceProvider::class); + } } diff --git a/tests/ShareImgTest.php b/tests/ShareImgTest.php index f892900..e421e3f 100644 --- a/tests/ShareImgTest.php +++ b/tests/ShareImgTest.php @@ -14,6 +14,8 @@ public function TestConfig() $config = config('filesystems.disks'); $this->assertArrayHasKey('MiniProgramShare', $config); + + $this->assertArrayHasKey('qiniu', $config); } /** @test */ @@ -22,7 +24,7 @@ public function TestGenerateShareImage() config(['ibrand.miniprogram-poster.width' => '1300px']); $url = 'https://www.ibrand.cc/'; - $result = MiniProgramShareImg::generateShareImage($url, 'ibrand'); + $result = MiniProgramShareImg::generateShareImage($url); $this->assertTrue(Storage::disk('MiniProgramShare')->exists($result['path'])); $result = MiniProgramShareImg::generateShareImage(''); @@ -38,25 +40,43 @@ public function TestShareImageV2() $goods = GoodsTestModel::find(1); //1. first build. - $result = MiniProgramShareImg::run($goods, $url); - $oldPath = $result['path']; - $this->assertTrue(Storage::disk('MiniProgramShare')->exists($result['path'])); - $this->assertEquals(1, count($goods->posters)); - - //2. rebuild and delete old. - $result = MiniProgramShareImg::run($goods, $url,true); - $oldPath2= $result['path']; - $this->assertTrue(Storage::disk('MiniProgramShare')->exists($result['path'])); - $this->assertFalse(Storage::disk('MiniProgramShare')->exists($oldPath)); - $this->assertEquals(1, count($goods->posters)); - - //3. rebuild but not delete old. - $this->app['config']->set('ibrand.miniprogram-poster.delete',false); - $result = MiniProgramShareImg::run($goods, $url,true); - $this->assertTrue(Storage::disk('MiniProgramShare')->exists($result['path'])); - $this->assertTrue(Storage::disk('MiniProgramShare')->exists($oldPath2)); + $result = MiniProgramShareImg::run($goods, $url); + $oldPath = $result['path']; + $this->assertTrue(Storage::disk('MiniProgramShare')->exists($result['path'])); + $this->assertEquals(1, count($goods->posters)); + + //2. rebuild and delete old. + $result = MiniProgramShareImg::run($goods, $url, true); + $oldPath2 = $result['path']; + $this->assertTrue(Storage::disk('MiniProgramShare')->exists($result['path'])); + $this->assertFalse(Storage::disk('MiniProgramShare')->exists($oldPath)); + $this->assertEquals(1, count($goods->posters)); + + //3. rebuild but not delete old. + $this->app['config']->set('ibrand.miniprogram-poster.delete', false); + $result = MiniProgramShareImg::run($goods, $url, true); + $this->assertTrue(Storage::disk('MiniProgramShare')->exists($result['path'])); + $this->assertTrue(Storage::disk('MiniProgramShare')->exists($oldPath2)); $poster = Poster::find(1); $this->assertEquals(GoodsTestModel::class, get_class($poster->posterable)); } + + /** @test */ + public function TestSaveToQiNiu() + { + config(['ibrand.miniprogram-poster.default.storage' => 'qiniu']); + + $config = config('ibrand.miniprogram-poster'); + $this->assertSame($config['default']['storage'], 'qiniu'); + + $url = 'https://www.ibrand.cc/'; + $result = MiniProgramShareImg::generateShareImage($url); + $this->assertTrue(Storage::disk('qiniu')->exists($result['path'])); + + $goods = GoodsTestModel::find(1); + $result = MiniProgramShareImg::run($goods, $url); + $this->assertTrue(Storage::disk('qiniu')->exists($result['path'])); + $this->assertEquals(1, count($goods->posters)); + } } \ No newline at end of file